📄 main.c
字号:
glBindTexture(GL_TEXTURE_2D, Sh_ShadowMapTexId); glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); glEnable(GL_TEXTURE_2D);// This is the shadow-pass// LPolyGroup->ShadowPass=TRUE; E3d_DrawModel(LModel, FALSE, &Sh_Light, Sh_BackFaceShadowElimination); glEnable(GL_LIGHTING); glDisable(GL_BLEND); glPopMatrix(); } } glDisable(GL_TEXTURE_2D); glPopMatrix();}/*==============================================*//* GLUT window-resize callback function *//*==============================================*/void Sh_Resize(int LXSize, int LYSize){ Sh_WindowXSize = LXSize; Sh_WindowYSize = LYSize; Sh_WindowAspect = (float)Sh_WindowXSize/(float)Sh_WindowYSize; glViewport(0, 0, Sh_WindowXSize, Sh_WindowYSize); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glutPostRedisplay();}/*======================================*//* GLUT main Display function *//*======================================*/void Sh_Display(void) { E3dMatrix LBlockerMatrix,LReceiverUVMatrix;#ifdef _WIN32 float newestTime;#else struct timeval LTV; struct timezone LTZ;#endif E3d_GLUpdateLight(0, &Sh_Light);#ifdef _WIN32// For timing// Sh_Frame+=1; newestTime = (float)timeGetTime()/1000.0f; if((newestTime-Sh_StartTime)>=10.0f) { printf("FrameRate: %3.2f fps\n",(float)Sh_Frame/(float)(newestTime-Sh_StartTime));fflush(stdout); Sh_Frame=0; Sh_StartTime=newestTime; }#else// For timing// Sh_Frame+=1; if(gettimeofday(<V,<Z)!=-1) { if((LTV.tv_sec-Sh_StartTime)>=10) { printf("FrameRate: %3.2f fps\n",(float)Sh_Frame/(float)(LTV.tv_sec-Sh_StartTime));fflush(stdout); Sh_Frame=0; Sh_StartTime=LTV.tv_sec; } }#endif glViewport(0, 0, Sh_WindowXSize, Sh_WindowYSize); glClearColor(0.3, 0.0, 0.0, 0.0); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); if(Scn_BlockerModel!=NULL) { E3d_ShadowMatrix(&Sh_Light,Scn_BlockerModel,LBlockerMatrix,LReceiverUVMatrix); Sh_CreateShadowMap(Sh_ShadowMapTexId,Sh_ShadowMapXSize, Sh_ShadowMapYSize, (E3dMesh*)(Scn_BlockerModel->Geometry), LBlockerMatrix);// Set the ShadowMapUV matrices of the receiver objects// if(Scn_ReceiverModel0!=NULL) { E3d_MatrixCopy(LReceiverUVMatrix,Scn_ReceiverModel0->ShadowMapUVMatrix); } if(Scn_ReceiverModel1!=NULL) { E3d_MatrixCopy(LReceiverUVMatrix,Scn_ReceiverModel1->ShadowMapUVMatrix); } }// The shadow map generator has set it's own viewport,// so we have to (re)configure it here// glViewport(0, 0, Sh_WindowXSize, Sh_WindowYSize);// We must clear the BACK buffer again before starting to render the scene// glClearColor(0.0, 0.0, 0.0, 0.0); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glMatrixMode(GL_PROJECTION); glLoadIdentity(); gluPerspective(64.0, Sh_WindowAspect, Sh_ZNear, Sh_ZFar); glMatrixMode(GL_MODELVIEW); glLoadIdentity(); // Camera transformation// glTranslatef(0.0,0.0,-Sh_ViewDistance); glRotatef(-Sh_Latitude, 1.0, 0.0, 0.0); glRotatef(Sh_Longitude, 0.0, 1.0, 0.0); E3d_GLUpdateLight(0, &Sh_Light); Sh_DrawScene(); glutSwapBuffers();}/*======================================*//* Mouse motion callback handler *//*======================================*/void ShCB_MouseMotion(int LX, int LY){ if (Sh_LeftButton) { Sh_Longitude -= (float)(Sh_PrevMX-LX) * 0.4; Sh_Latitude += (float)(Sh_PrevMY-LY) * 0.4; } if (Sh_MiddleButton) { switch(Sh_MiddleMouseMode) { case ShDOLLY_CAMERA: Sh_ViewDistance += (float)(Sh_PrevMY - LY) * 0.2; break; case ShMOVE_LIGHT: Sh_Light.Position.X -= (float)(Sh_PrevMX - LX)*0.2; if(Sh_Light.Position.X<-23.0) Sh_Light.Position.X=-23.0; else if(Sh_Light.Position.X>25.0) Sh_Light.Position.X=25.0; Sh_Light.Position.Z -= (float)(Sh_PrevMY - LY)*0.2; if(Sh_Light.Position.Z<-25.0) Sh_Light.Position.Z=-25.0; else if(Sh_Light.Position.Z>25.0) Sh_Light.Position.Z=25.0; break; } } Sh_PrevMX = LX;Sh_PrevMY = LY; glutPostRedisplay();}/*======================================*//* Mouse button callback handler *//*======================================*/void ShCB_MouseButtons(int LButton, int LState, int LX, int LY){ Sh_PrevMX = LX; Sh_PrevMY = LY; Sh_LeftButton = ((LButton == GLUT_LEFT_BUTTON) && (LState == GLUT_DOWN)); Sh_MiddleButton = ((LButton == GLUT_MIDDLE_BUTTON) && (LState == GLUT_DOWN));}/*======================================*//* Keyboard callback handler *//*======================================*/void ShCB_Keyboard(unsigned char LCh, int LX, int LY){ switch (LCh) { case 'c': Sh_MiddleMouseMode=ShDOLLY_CAMERA; break; case 'l': Sh_MiddleMouseMode=ShMOVE_LIGHT; break; case 27: exit(0); break; // "Esc" } glutPostRedisplay();}/*======================================*//* The main... *//*======================================*/void main(int LArgC, char** LArgV){ E3dMaterial* LMaterial; E3dMesh* LMesh; E3dPolyGroup* LPolyGroup; glutInit(&LArgC, LArgV); glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB | GLUT_DEPTH); glutInitWindowSize(420, 320); glutCreateWindow("Shadows"); glLightModelf(GL_LIGHT_MODEL_LOCAL_VIEWER, 1.0); E3d_MaterialDefault(&E3d_DefaultMaterial);// Read light-bulb geometry// if((Scn_BulbModel=E3d_ReadOBJFile("objects/bulb.obj")) != NULL) { if((LMesh=(E3dMesh*)(Scn_BulbModel->Geometry))!=NULL) {// Glass part// LPolyGroup=LMesh->PolyGroups[0]; LPolyGroup->Material=LMaterial=E3d_MaterialAllocate(); LMaterial->Type=E3dMAT_CONSTANT; LMaterial->Diffuse[0]=1.0; LMaterial->Diffuse[1]=1.0; LMaterial->Diffuse[2]=1.0;// Copper part// LPolyGroup=LMesh->PolyGroups[1]; LPolyGroup->Material=LMaterial=E3d_MaterialAllocate(); LMaterial->Type=E3dMAT_CONSTANT; LMaterial->Diffuse[0]=0.5; LMaterial->Diffuse[1]=0.3; LMaterial->Diffuse[2]=0.1; } }// Read a blocker object// ShCB_SetlectBlockerObject(0);// Initialize cloth model// if((Scn_ReceiverModel0=E3d_ReadOBJFile("objects/cloth.obj")) != NULL) { Scn_ReceiverModel0->Translation.Y=-5.0; Scn_ReceiverModel0->Translation.Z=-3.0; if((LMesh=(E3dMesh*)(Scn_ReceiverModel0->Geometry))!=NULL) { LPolyGroup=LMesh->PolyGroups[0]; LPolyGroup->ShadowPass=TRUE; LPolyGroup->Material=LMaterial=E3d_MaterialAllocate(); LMaterial->Diffuse[0]=0.7; LMaterial->Diffuse[1]=0.3; LMaterial->Diffuse[2]=0.1;// This object won't move, so we won't recompute it's local->world matrix at each frame// E3d_ModelRefreshMatrices(Scn_ReceiverModel0); } }// Initialize table model// if((Scn_ReceiverModel1=E3d_ReadOBJFile("objects/table.obj")) != NULL) { Scn_ReceiverModel1->Translation.Y=0.0; if((LMesh=(E3dMesh*)(Scn_ReceiverModel1->Geometry))!=NULL) { LPolyGroup=LMesh->PolyGroups[0];// Make material white so the wood texture will blend properly// LPolyGroup->Material=LMaterial=E3d_MaterialAllocate(); LMaterial->Diffuse[0]=1.6; LMaterial->Diffuse[1]=1.6; LMaterial->Diffuse[2]=1.6;// This object won't move, so we won't recompute it's local->world matrix at each frame// E3d_ModelRefreshMatrices(Scn_ReceiverModel1); } }// Initialize our light source// E3d_LightDefault(&Sh_Light); Sh_Light.Position.X=-12.0; Sh_Light.Position.Y=16.0; Sh_Light.Position.Z=7.5;// Allocate memory for the shadow map// Sh_ShadowMapImage=(unsigned long*)malloc(Sh_ShadowMapXSize*Sh_ShadowMapYSize*sizeof(unsigned long)); glEnable(GL_DEPTH_TEST); glDepthFunc(GL_LEQUAL); glPolygonOffset(1.0, 1.0); glEnable(GL_CULL_FACE); glHint(GL_LINE_SMOOTH_HINT, GL_NICEST); glHint(GL_POLYGON_SMOOTH_HINT, GL_NICEST); glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST);// glEnable(GL_COLOR_MATERIAL);// glColorMaterial(GL_FRONT, GL_DIFFUSE); E3d_GLUpdateLight(0, &Sh_Light); glEnable(GL_LIGHT0); Sh_InitTextures(); glutIdleFunc(Sh_Run); glutReshapeFunc(Sh_Resize); glutDisplayFunc(Sh_Display); glutKeyboardFunc(ShCB_Keyboard); glutMouseFunc(ShCB_MouseButtons); glutMotionFunc(ShCB_MouseMotion);// Select blocker object// Sh_BlockerObjectMenu = glutCreateMenu(ShCB_SetlectBlockerObject); glutAddMenuEntry("Torus", 0); glutAddMenuEntry("Hourglass", 1);// Shadow-map size selection// Sh_ShadowMapMenu = glutCreateMenu(ShCB_SetShadowMapSize); glutAddMenuEntry("32x32", 32); glutAddMenuEntry("64x64", 64); glutAddMenuEntry("128x128", 128); glutAddMenuEntry("256x256", 256);// Back-face shadow ON/OFF// Sh_BackFaceShadowMenu = glutCreateMenu(ShCB_BackFaceShadow); glutAddMenuEntry("OFF", 0); glutAddMenuEntry("ON", 1); Sh_MainMenu = glutCreateMenu(ShCB_MainMenu); glutAddSubMenu("Blocker object", Sh_BlockerObjectMenu); glutAddSubMenu("Back-face shadow elimination", Sh_BackFaceShadowMenu); glutAddSubMenu("Shadow-map size", Sh_ShadowMapMenu); glutAddMenuEntry("Exit", 5); glutAttachMenu(GLUT_RIGHT_BUTTON);#ifdef _WIN32 Sh_StartTime = (float)timeGetTime()/1000.0f;#else { struct timeval LTV; struct timezone LTZ; if(gettimeofday(<V,<Z)!=-1) { Sh_StartTime=LTV.tv_sec; } }#endif glutMainLoop();}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -