main.cc 6.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243
  1. #include "Angel.h"
  2. #include <fstream>
  3. #include <iostream>
  4. #include <vector>
  5. const int NumTriangles = 64770; // (6 faces)(2 triangles/face)
  6. const int NumVertices = 3 * NumTriangles;
  7. const int TextureWidth = 256;
  8. const int TextureHeight = 128;
  9. typedef Angel::vec4 point4;
  10. typedef Angel::vec4 color4;
  11. // Texture objects and storage for texture image
  12. GLuint textures[1];
  13. GLubyte image[TextureWidth][TextureHeight][3];
  14. // Vertex data arrays
  15. point4 points[NumVertices];
  16. vec2 tex_coords[NumVertices];
  17. // Array of rotation angles (in degrees) for each coordinate axis
  18. enum { Xaxis = 0, Yaxis = 1, Zaxis = 2, NumAxes = 3 };
  19. int Axis = Xaxis;
  20. GLfloat Theta[NumAxes] = {0.0, 0.0, 0.0};
  21. GLuint theta;
  22. //----------------------------------------------------------------------------
  23. void load_model(const std::string &file_name) {
  24. std::vector<point4> vertices;
  25. std::vector<vec2> tex_cods;
  26. std::fstream s(file_name, std::fstream::in);
  27. if (!s.is_open()) {
  28. std::cerr << "failed to open" << file_name << std::endl;
  29. } else {
  30. int index = 0;
  31. std::string t;
  32. float x, y, z;
  33. int a, b, c;
  34. int num = 0;
  35. while (s >> t) {
  36. if (t == "v") { // vertices
  37. s >> x >> y >> z;
  38. vertices.emplace_back(x / 50.0f, z / 50.0f, y / 50.0f, 1.0);
  39. } else if (t == "vt") {
  40. s >> x >> y;
  41. tex_cods.emplace_back(x, y);
  42. } else if (t == "f") {
  43. s >> a >> b >> c;
  44. a--;
  45. b--;
  46. c--;
  47. points[index] = vertices[a];
  48. tex_coords[index] = tex_cods[a];
  49. index++;
  50. points[index] = vertices[b];
  51. tex_coords[index] = tex_cods[b];
  52. index++;
  53. points[index] = vertices[c];
  54. tex_coords[index] = tex_cods[c];
  55. index++;
  56. num++;
  57. }
  58. }
  59. std::cout << "There are " << vertices.size() << "vertice(s)"
  60. << ", " << tex_cods.size() << "tex cor(s)" << std::endl
  61. << "There are " << num << "fragment(s)" << std::endl;
  62. s.close();
  63. }
  64. }
  65. //----------------------------------------------------------------------------
  66. void load_tex(const std::string &file_name) {
  67. char cline[1024];
  68. char p6[10];
  69. int width;
  70. int height;
  71. int depth;
  72. FILE *fp = fopen(file_name.data(), "rb");
  73. fgets(cline, sizeof(cline), fp);
  74. sscanf(cline, "%s %d %d %d", p6, &width, &height, &depth);
  75. std::cout << p6 << "," << width << "," << height << "," << depth << std::endl;
  76. fread(image, sizeof(GLubyte), width * height * 3, fp);
  77. fclose(fp);
  78. }
  79. void init() {
  80. load_tex("gc_tex.ppm");
  81. load_model("gc_tex.obj");
  82. // Initialize texture objects
  83. glGenTextures(1, textures);
  84. glBindTexture(GL_TEXTURE_2D, textures[0]);
  85. glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, TextureWidth, TextureHeight, 0, GL_RGB,
  86. GL_UNSIGNED_BYTE, image);
  87. glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
  88. glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
  89. glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
  90. glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
  91. glActiveTexture(GL_TEXTURE0);
  92. glBindTexture(GL_TEXTURE_2D, textures[0]);
  93. // Create a vertex array object
  94. GLuint vao;
  95. glGenVertexArrays(1, &vao);
  96. glBindVertexArray(vao);
  97. // Create and initialize a buffer object
  98. GLuint buffer;
  99. glGenBuffers(1, &buffer);
  100. glBindBuffer(GL_ARRAY_BUFFER, buffer);
  101. glBufferData(GL_ARRAY_BUFFER, sizeof(points) + sizeof(tex_coords), NULL,
  102. GL_STATIC_DRAW);
  103. // Specify an offset to keep track of where we're placing data in our
  104. // vertex array buffer. We'll use the same technique when we
  105. // associate the offsets with vertex attribute pointers.
  106. GLintptr offset = 0;
  107. glBufferSubData(GL_ARRAY_BUFFER, offset, sizeof(points), points);
  108. offset += sizeof(points);
  109. glBufferSubData(GL_ARRAY_BUFFER, offset, sizeof(tex_coords), tex_coords);
  110. // Load shaders and use the resulting shader program
  111. GLuint program = InitShader("vshader71.glsl", "fshader71.glsl");
  112. glUseProgram(program);
  113. // set up vertex arrays
  114. offset = 0;
  115. GLuint vPosition = glGetAttribLocation(program, "vPosition");
  116. glEnableVertexAttribArray(vPosition);
  117. glVertexAttribPointer(vPosition, 4, GL_FLOAT, GL_FALSE, 0,
  118. BUFFER_OFFSET(offset));
  119. offset += sizeof(points);
  120. GLuint vTexCoord = glGetAttribLocation(program, "vTexCoord");
  121. glEnableVertexAttribArray(vTexCoord);
  122. glVertexAttribPointer(vTexCoord, 2, GL_FLOAT, GL_FALSE, 0,
  123. BUFFER_OFFSET(offset));
  124. // Set the value of the fragment shader texture sampler variable
  125. // ("texture") to the the appropriate texture unit. In this case,
  126. // zero, for GL_TEXTURE0 which was previously set by calling
  127. // glActiveTexture().
  128. glUniform1i(glGetUniformLocation(program, "tex"), 0);
  129. theta = glGetUniformLocation(program, "theta");
  130. glEnable(GL_DEPTH_TEST);
  131. glClearColor(1.0, 1.0, 1.0, 1.0);
  132. }
  133. void display(void) {
  134. glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
  135. glUniform3fv(theta, 1, Theta);
  136. glDrawArrays(GL_TRIANGLES, 0, NumVertices);
  137. glutSwapBuffers();
  138. }
  139. //----------------------------------------------------------------------------
  140. void mouse(int button, int state, int x, int y) {
  141. if (state == GLUT_DOWN) {
  142. switch (button) {
  143. case GLUT_LEFT_BUTTON:
  144. Axis = Xaxis;
  145. break;
  146. case GLUT_MIDDLE_BUTTON:
  147. Axis = Yaxis;
  148. break;
  149. case GLUT_RIGHT_BUTTON:
  150. Axis = Zaxis;
  151. break;
  152. }
  153. }
  154. }
  155. //----------------------------------------------------------------------------
  156. void idle(void) {
  157. Theta[Axis] += 0.5;
  158. if (Theta[Axis] > 360.0) {
  159. Theta[Axis] -= 360.0;
  160. }
  161. glutPostRedisplay();
  162. }
  163. //----------------------------------------------------------------------------
  164. void keyboard(unsigned char key, int mousex, int mousey) {
  165. switch (key) {
  166. case 033: // Escape Key
  167. case 'q':
  168. case 'Q':
  169. exit(EXIT_SUCCESS);
  170. break;
  171. case 'b':
  172. case 'B':
  173. glutIdleFunc(idle);
  174. break;
  175. case 'e':
  176. case 'E':
  177. glutIdleFunc(NULL);
  178. break;
  179. }
  180. glutPostRedisplay();
  181. }
  182. //----------------------------------------------------------------------------
  183. int main(int argc, char **argv) {
  184. glutInit(&argc, argv);
  185. glutInitDisplayMode(GLUT_RGBA | GLUT_DOUBLE | GLUT_DEPTH);
  186. glutInitWindowSize(512, 512);
  187. glutInitContextVersion(3, 1);
  188. glutInitContextProfile(GLUT_CORE_PROFILE);
  189. glutCreateWindow("flying");
  190. if (glewInit() != GLEW_OK) {
  191. std::cerr << "Failed to initialize GLEW ... exiting" << std::endl;
  192. exit(EXIT_FAILURE);
  193. }
  194. init();
  195. glutDisplayFunc(display);
  196. glutKeyboardFunc(keyboard);
  197. glutMouseFunc(mouse);
  198. glutIdleFunc(idle);
  199. glutMainLoop();
  200. return 0;
  201. }