create_shader_program.h 2.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112
  1. #ifndef IGL_CREATE_SHADER_PROGRAM_H
  2. #define IGL_CREATE_SHADER_PROGRAM_H
  3. #include <string>
  4. #include <map>
  5. #ifdef __APPLE__
  6. # include <OpenGL/gl.h>
  7. #else
  8. # ifdef _WIN32
  9. # define NOMINMAX
  10. # include <Windows.h>
  11. # undef NOMINMAX
  12. # endif
  13. # include <GL/gl.h>
  14. #endif
  15. namespace igl
  16. {
  17. // Create a shader program with a vertex and fragments shader loading from
  18. // source strings and vertex attributes assigned from a map before linking the
  19. // shaders to the program, making it ready to use with glUseProgram(id)
  20. // Inputs:
  21. // vert_source string containing source code of vertex shader
  22. // frag_source string containing source code of fragment shader
  23. // attrib map containing table of vertex attribute strings add their
  24. // correspondingly ids (generated previously using glBindAttribLocation)
  25. // Outputs:
  26. // id index id of created shader, set to 0 on error
  27. // Returns true on success, false on error
  28. //
  29. // Note: Caller is responsible for making sure that current value of id is not
  30. // leaking a shader (since it will be overwritten)
  31. //
  32. // See also: destroy_shader_program
  33. inline bool create_shader_program(
  34. const std::string vert_source,
  35. const std::string frag_source,
  36. const std::map<std::string,GLuint> attrib,
  37. GLuint & id);
  38. }
  39. // Implementation
  40. #include "load_shader.h"
  41. #include "print_program_info_log.h"
  42. #include <cstdio>
  43. inline bool igl::create_shader_program(
  44. const std::string vert_source,
  45. const std::string frag_source,
  46. const std::map<std::string,GLuint> attrib,
  47. GLuint & id)
  48. {
  49. if(vert_source == "" && frag_source == "")
  50. {
  51. fprintf(
  52. stderr,
  53. "Error: create_shader_program() could not create shader program,"
  54. " both .vert and .frag source given were empty\n");
  55. return false;
  56. }
  57. // create program
  58. id = glCreateProgram();
  59. if(id == 0)
  60. {
  61. fprintf(
  62. stderr,
  63. "Error: create_shader_program() could not create shader program.\n");
  64. return false;
  65. }
  66. if(vert_source != "")
  67. {
  68. // load vertex shader
  69. GLuint v = igl::load_shader(vert_source.c_str(),GL_VERTEX_SHADER);
  70. if(v == 0)
  71. {
  72. return false;
  73. }
  74. glAttachShader(id,v);
  75. }
  76. if(frag_source != "")
  77. {
  78. // load fragment shader
  79. GLuint f = igl::load_shader(frag_source.c_str(),GL_FRAGMENT_SHADER);
  80. if(f == 0)
  81. {
  82. return false;
  83. }
  84. glAttachShader(id,f);
  85. }
  86. // loop over attributes
  87. for(
  88. std::map<std::string,GLuint>::const_iterator ait = attrib.begin();
  89. ait != attrib.end();
  90. ait++)
  91. {
  92. glBindAttribLocation(
  93. id,
  94. (*ait).second,
  95. (*ait).first.c_str());
  96. }
  97. // Link program
  98. glLinkProgram(id);
  99. // print log if any
  100. igl::print_program_info_log(id);
  101. return true;
  102. }
  103. #endif