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

Matrix3D.appendRotation()の動作確認。2

Matrix3D.appendRotation();
と同じ機能の関数を作ってみる。

各要素をrandomで値を入れて、appendRotationする。

赤い四角がビルトイン関数の計算結果。
青い丸が同機能関数(mtrx3D)の計算結果。

ビルトイン関数のほう、axisが単位ベクトルで無い場合、
どういう計算をしているのかがわからなかった。
クオータニオンとか軸角度の計算の場合は単位ベクトルにするのが
セオリーなんだから、自動的に単位ベクトル化してもいいくらいだと
思うんだけど、そうはなっていない。

あと、10,0,22,87より前のプラグインバグがあったので、
ところどころ1/20している。
↓これの話。
http://wonderfl.net/code/f38acee5dab57b47ee85f2c46a961f48b7d092a7


値を比較すると、小数点4桁以下の誤差が出ることがあるが、
これは恐らく、Marix3Dでは計算速度を高めるために、
値のテーブルを作って、参照させていると予想。
↓こんなふうに
http://wonderfl.net/code/659d1427c67d807afd7a52273ac54e9aba086261


ちなみに、helpにある、
myObject.z = 1; 
myObject.transform.matrix3D.appendTranslation(10,10,0);
myObject.transform.matrix3D.appendRotation(1, Vector3D.YAXIS);
myObject.transform.matrix3D.appendTranslation(-10,-10,0);

これは

myObject.z = 1; 
myObject.transform.matrix3D.position = new Vector3D();
myObject.transform.matrix3D.appendRotation(1, Vector3D.YAXIS,new Vector3D(-10,-10,0));

ともかける、はず。



【参考】
http://help.adobe.com/ja_JP/AS3LCR/Flash_10.0/flash/geom/Matrix3D.html
Get Adobe Flash player
by umhr 25 Jul 2009
    Embed
/**
 * Copyright umhr ( http://wonderfl.net/user/umhr )
 * MIT License ( http://www.opensource.org/licenses/mit-license.php )
 * Downloaded from: http://wonderfl.net/c/jKlS
 */

