рендеринг в OpenGL с использованием CAOpenGLLayer - PullRequest
0 голосов
/ 05 ноября 2010

У меня есть общий вопрос о том, как CAOpenGLLayer работает в Mac OS X. Можно ли нарисовать в OpenGL в месте, отличном от -[CAOpenGLLayer drawInCGLContext:] метода CAOpenGLLayer?

Я использую пример кода Apple CALayerEssentials и только что переместил код, который рисует прямоугольник, с drawInCGLContext на redrawGLContent.Метод redrawGLContent вызывается каждый раз, когда пользователь нажимает кнопку в окне OpenGL.
Когда код рисования находится в drawInCGLContext, он рисуется, как и ожидалось, но когда я перемещаю код в redrawGLContent, ничегообращается к окну OpenGL.Я пытаюсь понять, как это работает.

-(IBAction)redrawGLContent:(id)sender
{

// This part wass added, but does not draw the rectangle

    float timeInterval=0;
    GLfloat rotate = timeInterval * 60.0; // 60 degrees per second!
    glClear(GL_COLOR_BUFFER_BIT);
    glMatrixMode(GL_MODELVIEW);
    glPushMatrix();
    glRotatef(rotate, 0.0, 0.0, 1.0);
    glBegin(GL_QUADS);
        glColor3f(1.0, 0.0, 0.0);
        glVertex2f(-0.5, -0.5);
        glVertex2f(-0.5,  0.5);
        glVertex2f( 0.5,  0.5);
        glVertex2f( 0.5, -0.5);
    glEnd();
    glPopMatrix();
// up to here

    // Just tell the layer to display itself and it will redraw
    [hostCAOpenGLLayer.layer setNeedsDisplay];
}

-(void)drawInCGLContext:(CGLContextObj)glContext pixelFormat:(CGLPixelFormatObj)pixelFormat forLayerTime:(CFTimeInterval)timeInterval displayTime:(const CVTimeStamp *)timeStamp
{

    // Set the current context to the one given to us.
    CGLSetCurrentContext(glContext);


/* This part was removed.  When code is here the quad is displayed 

    GLfloat rotate = timeInterval * 60.0; // 60 degrees per second!
    glClear(GL_COLOR_BUFFER_BIT);
    glMatrixMode(GL_MODELVIEW);
    glPushMatrix();
    glRotatef(rotate, 0.0, 0.0, 1.0);
    glBegin(GL_QUADS);
        glColor3f(1.0, 0.0, 0.0);
        glVertex2f(-0.5, -0.5);
        glVertex2f(-0.5,  0.5);
        glVertex2f( 0.5,  0.5);
        glVertex2f( 0.5, -0.5);
    glEnd();
    glPopMatrix();
*/    
    // Call super to finalize the drawing. By default all it does is call glFlush().
    [super drawInCGLContext:glContext pixelFormat:pixelFormat forLayerTime:timeInterval displayTime:timeStamp];
}

1 Ответ

2 голосов
/ 01 мая 2013

Я знаю, что этот вопрос задавали некоторое время назад, но я решил ответить на него в любом случае на благо других. Нет ничего хуже, чем натолкнуться на вопрос о переполнении стека, который точно описывает вашу проблему, но на который нет ответа; -)

Я думаю, BinaryStar ударило по голове. Ваша проблема в том, что у вас нет действительного контекста GL для рисования.

Когда система вызывает drawInCGLContext:pixelFormat:forLayerTime:displayTime:, она дает вам контекст, готовый для использования вашим кодом. Например, текущий видовой экран будет установлен в этом контексте, чтобы вы рисовали в своих слоях bounds. В тот момент, когда вы вызываете свой пользовательский код, вы не можете гарантировать, что этот контекст был настроен правильно или что это даже текущий контекст.

Я думаю, что правильным подходом здесь было бы установить асинхронное свойство CAOpenGLLayer на NO. Затем из вашего кода обработки кнопок вызовите setNeedsDisplay на слое.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...