Tirion

  博客园 :: 首页 :: 博问 :: 闪存 :: 新随笔 :: 联系 :: 订阅 订阅 :: 管理 ::

国内关于CsGL的资料一直非常少,最近对这方面有些关注,随便写点东西吧,就当是学习记录了
对于我这样的初学者而言不能苛求太多,如果有错误的话希望大家指出。

-0- 关于CsGL
CsGL是openGL在.NET下的包装。
可以在SF.NET上下载:http://csgl.sourceforge.net/
目前关于CsGL的开发基本上已经停止,官方主页上的说法是认为CsGL对大多数应用而言已经足够稳定了。目前CsGL开发工作基本上集中在Example程序的撰写:
详情见:http://www.randyridge.com/Tao/Default.aspx 

-1- Hello, CsGL
在这里首先实现一个最简单的CsGL应用程序:一个旋转的立方体。
下面的步骤其实基本上就是
http://www.c-sharpcorner.com/Code/2002/Oct/SimpleOpenGL.asp
的复述了,只不过不是一对一的翻译而已。

首先建立一个C# WIndows应用程序。在引用中添加csgl.dll。

首先在主窗口创建一个新的线程用来更新窗口
引入名字空间
using System.Threading;
在主窗口类内声明如下私有成员:
private static Thread thrDraw;
而后定义一个私有类成员函数
private void OpenGL_Start()
{
        while(true)
       {
            this.view.Refresh();
        }
}
在Form_load方法中添加如下代码,启动线程:
  ThreadStart start = new ThreadStart(OpenGL_Start);
   thrDraw= new Thread(start);
   thrDraw.Start();
在主窗口的Dispose方法中退出线程
   thrDraw.Abort();

然后创建一个从OpenGLControl继承下来的类:MyView
using CsGL.OpenGL;

public class MyView : OpenGLControl
{
          public MyView() : base(){}
         
          /// <summary>
          /// 执行OpenGL初始化
          /// </summary>

         protected override void InitGLContext()
         {
                  base.InitGLContext ();

                  GL.glShadeModel(GL.GL_SMOOTH);            // Enable Smooth Shading
                  GL.glClearColor(0.0f, 0.0f, 0.0f, 0.5f);             // Black Background
                  GL.glClearDepth(1.0f);                                    //  Depth Buffer Setup
                  GL.glEnable(GL.GL_DEPTH_TEST);            // Enables Depth Testing
                  GL.glDepthFunc(GL.GL_LEQUAL);              //  The Type Of Depth Testing To Do
                  GL.glHint(GL.GL_PERSPECTIVE_CORRECTION_HINT, GL.GL_NICEST); 
                  
                  // TODO: 在此添加其他初始化动作,比如建立显示列表
         }

          /// <summary>
          /// 窗口大小改变时
          /// </summary>

        protected override void OnSizeChanged(EventArgs e)
        {
                base.OnSizeChanged (e);

                Size s = Size;
                // 计算窗口的纵横比
                double aspect_ratio = (double)s.Width / (double) s.Height;

                GL.glMatrixMode( GL.GL_PROJECTION );     //  设置当前为投影矩阵
                GL.glLoadIdentity();    // 重置投影矩阵

                GL.gluPerspective( 45.0f, aspect_ratio, 0.1f, 100.0f);

                GL.glMatrixMode( GL.GL_MODELVIEW ); // 设置当前为模型视图矩阵
                GL.glLoadIdentity();    // 重置模型视图矩阵
        }
}

