UIViewController以一种奇怪的方式释放我的Cocos2d场景

时间:2011-10-07 17:39:17

标签: iphone cocos2d-iphone

我有一个Cocos2d游戏场景加载了由UIViewController加载的EAGLView,但当我将游戏场景退回到UIKit菜单时,我的游戏场景正在以一种奇怪的方式解除分配。我想如果我在没有将它与UIKit结合的情况下将游戏纯粹放在Cocos2d中,那么这种情况就不会发生。如果我在UIViewController弹出时调用CCDirector上的暂停,我发现如果我想重新进入游戏场景,UIViewController将再次加载,只需恢复CCDirector就会显示一个带有OpenGL错误的空白屏幕。如果尝试[[CCDirector sharedDirector] runWithScene]它说如果一个场景已经在运行,我就不能这样做,但是如果我尝试使用replaceScene,它会说一个dealloc消息(对于一个CCSprite,不知道哪一个)被发送到一个解除分配的实例。以下是我的一些代码:

- (void)viewDidLoad {
    [super viewDidLoad];
    glView = [EAGLView viewWithFrame:self.view.bounds
                         pixelFormat:kEAGLColorFormatRGB565 // kEAGLColorFormatRGBA8
                         depthFormat:0                        // GL_DEPTH_COMPONENT16_OES
              ];
    glView.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight;
    [self.view insertSubview:glView atIndex:0];
    [[CCDirector sharedDirector] setOpenGLView:glView];

    if (![[CCDirector sharedDirector] runningScene]) {
        CCScene *scene = [GameLayer scene];
        [[CCDirector sharedDirector] runWithScene:scene];
    }
    else {
        [self.view insertSubview:[[CCDirector sharedDirector] openGLView] atIndex:0];
        [[CCDirector sharedDirector] resume];    // Pause is in viewWillDisappear

        // If I replace resume with below, I get message sent to deallocated instance
        [[CCDirector sharedDirector] replaceScene:scene];
    }
}

如果我这样运行,我会在glDrawElements(GL_TRIANGLES, (GLsizei) n*6, GL_UNSIGNED_SHORT, (GLvoid*)(start*6*sizeof(indices_[0])));

的行中的CCTextureAtlas中获得EXC_BAD_ACCESS

如果我在没有重新初始化glview的情况下运行它,只是第一次初始化,如if (![[CCDirector sharedDirector]openGLView]) initialize,我得到一个空白屏幕,并且 - [EAGLView swapBuffers]中的OpenGL错误0x0506。

我如何在不做太多扭曲的情况下保留我的场景,或者干净地释放我的场景以便我可以用[[CCDirected sharedDirector] runWithScene]重新加载它?

2 个答案:

答案 0 :(得分:1)

你如何“退出现场”?这将是更有趣的代码。

以下是我发现您发布的代码的奇怪内容:

- (void)viewDidLoad {
    … 

    if (![[CCDirector sharedDirector] runningScene]) {
        ...
    }
    else {
        // Where does this scene variable come from?
        [[CCDirector sharedDirector] replaceScene:scene];
    }
}

通常,当您运行replaceScene时,您将提供一个新场景。您可能尝试使用同一场景替换剧场,该场景也是当前正在运行的场景。这肯定会让cocos2d崩溃。如果要重新显示相同的场景,请不要调用replaceScene或重新创建场景。

您还需要检查当前运行的场景是否未释放。在场景的dealloc方法中设置断点。如果它deallocs你可能会因为误解你必须从内存中擦除cocos2d场景而感到沮丧。你不应该这样做,我相信cocos2d总是希望在你调用runWithScene之后至少有一个正在运行的场景。

对于它的价值,您将需要使用startAnimation和stopAnimation而不是暂停和恢复。这将完全停止Cocos2D而不释放场景,因此它的工作方式与暂停/恢复相同。我的猜测是内部它完全关闭游戏循环,而暂停/恢复使其以非常慢的速度运行,即如果我没记错的话,则为4 fps。

我遇到暂停/恢复会导致“[EAGLView swapBuffers]中的OpenGL错误0x0506”并且startAnimation / stopAnimation会解决此问题的情况。

答案 1 :(得分:1)

你怎么离开现场电话

[[CCDirector SharedDirector]end];

这将调用Director上的许多方法,使您能够毫无问题地重新进入场景。