zoukankan      html  css  js  c++  java
  • OpenGL第18,19,20讲小结

      18讲是通过调用库函数画一些简单的二次几何体,比如球体、圆锥体、圆盘等等。

      19讲简单的讲了下粒子系统。其实就是三角形贴上星星的纹理,通过启用混合(GL_BLEND)来达到一种动态的粒子效果。通过修改粒子刷新位置,粒子的加速度、初始速度、衰减速度等等,可以做成如喷泉、瀑布、火焰、等等,也可以当当五毛特效,反正我是玩的不亦乐乎。

      接下来20讲,讲了一个使用掩膜从而形成一种镂空的效果,我觉得有点绕。理来理去最终有了自己的一些理解,先贴下代码吧:

    int DrawGLScene(GLvoid)                                    // Here's Where We Do All The Drawing
    {
        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);    // Clear Screen And Depth Buffer
        glLoadIdentity();                                    // Reset The Current Modelview Matrix
        glTranslatef(0.0f,0.0f,-2.0f);                        // 物体移入屏幕2个单位
        glBindTexture(GL_TEXTURE_2D, texture[LOGO]);                // 选择Logo纹理
        glBegin(GL_QUADS);                            // 绘制纹理四边形
        glTexCoord2f(0.0f, -roll+0.0f); glVertex3f(-1.1f, -1.1f,  0.0f);    
        glTexCoord2f(3.0f, -roll+0.0f); glVertex3f( 1.1f, -1.1f,  0.0f);    
        glTexCoord2f(3.0f, -roll+3.0f); glVertex3f( 1.1f,  1.1f,  0.0f);    
        glTexCoord2f(0.0f, -roll+3.0f); glVertex3f(-1.1f,  1.1f,  0.0f);    
        glEnd();    
        glEnable(GL_BLEND);                            // 启用混合
        glDisable(GL_DEPTH_TEST);                            // 禁用深度测试
        if (masking)                                // 是否启用“掩模”
        {
            glBlendFunc(GL_DST_COLOR,GL_ZERO);                    // 使用黑白“掩模”混合屏幕颜色
        }
        if (scene)    
        {
            glTranslatef(0.0f,0.0f,-1.0f);                    // 移入屏幕一个单位
            glRotatef(roll*360,0.0f,0.0f,1.0f);                    // 沿Z轴旋转
            if (masking)                            // “掩模”是否打开
            {
                glBindTexture(GL_TEXTURE_2D, texture[MASK2]);        // 选择第二个“掩模”纹理
                glBegin(GL_QUADS);                    // 开始绘制四边形
                glTexCoord2f(0.0f, 0.0f); glVertex3f(-1.1f, -1.1f,  0.0f);    
                glTexCoord2f(1.0f, 0.0f); glVertex3f( 1.1f, -1.1f,  0.0f);    
                glTexCoord2f(1.0f, 1.0f); glVertex3f( 1.1f,  1.1f,  0.0f);    
                glTexCoord2f(0.0f, 1.0f); glVertex3f(-1.1f,  1.1f,  0.0f);    
                glEnd();                        
            }
            glBlendFunc(GL_ONE, GL_ONE);                // 把纹理2复制到屏幕(我的理解是把经过处理(白的变透明,其他颜色变为黑色)的黑白掩膜粘到接下来的这个纹理后面光从后面透过来,以贴在后面的掩膜图为准,能透则透)
            glBindTexture(GL_TEXTURE_2D, texture[IMAGE2]);            // 选择第二个纹理
            glBegin(GL_QUADS);                        // 绘制四边形
            glTexCoord2f(0.0f, 0.0f); glVertex3f(-1.1f, -1.1f,  0.0f);    
            glTexCoord2f(1.0f, 0.0f); glVertex3f( 1.1f, -1.1f,  0.0f);    
            glTexCoord2f(1.0f, 1.0f); glVertex3f( 1.1f,  1.1f,  0.0f);    
            glTexCoord2f(0.0f, 1.0f); glVertex3f(-1.1f,  1.1f,  0.0f);    
            glEnd();                        
        }
        else                                    
        {
            if (masking)                            // “掩模”是否打开
            {
                glBindTexture(GL_TEXTURE_2D, texture[MASK1]);        // 选择第一个“掩模”纹理
                glBegin(GL_QUADS);                    // 开始绘制四边形
                glTexCoord2f(roll+0.0f, 0.0f); glVertex3f(-1.1f, -1.1f,  0.0f);    
                glTexCoord2f(roll+4.0f, 0.0f); glVertex3f( 1.1f, -1.1f,  0.0f);    
                glTexCoord2f(roll+4.0f, 4.0f); glVertex3f( 1.1f,  1.1f,  0.0f);    
                glTexCoord2f(roll+0.0f, 4.0f); glVertex3f(-1.1f,  1.1f,  0.0f);    
                glEnd();                        
            }
            glBlendFunc(GL_ONE, GL_ONE);                    // 把纹理1复制到屏幕
            glBindTexture(GL_TEXTURE_2D, texture[IMAGE1]);    // 选择第一个纹理
            glBegin(GL_QUADS);                            // 开始绘制四边形
            glTexCoord2f(roll+0.0f, 0.0f); glVertex3f(-1.1f, -1.1f,  0.0f);    
            glTexCoord2f(roll+4.0f, 0.0f); glVertex3f( 1.1f, -1.1f,  0.0f);    
            glTexCoord2f(roll+4.0f, 4.0f); glVertex3f( 1.1f,  1.1f,  0.0f);    
            glTexCoord2f(roll+0.0f, 4.0f); glVertex3f(-1.1f,  1.1f,  0.0f);    
            glEnd();            
        }
        glEnable(GL_DEPTH_TEST);                            // 启用深度测试
        glDisable(GL_BLEND);                            // 禁用混合
        roll+=0.002f;                                // 增加纹理滚动变量
        if (roll>1.0f)                                // 大于1则减1
        {
            roll-=1.0f;                        
        }
    
        return TRUE;                                // 成功返回
    }

      上述代码为创建掩膜的一系列步骤。我的理解是:首先启用黑白掩膜混合屏幕颜色(没怎么懂它的意思,意会一下吧)来对黑白纹理图进行处理;

    glBlendFunc(GL_DST_COLOR,GL_ZERO);

      这个很重要,因为有了它,才能把只有黑白两色的掩膜的白色变为透明,其他颜色变成黑色(当然黑白掩膜只有黑白两色,所谓其他颜色就只有黑色而已),把黑白掩膜的白色变成透明之后,用它:

    glBlendFunc(GL_ONE, GL_ONE);                // 把纹理2复制到屏幕(我的理解是把经过处理(白的变透明,其他颜色变为黑色)的黑白掩膜粘到接下来的这个纹理后面光从后面透过来,以贴在后面的掩膜图为准,能透则透)

      来将刚才处理好的那层掩膜给复制到屏幕上,然后把与掩膜相对应的纹理图加载进来,画一个正方形,这样之后,后加载的这个纹理跟之前那个纹理就贴在一起了,掩膜在后面。这样就达到了镂空的效果,如下图:

      这是不使用掩膜的效果:

      我理解的原理就是这样的,想象光是从后面那块有字的正方形发射出来的,这些光通过这个紫色的网进入我们的眼睛,光能不能透过就取决于掩膜哪些地方是透明的,哪些地方不透明。通过反复的试验观察我就得出了这样一个结论,至于是否正确等待后面有机会再验证吧。

      假如不用掩膜,那最上面这层图像就会变得半透明,远没有用掩膜那样富有层次感。以上所有是今天所得,恩,感谢NeHe的教程。

  • 相关阅读:
    C#编程技巧之钩子函数的使用——SetWindowsHookEx
    JSON(Ajax)和JsonP
    C#对象与方法
    C#数据类型
    事务处理
    面向对象之继承与多态
    C#编程语言简介
    <转>成员函数的重载、覆盖与隐藏
    视图、索引
    C#方法
  • 原文地址:https://www.cnblogs.com/ForRickHuan/p/5705350.html
Copyright © 2011-2022 走看看