forked from: forked from: PV3D でマルチビュー(問題点あり)

by tkinjo forked from forked from: PV3D でマルチビュー(問題点あり) (diff: 69)
cameras[ 0 ] は座標 x = 0; y = 1000; z = 0; にあり、DisplayObject3D.ZERO をターゲットとして設定しています。
しかし、z = 0、x = 0 のときはターゲットの方向にカメラを向けることができない仕様(バグ?)になっているようです。
理由は、x = 0 で固定したまま、z を -1 から 0、1 へと変更するときにカメラの向きが y 軸を中心に反転してしまうためのようです。
その反転する境界である z = 0 のときはユーザーがカメラの向きを設定する必要があるようで。

気づかせてくれた JohnBrookes さん、ありがとうございました。
Thankyou!

--- もうひとつ検証 ---
PV3D でマルチビュー(問題点あり)の問題が起こる過程を再現
http://wonderfl.kayac.com/code/225f3df8bffa868aaad5f127b043dcdee0b75cf8

...
@author tkinjo
♥0 | Line 103 | Modified 2009-06-15 08:13:04 | MIT License
play

ActionScript3 source code

/**
 * Copyright tkinjo ( http://wonderfl.net/user/tkinjo )
 * MIT License ( http://www.opensource.org/licenses/mit-license.php )
 * Downloaded from: http://wonderfl.net/c/kr5Z
 */

