Cocos2D 2.0 - 截图捕获期间的奇怪行为 [英] Cocos2D 2.0 - bizarre behavior during a screenshot capture

查看:99
本文介绍了Cocos2D 2.0 - 截图捕获期间的奇怪行为的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个基于图层的类,包含两个子图形作为孩子。让我们称之为:背景和树。

I have a layer based class that contains two sprites as children. Lets call them: background and tree.

在这个类中,我有一个方法来捕获该图层的截图。该方法工作正常。每次我拍摄该图层的屏幕截图时,我会获得背景的树的组成。精细。在某一点上,我想得到没有树的那层的截图。所以我做的是,隐藏树,截取屏幕截图并再次显示树...像这样:

Inside this class I have a method to capture a screenshot of that layer. The method is working fine. Every time I take a screenshot of that layer, I obtain the composition of the tree over the background. Fine. At a certain point, I want to get the screenshot of that layer without the tree. So what I do is, to hide the tree, take the screenshot and show the tree again... like this:

[myLayer hideTree];
UIImage *screenshot = [myLayer screenshot];
[myLayer showTree];

令我惊讶的是,以这种方式生成的截图总是包含树。

To my surprise, the screenshots produced this way always contain the tree.

这是hideTree和showTree:

this is hideTree and showTree:

- (void) hideTree {
    [treeLayer setOpacity:0];
    // I have also tried [treelayer setVisible:NO];
}

- (void) showTree {
    [treeLayer setOpacity:255];
    // I have also tried [treelayer setVisible:YES];
}

我使用这个方法来截图,来自cocos2d论坛:

I am using this method for screenshots, from cocos2d forums:

-(UIImage*) screenshot
{
    CGSize displaySize  = [[CCDirector sharedDirector] winSize];
    CGSize winSize      = [self winSize];

    //Create buffer for pixels
    GLuint bufferLength = displaySize.width * displaySize.height * 4;
    GLubyte* buffer = (GLubyte*)malloc(bufferLength);

    //Read Pixels from OpenGL
    glReadPixels(0, 0, displaySize.width, displaySize.height, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
    //Make data provider with data.
    CGDataProviderRef provider = CGDataProviderCreateWithData(NULL, buffer, bufferLength, NULL);

    //Configure image
    int bitsPerComponent = 8;
    int bitsPerPixel = 32;
    int bytesPerRow = 4 * displaySize.width;
    CGColorSpaceRef colorSpaceRef = CGColorSpaceCreateDeviceRGB();
    CGBitmapInfo bitmapInfo = kCGBitmapByteOrderDefault;
    CGColorRenderingIntent renderingIntent = kCGRenderingIntentDefault;
    CGImageRef iref = CGImageCreate(displaySize.width, displaySize.height, bitsPerComponent, bitsPerPixel, bytesPerRow, colorSpaceRef, bitmapInfo, provider, NULL, NO, renderingIntent);

    uint32_t* pixels = (uint32_t*)malloc(bufferLength);
    CGContextRef context = CGBitmapContextCreate(pixels, winSize.width, winSize.height, 8, winSize.width * 4, CGImageGetColorSpace(iref), kCGImageAlphaPremultipliedLast | kCGBitmapByteOrder32Big);

    CGContextTranslateCTM(context, 0, displaySize.height);
    CGContextScaleCTM(context, 1.0f, -1.0f);

    UIDeviceOrientation orientation = [[UIDevice currentDevice] orientation];
    switch (orientation)
    {
        case UIDeviceOrientationPortrait: break;
        case UIDeviceOrientationPortraitUpsideDown:
            CGContextRotateCTM(context, CC_DEGREES_TO_RADIANS(180));
            CGContextTranslateCTM(context, -displaySize.width, -displaySize.height);
            break;
        case UIDeviceOrientationLandscapeLeft:
            CGContextRotateCTM(context, CC_DEGREES_TO_RADIANS(-90));
            CGContextTranslateCTM(context, -displaySize.height, 0);
            break;
        case UIDeviceOrientationLandscapeRight:
            CGContextRotateCTM(context, CC_DEGREES_TO_RADIANS(90));
            CGContextTranslateCTM(context, displaySize.width * 0.5f, -displaySize.height);
            break;
        case UIDeviceOrientationUnknown:
            break;
        case UIDeviceOrientationFaceUp:
            break;
        case UIDeviceOrientationFaceDown:
            break;
    }

    CGContextDrawImage(context, CGRectMake(0.0f, 0.0f, displaySize.width, displaySize.height), iref);
    CGImageRef imageRef = CGBitmapContextCreateImage(context);
    UIImage *outputImage = [UIImage imageWithCGImage:imageRef];

    //Dealloc
    CGImageRelease(imageRef);
    CGDataProviderRelease(provider);
    CGImageRelease(iref);
    CGColorSpaceRelease(colorSpaceRef);
    CGContextRelease(context);
    free(buffer);
    free(pixels);

    return outputImage;
}

我缺少什么?

推荐答案

您的代码正在游戏循环的更新过程中运行。

Your code is running during the update process of the game loop.

屏幕截图获取用于创建UIImage的当前像素。

The screenshot is getting the current pixels to use to create the UIImage.

当你告诉树不可见或者零不透明度,在下一个绘图循环之前不会生效。

When you tell the tree to not be visible or have zero opacity, that will not take effect until the next draw cycle.

要解决您的问题,您需要隐藏树,执行绘制循环,然后在下一次更新捕获框架与树不显示。

To fix your problem, you need to hide the tree, do a draw cycle, and then in the next update capture the frame with the tree not showing.

有意义吗?

这篇关于Cocos2D 2.0 - 截图捕获期间的奇怪行为的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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