2014-02-03 2 views
0

У меня есть класс, который создает программу OpenGL, присоединяет шейдер и хранят идентификаторы этих программ в простом std::map <std::string, GLuint>.программа Повторного использования в OpenGL на прошивке

Вот код из двух основных функций этого класса:

GLuint ShaderBuilder::build_shader(GLenum type, const GLchar * shaderStr) 
    { 
     GLuint shader = glCreateShader(type); 
     OutputTraceMsg(9, "glCreateShader: %x", glGetError()); 

     if(shader == 0) 
      return 0; 

     glShaderSource(shader, 1, &shaderStr, 0); 
     OutputTraceMsg(9, "glShaderSource: %x", glGetError()); 

     glCompileShader(shader); 
     OutputTraceMsg(9, "glCompileShader: %x", glGetError()); 

#ifdef DEBUG 
     GLint status = 0; 
     glGetShaderiv(shader, GL_COMPILE_STATUS, &status); 
     //OutputTraceMsg(9, "glGetShaderiv: %d", glGetError()); 

     if (status != GL_TRUE) 
     { 
      GLint logLength; 
      glGetShaderiv(shader, GL_INFO_LOG_LENGTH, &logLength); 
      if (logLength > 0) 
      { 
       GLchar *log = (GLchar *)malloc(logLength); 
       glGetShaderInfoLog(shader, logLength, &logLength, log); 
       OutputTraceMsg(1, "Error compiling shader: %s", log); 
       free(log); 
      } 

      glDeleteShader(shader); 
      return 0; 
     } 
#endif 
     return shader; 
    } 

    GLuint ShaderBuilder::create_program(const GLchar * vertexStr, const GLchar * fragmentStr) 
    { 
     GLuint vertexShader = this->build_shader(GL_VERTEX_SHADER, vertexStr); 
     GLuint fragmentShader = this->build_shader(GL_FRAGMENT_SHADER, fragmentStr); 

     GLuint program = glCreateProgram(); 
     if (program == 0) 
     { 
      OutputTraceMsg(3, "Filter: create program failed"); 
      return 0; 
     } 

     glAttachShader(program, vertexShader); 
     glAttachShader(program, fragmentShader); 
     glLinkProgram(program); 
     glValidateProgram(program); 

#ifdef DEBUG 
     GLint linked; 
     glGetProgramiv(program, GL_LINK_STATUS, &linked); 
     if(!linked) 
     { 

      GLint infoLen = 0; 
      glGetProgramiv(program, GL_INFO_LOG_LENGTH, &infoLen); 
      if (infoLen > 0) 
      { 
       char * infoLog = (char *)malloc(sizeof(char) * infoLen); 
       glGetProgramInfoLog(program, infoLen, &infoLen, infoLog); 
       OutputTraceMsg(3, "Error linking program: %s", infoLog); 
       free(infoLog); 
      } 
      glDeleteProgram(program); 
      return 0; 
     } 
#endif 

     return program; 
    } 

И у меня есть следующая ситуация: все шейдеры и программы компилируются на этапе инициализации, и я успешно заполняю эту std :: map идентификаторами этих программ. Но после этого, когда я пытаюсь использовать любой из этих идентификаторов с некоторыми функциями OpenGL, такими как glGetAttribLocation (программа, «позиция»), OpenGL возвращает мне GL_INVALID_VALUE. Это странно, потому что если я в этот момент сразу вызову функцию create_program с теми же шейдерами, которые я использовал ранее в своем классе, glGetAttribLocation (program, «position») возвращает 0. Кроме того, Instruments сообщает мне, чтобы гарантировать, что объекты программы не были удалены, но этот класс является классическим одноэлементным Мейерсом, поэтому срок жизни объекта этого класса должен быть равен времени жизни этой программы.

ответ

0
  1. Пожалуйста, убедитесь, что де-эталонное значение возвращается из std::map соответствует значению объекта программы, когда созданный на компиляции.

  2. Пожалуйста, убедитесь, что вы действительно выбрали программу, используя метод glUseProgram, прежде чем пытаться получить доступ к любому унифицированному/атрибуту.

  3. Также проверьте, правильно ли установлен текущий контекст GL.

    EAGLContext* context = [[EAGLContext alloc] initWithAPI:kEAGLRenderingAPIOpenGLES2]; 
    [EAGLContext setCurrentContext:context]; 
    [context release]; 
    

Надеется, что это помогает.

+0

Выделенное значение соответствует значению программного объекта, который я создал на этапе инициализации. И я использую glUseProgram сразу после того, как у меня есть идентификатор программы. Он также возвращает GL_INVALID_VALUE :( – vglazkov

+0

Вы получаете 'GL_INVALID_VALUE', когда вы создаете объект программы с помощью' glCreateProgram'? –

+0

№. Контекст тоже настроен правильно. Примечание: если я вызову glUseProgram сразу после создания программы - это нормально, верните значение равно 0, но если я попытаюсь использовать этот идентификатор после завершения инициализации класса в одной функции, у меня такая же ошибка, в другом я получил 0. Между этими функциями нет вызовов OpenGL ES, и они следуют один за другим. – vglazkov

Смежные вопросы