/*
Matrix3D.appendRotation();
と同じ機能の関数を作ってみる。

各要素をrandomで値を入れて、appendRotationする。

赤い四角がビルトイン関数の計算結果。
青い丸が同機能関数(mtrx3D)の計算結果。

ビルトイン関数のほう、axisが単位ベクトルで無い場合、
どういう計算をしているのかがわからなかった。
クオータニオンとか軸角度の計算の場合は単位ベクトルにするのが
セオリーなんだから、自動的に単位ベクトル化してもいいくらいだと
思うんだけど、そうはなっていない。

あと、10,0,22,87より前のプラグインバグがあったので、
ところどころ1/20している。
↓これの話。
http://wonderfl.net/code/f38acee5dab57b47ee85f2c46a961f48b7d092a7


値を比較すると、小数点4桁以下の誤差が出ることがあるが、
これは恐らく、Marix3Dでは計算速度を高めるために、
値のテーブルを作って、参照させていると予想。
↓こんなふうに
http://wonderfl.net/code/659d1427c67d807afd7a52273ac54e9aba086261


ちなみに、helpにある、
myObject.z = 1; 
myObject.transform.matrix3D.appendTranslation(10,10,0);
myObject.transform.matrix3D.appendRotation(1, Vector3D.YAXIS);
myObject.transform.matrix3D.appendTranslation(-10,-10,0);

これは

myObject.z = 1; 
myObject.transform.matrix3D.position = new Vector3D();
myObject.transform.matrix3D.appendRotation(1, Vector3D.YAXIS,new Vector3D(-10,-10,0));

ともかける、はず。



【参考】
http://help.adobe.com/ja_JP/AS3LCR/Flash_10.0/flash/geom/Matrix3D.html#appendRotation()
*/
package {
	import flash.display.Sprite;
	import flash.events.Event;
	import flash.events.TimerEvent;
	import flash.geom.Matrix3D;
	import flash.text.TextField;
	import flash.geom.Vector3D;
	import flash.system.Capabilities;
	import flash.utils.Timer;
	public class Main extends Sprite {
		private var builtinStage:Sprite = Create.newSprite( { x:stage.stageWidth / 2, y:stage.stageWidth/2 } );
		private var mtrx3DStage:Sprite = Create.newSprite( { x:stage.stageWidth / 2, y:stage.stageWidth/2 } );
		//ビルトイン関数用の赤い四角
		private var builtinRect:Sprite = Create.newSprite( { z:0 }, Create.drawRect( { x: -50, y: -50, width:100, height:100, color:0xFF0000 , alpha:0.5 } ));
		//同機能関数(mtrx3D)用の青い丸
		private var mtrx3DRect:Sprite = Create.newSprite( { z:0 }, Create.drawCircle( { radius:50, color:0x0000FF , alpha:0.5 } ));
		private var tf:TextField = Create.newTextField( { width:stage.stageWidth, height:stage.stageHeight, wordWrap:true } );
		//確認用の値を用意
		private var builtinEntity:Matrix3D=new Matrix3D();
		private var mtrx3DEntity:Matrix3D=new Matrix3D();
		public function Main() {
			
			addChild(tf);
			addChild(builtinStage);
			addChild(mtrx3DStage);
			builtinStage.addChild(builtinRect);
			mtrx3DStage.addChild(mtrx3DRect);
			
			var myTimer:Timer = new Timer(1000);
			myTimer.addEventListener(TimerEvent.TIMER, TIMER);
			myTimer.start();
			addEventListener(Event.ENTER_FRAME, ENTER_FRAME);
		}
		private function setTex():void {
			var txt:String = "◆同機能関数Mtrx3D.appendRotation" + Capabilities.version + "での実行結果\n\n";
			var builtinRawData:Vector.<Number>=builtinEntity.rawData;
			txt+="↓Matrix3D.appendRotationの結果\n"+builtinRawData+"\n";
			var mtrx3DRawData:Vector.<Number>=mtrx3DEntity.rawData;
			txt+="\n↓同機能関数Mtrx3D.appendRotationの結果\n"+mtrx3DRawData+"\n\n";
			txt+=Util.hikaku(builtinRawData,mtrx3DRawData);
			tf.text = txt;
		}
		
		private function TIMER(e:TimerEvent):void {
			if (Math.random() < 0.2) {
				//たまには初期化してやらないと、画面から外れ続けてしまうので。
				builtinEntity.identity();
				mtrx3DEntity.identity();
			}
			var degrees:Number = Math.random() * 720 - 360;
			var axis:Vector3D = new Vector3D(Math.random() - 0.5, Math.random() - 0.5, Math.random() - 0.5);
			var pivotPoint:Vector3D = new Vector3D(Math.random()*200-100,Math.random()*200-100,Math.random()*200-100);
			
			//normalizeしないと、同一の計算結果にならない。
			//ビルトイン関数の方は、normalizeしない場合
			axis.normalize();
			//計算
			Mtrx3D.appendRotation(mtrx3DEntity, degrees, axis, pivotPoint);
			builtinEntity.appendRotation(degrees, axis,pivotPoint);
			setTex();
		}
		private function ENTER_FRAME(e:Event):void {
			builtinRect.transform.matrix3D.interpolateTo(builtinEntity, 0.1);
			mtrx3DRect.transform.matrix3D.interpolateTo(mtrx3DEntity, 0.1);
		}
	}
}

