
キューブのどっかが光ったらそこをタッチするiPhoneアプリのサンプルコードを描いてみます。
import UIKit
import SceneKit
class ViewController: UIViewController {
weak var scene : SCNScene?
weak var sceneView : SCNView?
override func viewDidLoad() {
super.viewDidLoad()
self.view.backgroundColor = UIColor(hue: 0.3, saturation: 0.2, brightness: 0.8, alpha: 1)
self.setupScene()
self.createCamera()
self.createCube()
self.createUserConsole()
self.randomLight()
}
func setupScene() {
let w = CGRectGetMaxX(self.view.bounds)
let sv = SCNView(frame: CGRect(x: 0, y: 0, width: w, height: w))
sv.scene = SCNScene()
sv.backgroundColor = UIColor(hue: 0.3, saturation: 0.4, brightness: 0.2, alpha: 1)
self.view.addSubview(sv)
self.sceneView = sv;
self.scene = sv.scene
}
func createCamera() {
let camera = SCNNode()
camera.position = SCNVector3(x: 0, y: 0, z: 40)
camera.camera = SCNCamera()
self.scene?.rootNode.addChildNode(camera)
}
func createCube() {
let core = SCNBox(width: 20, height: 20, length: 20, chamferRadius: 1)
core.firstMaterial?.diffuse.contents = UIColor(hue: 0.3, saturation: 0, brightness: 0.9, alpha: 1)
let coreNode = SCNNode(geometry: core)
coreNode.name = “box”
self.scene?.rootNode.addChildNode(coreNode)
let d = Float (21.0 / 3.0)
for i in 0..<27 {
if i == 13 {
continue;
}
let x = Float(i%3) * d – d
let y = Float((i/3) % 3) * d – d
let z = Float(i/9) * d – d
let small = SCNBox(width: CGFloat(d*0.95), height: CGFloat(d*0.95), length: CGFloat(d*0.95), chamferRadius: 0.2)
small.firstMaterial?.diffuse.contents = UIColor(hue: 0.3, saturation: 0.5, brightness: 0.9, alpha: 0.8)
let smallNode = SCNNode(geometry: small)
smallNode.position = SCNVector3(x: x, y: y, z: z)
coreNode.addChildNode(smallNode)
}
}
func randomLight() {
if let box = self.scene?.rootNode.childNodeWithName(“box”, recursively: false) {
var seed = Int(arc4random()) % box.childNodes.count
let small = box.childNodes[seed] as SCNNode
small.geometry?.firstMaterial?.diffuse.contents = UIColor.yellowColor()
}
}
func createUserConsole() {
let names = [“Right”, “Down”, “Left”, “Up”]
let o = CGPoint(x: CGRectGetMidX(self.view.bounds), y: CGRectGetMaxY(self.view.bounds) * 3.0 / 4.0)
let r = CGRectGetMaxX(self.view.bounds) * 0.25
for (idx, name) in enumerate(names) {
let x = r * cos(CGFloat(idx) * CGFloat(M_PI) / 2.0) + o.x
let y = r * sin(CGFloat(idx) * CGFloat(M_PI) / 2.0) + o.y
let btn = UIButton.buttonWithType(.System) as UIButton
btn.titleLabel?.font = UIFont.boldSystemFontOfSize(30)
btn.setTitle(name, forState: .Normal)
btn.sizeToFit()
btn.center = CGPoint(x: x, y: y)
self.view.addSubview(btn)
btn.addTarget(self, action: “tapButton:”, forControlEvents: .TouchUpInside)
}
}
func tapButton(btn: UIButton) {
let name = btn.titleLabel!.text
var axis : SCNVector3 = SCNVector3(x: 1, y: 0, z: 0);
if (name == “UP”) {
axis = SCNVector3(x: 1, y: 0, z: 0)
} else if (name == “Left”) {
axis = SCNVector3(x: 0, y: 1, z: 0)
} else if (name == “Right”) {
axis = SCNVector3(x: 0, y: –1, z: 0)
} else if (name == “Down”) {
axis = SCNVector3(x: –1, y: 0, z: 0)
}
let box = self.scene?.rootNode.childNodeWithName(“box”, recursively: false)
box?.runAction(SCNAction.rotateByAngle(CGFloat(M_PI/2.0), aroundAxis: axis, duration: 0.5))
}
override func touchesBegan(touches: NSSet, withEvent event: UIEvent) {
let p = touches.anyObject()!.locationInView(self.sceneView)
if let hits = self.sceneView?.hitTest(p, options:[SCNHitTestSortResultsKey:true]) {
if let hit = hits.first as? SCNHitTestResult {
if (hit.node.geometry?.firstMaterial?.diffuse.contents as UIColor == UIColor.yellowColor()) {
hit.node.geometry?.firstMaterial?.diffuse.contents = UIColor.orangeColor().colorWithAlphaComponent(0.8)
self.randomLight()
}
}
}
}
}