MyGrid.cpp
上传用户:sz25923981
上传日期:2022-06-28
资源大小:3615k
文件大小:5k
源码类别:

OpenGL

开发平台:

Visual C++

  1. // MyGrid.cpp: implementation of the CMyGrid class.
  2. //
  3. //////////////////////////////////////////////////////////////////////
  4. #include "stdafx.h"
  5. #include "MyTerrain1.h"
  6. #include "MyGrid.h"
  7. #ifdef _DEBUG
  8. #undef THIS_FILE
  9. static char THIS_FILE[]=__FILE__;
  10. #define new DEBUG_NEW
  11. #endif
  12. //////////////////////////////////////////////////////////////////////
  13. // Construction/Destruction
  14. //////////////////////////////////////////////////////////////////////
  15. struct cvPoint
  16. {
  17. float x, y, z; //点的坐标
  18. };
  19. //矢量相乘 C = A x B 
  20. void vect_mult(struct cvPoint *A, struct cvPoint *B, struct cvPoint *C)
  21. {
  22. C->x = A->y*B->z - A->z*B->y;
  23. C->y = A->z*B->x - A->x*B->z;
  24. C->z = A->x*B->y - A->y*B->x;
  25. }
  26. // Catmull-Rom Curve calculations
  27. void cvCatmullRom(struct cvPoint *p, float t, struct cvPoint *outp)
  28. {
  29. float t2, t3, t1;
  30. t2 = t*t;
  31. t3 = t*t*t;
  32. t1 = (1-t)*(1-t);
  33. outp->x = (-t*t1*p[0].x + (2-5*t2+3*t3)*p[1].x + t*(1+4*t-3*t2)*p[2].x - t2*(1-t)*p[3].x)/2;
  34. outp->y = (-t*t1*p[0].y + (2-5*t2+3*t3)*p[1].y + t*(1+4*t-3*t2)*p[2].y - t2*(1-t)*p[3].y)/2;
  35. outp->z = (-t*t1*p[0].z + (2-5*t2+3*t3)*p[1].z + t*(1+4*t-3*t2)*p[2].z - t2*(1-t)*p[3].z)/2;
  36. }
  37. CMyGrid::CMyGrid()
  38. {
  39. grid = NULL;
  40. m_width = 0;
  41. m_height = 0;
  42. SetCellLength(1.0);
  43. SetHeight(0, 2);
  44. SetInterpolationLevel(20);
  45. SetDimensions(10, 10);
  46. }
  47. //带参数的构造函数
  48. CMyGrid::CMyGrid(int width, int height)
  49. {
  50. grid = NULL;
  51. m_width = 0;
  52. m_height = 0;
  53. SetCellLength(1.0);
  54. SetDimensions(width, height);
  55. SetHeight(0, 2);
  56. SetInterpolationLevel(20);
  57. }
  58. CMyGrid::~CMyGrid()
  59. {
  60. if (grid) delete [] grid;
  61. }
  62. // 设置地形的大小
  63. void CMyGrid::SetDimensions(int width, int height)
  64. {
  65. if (grid) delete [] grid;
  66. grid = new float [height*width];
  67. for (int i=0; i<(height*width); i++) grid[i] = 0;
  68. m_width = width;
  69. m_height = height;
  70. }
  71. // 网格的边长
  72. void CMyGrid::SetCellLength(float l)
  73. {
  74. m_cell = l;
  75. }
  76. // 设置地形最小和最大高度
  77. void CMyGrid::SetHeight(float min, float max)
  78. {
  79. m_min = min;
  80. m_max = max;
  81. }
  82. // 曲线内的插值阶数(曲线内点的个数)
  83. void CMyGrid::SetInterpolationLevel(int level)
  84. {
  85. m_interpol_level = level;
  86. }
  87. // 网格的生成
  88. void CMyGrid::GenerateNewGrid()
  89. {
  90. srand((unsigned int)time(NULL));
  91. for (int i=0; i<m_height; i++)
  92. for (int j=0; j<m_width; j++)
  93. {
  94. float a = m_min+(m_max-m_min)*(float)(rand() % 10000)/10000;
  95. grid[i*m_width+j] = a;
  96. }
  97. }
  98. // 绘制网格地形
  99. void CMyGrid::Draw()
  100. {
  101. glCallList(1);
  102. }
  103. // 生成网格列表
  104. void CMyGrid::Compile()
  105. {
  106. cvPoint pa[4];
  107. cvPoint op[4];
  108. cvPoint outp, a, b, c;
  109. float t_int_x=0, t_int_y=0, int_const;
  110. int flag;
  111. cvPoint *temp;
  112. int_const = 1.0f/m_interpol_level;
  113. temp = new cvPoint [m_interpol_level+1];
  114. glNewList(1, GL_COMPILE);
  115. glBegin(GL_TRIANGLES);
  116. for (int i=0; i<m_height-3; i++)
  117. {
  118. flag = 0;
  119. for (int j=0; j<m_width-3; j++)
  120. {
  121. t_int_x = 0;
  122. for (int m=0; m<m_interpol_level; m++)
  123. {
  124. for (int l=0; l<4; l++)
  125. {
  126. for (int k=0; k<4; k++)
  127. {
  128. pa[k].x = m_cell*(j+k);
  129. pa[k].y = m_cell*(i+l);
  130. pa[k].z = grid[(i+l)*m_width+(j+k)];
  131. }
  132. cvCatmullRom(pa, t_int_x, &op[l]);
  133. }
  134. t_int_y = 0;
  135. for (l=0; l<(m_interpol_level+1); l++)
  136. {
  137. cvCatmullRom(op, t_int_y, &outp);
  138. if (!flag) temp[l] = outp;
  139. else
  140. {
  141. if (l < (m_interpol_level))
  142. {
  143. // 计算矢量A
  144. a.x = temp[l+1].x - outp.x;
  145. a.y = temp[l+1].y - outp.y;
  146. a.z = temp[l+1].z - outp.z;
  147. // 计算矢量B
  148. b.x = temp[l].x - outp.x;
  149. b.y = temp[l].y - outp.y;
  150. b.z = temp[l].z - outp.z;
  151. // 计算矢量C = AxB
  152. vect_mult(&a, &b, &c);
  153. glNormal3f(c.x, c.y, c.z);
  154. glTexCoord2f(t_int_x, t_int_y);
  155. glVertex3f(outp.x, outp.y, outp.z);
  156. glTexCoord2f(t_int_x-int_const, t_int_y+int_const);
  157. glVertex3f(temp[l+1].x, temp[l+1].y, temp[l+1].z);
  158. glTexCoord2f(t_int_x-int_const, t_int_y);
  159. glVertex3f(temp[l].x, temp[l].y, temp[l].z);
  160. }
  161. if (l > 0)
  162. {
  163. // 计算矢量A
  164. a.x = temp[l].x - outp.x;
  165. a.y = temp[l].y - outp.y;
  166. a.z = temp[l].z - outp.z;
  167. // 计算矢量B
  168. b.x = temp[l-1].x - outp.x;
  169. b.y = temp[l-1].y - outp.y;
  170. b.z = temp[l-1].z - outp.z;
  171. // 计算矢量C = AxB
  172. vect_mult(&a, &b, &c);
  173. glNormal3f(c.x, c.y, c.z);
  174. glTexCoord2f(t_int_x, t_int_y);
  175. glVertex3f(outp.x, outp.y, outp.z);
  176. glTexCoord2f(t_int_x-int_const, t_int_y);
  177. glVertex3f(temp[l].x, temp[l].y, temp[l].z);
  178. glTexCoord2f(t_int_x-int_const, t_int_y-int_const);
  179. glVertex3f(temp[l-1].x, temp[l-1].y, temp[l-1].z);
  180. }
  181. temp[l] = outp;
  182. }
  183. t_int_y += int_const;
  184. }
  185. flag = 1;
  186. t_int_x += int_const;
  187. }
  188. }
  189. }
  190. glEnd();
  191. delete [] temp;
  192. glEndList();
  193. }