class Mtrx3D{
	import flash.geom.Matrix3D;
	public static function appendRotation(entity:Matrix3D,degrees:Number,axis:Vector3D,pivotPoint:Vector3D=null):void {
		if(!pivotPoint){
			pivotPoint = new Vector3D(0,0,0);
		}
		var _axis:Vector3D = axis.clone();
		//_axis.normalize();
		
		//AXIS_ANGLE to QUATERNION
		var degreesPIper360:Number = degrees/360*Math.PI;
		var w:Number = Math.cos(degreesPIper360);
		var x:Number = Math.sin(degreesPIper360)*_axis.x;
		var y:Number = Math.sin(degreesPIper360)*_axis.y;
		var z:Number = Math.sin(degreesPIper360) * _axis.z;
		
		//QUATERNION to Matrix
		var p:Vector.<Number> = new Vector.<Number>(16,true);
		p[0] = (w*w+x*x-y*y-z*z);
		p[1] = 2*(y*x+w*z);
		p[2] = 2*(z*x-w*y);
		p[3] = 0;
		p[4] = 2*(y*x-w*z);
		p[5] = (w*w-x*x+y*y-z*z);
		p[6] = 2*(w*x+z*y);
		p[7] = 0;
		p[8] = 2*(z*x+w*y);
		p[9] = 2*(z*y-w*x);
		p[10] = (w*w-x*x-y*y+z*z);
		p[11] = 0;
		p[12] = 0;
		p[13] = 0;
		p[14] = 0;
		p[15] = 1;
		
		//Matrix * entity
		var e:Vector.<Number> = entity.rawData;
		var pe:Vector.<Number> = new Vector.<Number>(16, true);
		//バグ対応。10,0,22,87未満の場合バグを含むように。
		var bug:int = 1;
		if(Util.version() <1000022087){
			bug = 20;
		}
		pe[0] = p[0]*e[0]+p[4]*e[1]+p[8]*e[2]+p[12]*e[3];
		pe[1] = p[1]*e[0]+p[5]*e[1]+p[9]*e[2]+p[13]*e[3];
		pe[2] = p[2]*e[0]+p[6]*e[1]+p[10]*e[2]+p[14]*e[3];
		pe[3] = p[3]*e[0]+p[7]*e[1]+p[11]*e[2]+p[15]*e[3];
		pe[4] = p[0]*e[4]+p[4]*e[5]+p[8]*e[6]+p[12]*e[7];
		pe[5] = p[1]*e[4]+p[5]*e[5]+p[9]*e[6]+p[13]*e[7];
		pe[6] = p[2]*e[4]+p[6]*e[5]+p[10]*e[6]+p[14]*e[7];
		pe[7] = p[3]*e[4]+p[7]*e[5]+p[11]*e[6]+p[15]*e[7];
		pe[8] = p[0]*e[8]+p[4]*e[9]+p[8]*e[10]+p[12]*e[11];
		pe[9] = p[1]*e[8]+p[5]*e[9]+p[9]*e[10]+p[13]*e[11];
		pe[10] = p[2]*e[8]+p[6]*e[9]+p[10]*e[10]+p[14]*e[11];
		pe[11] = p[3]*e[8]+p[7]*e[9]+p[11]*e[10]+p[15]*e[11];
		pe[12] = p[0]*e[12]+p[4]*e[13]+p[8]*e[14]+p[12]*e[15]+pivotPoint.x/bug;
		pe[13] = p[1]*e[12]+p[5]*e[13]+p[9]*e[14]+p[13]*e[15]+pivotPoint.y/bug;
		pe[14] = p[2]*e[12]+p[6]*e[13]+p[10]*e[14]+p[14]*e[15]+pivotPoint.z/bug;
		pe[15] = p[3]*e[12]+p[7]*e[13]+p[11]*e[14]+p[15]*e[15];
		entity.rawData = pe;
	}
}

import flash.geom.Matrix3D;
import flash.geom.Vector3D;
class Util {
	import flash.system.Capabilities;	
	public static function version():uint{
		var ver_array:Array = Capabilities.version.substr(4).split(",");
		return int(ver_array[0])*100000000+int(ver_array[1])*1000000+int(ver_array[2])*1000+int(ver_array[3]);
	}
	
	public static function hikaku(v0:Vector.<Number>,v1:Vector.<Number>):String {
		var _str:String="↓二つのMatrixの要素毎の差\n";
		var _n:int=v0.length;
		for (var i:int=0; i<_n; i++) {
			_str += "["+i+"]:"+(v0[i]-v1[i])+"\n";
		}
		return _str;
	}

	public static function random16():Vector.<Number> {
		var _v:Vector.<Number>=new Vector.<Number>(16,true);
		for (var i:int=0; i<16; i++) {
			_v[i]=Math.random()*200-100;
		}
		return _v;
	}
	public static function randomMatrix3D():Matrix3D{
		var mt:Matrix3D = new Matrix3D();
		var v:Vector.<Vector3D>=new Vector.<Vector3D>(3);
		v[0]=new Vector3D(200*Math.random()-100,200*Math.random()-100,200*Math.random()-100);//平行移動、
		v[1]=new Vector3D(10*Math.random()-5,10*Math.random()-5,10*Math.random()-5);//回転
		v[2] = new Vector3D(3 * Math.random(), 3 * Math.random(), 3 * Math.random());//拡大 / 縮小
		mt.recompose(v);
		return new Matrix3D(mt.rawData);
	}
}


import flash.display.DisplayObject;
import flash.display.Graphics;
import flash.text.TextField;
import flash.text.TextFieldType;
import flash.text.TextFormat;
import flash.display.Sprite;
import flash.display.Shape;
import flash.display.SimpleButton;

class Create{
	public static var defaultTextFormat:TextFormat = new TextFormat();
	