// forked from JohnBrookes's forked from: PV3D でマルチビュー(問題点あり)
// forked from tkinjo's PV3D でマルチビュー(問題点あり)
package  
{
	/**
	 * cameras[ 0 ] は座標 x = 0; y = 1000; z = 0; にあり、DisplayObject3D.ZERO をターゲットとして設定しています。
	 * しかし、z = 0、x = 0 のときはターゲットの方向にカメラを向けることができない仕様(バグ?)になっているようです。
	 * 理由は、x = 0 で固定したまま、z を -1 から 0、1 へと変更するときにカメラの向きが y 軸を中心に反転してしまうためのようです。
	 * その反転する境界である z = 0 のときはユーザーがカメラの向きを設定する必要があるようで。
	 * 
	 * 気づかせてくれた JohnBrookes さん、ありがとうございました。
	 * Thankyou!
	 * 
	 * 
	 * 
	 * --- もうひとつ検証 ---
	 * PV3D でマルチビュー(問題点あり)の問題が起こる過程を再現
	 * http://wonderfl.kayac.com/code/225f3df8bffa868aaad5f127b043dcdee0b75cf8
	 */
	
	import flash.display.Sprite;
	import flash.events.Event;
	import flash.events.MouseEvent;
	import flash.events.TimerEvent;
	import flash.text.TextField;
	import flash.text.TextFieldAutoSize;
	import flash.utils.Timer;
	import org.papervision3d.cameras.Camera3D;
	import org.papervision3d.core.proto.CameraObject3D;
	import org.papervision3d.core.proto.SceneObject3D;
	import org.papervision3d.materials.ColorMaterial;
	import org.papervision3d.materials.utils.MaterialsList;
	import org.papervision3d.materials.WireframeMaterial;
	import org.papervision3d.objects.DisplayObject3D;
	import org.papervision3d.objects.primitives.Cube;
	import org.papervision3d.render.BasicRenderEngine;
	import org.papervision3d.view.Viewport3D;
	
	[SWF(width = "465", height = "465", frameRate = "60", backgroundColor = "#ffffff")]
	/**
	 * ...
	 * @author tkinjo
	 */
	public class Main extends Sprite
	{
		/**
		 * 
		 */
		private var scene:SceneObject3D;
		private var renderer:BasicRenderEngine;
		
		private var viewports:Vector.<Viewport3D>;
		private var cameras:Vector.<CameraObject3D>;
		
		private var cube:Cube;
		
		private var textField:TextField;
		private var timer:Timer;
		
		/**
		 * 
		 */
		public function Main() 
		{
			scene = new SceneObject3D();
			renderer = new BasicRenderEngine();
			
			viewports = new Vector.<Viewport3D>();
			cameras = new Vector.<CameraObject3D>();
			for ( var i:uint = 0; i < 4; i++ ) {
				
				var viewport:Viewport3D = new Viewport3D( stage.stageWidth / 2, stage.stageHeight/ 2 );
				viewport.x = stage.stageWidth / 2 * ( i % 2 );
				viewport.y = stage.stageHeight / 2 * uint( i / 2 );
				
				var camera:CameraObject3D = new Camera3D();
				camera.target = DisplayObject3D.ZERO;
				camera.z = 0;
				camera.zoom = 115;
				
				viewports.push( viewport );
				cameras.push( camera );
				
				addChild( viewport );
			}
                        
			cameras[ 0 ].y = 1000;
                        //cameras[0].target = null;
			//cameras[ 0 ].z = 0;	// 0 だと表示されない。なぜ?
                        //cameras[0].rotationX=90;
			cameras[ 1 ].x = 1000;
			cameras[ 1 ].y = 1000;
			cameras[ 2 ].z = 1000;
			cameras[ 3 ].x = 1000;
			
			/**
			 * キューブの作成
			 * 
			 * キューブのコンストラクタ
			 * http://papervision3d.googlecode.com/svn/trunk/as3/trunk/docs/org/papervision3d/objects/primitives/Cube.html#Cube()
			 */
			var cubeMaterialParams:Array = [ 
					{ name:"front", color:0xff0000 }, 
					{ name:"back", color:0xffff00 }, 
					{ name:"right", color:0x00ff00 }, 
					{ name:"left", color:0x00ffff }, 
					{ name:"top", color:0x0000ff },
					{ name:"bottom", color:0xff00ff } 
				];
			var cubeMaterialsList:MaterialsList = new MaterialsList();
			for ( i = 0; i < 6; i++ ) {
				var colorMaterial:ColorMaterial = new ColorMaterial( cubeMaterialParams[ i ].color );
				//var colorMaterial:ColorMaterial = new ColorMaterial( cubeMaterialParams[ i ].color, 0.5 );
				colorMaterial.doubleSided = true;	// true にすると辺のふちが欠ける
				cubeMaterialsList.addMaterial( colorMaterial, cubeMaterialParams[ i ].name );
			}
			cube = new Cube( cubeMaterialsList, 100, 100, 100 );
			scene.addChild( cube );
			
			/**
			 * 問題点に関するテキストフィールド
			 */
			textField = new TextField();
			textField.autoSize = TextFieldAutoSize.LEFT;
			addChild( textField );
			
			
			var timer:Timer = new Timer( 3000 );
			var timerHandler:Function = function( event:TimerEvent ):void { changeZ(); };
			timer.addEventListener( TimerEvent.TIMER, timerHandler );
			timer.start();
			
			stage.addEventListener( MouseEvent.CLICK, function( event:MouseEvent ):void {
					if ( timer ) {
						timer.removeEventListener( TimerEvent.TIMER, timerHandler );
						timer = null;
					}
					changeZ();
				} );
			
			/**
			 * 
			 */
			addEventListener(Event.ENTER_FRAME, enterFrameHandler );
		}
		
		/**
		 * 
		 * @param	event
		 */
		private function changeZ():void {
			
			if ( cameras[ 0 ].z != 1 )
				cameras[ 0 ].z ++;
			
			else
				cameras[ 0 ].z = -1;
		}
		
		/**
		 * 
		 * @param	event
		 */
		private function enterFrameHandler( event:Event ):void {
			
			cube.rotationY++;
			
			for ( var i:uint = 0; i < 4; i++ ) {
				
				renderer.renderScene( scene, cameras[ i ], viewports[ i ] );
			}
			
			textField.text = "クリックで cameras[ 0 ].z の値を変更。" + 
					"\ncameras[ 0 ].z = " + cameras[ 0 ].z + 
					"\ncameras[ 0 ].rotationX = " + cameras[ 0 ].rotationX + 
					"\ncameras[ 0 ].rotationY = " + cameras[ 0 ].rotationY + 
					"\ncameras[ 0 ].rotationZ = " + cameras[ 0 ].rotationZ;
		}
	}
}