iOS截图因OpenGL而失败

时间:2016-09-09 06:48:52

标签: ios objective-c screenshot

这是我的代码

@implementation UIView (LCExtension)

- (UIImage *)screenshotWithRect:(CGRect)rect {

    UIGraphicsBeginImageContext(self.bounds.size);
    [self.layer renderInContext:UIGraphicsGetCurrentContext()];
    UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
    image = [UIImage imageWithCGImage:CGImageCreateWithImageInRect(image.CGImage, rect)];
    UIGraphicsEndImageContext();
    return image;
}

@end

我在这里设置了一个断点:

code

执行命令

  • 这是 view-self :(来自OpenGL渲染的图片)

    view-self

  • 这是生成的图片

    image

为什么这是一张黑色照片?

1 个答案:

答案 0 :(得分:1)

使用OpenGL(ES)时,是的,我假设您使用的是OpenGL ES,因为您有UIView类别,请在呈现渲染缓冲区之前记住捕获屏幕。一旦您或GLKViewController的子类呈现渲染缓冲区,它就会成为前帧缓冲区,然后屏幕帧缓冲区变为后帧缓冲区,除了您使用glClearColor设置的颜色外,它不会为您提供任何内容。

[EAGLContext presentRenderbuffer:]

以下是捕获屏幕的示例代码。

- (UIImage *)createImageFromFramebuffer {
    GLint params[10];
    glGetIntegerv(GL_VIEWPORT, params);
    int width = params[2];
    int height = params[3];
    const int renderTargetWidth = width;
    const int renderTargetHeight = height;
    const int renderTargetSize = renderTargetWidth*renderTargetHeight * 4;

    uint8_t* imageBuffer = (uint8_t*)malloc(renderTargetSize);
    glReadPixels(params[0], params[1],
             renderTargetWidth, renderTargetHeight,
             GL_RGBA, GL_UNSIGNED_BYTE, imageBuffer);

    const int rowSize = renderTargetWidth*4;

    CGDataProviderRef ref = CGDataProviderCreateWithData(NULL, imageBuffer, renderTargetSize, NULL);
    CGImageRef iref = CGImageCreate(renderTargetWidth, renderTargetHeight, 8, 32, rowSize,
                                CGColorSpaceCreateDeviceRGB(),
                                kCGImageAlphaLast | kCGBitmapByteOrderDefault, ref,
                                NULL, true, kCGRenderingIntentDefault);

    uint8_t* contextBuffer = (uint8_t*)malloc(renderTargetSize);
    memset(contextBuffer, 0, renderTargetSize);
    CGContextRef context = CGBitmapContextCreate(contextBuffer, renderTargetWidth, renderTargetHeight, 8, rowSize,
                                             CGImageGetColorSpace(iref),
                                             kCGImageAlphaPremultipliedFirst | kCGBitmapByteOrder32Big);
    CGContextTranslateCTM(context, 0.0, renderTargetHeight);
    CGContextScaleCTM(context, 1.0, -1.0);
    CGContextDrawImage(context, CGRectMake(0.0, 0.0, renderTargetWidth, renderTargetHeight), iref);
    CGImageRef outputRef = CGBitmapContextCreateImage(context);

    UIImage* image = [[UIImage alloc] initWithCGImage:outputRef];

    CGImageRelease(outputRef);
    CGContextRelease(context);
    CGImageRelease(iref);
    CGDataProviderRelease(ref);

free(contextBuffer);
    free(imageBuffer);
    return image;
}