第三步,创建要绘画的Cube类
using CsGL.OpenGL;

 public class Cube
 {
          private const int   CUBE = 1;
          private float fRotate;

          public void Cube(){}

         /// <summary>
          /// 创建显示列表
         /// </summary>

          public void glConstructList()
         {
                  GL.glNewList(CUBE, GL.GL_COMPILE);           // Start With The box Display List

                  GL.glBegin(GL.GL_QUADS);             // Start Drawing Quads
                       // Bottom Face
                      GL.glVertex3f(-1.0f, -1.0f, -1.0f);  
                      GL.glVertex3f( 1.0f, -1.0f, -1.0f);  
                      GL.glVertex3f( 1.0f, -1.0f,  1.0f);   
                      GL.glVertex3f(-1.0f, -1.0f,  1.0f);   

                      // Front Face
                      GL.glVertex3f(-1.0f, -1.0f,  1.0f);  
                      GL.glVertex3f( 1.0f, -1.0f,  1.0f);  
                      GL.glVertex3f( 1.0f,  1.0f,  1.0f);  
                      GL.glVertex3f(-1.0f,  1.0f,  1.0f);  

                      // Back Face
                      GL.glVertex3f(-1.0f, -1.0f, -1.0f);  
                      GL.glVertex3f(-1.0f,  1.0f, -1.0f);  
                      GL.glVertex3f( 1.0f,  1.0f, -1.0f);   
                      GL.glVertex3f( 1.0f, -1.0f, -1.0f);   

                      // Right face
                      GL.glVertex3f( 1.0f, -1.0f, -1.0f);   
                      GL.glVertex3f( 1.0f,  1.0f, -1.0f);   
                       GL.glVertex3f( 1.0f,  1.0f,  1.0f);   
                      GL.glVertex3f( 1.0f, -1.0f,  1.0f);   

                      // Left Face
                      GL.glVertex3f(-1.0f, -1.0f, -1.0f);   
                      GL.glVertex3f(-1.0f, -1.0f,  1.0f);   
                      GL.glVertex3f(-1.0f,  1.0f,  1.0f);  
                      GL.glVertex3f(-1.0f,  1.0f, -1.0f);  

                 GL.glEnd();               // Done Drawing Quads
                 GL.glEndList();         // Done Building The box Display List
          }

          /// <summary>
          /// 绘制方框
         /// </summary>

            public void glDraw()
            {
                   GL.glTranslatef(0.0f,0.0f, 6.0f);   
                   GL.glRotatef(90f, 1.0f, 1.0f, 1.0f);

                   GL.glRotatef(fRotate, 1.0f, 1.0f, 1.0f);
                   fRotate += 0.5f;

                   GL.glCallList(CUBE);
            }
}

OK,到现在为止,要做的基本上就结束了,接下来让立方体显示出来:
在MyView类中加入私有域成员:
private Cube cube;
在构造函数中初始化之:
cube = new Cube();
而InitGLContext()添加一行,建立显示列表:
cube.glConstructList();
最后增加一个重载成员函数负责绘制:
 public override void glDraw()
{
     GL.glClear( GL.GL_COLOR_BUFFER_BIT | GL.GL_DEPTH_BUFFER_BIT ); // 清理视窗以及深度缓存
     GL.glLoadIdentity(); // 重置当前模型视图矩阵
    
      // 绘图
     cube.glDrawCube();
     this.SwapBuffer();  // 交换缓存
}

最后一步,在主窗口类中增加私有成员变量
private MyView view;
在InitializeComponent()中加入view初始化:
  /// <summary>
  /// 设计器支持所需的方法 - 不要使用代码编辑器修改
  /// 此方法的内容。
  /// </summary>

  private void InitializeComponent()
  {
        this.view = new MyView();
        this.SuspendLayout();
        // 
        // view
        //
 
        this.view.Dock = System.Windows.Forms.DockStyle.Fill;
        this.view.Location = new System.Drawing.Point(0, 0);
        this.view.Name = "view";
        this.view.Size = new System.Drawing.Size(292, 266);
        this.view.TabIndex = 0;
        // 
        // MainWindow
        //
 
        this.AutoScaleBaseSize = new System.Drawing.Size(5, 13);
        this.ClientSize = new System.Drawing.Size(292, 266);
        this.Controls.Add(this.view);
        this.Name = "MainWindow";
        this.Text = "Simple CsGL App";
        this.Load += new System.EventHandler(this.MainWindow_Load);
        this.ResumeLayout(false);
}

大功告成。

posted on 2004-05-30 18:39  Findekano  阅读(5037)  评论(12编辑  收藏  举报