In case Flash no longer exists; a copy of this site is included in the Flashpoint archive's "ultimate" collection.

Dead Code Preservation :: Archived AS3 works from wonderfl.net

Gainerでの加速度センサによる、オブジェクトの回転、移動

Gainerでの加速度センサによる、オブジェクトの回転、移動。
* 
* 回転は360度回転したかったし、
* 移動は回転とは独立な値にしたかったけど、
* 加速度センサの限界っぽい。
* 
* ◆360度回転
* まず、360度回転は、x軸のみ、y軸のみだったら、問題ない。
* ただ、x,y両方を360度回転ではうまくいかない。
* いろいろ値をこねくり回してみたが駄目だった。
* 結局の所、z軸回転をとれないのだから、
* 正確な姿勢取得ができないという前提に戻ってあきらめた。
* 
* ◆水平移動の取得
* 回転とは独立の移動については、
* z軸の変化が少ない時に水平移動としてとらえる方法を試したが、
* 回転値の取得と兼用だとその判別が難しい。
* またセンサの誤差も吸収が困難だった。
* 
* wiiやPS3で、赤外線センサやジャイロセンサを併用している
* 理由もなんとなく実感できた。
* 
* ◆トラッキング
* 加速度センサはモジュールによって誤差が大きそうだったので、
* とりあえず水平時のトラッキング(xとyの中央値、zの最大値)を
* 取得してから始めるようにした。
* もっと正確にやるには、全部の値の最少、中央、最大値を
* 取得したほうがいいはずだけど、煩雑すぎるような。
* 
*
Get Adobe Flash player
by umhr 05 Apr 2010
    Embed
/**
 * Copyright umhr ( http://wonderfl.net/user/umhr )
 * MIT License ( http://www.opensource.org/licenses/mit-license.php )
 * Downloaded from: http://wonderfl.net/c/vfN1
 */

/*
 * Gainerでの加速度センサによる、オブジェクトの回転、移動。
 * 
 * 回転は360度回転したかったし、
 * 移動は回転とは独立な値にしたかったけど、
 * 加速度センサの限界っぽい。
 * 
 * ◆360度回転
 * まず、360度回転は、x軸のみ、y軸のみだったら、問題ない。
 * ただ、x,y両方を360度回転ではうまくいかない。
 * いろいろ値をこねくり回してみたが駄目だった。
 * 結局の所、z軸回転をとれないのだから、
 * 正確な姿勢取得ができないという前提に戻ってあきらめた。
 * 
 * ◆水平移動の取得
 * 回転とは独立の移動については、
 * z軸の変化が少ない時に水平移動としてとらえる方法を試したが、
 * 回転値の取得と兼用だとその判別が難しい。
 * またセンサの誤差も吸収が困難だった。
 * 
 * wiiやPS3で、赤外線センサやジャイロセンサを併用している
 * 理由もなんとなく実感できた。
 * 
 * ◆トラッキング
 * 加速度センサはモジュールによって誤差が大きそうだったので、
 * とりあえず水平時のトラッキング(xとyの中央値、zの最大値)を
 * 取得してから始めるようにした。
 * もっと正確にやるには、全部の値の最少、中央、最大値を
 * 取得したほうがいいはずだけど、煩雑すぎるような。
 * 
 * */

