OGLES2HelloTriangle_Qt.cpp 8.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258
  1. /******************************************************************************
  2. @File OGLES2HelloTriangle_Qt.cpp
  3. @Title OpenGL ES 2.0 Hello Triangle Tutorial
  4. @Version
  5. @Copyright Copyright (C) Imagination Technologies Limited.
  6. @Platform .
  7. @Description Basic Tutorial that shows step-by-step how to initialize OpenGL ES
  8. 2.0, use it for drawing a triangle and terminate it.
  9. ******************************************************************************/
  10. #include <stdio.h>
  11. #include "QApplication"
  12. #include "QMainWindow"
  13. #include "QDesktopWidget"
  14. #include "OGLES2HelloTriangle.h"
  15. /******************************************************************************
  16. Defines
  17. ******************************************************************************/
  18. // Index to bind the attributes to vertex shaders
  19. #define VERTEX_ARRAY 0
  20. COGLES2HelloTriangle::COGLES2HelloTriangle(QWidget *parent) : QGLWidget(parent),
  21. m_ui32Frame(0)
  22. {
  23. setAttribute(Qt::WA_PaintOnScreen);
  24. setAttribute(Qt::WA_NoSystemBackground);
  25. }
  26. COGLES2HelloTriangle::~COGLES2HelloTriangle()
  27. {
  28. }
  29. void COGLES2HelloTriangle::initializeGL()
  30. {
  31. // Fragment and vertex shaders code
  32. const char* pszFragShader = "\
  33. void main (void)\
  34. {\
  35. gl_FragColor = vec4(1.0, 1.0, 0.66 ,1.0);\
  36. }";
  37. const char* pszVertShader = "\
  38. attribute highp vec4 myVertex;\
  39. uniform mediump mat4 myPMVMatrix;\
  40. void main(void)\
  41. {\
  42. gl_Position = myPMVMatrix * myVertex;\
  43. }";
  44. // Create the fragment shader object
  45. m_uiFragShader = glCreateShader(GL_FRAGMENT_SHADER);
  46. // Load the source code into it
  47. glShaderSource(m_uiFragShader, 1, (const char**)&pszFragShader, NULL);
  48. // Compile the source code
  49. glCompileShader(m_uiFragShader);
  50. // Check if compilation succeeded
  51. GLint bShaderCompiled;
  52. glGetShaderiv(m_uiFragShader, GL_COMPILE_STATUS, &bShaderCompiled);
  53. if(!bShaderCompiled)
  54. {
  55. // An error happened, first retrieve the length of the log message
  56. int i32InfoLogLength, i32CharsWritten;
  57. glGetShaderiv(m_uiFragShader, GL_INFO_LOG_LENGTH, &i32InfoLogLength);
  58. // Allocate enough space for the message and retrieve it
  59. char* pszInfoLog = new char[i32InfoLogLength];
  60. glGetShaderInfoLog(m_uiFragShader, i32InfoLogLength, &i32CharsWritten, pszInfoLog);
  61. // Displays the error
  62. printf("Failed to compile fragment shader: %s\n", pszInfoLog);
  63. delete [] pszInfoLog;
  64. exit(0);
  65. }
  66. // Loads the vertex shader in the same way
  67. m_uiVertShader = glCreateShader(GL_VERTEX_SHADER);
  68. glShaderSource(m_uiVertShader, 1, (const char**)&pszVertShader, NULL);
  69. glCompileShader(m_uiVertShader);
  70. glGetShaderiv(m_uiVertShader, GL_COMPILE_STATUS, &bShaderCompiled);
  71. if(!bShaderCompiled)
  72. {
  73. int i32InfoLogLength, i32CharsWritten;
  74. glGetShaderiv(m_uiVertShader, GL_INFO_LOG_LENGTH, &i32InfoLogLength);
  75. char* pszInfoLog = new char[i32InfoLogLength];
  76. glGetShaderInfoLog(m_uiVertShader, i32InfoLogLength, &i32CharsWritten, pszInfoLog);
  77. printf("Failed to compile vertex shader: %s\n", pszInfoLog);
  78. delete [] pszInfoLog;
  79. exit(0);
  80. }
  81. // Create the shader program
  82. m_uiProgramObject = glCreateProgram();
  83. // Attach the fragment and vertex shaders to it
  84. glAttachShader(m_uiProgramObject, m_uiFragShader);
  85. glAttachShader(m_uiProgramObject, m_uiVertShader);
  86. // Bind the custom vertex attribute "myVertex" to location VERTEX_ARRAY
  87. glBindAttribLocation(m_uiProgramObject, VERTEX_ARRAY, "myVertex");
  88. // Link the program
  89. glLinkProgram(m_uiProgramObject);
  90. // Check if linking succeeded in the same way we checked for compilation success
  91. GLint bLinked;
  92. glGetProgramiv(m_uiProgramObject, GL_LINK_STATUS, &bLinked);
  93. if(!bLinked)
  94. {
  95. int ui32InfoLogLength, ui32CharsWritten;
  96. glGetProgramiv(m_uiProgramObject, GL_INFO_LOG_LENGTH, &ui32InfoLogLength);
  97. char* pszInfoLog = new char[ui32InfoLogLength];
  98. glGetProgramInfoLog(m_uiProgramObject, ui32InfoLogLength, &ui32CharsWritten, pszInfoLog);
  99. printf("Failed to link program: %s\n", pszInfoLog);
  100. delete [] pszInfoLog;
  101. exit(0);
  102. }
  103. // Actually use the created program
  104. glUseProgram(m_uiProgramObject);
  105. // Sets the clear color.
  106. // The colours are passed per channel (red,green,blue,alpha) as float values from 0.0 to 1.0
  107. glClearColor(0.6f, 0.8f, 1.0f, 1.0f); // clear blue
  108. // We're going to draw a triangle to the screen so create a vertex buffer object for our triangle
  109. // Interleaved vertex data
  110. GLfloat afVertices[] = { -0.4f,-0.4f,0.0f, // Position
  111. 0.4f ,-0.4f,0.0f,
  112. 0.0f ,0.4f ,0.0f};
  113. // Generate the vertex buffer object (VBO)
  114. glGenBuffers(1, &m_ui32Vbo);
  115. // Bind the VBO so we can fill it with data
  116. glBindBuffer(GL_ARRAY_BUFFER, m_ui32Vbo);
  117. // Set the buffer's data
  118. unsigned int uiSize = 3 * (sizeof(GLfloat) * 3); // Calc afVertices size (3 vertices * stride (3 GLfloats per vertex))
  119. glBufferData(GL_ARRAY_BUFFER, uiSize, afVertices, GL_STATIC_DRAW);
  120. }
  121. void COGLES2HelloTriangle::resizeGL(int w, int h)
  122. {
  123. glViewport(0, 0, w, h);
  124. }
  125. void COGLES2HelloTriangle::paintGL()
  126. {
  127. // Matrix used for projection model view (PMVMatrix)
  128. static const float pfIdentity[] =
  129. {
  130. 1.0f,0.0f,0.0f,0.0f,
  131. 0.0f,1.0f,0.0f,0.0f,
  132. 0.0f,0.0f,1.0f,0.0f,
  133. 0.0f,0.0f,0.0f,1.0f
  134. };
  135. /*
  136. Clears the color buffer.
  137. glClear() can also be used to clear the depth or stencil buffer
  138. (GL_DEPTH_BUFFER_BIT or GL_STENCIL_BUFFER_BIT)
  139. */
  140. glClear(GL_COLOR_BUFFER_BIT);
  141. /*
  142. Bind the projection model view matrix (PMVMatrix) to
  143. the associated uniform variable in the shader
  144. */
  145. // First gets the location of that variable in the shader using its name
  146. int i32Location = glGetUniformLocation(m_uiProgramObject, "myPMVMatrix");
  147. // Then passes the matrix to that variable
  148. glUniformMatrix4fv( i32Location, 1, GL_FALSE, pfIdentity);
  149. /*
  150. Enable the custom vertex attribute at index VERTEX_ARRAY.
  151. We previously binded that index to the variable in our shader "vec4 MyVertex;"
  152. */
  153. glEnableVertexAttribArray(VERTEX_ARRAY);
  154. // Sets the vertex data to this attribute index
  155. glVertexAttribPointer(VERTEX_ARRAY, 3, GL_FLOAT, GL_FALSE, 0, 0);
  156. /*
  157. Draws a non-indexed triangle array from the pointers previously given.
  158. This function allows the use of other primitive types : triangle strips, lines, ...
  159. For indexed geometry, use the function glDrawElements() with an index list.
  160. */
  161. glDrawArrays(GL_TRIANGLES, 0, 3);
  162. if(m_ui32Frame > 500)
  163. {
  164. // Tidy up before exit
  165. // Frees the OpenGL handles for the program and the 2 shaders
  166. glDeleteProgram(m_uiProgramObject);
  167. glDeleteShader(m_uiFragShader);
  168. glDeleteShader(m_uiVertShader);
  169. // Delete the VBO as it is no longer needed
  170. glDeleteBuffers(1, &m_ui32Vbo);
  171. exit(0); // We wish to exit our app
  172. }
  173. ++m_ui32Frame;
  174. // update our widget so paintGL is called again.
  175. update();
  176. }
  177. /*!****************************************************************************
  178. @Function main
  179. @Input argc Number of arguments
  180. @Input argv Command line arguments
  181. @Return int result code to OS
  182. @Description Main function of the program
  183. ******************************************************************************/
  184. int main(int argc, char **argv)
  185. {
  186. QApplication app(argc, argv);
  187. QMainWindow window;
  188. QDesktopWidget *desktop = QApplication::desktop();
  189. // set our CentralWidget. The window will take care of deleting
  190. // COGLES2HelloTriangle when the time is right
  191. window.setCentralWidget(new COGLES2HelloTriangle());
  192. // Resize to fit our screen dimensions
  193. window.resize(desktop->width(), desktop->height());
  194. // Show the window full screen
  195. window.showFullScreen();
  196. return app.exec();
  197. }
  198. /******************************************************************************
  199. End of file (OGLES2HelloTriangle_Qt.cpp)
  200. ******************************************************************************/