	public static function newSimpleButton(x_y_w_h_txt:Array = null,property:Array=null,graphics:Array=null):SimpleButton{
		
		var _x:Number = x_y_w_h_txt[0];
		var _y:Number = x_y_w_h_txt[1];
		var _width:Number = x_y_w_h_txt[2];
		var _height:Number = x_y_w_h_txt[3];
		var _text:String = x_y_w_h_txt[4];
		
		var upState:Sprite = newSprite({x:_x,y:_y},{graphics:toDrawRect({color:0xCCCCCC,width:_width,height:_height,round:8})});
		upState.addChild(newShape({x:2,y:2},{graphics:toDrawRect({color:0xE5E5E5,width:_width-4,height:_height-4,round:6})}));
		var overState:Sprite = newSprite({x:_x,y:_y},{graphics:toDrawRect({color:0xBBBBBB,width:_width,height:_height,round:8})});
		overState.addChild(newShape({x:2,y:2},{graphics:toDrawRect({color:0xEEEEEE,width:_width-4,height:_height-4,round:6})}));
		var downState:Sprite = newSprite({x:_x,y:_y},{graphics:toDrawRect({color:0xAAAAAA,width:_width,height:_height,round:8})});
		downState.addChild(newShape({x:2,y:2},{graphics:toDrawRect({color:0xDDDDDD,width:_width-4,height:_height-4,round:6})}));
		var hitTestState:Shape = newShape({x:_x,y:_y},{graphics:toDrawRect({width:_width,height:_height,round:8})});

		if(x_y_w_h_txt[4]){
			upState.addChild(newTextField({x:0,y:2,width:x_y_w_h_txt[2],height:x_y_w_h_txt[3]-2,text:x_y_w_h_txt[4],setTextFormat:[{font:"_sans",align:"center"}]}));
			overState.addChild(newTextField({x:0,y:2,width:x_y_w_h_txt[2],height:x_y_w_h_txt[3]-2,text:x_y_w_h_txt[4],setTextFormat:[{font:"_sans",align:"center"}]}));
			downState.addChild(newTextField({x:0,y:3,width:x_y_w_h_txt[2],height:x_y_w_h_txt[3]-3,text:x_y_w_h_txt[4],setTextFormat:[{font:"_sans",align:"center"}]}));
		}
		var sb:SimpleButton = new SimpleButton(upState,overState,downState,hitTestState);
		
		return sb;
	}
	public static function toDrawRect(... args):Array{
		var _x:Number = args[0]["x"]?args[0]["x"]:0;
		var _y:Number = args[0]["y"]?args[0]["y"]:0;
		var _width:Number = args[0]["width"]?args[0]["width"]:100;
		var _height:Number = args[0]["height"]?args[0]["height"]:100;
		var _color:Number = args[0]["color"]?args[0]["color"]:0xFF0000;
		var _alpha:Number = args[0]["alpha"]?args[0]["alpha"]:1;
		var _round:Number = args[0]["round"]?args[0]["round"]:0;
		var _lineSize:Number = args[0]["lineSize"]?args[0]["lineSize"]:0;
		var _lineColor:Number = args[0]["lineColor"]?args[0]["lineColor"]:0;
		var _lineAlpha:Number = args[0]["lineAlpha"]?args[0]["lineAlpha"]:0;
		var _ellipseWidth:Number = args[0]["ellipseWidth"]?args[0]["ellipseWidth"]:_round;
		var _ellipseHeight:Number = args[0]["ellipseHeight"]?args[0]["ellipseHeight"]:_ellipseWidth;
		return [{beginFill:[_color,_alpha]},{drawRoundRect:[_x,_y,_width,_height,_ellipseWidth,_ellipseHeight]}];
	}
	public static function drawRect(... args):Object{
		var _x:Number = args[0]["x"]?args[0]["x"]:0;
		var _y:Number = args[0]["y"]?args[0]["y"]:0;
		var _width:Number = args[0]["width"]?args[0]["width"]:100;
		var _height:Number = args[0]["height"]?args[0]["height"]:100;
		var _color:Number = args[0]["color"]?args[0]["color"]:0xFF0000;
		var _alpha:Number = args[0]["alpha"]?args[0]["alpha"]:1;
		var _round:Number = args[0]["round"]?args[0]["round"]:0;
		var _lineSize:Number = args[0]["lineSize"]?args[0]["lineSize"]:0;
		var _lineColor:Number = args[0]["lineColor"]?args[0]["lineColor"]:0;
		var _lineAlpha:Number = args[0]["lineAlpha"]?args[0]["lineAlpha"]:0;
		var _ellipseWidth:Number = args[0]["ellipseWidth"]?args[0]["ellipseWidth"]:_round;
		var _ellipseHeight:Number = args[0]["ellipseHeight"]?args[0]["ellipseHeight"]:_ellipseWidth;
		var resultObj:Object;
		if(_round || _ellipseWidth || _ellipseHeight){
			resultObj = { graphics:[ { beginFill:[_color, _alpha] }, { drawRoundRect:[_x, _y, _width, _height, _ellipseWidth, _ellipseHeight] } ] };
		}else {
			resultObj = { graphics:[ { beginFill:[_color, _alpha] }, { drawRect:[_x, _y, _width, _height] } ] };
		}
		return resultObj;
	}
	public static function drawCircle(... args):Object{
		var _x:Number = args[0]["x"]?args[0]["x"]:0;
		var _y:Number = args[0]["y"]?args[0]["y"]:0;
		var _color:Number = args[0]["color"]?args[0]["color"]:0xFF0000;
		var _alpha:Number = args[0]["alpha"]?args[0]["alpha"]:1;
		var _r:Number = args[0]["r"]?args[0]["r"]:100;
		var _radius:Number = args[0]["radius"]?args[0]["radius"]:_r;
		var _width:Number = args[0]["width"]?args[0]["width"]:_radius;
		var _height:Number = args[0]["height"]?args[0]["height"]:_radius;
		var _lineSize:Number = args[0]["lineSize"]?args[0]["lineSize"]:0;
		var _lineColor:Number = args[0]["lineColor"]?args[0]["lineColor"]:0;
		var _lineAlpha:Number = args[0]["lineAlpha"]?args[0]["lineAlpha"]:0;
		var resultObj:Object;
		if(_width == _height){
			resultObj = { graphics:[ { beginFill:[_color, _alpha] }, { drawCircle:[_x, _y, _radius] } ] };
		}else {
			resultObj = { graphics:[ { beginFill:[_color, _alpha] }, { drawEllipse:[_x, _y, _width, _height] } ] };
		}
		return resultObj;
	}

