Source code of Windows XP (NT5)
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

585 lines
14 KiB

  1. /*
  2. * (c) Copyright 1993, Silicon Graphics, Inc.
  3. * 1993, 1994 Microsoft Corporation
  4. *
  5. * ALL RIGHTS RESERVED
  6. *
  7. * Please refer to OpenGL/readme.txt for additional information
  8. *
  9. */
  10. #include "glos.h"
  11. #include <stdio.h>
  12. #include <string.h>
  13. #include <stdlib.h>
  14. #include <math.h>
  15. #include <gl\glaux.h>
  16. #include "tk.h"
  17. #include "trackbal.h"
  18. #define PI 3.141592654
  19. #define BLACK 0
  20. #define GRAY 128
  21. #define WHITE 255
  22. #define RD 0xA40000FF
  23. #define WT 0xFFFFFFFF
  24. #define brickImageWidth 16
  25. #define brickImageHeight 16
  26. //static void CALLBACK ErrorHandler(unsigned long which);
  27. static void Init(void );
  28. static void CALLBACK Reshape(int width,int height);
  29. static void CALLBACK Draw( void );
  30. static unsigned long Args(int argc,char **argv );
  31. GLenum rgb, doubleBuffer;
  32. GLint wWidth = 300, wHeight = 300;
  33. GLenum doDither = GL_TRUE;
  34. GLenum shade = GL_TRUE;
  35. GLenum texture = GL_TRUE;
  36. BOOL bPolyOffset = TRUE;
  37. #if 1
  38. float factor=0.0f, units=0.0f;
  39. #else
  40. float factor=-1.0f, units=0.0f;
  41. #endif
  42. float inc = 1.0f;
  43. int polygonMode = GL_LINE;
  44. GLenum polyFace = GL_FRONT;
  45. float zTrans = -2.7;
  46. BOOL bCullFace = FALSE;
  47. BOOL bHiddenLine;
  48. GLint radius1, radius2;
  49. GLdouble angle1, angle2;
  50. GLint slices, stacks;
  51. GLint height;
  52. GLint whichQuadric;
  53. GLUquadricObj *quadObj;
  54. GLubyte brickImage[brickImageWidth*brickImageHeight] = {
  55. RD, RD, RD, RD, RD, RD, RD, RD, RD, WT, RD, RD, RD, RD, RD, RD,
  56. RD, RD, RD, RD, RD, RD, RD, RD, RD, WT, RD, RD, RD, RD, RD, RD,
  57. RD, RD, RD, RD, RD, RD, RD, RD, RD, WT, RD, RD, RD, RD, RD, RD,
  58. RD, RD, RD, RD, RD, RD, RD, RD, RD, WT, RD, RD, RD, RD, RD, RD,
  59. WT, WT, WT, WT, WT, WT, WT, WT, WT, WT, WT, WT, WT, WT, WT, WT,
  60. RD, RD, RD, WT, RD, RD, RD, RD, RD, RD, RD, RD, RD, WT, RD, RD,
  61. RD, RD, RD, WT, RD, RD, RD, RD, RD, RD, RD, RD, RD, WT, RD, RD,
  62. RD, RD, RD, WT, RD, RD, RD, RD, RD, RD, RD, RD, RD, WT, RD, RD,
  63. RD, RD, RD, WT, RD, RD, RD, RD, RD, RD, RD, RD, RD, WT, RD, RD,
  64. WT, WT, WT, WT, WT, WT, WT, WT, WT, WT, WT, WT, WT, WT, WT, WT,
  65. RD, RD, RD, RD, RD, RD, RD, WT, RD, RD, RD, RD, RD, RD, RD, RD,
  66. RD, RD, RD, RD, RD, RD, RD, WT, RD, RD, RD, RD, RD, RD, RD, RD,
  67. RD, RD, RD, RD, RD, RD, RD, WT, RD, RD, RD, RD, RD, RD, RD, RD,
  68. RD, RD, RD, RD, RD, RD, RD, WT, RD, RD, RD, RD, RD, RD, RD, RD,
  69. WT, WT, WT, WT, WT, WT, WT, WT, WT, WT, WT, WT, WT, WT, WT, WT,
  70. RD, RD, RD, RD, WT, RD, RD, RD, RD, RD, RD, RD, RD, RD, WT, RD
  71. };
  72. char *texFileName = 0;
  73. #if 0
  74. static void CALLBACK ErrorHandler(GLenum which)
  75. {
  76. fprintf(stderr, "Quad Error: %s\n", gluErrorString(which));
  77. }
  78. #endif
  79. static void UpdateInfo()
  80. {
  81. HWND hwnd = tkGetHWND();
  82. char buf[100];
  83. sprintf( buf, "Factor = %4.1f, Units = %4.1f", factor, units );
  84. SendMessage( hwnd, WM_SETTEXT, 0, (LPARAM)buf );
  85. }
  86. static void SetMaterial( bBlack )
  87. {
  88. static float front_mat_shininess[] = {30.0};
  89. static float front_mat_specular[] = {0.2, 0.2, 0.2, 1.0};
  90. static float front_mat_diffuse[] = {0.5, 0.28, 0.38, 1.0};
  91. static float back_mat_shininess[] = {50.0};
  92. static float back_mat_specular[] = {0.5, 0.5, 0.2, 1.0};
  93. static float back_mat_diffuse[] = {1.0, 1.0, 0.2, 1.0};
  94. static float black_mat_shininess[] = {0.0};
  95. static float black_mat_specular[] = {0.0, 0.0, 0.0, 0.0};
  96. static float black_mat_diffuse[] = {0.0, 0.0, 0.0, 0.0};
  97. static float ambient[] = {0.1, 0.1, 0.1, 1.0};
  98. static float no_ambient[] = {0.0, 0.0, 0.0, 0.0};
  99. static float lmodel_ambient[] = {1.0, 1.0, 1.0, 1.0};
  100. static float lmodel_no_ambient[] = {0.0, 0.0, 0.0, 0.0};
  101. if( !bBlack ) {
  102. glMaterialfv(GL_FRONT, GL_SHININESS, front_mat_shininess);
  103. glMaterialfv(GL_FRONT, GL_SPECULAR, front_mat_specular);
  104. glMaterialfv(GL_FRONT, GL_DIFFUSE, front_mat_diffuse);
  105. glMaterialfv(GL_BACK, GL_SHININESS, back_mat_shininess);
  106. glMaterialfv(GL_BACK, GL_SPECULAR, back_mat_specular);
  107. glMaterialfv(GL_BACK, GL_DIFFUSE, back_mat_diffuse);
  108. glLightfv(GL_LIGHT0, GL_AMBIENT, ambient);
  109. glLightModelfv(GL_LIGHT_MODEL_AMBIENT, lmodel_ambient);
  110. } else {
  111. glMaterialfv(GL_FRONT, GL_SHININESS, black_mat_shininess);
  112. glMaterialfv(GL_FRONT, GL_SPECULAR, black_mat_specular);
  113. glMaterialfv(GL_FRONT, GL_DIFFUSE, black_mat_diffuse);
  114. glMaterialfv(GL_BACK, GL_SHININESS, black_mat_shininess);
  115. glMaterialfv(GL_BACK, GL_SPECULAR, black_mat_specular);
  116. glMaterialfv(GL_BACK, GL_DIFFUSE, black_mat_diffuse);
  117. glLightfv(GL_LIGHT0, GL_AMBIENT, no_ambient);
  118. glLightModelfv(GL_LIGHT_MODEL_AMBIENT, lmodel_no_ambient);
  119. }
  120. }
  121. static void Init(void)
  122. {
  123. static GLint colorIndexes[3] = {0, 200, 255};
  124. static float ambient[] = {0.1, 0.1, 0.1, 1.0};
  125. static float diffuse[] = {0.5, 1.0, 1.0, 1.0};
  126. static float position[] = {90.0, 90.0, 150.0, 0.0};
  127. static float lmodel_ambient[] = {1.0, 1.0, 1.0, 1.0};
  128. static float lmodel_twoside[] = {GL_TRUE};
  129. static float decal[] = {GL_DECAL};
  130. static float modulate[] = {GL_MODULATE};
  131. static float repeat[] = {GL_REPEAT};
  132. static float nearest[] = {GL_NEAREST};
  133. AUX_RGBImageRec *image;
  134. if (!rgb) {
  135. auxSetGreyRamp();
  136. }
  137. glClearColor(0.0, 0.0, 0.0, 0.0);
  138. glDepthFunc(GL_LEQUAL);
  139. glEnable(GL_DEPTH_TEST);
  140. glLightfv(GL_LIGHT0, GL_AMBIENT, ambient);
  141. glLightfv(GL_LIGHT0, GL_DIFFUSE, diffuse);
  142. glLightfv(GL_LIGHT0, GL_POSITION, position);
  143. glLightModelfv(GL_LIGHT_MODEL_AMBIENT, lmodel_ambient);
  144. glLightModelfv(GL_LIGHT_MODEL_TWO_SIDE, lmodel_twoside);
  145. glEnable(GL_LIGHTING);
  146. glEnable(GL_LIGHT0);
  147. bHiddenLine = FALSE;
  148. SetMaterial( bHiddenLine );
  149. glTexEnvfv(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, decal);
  150. glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, repeat);
  151. glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, repeat);
  152. glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, nearest);
  153. glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, nearest);
  154. if (texFileName) {
  155. image = auxRGBImageLoad(texFileName);
  156. glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
  157. gluBuild2DMipmaps(GL_TEXTURE_2D, 3, image->sizeX, image->sizeY,
  158. GL_RGB, GL_UNSIGNED_BYTE, image->data);
  159. } else {
  160. glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
  161. glTexImage2D(GL_TEXTURE_2D, 0, 4, brickImageWidth, brickImageHeight,
  162. 0, GL_RGBA, GL_UNSIGNED_BYTE, (GLvoid *)brickImage);
  163. }
  164. quadObj = gluNewQuadric();
  165. radius1 = 10;
  166. radius2 = 5;
  167. angle1 = 90;
  168. angle2 = 180;
  169. slices = 16;
  170. stacks = 10;
  171. height = 20;
  172. glCullFace( GL_BACK );
  173. UpdateInfo();
  174. }
  175. static void SetDistance( void )
  176. {
  177. glMatrixMode(GL_PROJECTION);
  178. glLoadIdentity();
  179. glFrustum(-1, 1, -1, 1, 1, 10);
  180. // This defines how far away we're looking from
  181. glTranslated( 0, 0, zTrans );
  182. }
  183. static void CALLBACK Reshape(int width, int height)
  184. {
  185. trackball_Resize( width, height );
  186. glViewport(0, 0, (GLint)width, (GLint)height);
  187. glMatrixMode(GL_PROJECTION);
  188. glLoadIdentity();
  189. glFrustum(-1, 1, -1, 1, 1, 10);
  190. // This defines how far away we're looking from
  191. glTranslated( 0, 0, zTrans );
  192. }
  193. static GLenum Key(int key, GLenum mask)
  194. {
  195. switch (key) {
  196. case TK_ESCAPE:
  197. tkQuit();
  198. case TK_LEFT:
  199. units -= inc;
  200. break;
  201. case TK_RIGHT:
  202. units += inc;
  203. break;
  204. case TK_UP:
  205. factor += inc;
  206. break;
  207. case TK_DOWN:
  208. factor -= inc;
  209. break;
  210. case TK_v:
  211. break;
  212. case TK_X:
  213. break;
  214. case TK_x:
  215. break;
  216. case TK_a:
  217. if (stacks > 1)
  218. stacks--;
  219. break;
  220. case TK_A:
  221. stacks++;
  222. break;
  223. case TK_b:
  224. bHiddenLine = !bHiddenLine;
  225. SetMaterial( bHiddenLine );
  226. break;
  227. case TK_c:
  228. bCullFace = !bCullFace;
  229. if( bCullFace )
  230. glEnable( GL_CULL_FACE );
  231. else
  232. glDisable( GL_CULL_FACE );
  233. break;
  234. case TK_f:
  235. whichQuadric = whichQuadric >= 3 ? 0 : whichQuadric + 1;
  236. break;
  237. case TK_G:
  238. radius1 += 1;
  239. break;
  240. case TK_g:
  241. if (radius1 > 0)
  242. radius1 -= 1;
  243. break;
  244. case TK_H:
  245. height += 2;
  246. break;
  247. case TK_h:
  248. if (height > 0)
  249. height -= 2;
  250. break;
  251. case TK_i:
  252. factor = 0.0f;
  253. units = 0.0f;
  254. break;
  255. case TK_J:
  256. radius2 += 1;
  257. break;
  258. case TK_j:
  259. if (radius2 > 0)
  260. radius2 -= 1;
  261. break;
  262. case TK_K:
  263. angle1 += 5;
  264. break;
  265. case TK_k:
  266. angle1 -= 5;
  267. break;
  268. case TK_L:
  269. angle2 += 5;
  270. break;
  271. case TK_l:
  272. angle2 -= 5;
  273. break;
  274. case TK_M:
  275. break;
  276. case TK_m:
  277. break;
  278. case TK_n:
  279. break;
  280. case TK_N:
  281. break;
  282. case TK_o:
  283. bPolyOffset = !bPolyOffset;
  284. break;
  285. case TK_p:
  286. switch (polyFace) {
  287. case GL_BACK:
  288. polyFace = GL_FRONT;
  289. break;
  290. case GL_FRONT:
  291. polyFace = GL_FRONT_AND_BACK;
  292. break;
  293. case GL_FRONT_AND_BACK:
  294. polyFace = GL_BACK;
  295. break;
  296. }
  297. break;
  298. case TK_s:
  299. if (slices > 3)
  300. slices--;
  301. break;
  302. case TK_S:
  303. slices++;
  304. break;
  305. case TK_t:
  306. texture = !texture;
  307. if (texture) {
  308. gluQuadricTexture(quadObj, GL_TRUE);
  309. glEnable(GL_TEXTURE_2D);
  310. } else {
  311. gluQuadricTexture(quadObj, GL_FALSE);
  312. glDisable(GL_TEXTURE_2D);
  313. }
  314. break;
  315. case TK_z:
  316. zTrans += 0.1f;
  317. SetDistance();
  318. break;
  319. case TK_Z:
  320. zTrans -= 0.1f;
  321. SetDistance();
  322. break;
  323. case TK_0:
  324. shade = !shade;
  325. if (shade) {
  326. glShadeModel(GL_SMOOTH);
  327. gluQuadricNormals(quadObj, GLU_SMOOTH);
  328. } else {
  329. glShadeModel(GL_FLAT);
  330. gluQuadricNormals(quadObj, GLU_FLAT);
  331. }
  332. break;
  333. case TK_1:
  334. polygonMode = GL_FILL;
  335. break;
  336. case TK_2:
  337. polygonMode = GL_LINE;
  338. break;
  339. case TK_3:
  340. polygonMode = GL_POINT;
  341. break;
  342. case TK_4:
  343. break;
  344. default:
  345. return GL_FALSE;
  346. }
  347. UpdateInfo();
  348. return GL_TRUE;
  349. }
  350. static void DrawRect( void )
  351. {
  352. glBegin( GL_QUADS );
  353. glVertex2f( 1.0f, 1.0f );
  354. glVertex2f( -1.0f, 1.0f );
  355. glVertex2f( -1.0f, -1.0f );
  356. glVertex2f( 1.0f, -1.0f );
  357. glEnd();
  358. }
  359. static void DrawTri( void )
  360. {
  361. glBegin( GL_TRIANGLES );
  362. glVertex2f( 1.0f, 1.0f );
  363. glVertex2f( -1.0f, 1.0f );
  364. glVertex2f( -1.0f, -1.0f );
  365. glEnd();
  366. }
  367. static void DrawObject( void )
  368. {
  369. #if 1
  370. switch (whichQuadric) {
  371. case 0:
  372. gluCylinder(quadObj, radius1/10.0, radius2/10.0, height/10.0,
  373. slices, stacks);
  374. break;
  375. case 1:
  376. gluSphere(quadObj, radius1/10.0, slices, stacks);
  377. break;
  378. case 2:
  379. gluPartialDisk(quadObj, radius2/10.0, radius1/10.0, slices,
  380. stacks, angle1, angle2);
  381. break;
  382. case 3:
  383. gluDisk(quadObj, radius2/10.0, radius1/10.0, slices, stacks);
  384. break;
  385. }
  386. #else
  387. // simple debugging ojbects
  388. //mf: ? these aren't centered when rotating
  389. #if 0
  390. DrawRect();
  391. #else
  392. DrawTri();
  393. #endif
  394. #endif
  395. }
  396. static void CALLBACK Draw( void )
  397. {
  398. float matRot[4][4];
  399. glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT);
  400. glMatrixMode( GL_MODELVIEW );
  401. glLoadIdentity();
  402. trackball_CalcRotMatrix( matRot );
  403. glMultMatrixf( &(matRot[0][0]) );
  404. #if 0
  405. glColor3f(1.0, 1.0, 1.0);
  406. #endif
  407. if( whichQuadric == 0 ) // cylinder
  408. glTranslatef(0, 0, -height/20.0);
  409. // Draw object normally
  410. DrawObject();
  411. // Draw object again with polygon offset
  412. // Set polygon mode for offset faces
  413. glPolygonMode( GL_FRONT_AND_BACK, polygonMode );
  414. if( bPolyOffset ) {
  415. switch( polygonMode ) {
  416. case GL_FILL:
  417. glEnable( GL_POLYGON_OFFSET_FILL );
  418. break;
  419. case GL_LINE:
  420. glEnable( GL_POLYGON_OFFSET_LINE );
  421. break;
  422. case GL_POINT:
  423. glEnable( GL_POLYGON_OFFSET_POINT );
  424. break;
  425. }
  426. }
  427. glPolygonOffset( factor, units );
  428. glColor3f(1.0, 0.0, 0.0);
  429. glDisable( GL_LIGHTING );
  430. DrawObject();
  431. glEnable( GL_LIGHTING );
  432. // restore modes
  433. glPolygonMode( GL_FRONT_AND_BACK, GL_FILL );
  434. if( bPolyOffset ) {
  435. glDisable( GL_POLYGON_OFFSET_FILL );
  436. glDisable( GL_POLYGON_OFFSET_LINE );
  437. glDisable( GL_POLYGON_OFFSET_POINT );
  438. }
  439. glFlush();
  440. if (doubleBuffer) {
  441. tkSwapBuffers();
  442. }
  443. }
  444. static unsigned long Args(int argc, char **argv)
  445. {
  446. GLint i;
  447. rgb = GL_TRUE;
  448. doubleBuffer = GL_TRUE;
  449. for (i = 1; i < argc; i++) {
  450. if (strcmp(argv[i], "-ci") == 0) {
  451. rgb = GL_FALSE;
  452. } else if (strcmp(argv[i], "-rgb") == 0) {
  453. rgb = GL_TRUE;
  454. } else if (strcmp(argv[i], "-sb") == 0) {
  455. doubleBuffer = GL_FALSE;
  456. } else if (strcmp(argv[i], "-db") == 0) {
  457. doubleBuffer = GL_TRUE;
  458. } else if (strcmp(argv[i], "-f") == 0) {
  459. if (i+1 >= argc || argv[i+1][0] == '-') {
  460. //printf("-f (No file name).\n");
  461. return GL_FALSE;
  462. } else {
  463. texFileName = argv[++i];
  464. }
  465. } else {
  466. //printf("%s (Bad option).\n", argv[i]);
  467. return GL_FALSE;
  468. }
  469. }
  470. return GL_TRUE;
  471. }
  472. void main(int argc, char **argv)
  473. {
  474. GLenum type;
  475. if (Args(argc, argv) == GL_FALSE) {
  476. auxQuit();
  477. }
  478. tkInitPosition(0, 0, wWidth, wHeight);
  479. #if 0
  480. type = TK_DEPTH24;
  481. #else
  482. type = TK_DEPTH16;
  483. #endif
  484. type |= (rgb) ? TK_RGB : TK_INDEX;
  485. type |= (doubleBuffer) ? TK_DOUBLE : TK_SINGLE;
  486. tkInitDisplayMode(type);
  487. if (tkInitWindow("Quad Test") == GL_FALSE) {
  488. tkQuit();
  489. }
  490. Init();
  491. tkExposeFunc(Reshape);
  492. tkReshapeFunc(Reshape);
  493. tkKeyDownFunc( Key );
  494. tkMouseDownFunc( trackball_MouseDown );
  495. tkMouseUpFunc( trackball_MouseUp );
  496. trackball_Init( wWidth, wHeight );
  497. tkIdleFunc( Draw );
  498. tkDisplayFunc( 0 );
  499. tkExec();
  500. }