package {
    import flash.display.Sprite;
	import flash.events.Event;
    import flash.events.MouseEvent;
	import flash.geom.Matrix3D;
	import flash.geom.PerspectiveProjection;
	import flash.geom.Point;
	import flash.geom.Vector3D;
	import flash.display.DisplayObjectContainer;
	
    public class Main extends Sprite {
		private var fin:Fin;
		public function Main() {
			
			stage.transform.perspectiveProjection = new PerspectiveProjection();
			stage.transform.perspectiveProjection.projectionCenter = new Point(465/2,465/2);
			
			fin = new Fin();
			fin.z = 0;
			fin.x = 465 / 2;
			fin.y = 465 / 2+50;
			this.addChild(fin);
			zSort(fin);
			
			var accelerometerWrapper:AccelerometerWrapper = new AccelerometerWrapper();
			this.addChild(accelerometerWrapper);
			accelerometerWrapper.onParam = onParam;
			
        }
		
		public function onParam(rArray:Array, tArray:Array):void {
			fin.rotationX = rArray[0];
			fin.rotationY = rArray[1];
			fin.rotationZ = rArray[2];
			fin.x += tArray[0];
			fin.y += tArray[1];
			fin.z += tArray[2];
			zSort(fin);
		}
		
		private function zSort(target:DisplayObjectContainer):void {
			if(!target.root){return};
			var n:int = target.numChildren;
			var array:Array = [];
			var reference:Array = [];
			for (var i:int = 0; i < n; i++) {
				var poz:Vector3D = target.getChildAt(i).transform.getRelativeMatrix3D(this.root.stage).position;
				var point:Point = stage.transform.perspectiveProjection.projectionCenter;
				array[i] = poz.subtract(new Vector3D(point.x,point.y,-stage.transform.perspectiveProjection.focalLength)).length;
				reference[i] = target.getChildAt(i);
			}
			var temp:Array = array.sort(Array.NUMERIC | Array.RETURNINDEXEDARRAY);
			for (i = 0; i < n; i++) {
				target.setChildIndex(reference[temp[i]],0);
				if(reference[temp[i]].numChildren > 1){
					zSort(reference[temp[i]]);
				}
			}
		}
    }
}

import flash.display.Sprite;
import flash.events.Event;
import flash.events.MouseEvent;
import flash.text.TextField;
import flash.text.TextFormat;
import funnel.*;
import funnel.gui.*;
import funnel.ui.*;

class AccelerometerWrapper extends Sprite {
	// Gainerオブジェクト
	private var _gainer:Gainer;
	private var _textSp:Sprite;
	public function AccelerometerWrapper() {
		// Gainerのインスタンスを生成
		_gainer = new Gainer();
		
		// Gainer GUIのインスタンスを生成して配置
		var gui:GainerGUI = new GainerGUI();
		//gui.x = 200;
		//gui.y = 200;
		addChild(gui);
		_gainer.gui = gui;
		
		
		var _textField:TextField = new TextField();
		_textField.defaultTextFormat = new TextFormat("_sans", 14, 0xFFFFFF);
		_textField.text = "Gainerモジュールを\n平らな机の上に置いて\nモジュール上の\nButtonを押してください。";
		_textField.autoSize = "left";
		
		_textSp = new Sprite();
		_textSp.graphics.beginFill(0x000000, 0.8);
		_textSp.graphics.drawRoundRect(0, 0, _textField.width+32, _textField.height+32, 16, 16);
		_textSp.graphics.endFill();
		_textSp.x = (465 - _textSp.width) / 2;
		_textSp.y = (465 - _textSp.height) / 2+32;
		this.addChild(_textSp);
		
		_textField.x = (_textSp.width - _textField.width) / 2;
		_textField.y = (_textSp.height - _textField.height) / 2;
		_textSp.addChild(_textField);
		
		
		// ボタンに対してイベントリスナをセット
		_gainer.button.addEventListener(ButtonEvent.PRESS, onPress);
		_gainer.analogInput(0).filters = [new Convolution(Convolution.MOVING_AVERAGE)];
		_gainer.analogInput(1).filters = [new Convolution(Convolution.MOVING_AVERAGE)];
		_gainer.analogInput(2).filters = [new Convolution(Convolution.MOVING_AVERAGE)];
		
	}
	private function onPress(event:ButtonEvent):void {
		trace(event.type);
		if (event.type == "press") {
			_gainer.button.removeEventListener(ButtonEvent.PRESS, onPress);
			this.removeChild(_textSp);
			trace(_gainer.analogInput(0).value);
			trace(_gainer.analogInput(1).value);
			trace(_gainer.analogInput(2).value);
			
			setTrackingValue(_gainer.analogInput(0).value, _gainer.analogInput(1).value, _gainer.analogInput(2).value);
			
			this.removeEventListener(Event.ENTER_FRAME, onEnter);
			this.addEventListener(Event.ENTER_FRAME, onEnter);
		}
	}
	
