My newest game, SpaceDebris, is now online in the App Store and Mac App Store. Check it out!
My newest game, SpaceDebris, is now online in the App Store and Mac App Store. Check it out!
So I’ve struggled quite a bit getting a UIImage from my OpenGL view, as most of the stackoverflow.com posts were about OpenGL ES 1.0 (which seems a little bit different from 2.0). A few days later i contact the Apple Support as i had a few help-tickets left and they were able to tell me one line I was missing in my code. As this may be helpful to other programmers i decided to post it here. Here’s the source code (just replace the ‘draw code here’-comment with your code).
@interface RenderToImage() { EAGLContext* myContext; GLuint framebuffer; GLuint colorRenderbuffer; GLuint depthRenderbuffer; int width; int height; } @end @implementation RenderToImage - (id) init { self = [super init]; if (self) { } return self; } -(void) setupOpenGL { [EAGLContext setCurrentContext:myContext]; glGenFramebuffersOES(1, &framebuffer); glBindFramebufferOES(GL_FRAMEBUFFER, framebuffer); glGenRenderbuffersOES(1, &colorRenderbuffer); glBindRenderbufferOES(GL_RENDERBUFFER, colorRenderbuffer); glRenderbufferStorageOES(GL_RENDERBUFFER, GL_RGBA8_OES, width, height); glFramebufferRenderbufferOES(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER, colorRenderbuffer); //GLuint depthRenderbuffer; glGenRenderbuffersOES(1, &depthRenderbuffer); glBindRenderbufferOES(GL_RENDERBUFFER, depthRenderbuffer); glRenderbufferStorageOES(GL_RENDERBUFFER, GL_DEPTH_COMPONENT16, width, height); glFramebufferRenderbufferOES(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, depthRenderbuffer); GLenum status = glCheckFramebufferStatus(GL_FRAMEBUFFER) ; if(status != GL_FRAMEBUFFER_COMPLETE) { NSLog(@"failed to make complete framebuffer object %x", status); } sample = [[OpenGLSample alloc] init]; [sample setContext:myContext]; [sample setupGL]; } -(UIImage *) renderWithSize:(CGSize)size { myContext = [[EAGLContext alloc] initWithAPI:kEAGLRenderingAPIOpenGLES2]; width = size.width; height = size.height; [EAGLContext setCurrentContext:myContext]; [self setupOpenGL]; glViewport(0,0,width,height); glBindFramebufferOES(GL_FRAMEBUFFER_OES, framebuffer); glBindRenderbufferOES(GL_RENDERBUFFER_OES, colorRenderbuffer); // --- DRAW CODE HERE --- // grabbing image from FBO GLint backingWidth, backingHeight; glGetRenderbufferParameterivOES(GL_RENDERBUFFER_OES, GL_RENDERBUFFER_WIDTH_OES, &backingWidth); glGetRenderbufferParameterivOES(GL_RENDERBUFFER_OES, GL_RENDERBUFFER_HEIGHT_OES, &backingHeight); NSInteger x = 0, y = 0; NSInteger dataLength = width * height * 4; GLubyte *data = (GLubyte*)malloc(dataLength * sizeof(GLubyte)); glPixelStorei(GL_PACK_ALIGNMENT, 4); glReadPixels(x, y, width, height, GL_RGBA, GL_UNSIGNED_BYTE, data); CGDataProviderRef ref = CGDataProviderCreateWithData(NULL, data, dataLength, NULL); CGColorSpaceRef colorspace = CGColorSpaceCreateDeviceRGB(); CGImageRef iref = CGImageCreate(width, height, 8, 32, width * 4, colorspace, kCGBitmapByteOrder32Big | kCGImageAlphaPremultipliedLast, ref, NULL, true, kCGRenderingIntentDefault); UIGraphicsBeginImageContext(CGSizeMake(width, height)); CGContextRef cgcontext = UIGraphicsGetCurrentContext(); CGContextSetBlendMode(cgcontext, kCGBlendModeCopy); CGContextDrawImage(cgcontext, CGRectMake(0.0, 0.0, width, height), iref); UIImage *image = UIGraphicsGetImageFromCurrentImageContext(); UIGraphicsEndImageContext(); free(data); CFRelease(ref); CFRelease(colorspace); CGImageRelease(iref); [EAGLContext setCurrentContext:nil]; return image; } @end
© 2024 thomasguenzel.com
Theme by Anders Noren — Up ↑
Recent Comments