1.原始代码
#define GLUT_DISABLE_ATEXIT_HACK #include <stdlib.h> #include <string.h> #include "stdio.h" #include "math.h" #include "GL/glut.h" #if !defined(GLUT_WHEEL_UP) # define GLUT_WHEEL_UP 3 # define GLUT_WHEEL_DOWN 4 #endif //向量 struct GLvector { GLfloat fX; GLfloat fY; GLfloat fZ; }; //立方体8个顶点 static const GLfloat a2fVertexOffset[8][3] = { {0.0, 0.0, 0.0},{1.0, 0.0, 0.0},{1.0, 1.0, 0.0},{0.0, 1.0, 0.0}, {0.0, 0.0, 1.0},{1.0, 0.0, 1.0},{1.0, 1.0, 1.0},{0.0, 1.0, 1.0} }; // 立方体12个边 static const GLint a2iEdgeConnection[12][2] = { {0,1}, {1,2}, {2,3}, {3,0}, {4,5}, {5,6}, {6,7}, {7,4}, {0,4}, {1,5}, {2,6}, {3,7} }; //立方体 12个边的方向向量 static const GLfloat a2fEdgeDirection[12][3] = { {1.0, 0.0, 0.0},{0.0, 1.0, 0.0},{-1.0, 0.0, 0.0},{0.0, -1.0, 0.0}, {1.0, 0.0, 0.0},{0.0, 1.0, 0.0},{-1.0, 0.0, 0.0},{0.0, -1.0, 0.0}, {0.0, 0.0, 1.0},{0.0, 0.0, 1.0},{ 0.0, 0.0, 1.0},{0.0, 0.0, 1.0} }; static const GLfloat afAmbientWhite [] = {0.25, 0.25, 0.25, 1.00}; // 周围 环绕 白 static const GLfloat afAmbientRed [] = {0.25, 0.00, 0.00, 1.00}; // 周围 环绕 红 static const GLfloat afAmbientGreen [] = {0.00, 0.25, 0.00, 1.00}; // 周围 环绕 绿 static const GLfloat afAmbientBlue [] = {0.00, 0.00, 0.25, 1.00}; // 周围 环绕 蓝 static const GLfloat afDiffuseWhite [] = {0.75, 0.75, 0.75, 1.00}; // 漫射 白 static const GLfloat afDiffuseRed [] = {0.75, 0.00, 0.00, 1.00}; // 漫射 红 static const GLfloat afDiffuseGreen [] = {0.00, 0.75, 0.00, 1.00}; // 漫射 绿 static const GLfloat afDiffuseBlue [] = {0.00, 0.00, 0.75, 1.00}; // 漫射 蓝 static const GLfloat afSpecularWhite[] = {1.00, 1.00, 1.00, 1.00}; // 反射 白 static const GLfloat afSpecularRed [] = {1.00, 0.25, 0.25, 1.00}; // 反射 红 static const GLfloat afSpecularGreen[] = {0.25, 1.00, 0.25, 1.00}; // 反射 绿 static const GLfloat afSpecularBlue [] = {0.25, 0.25, 1.00, 1.00}; // 反射 蓝 GLenum ePolygonMode = GL_FILL; GLfloat fTargetValue = 100.0; GLboolean bLight = true; void vIdle(); void vDrawScene(); void vResize(GLsizei, GLsizei); void vKeyboard(unsigned char cKey, int iX, int iY); void vSpecial(int iKey, int iX, int iY); void spinDisplay(); void fYawDisplay(void); void myMouseCall(int button, int state, int x ,int y); GLvoid vMarchingCubes(); GLvoid vMarchCube1(GLfloat fX, GLfloat fY, GLfloat fZ, GLfloat fScale); #define NX 200 #define NY 160 #define NZ 160 short int ***data; GLfloat HoriRotate = 90; GLfloat VertiRotate = 0; GLfloat Xtranform=-90.0; GLfloat Ytranform= 80.0; GLfloat Ztranform=-10.0; GLfloat ZoonAspect=140.0; GLfloat ZoomScale=1.0; short int themax = 0,themin = 255; void main(int argc, char **argv) { int i,j,k,c; short int isolevel = 128; FILE *fptr; argc=2; argv[1]="F:\\软件\\OpenGL\\mri.raw"; for (i=1;i<argc;i++) { if (strcmp(argv[i],"-i") == 0) isolevel = atof(argv[i+1]); } // Malloc the volumetric data, hardwired size! data = (short int ***)malloc(NX*sizeof(short int **)); for (i=0;i<NX;i++) data[i] = (short int **)malloc(NY*sizeof(short int *)); for (i=0;i<NX;i++) for (j=0;j<NY;j++) data[i][j] = (short int *)malloc(NZ*sizeof(short int)); // Open and read the raw data fprintf(stderr,"Reading data ...\n"); if ((fopen_s(fptr,argv[argc-1],"rb")) != NULL) { fprintf(stderr,"File open failed\n"); exit(-1); } for (k=0;k<NZ;k++) { for (j=0;j<NY;j++) { for (i=0;i<NX;i++) { if ((c = fgetc(fptr)) == EOF) { fprintf(stderr,"Unexpected end of file\n"); exit(-1); } data[i][j][k] = c; if (c > themax) themax = c; if (c < themin) themin = c; } } } fclose(fptr); fprintf(stderr,"Volumetric data range: %d -> %d\n",themin,themax); GLfloat afPropertiesAmbient [] = {0.25, 0.25, 0.25, 1.00}; GLfloat afPropertiesDiffuse [] = {0.75, 0.75, 0.75, 1.00}; GLfloat afPropertiesSpecular[] = {1.00, 0.25, 0.25, 1.00}; GLsizei iWidth = 640.0; GLsizei iHeight = 480.0; glutInit(&argc, argv); glutInitWindowPosition( 0, 0); glutInitWindowSize(iWidth, iHeight); glutInitDisplayMode( GLUT_RGB | GLUT_DEPTH | GLUT_DOUBLE ); glutCreateWindow( "Marching Cubes" ); glutDisplayFunc( vDrawScene ); glutIdleFunc( vIdle ); glutReshapeFunc( vResize ); glutKeyboardFunc( vKeyboard ); glutSpecialFunc( vSpecial ); glutMouseFunc(myMouseCall); glClearColor( 0.0, 0.0, 0.0, 1.0 ); glClearDepth( 1.0 ); glEnable(GL_DEPTH_TEST); glEnable(GL_LIGHTING); glPolygonMode(GL_FRONT_AND_BACK, ePolygonMode); glLightfv( GL_LIGHT0, GL_AMBIENT, afPropertiesAmbient); glLightfv( GL_LIGHT0, GL_DIFFUSE, afPropertiesDiffuse); glLightfv( GL_LIGHT0, GL_SPECULAR, afPropertiesSpecular); glLightModelf(GL_LIGHT_MODEL_TWO_SIDE, 1.0); glEnable( GL_LIGHT0 ); // 材质颜色 ***里外 *** glMaterialfv(GL_BACK, GL_AMBIENT, afAmbientRed); glMaterialfv(GL_BACK, GL_DIFFUSE, afDiffuseRed); glMaterialfv(GL_FRONT, GL_AMBIENT, afAmbientWhite); glMaterialfv(GL_FRONT, GL_DIFFUSE, afDiffuseWhite); glMaterialfv(GL_FRONT, GL_SPECULAR, afSpecularWhite); glMaterialf( GL_FRONT, GL_SHININESS, 10.0); vResize(iWidth, iHeight); glutMainLoop(); } // 窗口改变响应 void vResize( GLsizei iWidth, GLsizei iHeight ) { GLfloat fAspect, fHalfWorldSize = (1.4142135623730950488016887242097/2); glViewport( 0, 0, iWidth, iHeight ); glMatrixMode (GL_PROJECTION); glLoadIdentity (); if(iWidth <= iHeight) { fAspect = (GLfloat)iHeight / (GLfloat)iWidth; glOrtho(-fHalfWorldSize*ZoonAspect, fHalfWorldSize*ZoonAspect, -fHalfWorldSize*fAspect*ZoonAspect, fHalfWorldSize*fAspect*ZoonAspect, -10*fHalfWorldSize*ZoonAspect, 10*fHalfWorldSize*ZoonAspect); } else { fAspect = (GLfloat)iWidth / (GLfloat)iHeight; glOrtho(-fHalfWorldSize*fAspect*ZoonAspect, fHalfWorldSize*fAspect*ZoonAspect, -fHalfWorldSize*ZoonAspect, fHalfWorldSize*ZoonAspect, -10*fHalfWorldSize*ZoonAspect, 10*fHalfWorldSize*ZoonAspect); } glMatrixMode( GL_MODELVIEW ); } void spinDisplay(void) { HoriRotate = HoriRotate+10.0; if (HoriRotate >360.0) HoriRotate = HoriRotate -360.0; glutPostRedisplay(); } void fYawDisplay(void) { VertiRotate = VertiRotate+10.0; if (VertiRotate >360.0) VertiRotate = VertiRotate -360.0; glutPostRedisplay(); } // 鼠标响应 void myMouseCall(int button, int state, int x ,int y) { switch (butt