从GLPaint保存imageRef会创建完全黑色的图像 [英] Saving imageRef from GLPaint creates completely black image

查看:74
本文介绍了从GLPaint保存imageRef会创建完全黑色的图像的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

您好我正在尝试绘制应用程序并在保存绘制的图像时遇到问题。现在我很早就学会了这个,但我添加了以下代码:
如何从EAGLView获取UIImage?以保存绘制的图像。

Hi I am trying out drawing app and have a problem when it comes to saving the image that is drawn. Right now I'm very early in learning this but I have added code from: How to get UIImage from EAGLView? to save the image that was drawn.

我创建了一个新应用,然后显示了我创建的viewController。在IB中我添加了一个视图,它是PaintingView,后面是一个imageView。

I have created a new app, then displayed a viewController that I created. In IB I have added a view which is the PaintingView, and an imageView lies behind it.

到目前为止,我对PaintingView所做的唯一修改是将背景更改为清除并将背景设置为清除,以便我可以在其后面显示图像。绘图效果很好,我唯一的问题是保存。

The only modification I have done to the PaintingView so far is to change the background to clear and set the background to clear so that I can display an image behind it. The drawing works great, my only problem is saving.

- (void)saveImageFromGLView:(UIView *)glView {

    if(glCheckFramebufferStatusOES(GL_FRAMEBUFFER_OES) != GL_FRAMEBUFFER_COMPLETE_OES)
        {
            /// This IS being activated with code 0
            NSLog(@"failed to make complete framebuffer object %x", glCheckFramebufferStatusOES(GL_FRAMEBUFFER_OES));
    }


    int s = 1;
    UIScreen* screen = [ UIScreen mainScreen ];
    if ( [ screen respondsToSelector:@selector(scale) ] )
        s = (int) [ screen scale ];

    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;
    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 ];
    UIImageWriteToSavedPhotosAlbum( myImage, nil, nil, nil );
    CGImageRelease( imageRef );
    CGDataProviderRelease(provider);
    CGColorSpaceRelease(colorSpaceRef);
    free(buffer2);    

}

将上述代码添加到Sample app工作正常,问题是在我的新应用程序中执行。我可以说的唯一区别是我没有包括PaintingWindow - 这会是问题吗?

Adding the above code to the Sample app works fine, the problem is doing it in my new app. The only difference I can tell is that I have not included PaintingWindow - would that be the problem?

就好像saveImage方法没有看到图纸的数据一样。

It's as if the saveImage method isn't seeing the data for drawings.

推荐答案

应该在OpenGL上下文的范围内调用save方法。
要解决此问题,您可以在同一个渲染.m文件中移动方法,并从外部调用此函数。

The save method should be called within the scope of the OpenGL context. To solve this you can move your method within the same rendering .m file and call this function from outside.

另外你需要考虑OpenGL的清晰颜色。

Also you need to consider OpenGL clear color.

(评论中的详细解释,lol)

(detail explanation in comments, lol)

这篇关于从GLPaint保存imageRef会创建完全黑色的图像的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