iPhone坂道ビルダー

坂道をつくって車をゴールに向かわせるiPhoneアプリのサンプルコードを描いてみます。

import UIKit

import SpriteKit

class ViewController: UIViewController, SKSceneDelegate {

    weak var scene : SKScene?

    weak var selectObj : SKNode?

    

    override func viewDidAppear(animated: Bool) {

        super.viewDidAppear(animated)

        

        self.setupScene()

        self.createObjects()

        self.createCar()

    }

    func setupScene() {

        var spriteView = SKView(frame: self.view.bounds)

        var scene = SKScene(size: spriteView.frame.size)

        scene.backgroundColor = UIColor(hue: 0.15, saturation: 0.5, brightness: 0.5, alpha: 1)

        spriteView.presentScene(scene)

        self.view.addSubview(spriteView)

        

        self.scene = spriteView.scene

        self.scene?.physicsBody = SKPhysicsBody(edgeLoopFromRect: self.view.bounds)

        self.scene?.delegate = self

    }

    

    func createObjects() {

        var triangle = { (o : CGPoint) -> SKNode in

            let path = UIBezierPath()

            for p in [CGPoint(x: –30, y: –30), CGPoint(x: 30, y: 30), CGPoint(x: 30, y: –30)] {

                if(p.x ==30) { path.moveToPoint(p) }

                else { path.addLineToPoint(p) }

            }

            var triangle = SKShapeNode(path: path.CGPath)

            triangle.name = “object”

            triangle.fillColor = UIColor(hue: 0.2, saturation: 0.3, brightness: 0.8, alpha: 1)

            triangle.position = o

            self.scene?.addChild(triangle)

            

            triangle.physicsBody = SKPhysicsBody(polygonFromPath: path.CGPath)

            triangle.physicsBody?.friction = 0.8

            return triangle

        }

        

        var box = { (o:CGPoint) -> SKNode in

            var rectangle = SKSpriteNode(color: UIColor(hue: 0.3, saturation: 0.3, brightness: 0.8, alpha: 1), size: CGSize(width: 60, height: 60))

            rectangle.name = “object”

            rectangle.position = o

            self.scene?.addChild(rectangle)

            

            rectangle.physicsBody = SKPhysicsBody(rectangleOfSize: rectangle.size)

            return rectangle

        }

        

        var checker = SKSpriteNode(color: UIColor.whiteColor(), size: CGSizeMake(120, 60))

        checker.position = CGPoint(x: CGRectGetMaxX(self.view.bounds) 80.0, y: 180.0)

        checker.name = “checker”

        self.scene?.addChild(checker)

        for i in 0..<32 {

            if (i + i / 8) % 2 == 0 {continue}

            var n = SKSpriteNode(color:UIColor.blackColor(), size:CGSize(width: 16.0, height: 16.0))

            n.position = CGPoint(x: (i%8) * 1552, y: (i/8) * 1522)

            checker.addChild(n)

        }

        

        triangle(CGPoint(x: 250, y: 50))

        triangle(CGPoint(x: 370, y: 80))

        triangle(CGPoint(x: 420, y: 150))

        box(CGPoint(x: 450, y: 80))

        box(CGPoint(x: 450, y: 150))

        box(CGPoint(x: 200, y: 100))

        box(CGPoint(x: 250, y: 160))

    }

    

    func createCar() {

        var car = SKSpriteNode(color: UIColor.redColor(), size: CGSize(width: 40, height: 20))

        car.name = “car”

        car.position = CGPoint(x: 50, y: 50)

        car.physicsBody = SKPhysicsBody(rectangleOfSize: car.size)

        self.scene?.addChild(car)

        

        for i in 0..<2 {

            var tire = SKShapeNode(circleOfRadius: 10)

            tire.name = “tire”

            tire.position = CGPoint(x: –20 + i*40 , y: –10)

            tire.fillColor = UIColor.blackColor()

            car.addChild(tire)

            

            tire.physicsBody = SKPhysicsBody(circleOfRadius: 10)

            tire.physicsBody?.friction = 0.8

            var joint = SKPhysicsJointPin.jointWithBodyA(car.physicsBody, bodyB: tire.physicsBody, anchor: CGPoint(x:30 + i*40, y:40))

            self.scene?.physicsWorld.addJoint(joint)

        }

    }

    

    func update(currentTime: NSTimeInterval, forScene scene: SKScene) {

        self.scene?.enumerateChildNodesWithName(“car”, usingBlock: { (n, b) -> Void in

            let car : SKNode = n

            for ch in [car.children[0], car.children[1]] {

                let tire : SKNode = ch as SKNode

                if tire.physicsBody?.velocity.dx < 5 {

                    car.physicsBody?.velocity =  CGVectorMake(35, car.physicsBody!.velocity.dy)

                    tire.physicsBody?.applyTorque(-100)

                }

            }

        })

    }

    

    override func touchesBegan(touches: NSSet, withEvent event: UIEvent) {

        var p = touches.anyObject()!.locationInNode(self.scene)

        self.scene?.enumerateChildNodesWithName(“object”, usingBlock: { (n :SKNode!, b:UnsafeMutablePointer<ObjCBool>) -> Void in

            if n.containsPoint(p) {

                n.physicsBody?.dynamic = false

                self.selectObj = n

            }

        })

    }

    override func touchesMoved(touches: NSSet, withEvent event: UIEvent) {

        var p = touches.anyObject()!.locationInNode(self.scene)

        if let node = self.selectObj {

            node.position = p

        }

    }

    

    override func touchesEnded(touches: NSSet, withEvent event: UIEvent) {

        if let node = self.selectObj {

            node.physicsBody?.dynamic = true

        }

    }

}