我有两个 UIViewControllers。用户从UIViewController开始。然后用户点击一个按钮来玩游戏。因此应用程序继续切换到另一个视图控制器PlayViewController ,它显示了使用SKView进行的游戏。而ActionScene是负责游戏玩法的SKScene子类。当用户失败时,应用程序会显示一个标签(SKLabelNode)并询问他或她是否想退出游戏。如果用户点击这个标签,玩家将通过 PlayViewController 回到主视图控制器(UIViewController)。所以我认为 ActionScene 应该将此任务委托给 PlayViewController。以下来自ActionScene。
// ActionScene.h
#import <SpriteKit/SpriteKit.h>
@protocol actionDelegate;
@interface ActionScene : SKScene
@property (weak) id <actionDelegate> delegate;
@end
@protocol actionDelegate <NSObject>
@required
// Delegate
- (void)closeScene;
@end
// ActionScene.m
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event {
for (UITouch *touch in touches) {
SKNode *n = [self nodeAtPoint:[touch locationInNode:self]];
if (n != self && [n.name isEqual: @"doneLabel"]) { // It was else if before. I've made a change.
[[self childNodeWithName:@"doneLabel"] removeFromParent]; // The user chooses to end the game by tapping doneLabel (SKLabelNode)
[self.delegate closeScene];
}
}
}
至于 PlayViewController,它负责将 ActionScene 呈现给 SKView,并将用户返回给 UIViewController,如下所示。
// PlayViewController.h
#import "ActionScene.h"
@interface PlayViewController : UIViewController <actionDelegate>
@property (strong,nonatomic) ActionScene *actionScene;
@end
// PlayViewController.m
- (void)viewWillLayoutSubviews {
SKView *spriteView = [[SKView alloc] initWithFrame:self.view.bounds];
[self.view addSubview:spriteView];
SKScene *scene = [[ActionScene alloc] initWithSize:spriteView.frame.size];
[self.actionScene setDelegate:self]; // Letting ActionScene delegate a task to itself
[spriteView presentScene:scene];
}
- (void)closeScene {
// It doesn't get a call from ActionScene
}
所以当用户点击 done 标签时,closeScene 被设计为启动。但是这个委托方法永远不会被调用。在过去的 9 个月里,我没有开发过 iOS 应用程序。但我认为我的想法是正确的。我究竟做错了什么?到目前为止,我已经阅读了这个主题、这个主题和其他主题。
感谢您的帮助。
// 补充说明 //
- 在用户点击 doneLabel 之前,所有操作都会被删除。
- 游戏应用程序将进入 touchBegan。然而,它会跳过 [spriteView presentScene:scene] 行。