画面真ん中らへんにあるスイッチにボールをぶつけてドアを開けるといった、iPhoneアプリのサンプルコードを描いてみます。
#import “ViewController.h”
@import SpriteKit;
@interface DoorScene : SKScene <SKPhysicsContactDelegate>
@property (nonatomic) BOOL start;
@end
@implementation DoorScene
– (void)didMoveToView:(SKView *)view
{
self.backgroundColor = [UIColor lightGrayColor];
self.physicsWorld.contactDelegate = self;
self.physicsBody = [SKPhysicsBody bodyWithEdgeLoopFromRect:self.frame];
self.physicsBody.restitution = 1.0;
[self createSwitch];
[self createJumper];
[self createDoor];
}
– (void)createSwitch
{
SKSpriteNode *shelf = [SKSpriteNode spriteNodeWithColor:[SKColor brownColor] size:CGSizeMake(50, 15)];
shelf.position = CGPointMake(160, CGRectGetMaxY(self.frame) – 150);
shelf.zPosition = 1;
[self addChild:shelf];
shelf.physicsBody = [SKPhysicsBody bodyWithRectangleOfSize:shelf.size];
shelf.physicsBody.dynamic = NO;
SKSpriteNode *btn = [SKSpriteNode spriteNodeWithColor:[SKColor redColor] size:CGSizeMake(40, 30)];
btn.name = @”btn”;
btn.position = CGPointMake(shelf.position.x, shelf.position.y + 15);
btn.zPosition = 0;
[self addChild:btn];
SKAction *flash = [SKAction repeatActionForever:[SKAction sequence:@[[SKAction fadeAlphaTo:0.7 duration:0.5], [SKAction fadeAlphaTo:1.0 duration:0.5]]]];
[btn runAction:flash];
}
– (void)createJumper
{
UIBezierPath *path = [UIBezierPath bezierPathWithArcCenter:CGPointZero radius:15 startAngle:0 endAngle:2.0*M_PI clockwise:NO];
SKShapeNode *jumper = [SKShapeNode node];
jumper.name = @”jumper”;
jumper.path= path.CGPath;
jumper.position = CGPointMake(160, 200);
jumper.fillColor = [SKColor blackColor];
jumper.zPosition = 4;
[self addChild:jumper];
jumper.physicsBody = [SKPhysicsBody bodyWithCircleOfRadius:15];
jumper.physicsBody.linearDamping = 0;
jumper.physicsBody.angularDamping = 0;
jumper.physicsBody.friction = 0;
jumper.physicsBody.restitution = 1.0;
jumper.physicsBody.categoryBitMask = 0x1;
jumper.physicsBody.contactTestBitMask = 0x2;
}
– (void)createDoor
{
for (int i=0; i<2; i++) {
UIBezierPath *path = [UIBezierPath bezierPathWithArcCenter:CGPointZero radius:20 startAngle:M_PI * 0.3 endAngle:M_PI * 1.3 clockwise:i];
SKShapeNode *medal = [SKShapeNode node];
medal.path = path.CGPath;
medal.fillColor = i ? [SKColor colorWithRed:0.95 green:0.95 blue:0 alpha:1] : [SKColor colorWithRed:0.9 green:0.9 blue:0 alpha:1];
medal.strokeColor = [SKColor yellowColor];
medal.position = CGPointMake(280, 30);
medal.zPosition = 1;
[self addChild:medal];
SKSpriteNode *ribbon = [SKSpriteNode spriteNodeWithColor:i ? [SKColor colorWithRed:0 green:0.9 blue:0 alpha:1] : [SKColor colorWithRed:0 green:0.8 blue:0 alpha:1] size:CGSizeMake(20, 40)];
ribbon.position = CGPointMake(i ? 270 : 290 , 60);
ribbon.zRotation = i ? M_PI * 0.1 : – M_PI * 0.1;
ribbon.zPosition = 0;
[self addChild:ribbon];
}
SKNode *door = [SKNode node];
door.name = @”door”;
door.position = CGPointMake(280, 40);
door.zPosition = 3;
for (int i=0; i<5; i++) {
SKSpriteNode *n = [SKSpriteNode spriteNodeWithColor:[SKColor darkGrayColor] size:CGSizeMake(5, 80)];
n.position = CGPointMake(i * 13 – 26, 0);
[door addChild:n];
}
for (int i=0; i<2; i++) {
SKSpriteNode *n = [SKSpriteNode spriteNodeWithColor:[SKColor darkGrayColor] size:CGSizeMake(60, 5)];
n.position = CGPointMake(0, i ? –40 : 40);
[door addChild:n];
}
[self addChild:door];
}
– (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event
{
if (!self.start) {
self.start = YES;
SKNode *jumper = [self childNodeWithName:@”jumper”];
[jumper.physicsBody applyImpulse:CGVectorMake(15.0, 0)];
return;
}
CGPoint p = [[touches anyObject] locationInNode:self];
SKSpriteNode *block = [SKSpriteNode spriteNodeWithColor:[SKColor brownColor] size:CGSizeMake(60, 5)];
block.name = @”block”;
block.position = p;
[self addChild:block];
block.physicsBody = [SKPhysicsBody bodyWithRectangleOfSize:block.size];
block.physicsBody.dynamic = NO;
block.physicsBody.friction = 0;
block.physicsBody.categoryBitMask = 0x2;
}
– (void)update:(NSTimeInterval)currentTime
{
SKNode *jumper = [self childNodeWithName:@”jumper”];
SKNode *btn = [self childNodeWithName:@”btn”];
SKNode *door = [self childNodeWithName:@”door”];
float ux = fabs(jumper.physicsBody.velocity.dx);
float uy = fabs(jumper.physicsBody.velocity.dx);
if (ux > 80) {
jumper.physicsBody.velocity = CGVectorMake(80 * jumper.physicsBody.velocity.dx/ux, jumper.physicsBody.velocity.dy);
} else if (uy > 80) {
jumper.physicsBody.velocity = CGVectorMake(jumper.physicsBody.velocity.dx, 80 * jumper.physicsBody.velocity.dy/uy);
}
if ([btn intersectsNode:jumper]) {
// clear!!
if (jumper.physicsBody) {
[btn runAction:[SKAction moveByX:0 y:-20 duration:0.5]];
[door runAction:[SKAction moveByX:0 y:80 duration:1.5]];
}
jumper.physicsBody = nil;
}
}
– (void)didBeginContact:(SKPhysicsContact *)contact
{
if([contact.bodyA.node.name isEqual:@”block”]) {
[contact.bodyB applyImpulse:CGVectorMake(0, 2.0)];
}
}
@end
@interface ViewController ()
@end
@implementation ViewController
– (void)viewDidLoad
{
[super viewDidLoad];
SKView *spriteView = [[SKView alloc] initWithFrame:self.view.bounds];
[self.view addSubview:spriteView];
SKScene *scene = [[DoorScene alloc] initWithSize:spriteView.frame.size];
[spriteView presentScene:scene];
}
@end