iPhoneたつまき

たつまきみたいにブロックをクルクルまわすiPhoneアプリのサンプルコードを描いてみます。

import UIKit

import SceneKit

class ViewController: UIViewController, SCNSceneRendererDelegate {

    weak var sceneView : SCNView?

    

    override func viewDidLoad() {

        super.viewDidLoad()

        setupScene()

        createField()

        createBlocks()

        createCamera()

    }

    func setupScene() {

        let sv = SCNView(frame: view.bounds)

        sv.scene = SCNScene()

        sv.delegate = self

        view.addSubview(sv)

        

        sceneView = sv

    }

    

    func createField() {

        let box = SCNBox(width: 20, height: 20, length: 20, chamferRadius: 0)

        box.firstMaterial?.diffuse.contents = UIColor.blueColor().colorWithAlphaComponent(0.1)

        let boxNode = SCNNode(geometry: box)

        boxNode.physicsField = SCNPhysicsField.vortexField()

        boxNode.physicsField?.strength = 1

        sceneView?.scene?.rootNode.addChildNode(boxNode)

    }

    

    func createBlocks() {

        

        let b = SCNBox(width: 10, height: 10, length: 10, chamferRadius: 0)

        b.firstMaterial?.diffuse.contents = UIColor(hue: CGFloat(arc4random_uniform(10)) * 0.1, saturation: 0.2, brightness: 1, alpha: 1)

        let bnode = SCNNode(geometry: b)

        bnode.position = SCNVector3(x: Float(arc4random_uniform(80)) – 40, y: 100, z: Float(arc4random_uniform(80)) – 40)

        bnode.physicsBody = SCNPhysicsBody.dynamicBody()

        bnode.physicsBody?.damping = 0.4

        bnode.physicsBody?.applyForce(SCNVector3(x: 0, y: –70, z: 0), impulse: true)

        self.sceneView?.scene?.rootNode.addChildNode(bnode)

        delay(10.0) {

            bnode.removeFromParentNode()

        }

    }

    

    func createCamera() {

        let camera = SCNNode()

        camera.camera = SCNCamera()

        camera.camera?.zFar = 600

        camera.position = SCNVector3(x: 0, y: 0, z: 200)

        sceneView?.scene?.rootNode.addChildNode(camera)

    }

    

    var lasttime = 0.0

    func renderer(aRenderer: SCNSceneRenderer, updateAtTime time: NSTimeInterval) {

        if (time – lasttime > 0.05) {

            lasttime = time

            self.createBlocks()

        }

    }

}

extension Array {

    func each(doit:T -> Void) { for i in self {doit(i)} }

}

func delay (delay:Double, doit:() -> Void) {

    dispatch_after(dispatch_time(DISPATCH_TIME_NOW, Int64(delay * Double(NSEC_PER_SEC))), dispatch_get_main_queue(), doit)

}