我正在尝试用opengl写一个游戏,但是我在使用新的glkit类和iOS的默认模板时遇到了很多麻烦。
- (void)viewDidLoad
{
[super viewDidLoad];
self.context = [[EAGLContext alloc] initWithAPI:kEAGLRenderingAPIOpenGLES2];
if (!self.context) {
NSLog(@"Failed to create ES context");
}
if(!renderer)
renderer = [RenderManager sharedManager];
tiles = [[TileSet alloc]init];
GLKView *view = (GLKView *)self.view;
view.context = self.context;
view.drawableDepthFormat = GLKViewDrawableDepthFormat24;
[self setupGL];
}
- (void)setupGL
{
int width = [[self view] bounds].size.width;
int height = [[self view] bounds].size.height;
[EAGLContext setCurrentContext:self.context];
self.effect = [[GLKBaseEffect alloc] init];
self.effect.light0.enabled = GL_TRUE;
self.effect.light0.diffuseColor = GLKVector4Make(0.4f, 0.4f, 0.4f, 1.0f);
//Configure Buffers
glGenFramebuffers(1, &framebuffer);
glBindFramebuffer(GL_FRAMEBUFFER, framebuffer);
glGenRenderbuffers(2, &colourRenderBuffer);
glBindRenderbuffer(GL_RENDERBUFFER, colourRenderBuffer);
glRenderbufferStorage(GL_RENDERBUFFER, GL_RGBA8_OES, width, height);
glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER, colourRenderBuffer);
glGenRenderbuffers(3, &depthRenderBuffer);
glBindRenderbuffer(GL_RENDERBUFFER, depthRenderBuffer);
glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT16, width, height);
glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, depthRenderBuffer);
//Confirm everything happened awesomely
GLenum status = glCheckFramebufferStatus(GL_FRAMEBUFFER) ;
if(status != GL_FRAMEBUFFER_COMPLETE) {
NSLog(@"failed to make complete framebuffer object %x", status);
}
glEnable(GL_DEPTH_TEST);
// Enable the OpenGL states we are going to be using when rendering
glEnableClientState(GL_VERTEX_ARRAY);
}
- (void)glkView:(GLKView *)view drawInRect:(CGRect)rect
{
glClearColor(0.4f, 0.4f, 0.4f, 1.0f);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glBindFramebuffer(GL_FRAMEBUFFER, framebuffer);
float iva[] = {
0.0,0.0,0.0,
0.0,1.0,0.0,
1.0,1.0,0.0,
1.0,0.0,0.0,
};
glVertexPointer(3, GL_FLOAT, sizeof(float) * 3, iva);
glDrawArrays(GL_POINTS, 0, 4);
}
@end这样,缓冲区就会清除(变为灰色),但顶点数组中的任何内容都不会渲染。我不知道从这里做什么,而且由于技术的年龄,关于如何正确使用glkit的信息并不多。
发布于 2011-10-19 09:16:03
我没有在你的设置代码中看到任何加载你的着色器的东西-我假设你在你的代码中的某个地方做了这件事?
此外,在设置代码中,您正在创建帧缓冲区。GLKView会帮你做到这一点--实际上,你是在告诉视图在你的viewDidLoad方法中使用一个24位的深度缓冲区:
GLKView *view = (GLKView *)self.view;
view.context = self.context;
view.drawableDepthFormat = GLKViewDrawableDepthFormat24;因此,上面的glkView:drawInRect:代码所做的是:“绑定我的手工帧缓冲区,并在其中绘制一些东西”。然后GLKView会自动出现,但没有任何东西被绘制到其中,您只是绘制到了您的手工缓冲区中。除非您需要额外的帧缓冲区对象来执行诸如渲染到纹理之类的任务,否则您根本不需要关心帧缓冲区的创建-让GLKView自动完成。
您应该在setupGL方法(或设置中的任意位置)中执行的操作是创建顶点数组对象,这些对象记住执行绘制所需的openGL状态。然后,在glkView:drawInRect:方法中,您应该:
使用glClear().
glDrawArrays()或VAO启用相应的折点属性以获取数据GLKView会自动将其上下文设置为当前上下文,并在每个绘制周期之前绑定其帧缓冲区对象。
也许可以试着把GLKView想得更像一个普通的UIView。它为您处理幕后的大部分openGL代码,让您简单地告诉它需要绘制什么。它的drawRect:代码就像一个普通的UIView一样--在drawRect:中使用一个普通的UIView,你只需告诉它应该绘制什么,例如使用核心图形函数-然后你不需要告诉它呈现自己。
然后,GLKViewController最好被认为是在幕后处理呈现循环的机制。您不需要实现计时器,甚至不需要担心在应用程序进入后台时暂停动画。您只需覆盖update或glkViewControllerUpdate:方法(取决于是子类化还是委托),即可更新openGL对象或视图矩阵的状态。
发布于 2012-03-27 23:11:07
我写了一篇关于如何使用GLKit设置基本项目模板的文章。你可以在这里找到它:
Steve Zissou's Programming Blog
发布于 2011-10-18 20:31:47
我还没有使用过GLKit,但似乎在绘制到它之后,你没有呈现你的帧缓冲区。在一个在iOs下使用OpenGL ES 2但没有使用GLKit的应用程序中,我使用在呈现循环结束时调用以下代码。
if(context) {
[EAGLContext setCurrentContext:context];
glBindRenderbuffer(GL_RENDERBUFFER, viewRenderbuffer);
[context presentRenderbuffer:GL_RENDERBUFFER];}
正如我所说的,我还没有使用过GLKit,所以我希望这可能会有用。
https://stackoverflow.com/questions/7807060
复制相似问题