高分辨率 - Retina显示OpenGL ES [CAEAGLLayer]内容的屏幕截图

时间:2011-07-20 08:14:13

标签: iphone objective-c ios xcode opengl-es

我在我的Paint应用程序中使用GLPaint示例,我需要截取OpenGL ES [CAEAGLLayer]渲染内容的屏幕截图。我正在使用功能:

-(UIImage *)snapUIImage
{

    int s = 2;


    const int w = self.frame.size.width;
    const int h = self.frame.size.height;
    const NSInteger myDataLength = w * h * 4 * s * s;


    // allocate array and read pixels into it.
    GLubyte *buffer = (GLubyte *) malloc(myDataLength);


    glReadPixels(0, 0, w*s, h*s, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
    // gl renders "upside down" so swap top to bottom into new array.
    // there's gotta be a better way, but this works.
    GLubyte *buffer2 = (GLubyte *) malloc(myDataLength);
    for(int y = 0; y < h*s; y++)
    {
        memcpy( buffer2 + (h*s - 1 - y) * w * 4 * s, buffer + (y * 4 * w * s), w * 4 * s );
    }
    free(buffer); // work with the flipped buffer, so get rid of the original one.

    // make data provider with data.
    CGDataProviderRef provider = CGDataProviderCreateWithData(NULL, buffer2, myDataLength, NULL);
    // prep the ingredients
    int bitsPerComponent = 8;
    int bitsPerPixel = 32;
    int bytesPerRow = 4 * w * s;
    CGColorSpaceRef colorSpaceRef = CGColorSpaceCreateDeviceRGB();
    CGBitmapInfo bitmapInfo = kCGBitmapByteOrderDefault | kCGImageAlphaLast;
    CGColorRenderingIntent renderingIntent = kCGRenderingIntentDefault;

    // make the cgimage
    CGImageRef imageRef = CGImageCreate(w*s, h*s, bitsPerComponent, bitsPerPixel, bytesPerRow, colorSpaceRef, bitmapInfo, provider, NULL, NO, renderingIntent);
    // then make the uiimage from that
    UIImage *myImage = [ UIImage imageWithCGImage:imageRef scale:s orientation:UIImageOrientationUp ];


    CGImageRelease( imageRef );

    CGDataProviderRelease(provider);
    CGColorSpaceRelease(colorSpaceRef);
    // buffer2 will be destroyed once myImage is autoreleased.

    return myImage;

}



-(void)captureToPhotoAlbum {
        UIImage *image = [self snapUIImage];
            UIImageWriteToSavedPhotosAlbum(image, self, nil, nil);
}

以上代码正常工作我正在获取图像,但它不是高分辨率[Retina显示]图像。请帮忙。

提前致谢。

1 个答案:

答案 0 :(得分:0)

工作代码解决方案

- (UIImage*) getGLScreenshot
{
    int myWidth  = self.frame.size.width*2;
    int myHeight = self.frame.size.height*2;
    int myY = 0;
    int myX = 0;
    int bufferLength = (myWidth*myHeight*4);

    //unsigned char buffer[bufferLength];
    unsigned char* buffer =(unsigned char*)malloc(bufferLength);
    glReadPixels(myX, myY, myWidth, myHeight, GL_RGBA, GL_UNSIGNED_BYTE, buffer);

    CGDataProviderRef ref = CGDataProviderCreateWithData(NULL, buffer, bufferLength, NULL);
    CGImageRef iref = CGImageCreate(myWidth,myHeight,8,32,myWidth*4,CGColorSpaceCreateDeviceRGB(),
                                    kCGBitmapByteOrderDefault,ref,NULL, true, kCGRenderingIntentDefault);
    uint32_t* pixels = (uint32_t *)malloc(bufferLength);
    CGContextRef context = CGBitmapContextCreate(pixels, myWidth, myHeight, 8, myWidth*4, CGImageGetColorSpace(iref),
                                                 kCGImageAlphaNoneSkipFirst | kCGBitmapByteOrder32Big);
    CGContextTranslateCTM(context, 0.0, myHeight);
    CGContextScaleCTM(context, 1.0, -1.0);
    CGContextDrawImage(context, CGRectMake(0.0, 0.0, myWidth, myHeight), iref);
    CGImageRef outputRef = CGBitmapContextCreateImage(context);

    UIImage *image = nil;
    if(regardOrientation) {
        UIDeviceOrientation deviceOrientation = [UIDevice currentDevice].orientation;
        if (deviceOrientation == UIDeviceOrientationPortraitUpsideDown) {
            image = [UIImage imageWithCGImage:outputRef scale:1 orientation:UIImageOrientationDown];
        } else if (deviceOrientation == UIDeviceOrientationLandscapeLeft) {
            image = [UIImage imageWithCGImage:outputRef scale:1 orientation:UIImageOrientationLeft];
        } else if (deviceOrientation == UIDeviceOrientationLandscapeRight) {
            image = [UIImage imageWithCGImage:outputRef scale:1 orientation:UIImageOrientationRight];
        } else {
            image = [UIImage imageWithCGImage:outputRef scale:1 orientation:UIImageOrientationUp];
        }
    } else {
        image = [UIImage imageWithCGImage:outputRef scale:1 orientation:UIImageOrientationUp];
    }

    image = [UIImage imageWithCGImage:outputRef scale:1 orientation:UIImageOrientationUp];

    CGImageRelease(iref);
    CGImageRelease(outputRef);
    CGContextRelease(context);
    CGDataProviderRelease(ref);
    free(buffer);
    free(pixels);

    UIImageWriteToSavedPhotosAlbum(image, nil, nil, nil);

    return image;
}