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.

254 lines
6.8 KiB

  1. /******************************Module*Header*******************************\
  2. * Module Name: genstrip.c
  3. *
  4. * The Ribbon and 2 Ribbon styles of the 3D Flying Objects screen saver.
  5. *
  6. * Animation of 1 or 2 quad strips floating about.
  7. *
  8. * Copyright (c) 1994 Microsoft Corporation
  9. *
  10. \**************************************************************************/
  11. #include <windows.h>
  12. #include <GL\gl.h>
  13. #include <string.h>
  14. #include <math.h>
  15. #include "ss3dfo.h"
  16. #include "mesh.h"
  17. static MESH stripMesh;
  18. static int iPrec = 40;
  19. void genStrip()
  20. {
  21. static int counter = 0;
  22. int i;
  23. int facecount;
  24. // Use Hermite basis, pg 488, FVD
  25. static float M[4][4] = {{2.0f, -2.0f, 1.0f, 1.0f},
  26. {-3.0f, 3.0f, -2.0f, -1.0f},
  27. {0.0f, 0.0f, 1.0f, 0.0f},
  28. {1.0f, 0.0f, 0.0f, 0.0f}};
  29. float xx[4], yy[4], zz[4];
  30. float cx[4], cy[4], cz[4];
  31. float d = 1.0f / (float) iPrec;
  32. float t = 0.0f;
  33. float t2, t3;
  34. POINT3D p1 = {-0.5f, 0.0f, 0.0f};
  35. POINT3D p2 = {0.5f, 0.0f, 0.0f};
  36. POINT3D v1 = {1.5f, 1.5f, 0.0f};
  37. POINT3D v2 = {0.0f, 3.0f, 0.0f};
  38. POINT3D norm;
  39. float sinVal;
  40. float angle;
  41. float angleStep = (float) (PI / iPrec);
  42. static float rotA = 0.0f;
  43. static float rotB = (float) (PI / 2.0);
  44. static float sideSin = 0.0f;
  45. float rotStepA = (float) (PI / (2.0 * iPrec));
  46. float rotStepB = (float) (PI / (4.0 * iPrec));
  47. MESH *mesh = &stripMesh;
  48. #define NORMS(x, y) stripMesh.norms[((x) * iPrec) + y]
  49. #define GRID(x, y) stripMesh.pts[((x) * iPrec) + y]
  50. v1.x = (float) (4.0 * cos(rotA));
  51. v1.y = (float) (4.0 * sin(rotA));
  52. p2.x = (float) (0.5 * sin(rotB));
  53. // p2.y = (float) (0.5 * sin(rotB));
  54. rotA += rotStepA;
  55. rotB += rotStepB;
  56. counter++;
  57. if (counter >= (2 * iPrec)) {
  58. rotStepA = -rotStepA;
  59. counter = 0;
  60. }
  61. angle = sideSin;
  62. sideSin += (float) (PI / 80.0);
  63. xx[0] = p1.x;
  64. xx[1] = p2.x;
  65. xx[2] = v1.x;
  66. xx[3] = v2.x;
  67. yy[0] = p1.y;
  68. yy[1] = p2.y;
  69. yy[2] = v1.y;
  70. yy[3] = v2.y;
  71. zz[0] = p1.z;
  72. zz[1] = p2.z;
  73. zz[2] = v1.z;
  74. zz[3] = v2.z;
  75. for (i = 0; i < 4; i++) {
  76. cx[i] = xx[0] * M[i][0] + xx[1] * M[i][1] +
  77. xx[2] * M[i][2] + xx[3] * M[i][3];
  78. cy[i] = yy[0] * M[i][0] + yy[1] * M[i][1] +
  79. yy[2] * M[i][2] + yy[3] * M[i][3];
  80. cz[i] = zz[0] * M[i][0] + zz[1] * M[i][1] +
  81. zz[2] * M[i][2] + zz[3] * M[i][3];
  82. }
  83. for (i = 0; i < iPrec; i++) {
  84. float x, y;
  85. t += d;
  86. t2 = t * t;
  87. t3 = t2 * t;
  88. x = cx[0] * t3 + cx[1] * t2 + cx[2] * t + cx[3];
  89. y = cy[0] * t3 + cy[1] * t2 + cy[2] * t + cy[3];
  90. sinVal = (float) (sin(angle) / 5.0);
  91. if (sinVal < 0.0)
  92. sinVal = -sinVal;
  93. angle += angleStep;
  94. GRID(0, i).x = x;
  95. GRID(0, i).z = y;
  96. GRID(0, i).y = 0.25f; // extrusion // + sinVal;
  97. GRID(1, i).x = x;
  98. GRID(1, i).z = y;
  99. GRID(1, i).y = -0.25f; // - sinVal;
  100. }
  101. stripMesh.numFaces = 0;
  102. for (i = 0; i < 2 * iPrec; i++)
  103. mesh->norms[i] = ss_ptZero;
  104. for (facecount = 0, i = 0; i < (iPrec - 1); i++) {
  105. ss_calcNorm(&norm, &GRID(0, i + 1), &GRID(0, i), &GRID(1, i));
  106. stripMesh.faces[facecount].material = 0;
  107. stripMesh.faces[facecount].norm = norm;
  108. NORMS(0, i).x += norm.x;
  109. NORMS(0, i).y += norm.y;
  110. NORMS(0, i).z += norm.z;
  111. NORMS(1, i).x += norm.x;
  112. NORMS(1, i).y += norm.y;
  113. NORMS(1, i).z += norm.z;
  114. if (i != (iPrec - 1)) {
  115. NORMS(0, i+1).x += norm.x;
  116. NORMS(0, i+1).y += norm.y;
  117. NORMS(0, i+1).z += norm.z;
  118. NORMS(1, i+1).x += norm.x;
  119. NORMS(1, i+1).y += norm.y;
  120. NORMS(1, i+1).z += norm.z;
  121. }
  122. stripMesh.faces[facecount].p[0] = i;
  123. stripMesh.faces[facecount].p[1] = iPrec + i;
  124. stripMesh.faces[facecount].p[2] = i + 1;
  125. stripMesh.faces[facecount].p[3] = iPrec + i + 1;
  126. stripMesh.numFaces++;
  127. facecount++;
  128. }
  129. stripMesh.numPoints = 2 * iPrec;
  130. ss_normalizeNorms(stripMesh.norms, stripMesh.numPoints);
  131. }
  132. void initStripScene()
  133. {
  134. iPrec = (int)(fTesselFact * 40.5);
  135. if (iPrec < 4)
  136. iPrec = 4;
  137. newMesh(&stripMesh, iPrec, 2 * iPrec);
  138. glMatrixMode(GL_PROJECTION);
  139. glLoadIdentity();
  140. glOrtho(-1.1, 1.1, -1.1, 1.1, 0.0, 3.0);
  141. glTranslatef(0.0f, 0.0f, -1.5f);
  142. glRotatef(50.0f, 1.0f, 0.0f, 0.0f);
  143. glRotatef(50.0f, 0.0f, 1.0f, 0.0f);
  144. glRotatef(12.0f, 0.0f, 0.0f, 1.0f);
  145. glMatrixMode(GL_MODELVIEW);
  146. }
  147. void delStripScene()
  148. {
  149. delMesh(&stripMesh);
  150. }
  151. void updateStripScene(int flags)
  152. {
  153. static double mxrot = 0.0;
  154. static double myrot = 0.0;
  155. static double mzrot = 0.0;
  156. static double mxrotInc = 0.0;
  157. static double myrotInc = 0.1;
  158. static double mzrotInc = 0.0;
  159. static int h = 0;
  160. RGBA color;
  161. if( gbBounce ) {
  162. // floating window bounced off an edge
  163. if (mxrotInc) {
  164. mxrotInc = 0.0;
  165. myrotInc = 0.1;
  166. } else if (myrotInc) {
  167. myrotInc = 0.0;
  168. mzrotInc = 0.1;
  169. } else if (mzrotInc) {
  170. mzrotInc = 0.0;
  171. mxrotInc = 0.1;
  172. }
  173. gbBounce = FALSE;
  174. }
  175. glLoadIdentity();
  176. glRotatef((GLfloat) (mxrot * (180.0 / PI)), 1.0f, 0.0f, 0.0f);
  177. glRotatef((GLfloat) (myrot * (180.0 / PI)), 0.0f, 1.0f, 0.0f);
  178. glRotatef((GLfloat) (mzrot * (180.0 / PI)), 0.0f, 0.0f, 1.0f);
  179. genStrip();
  180. if (bColorCycle) {
  181. ss_HsvToRgb((float)h, 1.0f, 1.0f, &color );
  182. glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE,
  183. (GLfloat *) &color);
  184. h++;
  185. h %= 360;
  186. } else {
  187. glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE,
  188. (GLfloat *) &Material[1].kd);
  189. }
  190. updateObject(&stripMesh, bSmoothShading);
  191. if (flags & 0x4) {
  192. glLoadIdentity();
  193. glTranslatef(0.05f, 0.0f, 0.0f);
  194. glRotatef((GLfloat) (myrot * (180.0 / PI)), 1.0f, 0.0f, 0.0f);
  195. glRotatef((GLfloat) (mxrot * (180.0 / PI)), 0.0f, 1.0f, 0.0f);
  196. glRotatef((GLfloat) (mzrot * (180.0 / PI)), 0.0f, 0.0f, 1.0f);
  197. if (bColorCycle) {
  198. color.r = 1.0f - color.r;
  199. color.g = 1.0f - color.g;
  200. color.b = 1.0f - color.b;
  201. glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE,
  202. (GLfloat *) &color);
  203. } else {
  204. glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE,
  205. (GLfloat *) &Material[2].kd);
  206. }
  207. updateObject(&stripMesh, bSmoothShading);
  208. }
  209. mxrot += mxrotInc;
  210. myrot += myrotInc;
  211. mzrot += mzrotInc;
  212. }