ios7 - ¿Cómo presento UIViewController de SKscene con el marco social?
sprite-kit flappy-bird-clone (1)
Estoy haciendo un juego como Flappy Bird. ¿Cómo presento un UIViewController de SKScene? Antes que nada, le digo a mis entornos
- Mac OS X 10.9
- Xcode 5.0.2
- Sprite Kit (framework), social.framework (framework) se agregan a mi proyecto
Mi objetivo es mostrar un botón "Compartir" en Game Over. Tocando la imagen del botón compartir debe presentar un SLComposeViewController (Twitter Share). El contenido de la escena no debería cambiar.
Me gustaría resolver un problema a continuación y cambiar la visualización de GameOverScene a tweetSheet (visualización) compuesta con social.framework.
La cuestión
[self presentViewController:tweetSheet animated:YES completion:nil];
//Error:No visible @interface for ''GameOverScene'' declares the selector "presentViewController":animated:completion:
Mis archivos de codificación están debajo (extraje partes de códigos importantes).
ViewController.h
import <UIKit/UIKit.h>
import <SpriteKit/SpriteKit.h>
import <iAd/iAd.h>
@interface ViewController : UIViewController<ADBannerViewDelegate><br>
@end
GameOverScene.h
#import <SpriteKit/SpriteKit.h>
@class SpriteViewController;
@interface GameOverScene : SKScene {
}
@end
GameOverScene.m
#import "GameOverScene.h"
#import "NewGameScene.h"
#import "MainScene.h"
#import <Social/Social.h>
@implementation GameOverScene {
//The twitter button
SKSpriteNode *_twitterbutton;
}
- (id)initWithSize:(CGSize)size
{
if (self = [super initWithSize:size]) {
//Creating the twitterbutton with the twitterbutton image from Images.xcassets
_twitterbutton = [SKSpriteNode spriteNodeWithImageNamed:@"twitterbutton"];
[_twitterbutton setSize:CGSizeMake(50, 50)];
[_twitterbutton setPosition:CGPointMake(self.size.width/2, self.size.height/5 + 50)];
//Adding the twitter button
[self addChild:_twitterbutton];
//Again, this is important, otherwise we can''t identify what button is pressed
_twitterbutton.name = @"twitterbutton";
[_twitterbutton setPosition:CGPointMake(self.size.width/2, self.size.height/5 + 50)]
}
return self;
}
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event
{
//Same as in NewGameScene menu
UITouch *touch = [touches anyObject];
CGPoint location = [touch locationInNode:self];
SKNode *node = [self nodeAtPoint:location];
//Is the twitter button touched?
if([node.name isEqualToString:@"twitterbutton"]){
if ([SLComposeViewController isAvailableForServiceType:SLServiceTypeTwitter]){
SLComposeViewController *tweetSheet = [SLComposeViewController composeViewControllerForServiceType:SLServiceTypeTwitter];
[tweetSheet setInitialText:@"TestTweet from the Game !!"];
[self presentViewController:tweetSheet animated:YES completion:nil];
**//Error:No visible @interface for ''GameOverScene'' declares the selector "presentViewController":animated:completion:**
}
}
ViewControlloer.m
#import "ViewController.h"
#import "NewGameScene.h"
@implementation ViewController
//Loads the view onto our main class
- (void)loadView
{
self.view = [[SKView alloc] initWithFrame:[[UIScreen mainScreen] applicationFrame]];
}
//Executes when view finishes loading
- (void)viewWillLayoutSubviews
{
[super viewDidLoad];
//Set the resize mode to flexible width and height
[self.view setAutoresizingMask:UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight];
//Create our view from our original view
//Make sure to leave originalContentView in, otherwise the app will crash
SKView *skView = (SKView *)self.originalContentView;
//We create a new NewGameScene according to the current dimensions
SKScene *scene = [NewGameScene sceneWithSize:skView.bounds.size];
//Create a transition class with animation type fade and a duration of .4 seconds
SKTransition *transition = [SKTransition fadeWithDuration:.4];
//Present the menu view (NewGameScene) with our fade in transition
[skView presentScene:scene transition:transition];
}
@end
No puede presentar un viewController dentro de un SKScene, ya que en realidad solo se representa en un SKView. Necesita una forma de enviar un mensaje a viewController, que a su vez presentará viewController. Para esto, puedes usar la delegación .
Agregue la siguiente definición de protocolo al archivo .h de su SKScene:
@protocol sceneDelegate <NSObject>
-(void)showShareScreen;
@end
Y declare una propiedad de delegado en la interfaz:
@property (weak, nonatomic) id <sceneDelegate> delegate;
Luego, en el punto donde desea presentar la pantalla de compartir, en lugar de la línea:
[self presentViewController:tweetSheet animated:YES completion:nil];
Usa esta linea:
[self.delegate showShareScreen];
Ahora, en el archivo .h de viewController, implemente el protocolo:
@interface ViewController : UIViewController <sceneDelegate>
Y, en su archivo .m, agregue la siguiente línea antes de presentar la escena:
scene.delegate = self;
A continuación, agregue el siguiente método allí:
-(void)presentShareScreen
{
if ([SLComposeViewController isAvailableForServiceType:SLServiceTypeTwitter])
{
SLComposeViewController *tweetSheet = [SLComposeViewController
composeViewControllerForServiceType:SLServiceTypeTwitter];
[tweetSheet setInitialText:@"TestTweet from the Game !!"];
[self presentViewController:tweetSheet animated:YES completion:nil];
}
}
Un método alternativo sería usar NSNotificationCenter
Guarde el método de -presentShareScreen
como se describe en la alternativa anterior.
Agregue viewController como un oyente a la notificación en su método -viewDidLoad
:
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(presentShareScreen) name:@"showShareScreen" object:nil];
Luego, en la escena en el punto donde quieres mostrar este viewController, usa esta línea:
[[NSNotificationCenter defaultCenter] postNotificationName: @ objeto "showShareScreen": nil];