Вот пример приложения «GLKView Subview», который я написал на основе примера проекта OpenGL Game в Xcode 4.5. Это создает GLKView подвид с делегатом, установленным в GLKViewController владельца файла, так что оба вида OpenGL ES 2 управляется одним контроллером:GLKView размер и размер рамки вложенных подкадров вложенных объектов
Вот скриншот, я тонированная предыстория подвида в красной для контраста:
Я был возбужден, что у меня простой способ добавить несколько GLKViews под одной GLKViewController и EAGLContext (для совместного использования текстур и т.д.), пока не понял, что размер кадра нарушается в:
- (void)glkView:(GLKView *)view drawInRect:(CGRect)rect
{
NSLog(@"My view frame: %@", NSStringFromCGRect(view.bounds));
float aspect = fabsf(view.bounds.size.width/view.bounds.size.height);
GLKMatrix4 projectionMatrix = GLKMatrix4MakePerspective(GLKMathDegreesToRadians(65.0f), aspect, 0.1f, 100.0f);
self.effect.transform.projectionMatrix = projectionMatrix;
GLKMatrix4 baseModelViewMatrix = GLKMatrix4MakeTranslation(0.0f, 0.0f, -4.0f);
baseModelViewMatrix = GLKMatrix4Rotate(baseModelViewMatrix, _rotation, 0.0f, 1.0f, 0.0f);
// Compute the model view matrix for the object rendered with GLKit
GLKMatrix4 modelViewMatrix = GLKMatrix4MakeTranslation(0.0f, 0.0f, -1.5f);
modelViewMatrix = GLKMatrix4Rotate(modelViewMatrix, _rotation, 1.0f, 1.0f, 1.0f);
modelViewMatrix = GLKMatrix4Multiply(baseModelViewMatrix, modelViewMatrix);
self.effect.transform.modelviewMatrix = modelViewMatrix;
// Compute the model view matrix for the object rendered with ES2
modelViewMatrix = GLKMatrix4MakeTranslation(0.0f, 0.0f, 1.5f);
modelViewMatrix = GLKMatrix4Rotate(modelViewMatrix, _rotation, 1.0f, 1.0f, 1.0f);
modelViewMatrix = GLKMatrix4Multiply(baseModelViewMatrix, modelViewMatrix);
_normalMatrix = GLKMatrix3InvertAndTranspose(GLKMatrix4GetMatrix3(modelViewMatrix), NULL);
_modelViewProjectionMatrix = GLKMatrix4Multiply(projectionMatrix, modelViewMatrix);
if(view == self.view)
{
glClearColor(0.65f, 0.65f, 1.0f, 1.0f);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glBindVertexArrayOES(_vertexArray);
// Render the object with GLKit
[self.effect prepareToDraw];
glDrawArrays(GL_TRIANGLES, 0, 36);
// Render the object again with ES2
glUseProgram(_program);
glUniformMatrix4fv(uniforms[UNIFORM_MODELVIEWPROJECTION_MATRIX], 1, 0, _modelViewProjectionMatrix.m);
glUniformMatrix3fv(uniforms[UNIFORM_NORMAL_MATRIX], 1, 0, _normalMatrix.m);
glDrawArrays(GL_TRIANGLES, 0, 36);
[self.subview display];
}
else
{
glClearColor(1.0f, 0.65f, 0.65f, 1.0f);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glBindVertexArrayOES(_vertexArray);
// Render the object with GLKit
[self.effect prepareToDraw];
glDrawArrays(GL_TRIANGLES, 0, 36);
// Render the object again with ES2
glUseProgram(_program);
glUniformMatrix4fv(uniforms[UNIFORM_MODELVIEWPROJECTION_MATRIX], 1, 0, _modelViewProjectionMatrix.m);
glUniformMatrix3fv(uniforms[UNIFORM_NORMAL_MATRIX], 1, 0, _normalMatrix.m);
glDrawArrays(GL_TRIANGLES, 0, 36);
}
}
Выход в IOS Simulator с iPhone 4" Retina:
2013-04-27 15:50:56.149 GLKView Subview[48136:11903] My view frame: {{0, 0}, {568, 320}}
2013-04-27 15:50:56.152 GLKView Subview[48136:11903] My view frame: {{0, 0}, {248, 100}}
Рама подвид должна быть {100, 100}, но по какой-то причине он выходит на {248, 100}. Я пробовал все, о чем я мог думать, даже встраивая его в UIView, думая, что, возможно, его ограничения авторезистентности ошибочны, если основной GLKView был его родителем. Как вы видите, размер UIView правильный, но размер дочернего элемента GLKView.
Как разработчик, это казалось первым делом, но Apple, как правило, имеет другие идеи. Без авторазрешения GLKView бесполезен для макетов свободной формы, которые работают с любым размером устройства.
Мне удалось получить несколько GLKViewControllers, совместно использующих один EAGLContext, работающих в качестве дочерних контроллеров в другом проекте. Но я не понимаю, почему нам нужно носить багаж для создания GLKViewController каждый раз, когда мы хотим добавить GLKView на экран. Я предполагаю, что GLKViewController запутался, когда он является делегатом для GLKView, который не является его собственным представлением.
Мне также удалось заставить мои представления работать вручную, просто используя glViewport(), и после потери двух дней на проблемы с GLKView я, вероятно, порекомендую пройти этот маршрут всем, кто это прочитает (также получая преимущества перекрестной платформы).
Я надеюсь, что есть простое объяснение/исправление, даже если это просто «вы должны сделать GLKViewController для каждого GLKView». Заранее благодарю всех, кто сумеет заставить его работать. Если нет, возможно, пример этой ошибки
поможет кому-то.