8

I'm trying to set up a simple Sprite Kit setup. All I'm doing is re-creating the default xCode template 'Sprite Kit Game' from an 'Empty Application'.

It keeps crashing on the skView.showsFPS = YES; line. Which I can't explain. Can you? Thanks!

Some code:

AppDelegate.m

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:    (NSDictionary *)launchOptions
{
  self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
  MenuController *menuController = [[MenuController alloc] init];
  self.window.rootViewController = menuController;
  [self.window makeKeyAndVisible];
  return YES;
}

MenuController.m

- (void)viewDidLoad
{
  [super viewDidLoad];

  SKView *skView = (SKView *)self.view;
  skView.showsFPS = YES;
  skView.showsNodeCount = YES;

  MultiplayerView *gameView = [MultiplayerView sceneWithSize:skView.bounds.size];
  gameView.scaleMode = SKSceneScaleModeAspectFill;

  [skView presentScene:gameView];
}

When I launch this, the following error occurs:

2013-11-10 13:08:01.605 ByS[9419:70b] -[UIView setShowsFPS:]: unrecognized selector sent to instance 0x10c00bc60
2013-11-10 13:08:01.608 ByS[9419:70b] *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[UIView setShowsFPS:]: unrecognized selector sent to instance 0x10c00bc60'
Lapidus
  • 925
  • 1
  • 10
  • 16

4 Answers4

25

In the interface builder, change the class of the window's view to SKView. Type-casting a UIView into SKView won't do anything unless the UIView was previously obtained by casting a SKView.

Roshan
  • 1,937
  • 1
  • 13
  • 25
  • 1
    A good hint that this is the case is in the error: The class it lists is `UIView`, not `SKView`. In addition, the error is about the selector `setShowFPS:` not being recognized (which is implemented by SKView, but not its parent class UIView). – Kitsune Nov 10 '13 at 15:37
  • Thanks, but not using any storyboards here. So no interface builder. Anyway to do this in code? Thought it was the _SKView *skView = (SKView *)self.view;_ line.. – Lapidus Nov 11 '13 at 10:05
  • Re-created 'MenuController' with xib and changed the view to SKView. Perfectly working, thanks! Would be nice to avoid the xib though.. – Lapidus Nov 11 '13 at 10:12
  • 1
    If you are doing it by code, try creating an `SKView` and assigning it to the view controller's `view` property in the `init` method of the view controller. – Roshan Nov 12 '13 at 04:59
5

I had the same issue when starting from a single-view or empty application, vs the usual SpriteKit template. Mine worked when I added some code I found to overwrite the loadView method. Try putting it just above your viewDidLoad in your View Controller.

- (void)loadView {
    CGRect applicationFrame = [[UIScreen mainScreen] applicationFrame];
    SKView *skView = [[SKView alloc] initWithFrame:applicationFrame];
    self.view = skView;
}

The .h file is the usual UIViewController. And remember to #import after you have linked the framework!:

@interface CharacterViewController : UIViewController

So the full .m code would be something like:

@implementation CharacterViewController

- (void)loadView {
    CGRect applicationFrame = [[UIScreen mainScreen] applicationFrame];
    SKView *skView = [[SKView alloc] initWithFrame:applicationFrame];
    self.view = skView;
}


- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
{
    self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
    if (self) {
        // Custom initialization
    }
    return self;
}

- (void)viewDidLoad
{
    [super viewDidLoad];
    NSLog(@"CharacterViewController viewDidLoad");
    // Do any additional setup after loading the view.

    // Configure the view.
    SKView * skView = (SKView *)self.view;
    skView.showsFPS = YES;
    skView.showsNodeCount = YES;


    // Create and configure the scene.
    CharacterScene *character = [[CharacterScene alloc]initWithSize:CGSizeMake(skView.bounds.size.width, skView.bounds.size.height)];

    character.backgroundColor = [UIColor blueColor];

    [skView presentScene:character];

}
Mike Critchley
  • 1,643
  • 15
  • 20
1

Or you can fix it fast and dirty in prepareForSegue: or before any other presentation

-(void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender{
     UIViewController *destinationVC = segue.destinationViewController;
     SKView * skView = (SKView *)destinationVC.view;

    if (![skView isKindOfClass:[SKView class]]) {
        skView = [[SKView alloc] initWithFrame: skView.frame]; // self.view.bounds
        destinationVC.view = skView;
    }
}
Laszlo
  • 2,803
  • 2
  • 28
  • 33
0

In MenuController.m replace your initialisation

SKView *skView = (SKView *) self.view;

with

SKView *skView = [[SKView alloc initWithFrame : self.view.frame];
  • You just need to initialize object of SKView by giving frame of self.view not by assigning a reference object of self.view.
Sunil M.
  • 554
  • 5
  • 17