iPhone回る色環

カラーサークルに紐をつけたかんじで回してみるiPhoneアプリのサンプルコードを描いてみます。

import UIKit

import SpriteKit

class ViewController: UIViewController, SKSceneDelegate {

    weak var scene : SKScene?

    weak var select : SKNode?

    

    override func viewDidLoad() {

        super.viewDidLoad()

        self.setupScene()

        self.createCircle()

    }

    func setupScene() {

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

        let scene = SKScene(size: spriteView.bounds.size)

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

        scene.delegate = self

        spriteView.presentScene(scene)

        

        self.view.addSubview(spriteView)

        self.scene = scene

    }

    

    func createCircle() {

        

        let o = CGPoint(x:CGRectGetMidX(self.view.bounds), y:CGRectGetMidY(self.view.bounds))

        let r = o.x * 0.8

        let basecircle = SKShapeNode()

        basecircle.name = “base”

        basecircle.position = o

        basecircle.fillColor = UIColor.clearColor()

        basecircle.strokeColor = UIColor.whiteColor()

        basecircle.lineWidth = 1;

        self.scene?.addChild(basecircle)

        

        let r2 = CGFloat(M_PI) * r / 22.0

        for i in 0..<20 {

            

            let angle = CGFloat(i) * CGFloat(M_PI) / 10.0

            let x = r * cos(angle)

            let y = r * sin(angle)

            

            let c = SKShapeNode(circleOfRadius: r2)

            c.name = “circle”

            c.position = CGPoint(x: x, y: y)

            c.fillColor = UIColor(hue: CGFloat(i) * 0.05, saturation: 0.3, brightness: 1, alpha: 1)

            c.userData = [“angle”: angle, “origin”: angle]

            basecircle.addChild(c)

        }

    }

    

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

        

        if let base = self.scene?.childNodeWithName(“base”) {

            let p = touches.anyObject()!.locationInNode(base)

            let hit = base.nodeAtPoint(p)

            if hit.name == “circle” {

                self.select = hit

            } else {

                self.select = nil

            }

        }

    }

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

        

        if let base = self.scene?.childNodeWithName(“base”) as? SKShapeNode {

            if self.select == nil {

                

                base.enumerateChildNodesWithName(“circle”, usingBlock: {

                    let origin = $0.0.userData![“origin”] as CGFloat

                    let angle = $0.0.userData![“angle”] as CGFloat

                    if fabs(origin angle) > 0.1 {

                        let d : CGFloat = origin > angle ? 0.1 : 0.1

                        self.moveAtAngle(angle + d, node: $0.0)

                    } else {

                        self.moveAtAngle(origin, node: $0.0)

                    }

                })

                

            } else {

                let selectedAngle = self.select!.userData![“origin”] as CGFloat

                base.enumerateChildNodesWithName(“circle”, usingBlock: {

                    let angle = $0.0.userData![“angle”] as CGFloat

                    if fabs(selectedAngle angle) > 0.1 {

                        let d : CGFloat = selectedAngle > angle ? 0.1 : 0.1

                        self.moveAtAngle(angle + d, node: $0.0)

                    } else {

                        self.moveAtAngle(selectedAngle, node: $0.0)

                    }

                })

            }

            

            base.path = nil

            let r = CGRectGetMidX(self.view.bounds) * 0.8

            let basepath = UIBezierPath(arcCenter: CGPointZero, radius: r, startAngle: 0, endAngle: 2.0 * CGFloat(M_PI), clockwise: false)

            for (i, c) in enumerate(base.children) {

                let connect = base.children[(i + 3) % 20] as SKNode

                let path = UIBezierPath()

                path.moveToPoint(c.position)

                path.addQuadCurveToPoint(connect.position, controlPoint: CGPointZero)

                basepath.appendPath(path)

            }

            base.path = basepath.CGPath

        }

    }

    

    func moveAtAngle(angle : CGFloat, node : SKNode) {

        let r = CGRectGetMidX(self.view.bounds) * 0.8

        let x = r * cos(angle)

        let y = r * sin(angle)

        node.userData![“angle”] = angle

        node.position = CGPoint(x: x, y: y)

    }

}