	private var tracking:Array;
	private function setTrackingValue(a0:Number, a1:Number, a2:Number):void {
		tracking = [];
		tracking[0] = [0.345, 0.584, 0.831];
		tracking[1] = [0.328, 0.561, 0.815];
		tracking[2] = [0.42, 0.635, 0.853];
		tracking[0][1] = a0;
		tracking[1][1] = a1;
		tracking[2][2] = a2;
	}
	private function scale0(num:Number):Number {
		var y:Number;
		if (num < tracking[0][1]) {
			y = -(tracking[0][1] - num) / (tracking[0][1] - tracking[0][0]);
		}else {
			y = (num - tracking[0][1]) / (tracking[0][2] - tracking[0][1]);
		}
		y = Math.min(1, Math.max(-1, y));
		return y;
	}
	private function scale1(num:Number):Number {
		var y:Number;
		if (num < tracking[1][1]) {
			y = -(tracking[1][1] - num) / (tracking[1][1] - tracking[1][0]);
		}else {
			y = (num - tracking[1][1]) / (tracking[1][2] - tracking[1][1]);
		}
		y = Math.min(1, Math.max(-1, y));
		return y;
	}
	private function scale2(num:Number):Number {
		var y:Number;
		if (num < tracking[2][1]) {
			y = -(tracking[2][1] - num) / (tracking[2][1] - tracking[2][0]);
		}else {
			y = (num - tracking[2][1]) / (tracking[2][2] - tracking[2][1]);
		}
		y = Math.min(1, Math.max(-1, y));
		return y;
	}
	
	private function onEnter(event:Event):void {
		atParam(_gainer.analogInput(0).value, _gainer.analogInput(1).value, _gainer.analogInput(2).value);
	}
	
	public var onParam:Function = function(rArray:Array, tArray:Array):void { };
	public function atParam(a0:Number, a1:Number, a2:Number):void {
		a0 = scale0(a0);
		a1 = scale1(a1);
		a2 = scale2(a2);
		
		var rArray:Array = [0, 0, 0];
		var tArray:Array = [0, 0, 0];
		if(Math.abs(a2)<97){
			rArray[0] = Math.asin(a0) / Math.PI * 180;
			tArray[0] = a1*5;
			rArray[2] = Math.asin(a1) / Math.PI * 180;
			tArray[2] = -a0*5;
		}
		onParam(rArray, tArray);
	}
}


import flash.display.Sprite;
class Fin extends Sprite {
	public function Fin() {
		var xyr:Array = [[90, 0, 0, 0xFF0000], [0, 0, 0, 0x00FF00], [0, 90, 0, 0x0000FF]];
		for (var j:int = 0; j < 3; j++) {
			for (var i:int = 0; i < 4; i++) {
				var sp:Sprite = new Sprite();
				sp.graphics.lineStyle(1, xyr[j][3], 0.5);
				sp.graphics.beginFill(xyr[j][3], 0.25);
				sp.graphics.drawRect(-25, -25, 50, 50);
				sp.graphics.endFill();
				sp.rotationX = xyr[j][0];
				sp.rotationY = xyr[j][1];
				if (j == 0) {
					sp.x = 25-50 * (i % 2);
					sp.z = 25-50*(Math.floor(i/2));
				}else if (j == 1) {
					sp.x = 25-50 * (i % 2);
					sp.y = 25-50*(Math.floor(i/2));
				}else if (j == 2) {
					sp.y = 25-50 * (i % 2);
					sp.z = 25-50*(Math.floor(i/2));
				}
				
				this.addChild(sp);
			}
		}
		
	}
}