首页 诗词 字典 板报 句子 名言 友答 励志 学校 网站地图
当前位置: 首页 > 教程频道 > 开发语言 > 编程 >

OpenGL学习二十七:混同

2014-01-26 
OpenGL学习二十七:混合???????????????????? OpenGL 会把源颜色和目标颜色各自取出(源颜色认为是片段。目标

OpenGL学习二十七:混合
???????????????????? OpenGL学习二十七:混同

OpenGL 会把源颜色和目标颜色各自取出(源颜色认为是片段。目标演示是帧缓冲区内容),并乘以一个系数(源颜色乘以的系数称为“源因子”,目标颜色乘以的系数称为“目标因子”),然后相加,这样就得到了新的颜色。(也可以不是相加,新版本的OpenGL可以设置运算方式,包括加、减、取两者中较大的、取两者中较小的、逻辑运算等,但我们这里为了简单起见,不讨 论这个了) 下面用数学公式来表达一下这个运算方式。假设源颜色的四个分量(指红色,绿色,蓝色,alpha值)是(Rs, Gs, Bs, As),目标颜色的四个分量是(Rd, Gd, Bd, Ad),又设源因子为(Sr, Sg, Sb, Sa),目标因子为(Dr, Dg, Db, Da)。则混合产生的新颜色可以表示为: (Rs*Sr+Rd*Dr, Gs*Sg+Gd*Dg, Bs*Sb+Bd*Db, As*Sa+Ad*Da) 当然了,如果颜色的某一分量超过了1.0,则它会被自动截取为1.0,不需要考虑越界的问题。

源因子和目标因子是可以通过glBlendFunc函数来进行设置的。glBlendFunc有两个参数,前者表示源因子,后者表示目标因子。这两个参数可以是多种值,下面介绍比较常用的几种。

GL_ZERO: 表示使用0.0作为因子,实际上相当于不使用这种颜色参与混合运算。
GL_ONE: 表示使用1.0作为因子,实际上相当于完全的使用了这种颜色参与混合运算。
GL_SRC_ALPHA:表示使用源颜色的alpha值来作为因子。
GL_DST_ALPHA:表示使用目标颜色的alpha值来作为因子。
GL_ONE_MINUS_SRC_ALPHA:表示用1.0减去源颜色的alpha值来作为因子。
GL_ONE_MINUS_DST_ALPHA:表示用1.0减去源颜色的alpha值来作为因子。
GL_SRC_COLOR
GL_ONE_MINUS_SRC_COLOR
GL_DST_COLOR
GL_ONE_MINUS_DST_COLOR

?

混合方程式组合像素
void glBlendEquation(Glenum mode)
假设缓冲区颜色为(1,0,0) 片段颜色是(1,1,0)
GL_FUNC_ADD=(1,1,0)+(1,0,0)=(1,1,0)
GL_FUNC_SUBTRACT=(1,1,0)-(1,0,0)=(0,1,0)
GL_FUNC_REVERSE_SUBTRACT=(1,0,0)-(1,1,0)=(0,0,0)
GL_MIN=min((1,0,0),(1,1,0))=(1,0,0)
GL_MAX=max((1,0,0),(1,1,0))=(1,1,0)
GL_LOGIC_OP

?

#include "header.h"GLfloatxrot;GLfloatyrot;GLfloat xspeed;GLfloat yspeed;GLfloatz=-5.0f;GLfloat LightAmbient[]={ 0.5f, 0.5f, 0.5f, 1.0f };GLfloat LightDiffuse[]={ 1.0f, 1.0f, 1.0f, 1.0f };GLfloat LightPosition[]={ 0.0f, 0.0f, 2.0f, 1.0f };GLuintfilter;GLuinttexture[3];AUX_RGBImageRec *LoadBMP(char *Filename){FILE *File=NULL;if (!Filename){return NULL;}File=fopen(Filename,"r");if (File){fclose(File);return auxDIBImageLoad(Filename);}return NULL;}int LoadGLTextures(){int Status=FALSE;AUX_RGBImageRec *TextureImage[1];memset(TextureImage,0,sizeof(void *)*1);           if (TextureImage[0]=LoadBMP("Data/glass.bmp")){Status=TRUE;glGenTextures(3, &texture[0]);// Create Nearest Filtered TextureglBindTexture(GL_TEXTURE_2D, texture[0]);glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MAG_FILTER,GL_NEAREST);glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_NEAREST);glTexImage2D(GL_TEXTURE_2D, 0, 3, TextureImage[0]->sizeX, TextureImage[0]->sizeY, 0, GL_RGB, GL_UNSIGNED_BYTE, TextureImage[0]->data);// Create Linear Filtered TextureglBindTexture(GL_TEXTURE_2D, texture[1]);glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MAG_FILTER,GL_LINEAR);glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_LINEAR);glTexImage2D(GL_TEXTURE_2D, 0, 3, TextureImage[0]->sizeX, TextureImage[0]->sizeY, 0, GL_RGB, GL_UNSIGNED_BYTE, TextureImage[0]->data);// Create MipMapped TextureglBindTexture(GL_TEXTURE_2D, texture[2]);glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MAG_FILTER,GL_LINEAR);glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_LINEAR_MIPMAP_NEAREST);gluBuild2DMipmaps(GL_TEXTURE_2D, 3, TextureImage[0]->sizeX, TextureImage[0]->sizeY, GL_RGB, GL_UNSIGNED_BYTE, TextureImage[0]->data);}if (TextureImage[0]){if (TextureImage[0]->data){free(TextureImage[0]->data);}free(TextureImage[0]);}return Status;}GLvoid ReSizeGLScene(GLsizei width, GLsizei height){if (height==0){height=1;}glViewport(0,0,width,height);glMatrixMode(GL_PROJECTION);glLoadIdentity();// Calculate The Aspect Ratio Of The WindowgluPerspective(45.0f,(GLfloat)width/(GLfloat)height,0.1f,100.0f);glMatrixMode(GL_MODELVIEW);glLoadIdentity();}int InitGL(GLvoid){if (!LoadGLTextures()){return FALSE;}glEnable(GL_TEXTURE_2D);glShadeModel(GL_SMOOTH);glClearColor(0.0f, 0.0f, 0.0f, 0.5f);glClearDepth(1.0f);glEnable(GL_DEPTH_TEST);glDepthFunc(GL_LEQUAL);glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST);glLightfv(GL_LIGHT1, GL_AMBIENT, LightAmbient);glLightfv(GL_LIGHT1, GL_DIFFUSE, LightDiffuse);glLightfv(GL_LIGHT1, GL_POSITION,LightPosition);glEnable(GL_LIGHT1);glColor4f(1.0f, 1.0f, 1.0f, 0.5);glBlendFunc(GL_SRC_ALPHA,GL_ONE);return TRUE;}void DrawGLScene(void){glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);glLoadIdentity();glTranslatef(0.0f,0.0f,z);glRotatef(xrot,1.0f,0.0f,0.0f);glRotatef(yrot,0.0f,1.0f,0.0f);glBindTexture(GL_TEXTURE_2D, texture[filter]);glBegin(GL_QUADS);// Front FaceglNormal3f( 0.0f, 0.0f, 1.0f);glTexCoord2f(0.0f, 0.0f); glVertex3f(-1.0f, -1.0f,  1.0f);glTexCoord2f(1.0f, 0.0f); glVertex3f( 1.0f, -1.0f,  1.0f);glTexCoord2f(1.0f, 1.0f); glVertex3f( 1.0f,  1.0f,  1.0f);glTexCoord2f(0.0f, 1.0f); glVertex3f(-1.0f,  1.0f,  1.0f);// Back FaceglNormal3f( 0.0f, 0.0f,-1.0f);glTexCoord2f(1.0f, 0.0f); glVertex3f(-1.0f, -1.0f, -1.0f);glTexCoord2f(1.0f, 1.0f); glVertex3f(-1.0f,  1.0f, -1.0f);glTexCoord2f(0.0f, 1.0f); glVertex3f( 1.0f,  1.0f, -1.0f);glTexCoord2f(0.0f, 0.0f); glVertex3f( 1.0f, -1.0f, -1.0f);// Top FaceglNormal3f( 0.0f, 1.0f, 0.0f);glTexCoord2f(0.0f, 1.0f); glVertex3f(-1.0f,  1.0f, -1.0f);glTexCoord2f(0.0f, 0.0f); glVertex3f(-1.0f,  1.0f,  1.0f);glTexCoord2f(1.0f, 0.0f); glVertex3f( 1.0f,  1.0f,  1.0f);glTexCoord2f(1.0f, 1.0f); glVertex3f( 1.0f,  1.0f, -1.0f);// Bottom FaceglNormal3f( 0.0f,-1.0f, 0.0f);glTexCoord2f(1.0f, 1.0f); glVertex3f(-1.0f, -1.0f, -1.0f);glTexCoord2f(0.0f, 1.0f); glVertex3f( 1.0f, -1.0f, -1.0f);glTexCoord2f(0.0f, 0.0f); glVertex3f( 1.0f, -1.0f,  1.0f);glTexCoord2f(1.0f, 0.0f); glVertex3f(-1.0f, -1.0f,  1.0f);// Right faceglNormal3f( 1.0f, 0.0f, 0.0f);glTexCoord2f(1.0f, 0.0f); glVertex3f( 1.0f, -1.0f, -1.0f);glTexCoord2f(1.0f, 1.0f); glVertex3f( 1.0f,  1.0f, -1.0f);glTexCoord2f(0.0f, 1.0f); glVertex3f( 1.0f,  1.0f,  1.0f);glTexCoord2f(0.0f, 0.0f); glVertex3f( 1.0f, -1.0f,  1.0f);// Left FaceglNormal3f(-1.0f, 0.0f, 0.0f);glTexCoord2f(0.0f, 0.0f); glVertex3f(-1.0f, -1.0f, -1.0f);glTexCoord2f(1.0f, 0.0f); glVertex3f(-1.0f, -1.0f,  1.0f);glTexCoord2f(1.0f, 1.0f); glVertex3f(-1.0f,  1.0f,  1.0f);glTexCoord2f(0.0f, 1.0f); glVertex3f(-1.0f,  1.0f, -1.0f);glEnd();xrot+=xspeed;yrot+=yspeed;glFlush();}void rotate(){glutPostRedisplay();}void keyboard(unsigned char key,int x,int y){switch (key){case 'L':glEnable(GL_LIGHTING);glutPostRedisplay();break;case 'l':glDisable(GL_LIGHTING);glutPostRedisplay();break;case 'B':glEnable(GL_BLEND);glDisable(GL_DEPTH_TEST);glutPostRedisplay();break;case 'b':glDisable(GL_BLEND);glEnable(GL_DEPTH_TEST);glutPostRedisplay();break;case 'F':filter+=1;if (filter>2){filter=0;}glutPostRedisplay();break;case 'W':yspeed+=0.01f;glutIdleFunc(rotate);break;case 'S':yspeed-=0.01f;glutIdleFunc(rotate);break;case 'A':xspeed+=0.01f;glutIdleFunc(rotate);break;case 'D':xspeed-=0.01f;glutIdleFunc(rotate);break;case 'Z':z-=0.01f;glutIdleFunc(rotate);break;case 'X':z+=0.01f;glutIdleFunc(rotate);break;case 'R':glutIdleFunc(NULL);break;}}int main(int argc,char **argv){glutInit(&argc,argv);glutInitDisplayMode(GLUT_SINGLE|GLUT_RGB|GLUT_DEPTH);glutInitWindowSize(800,600);glutInitWindowPosition(100,100);glutCreateWindow("混合");InitGL();glutDisplayFunc(DrawGLScene);glutKeyboardFunc(keyboard);glutReshapeFunc(ReSizeGLScene);glutMainLoop();}

?

热点排行