	public static function newShape(... args):Shape{
		var sp:Shape;
		var _str:String;
		var _length:int = args.length;
		for (var i:int = 0; i < _length; i++) {
			var _obj:Object = args[i];
			if(i == 0){
				if(_obj.Shape){
					sp = _obj.Shape;
				}else{
					sp = new Shape();
				}
			}
			if(_obj.graphics){
				for (var j:int = 0; j < _obj.graphics.length; j++) {
					if(_obj.graphics[j]){
						for (_str in _obj.graphics[j]) {
							//trace(_str,_obj.graphics[j][_str])
							sp.graphics[_str].apply(null, _obj.graphics[j][_str]);
						}
					}
				}
			}
			for (_str in _obj) {
				if(_str != "Shape" && _str != "graphics"){
					sp[_str] = _obj[_str];
				}
			}
		}
		return sp;
	}
	public static function newSprite(... args):Sprite{
		var sp:Sprite;
		var _str:String;
		var _length:int = args.length;
		for (var i:int = 0; i < _length; i++) {
			var _obj:Object = args[i];
			if(i == 0){
				if(_obj.Sprite){
					sp = _obj.Sprite;
				}else{
					sp = new Sprite();
				}
			}
			if(_obj.graphics){
				for (var j:int = 0; j < _obj.graphics.length; j++) {
					if(_obj.graphics[j]){
						for (_str in _obj.graphics[j]) {
							sp.graphics[_str].apply(null, _obj.graphics[j][_str]);
						}
					}
				}
			}
			for (_str in _obj) {
				if(_str != "Sprite" && _str != "graphics" && _str != "addChild"){
					sp[_str] = _obj[_str];
				}
			}
			if(_obj.addChild){
				sp.addChild(_obj.addChild);
			}
		}
		return sp;
	}
	public static function newTextField(... args):TextField{
		var ta:TextField = new TextField();
		ta.defaultTextFormat = defaultTextFormat;
		var _length:int = args.length;
		for (var i:int = 0; i < _length; i++) {
			var _obj:Object = args[i];
			for (var _str:String in _obj) {
				if(_str != "setTextFormat"){
					ta[_str] = _obj[_str];
				}
			}
			if(_obj.setTextFormat){
				var format:TextFormat = new TextFormat();
				if(_obj.setTextFormat[0] is TextFormat){
					format = _obj.setTextFormat[0];
				}else{
					for (var tf_str:String in _obj.setTextFormat[0]) {
						format[tf_str] = _obj.setTextFormat[0][tf_str];
					}
				}
				ta.setTextFormat(format,isNaN(_obj.setTextFormat[1])?-1:_obj.setTextFormat[1],isNaN(_obj.setTextFormat[2])?-1:_obj.setTextFormat[2]);
			}
		}
		return ta;
	}
}