iPhoneカラー格子

色をつけた点をジョイントで結んでプラプラさせて遊ぶiPhoneアプリのサンプルコードを描いてみます。

動かすとこんなんです。

サンプルコード

#import “ViewController.h”

#import <SpriteKit/SpriteKit.h>

@interface JointScene : SKScene

@property (nonatomic, weak) SKNode *selected;

@end

@implementation JointScene

– (void)didMoveToView:(SKView *)view

{

    [self createSceneContents];

}

– (void)createSceneContents

{

    [self createWall];

    [self createNodes];

    [self createJoints];

}

– (void)createWall

{

    SKSpriteNode *wall = [SKSpriteNode spriteNodeWithColor:[SKColor clearColor] size:self.size];

    wall.name = @”wall”;

    [self addChild:wall];

    wall.physicsBody = [SKPhysicsBody bodyWithEdgeLoopFromRect:self.frame];

}

– (void)createNodes

{

    UIBezierPath *path = [UIBezierPath bezierPathWithOvalInRect:CGRectMake(-5, –5, 10, 10)];

    

    for (int i=0; i< 100; i++) {

        SKShapeNode *n = [SKShapeNode node];

        n.path = path.CGPath;

        float x = (i % 10) * 20 + 60;

        float y = (i / 10) * 20 + 100;

        n.position = CGPointMake(x, y);

        n.name = [@(i) stringValue];

        n.strokeColor = [SKColor colorWithHue:i/100.0 saturation:0.7 brightness:1.0 alpha:1];

        n.fillColor = n.strokeColor;

        [self addChild:n];

        

        n.physicsBody = [SKPhysicsBody bodyWithCircleOfRadius:10];

    }

}

– (void)createJoints

{

    for (int i=0; i< 90; i++) {

        // horizontal

        int index = (i % 9) + (i / 9) * 10;

        SKNode *na = [self childNodeWithName:[@(index) stringValue]];

        SKNode *nb = [self childNodeWithName:[@(index + 1) stringValue]];

        SKPhysicsJointSpring *spring = [SKPhysicsJointSpring jointWithBodyA:na.physicsBody bodyB:nb.physicsBody anchorA:na.position anchorB:nb.position];

        [self.physicsWorld addJoint:spring];

        SKPhysicsJointSpring *l = [SKPhysicsJointSpring jointWithBodyA:na.physicsBody bodyB:nb.physicsBody anchorA:na.position anchorB:nb.position];

        l.frequency = 10000;

        [self.physicsWorld addJoint:l];

        

        

        // vertical

        int vindex = (i % 10) + (i / 10) * 10;

        SKNode *vna = [self childNodeWithName:[@(vindex) stringValue]];

        SKNode *vnb = [self childNodeWithName:[@(vindex + 10) stringValue]];

        SKPhysicsJointSpring *vspring = [SKPhysicsJointSpring jointWithBodyA:vna.physicsBody bodyB:vnb.physicsBody anchorA:vna.position anchorB:vnb.position];

        [self.physicsWorld addJoint:vspring];

        

        SKPhysicsJointSpring *vl = [SKPhysicsJointSpring jointWithBodyA:vna.physicsBody bodyB:vnb.physicsBody anchorA:vna.position anchorB:vnb.position];

        vl.frequency = 10000;

        [self.physicsWorld addJoint:vl];

    }

}

– (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event

{

    CGPoint p = [[touches anyObject] locationInNode:self];

    SKNode *wall = [self childNodeWithName:@”wall”];

    

    [self.children enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {

        if (obj != wall && [obj containsPoint:p]) {

            self.selected = obj;

            self.selected.physicsBody.dynamic = NO;

        }

    }];

}

– (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event

{

    CGPoint p = [[touches anyObject] locationInNode:self];

    

    SKAction *move = [SKAction moveTo:p duration:0.01];

    [self.selected runAction:move];

}

– (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event

{

    self.selected.physicsBody.dynamic = YES;

    self.selected = nil;

}

@end

@interface ViewController ()

@end

@implementation ViewController

– (void)viewDidLoad

{

    [super viewDidLoad];

    

    SKView *spriteView = [[SKView alloc] initWithFrame:self.view.bounds];

    [self.view addSubview:spriteView];

    

    SKScene *scene = [[JointScene alloc] initWithSize:spriteView.frame.size];

    [spriteView presentScene:scene];

}

– (void)didReceiveMemoryWarning

{

    [super didReceiveMemoryWarning];

    // Dispose of any resources that can be recreated.

}

@end