[flash 3D]flash CS4 3D功能加PV3D的建築物內部旋轉

有點落落長的標題….
大概也說完這篇的CODE要做的事了啦^^”

為什麼不全部都用PV3D勒!?
因為PV3D的定位真的是太麻煩了
所以能不用外部LOAD近來的東西我就儘量避開囉

flash CS4 3D功能的部分是建築物的各樓層
PV3D的部分就是LOGO們
按左右的按鈕可以控制旋轉
懶得弄DEMO了…等正式上線在回來補上吧!!

為了分開各層的深度跟旋轉角度…等
所以每一層的LOGO都獨立一個BasicView
在addChild時也要注意一下深度的排列(跟各樓層的MC交叉排列)

每個建築的內部跟放的LOGO數量都不一樣
所以除了用biruNaka.as控制相同的部份外
各建築還要多用個AS(biru_nakaX.as)做主要的控制

biruNaka.as

package {

	import flash.events.*;
	import flash.display.MovieClip;
	import caurina.transitions.Tweener;	
	import flash.utils.Timer;
	
	import caurina.transitions.properties.ColorShortcuts;
	ColorShortcuts.init();
	
	public class biruNaka extends MovieClip {
		var mod:ModelLocator = ModelLocator.getInstance(); 
		var citymod:CityLocator = CityLocator.getInstance();
		var lBtnX:Number;
		var rBtnX:Number;
		var btnY:Number;
		var _btn_left:btn_left = new btn_left();
		var _btn_right:btn_right = new btn_right();

		public function biruNaka() {
			addEventListener(Event.ADDED_TO_STAGE, init);
		}
		
		private function init(e:Event) {
			_btn_left.alpha = _btn_right.alpha = 0;
			addChild(_btn_left);
			addChild(_btn_right);
			
			btnY = (this.height - _btn_left.height - this.y) / 2;
			_btn_left.y = _btn_right.y = btnY;
			
			lBtnX = this.x - _btn_left.width - 10 - citymod.cityNaka_arr_d3d[mod.now_3d][0] +citymod.cityNaka_fix_arr[mod.now_3d];
			rBtnX = this.x + this.width + 10 - citymod.cityNaka_arr_d3d[mod.now_3d][0] + citymod.cityNaka_fix_arr[mod.now_3d];
			_btn_left.x = lBtnX + 5;
			_btn_right.x = rBtnX - 5;
			
			Tweener.addTween(_btn_left, { x:lBtnX, alpha:1, time:0.5, transition:"easeOutBack", delay:1 } );
			Tweener.addTween(_btn_right, { x:rBtnX, alpha:1, time:0.5, transition:"easeOutBack", delay:1 } );
		}
	}
}

biru_naka1.as

package {

	import flash.events.*;
	import flash.display.MovieClip;
	import caurina.transitions.Tweener;	
	import flash.utils.Timer;
	
	import org.papervision3d.objects.primitives.*;
	import org.papervision3d.materials.*;
	import org.papervision3d.events.*
	import org.papervision3d.objects.DisplayObject3D;
	import org.papervision3d.view.BasicView;
	import org.papervision3d.view.layer.ViewportLayer;
	import org.papervision3d.materials.BitmapAssetMaterial;
	import org.papervision3d.view.layer.util.ViewportLayerSortMode;
	
	import caurina.transitions.properties.ColorShortcuts;
	ColorShortcuts.init();
	
	public class biru_naka1 extends biruNaka {
		var view:BasicView;
		var _kakudou:Array = new Array(0, 90, 270);
		var now_kakudou:int = 0;
		var now_kakudou_num:int = 0;
		
		var logolist:XMLList;
		var floorArr:XMLList;
		var radius:int = 187;//半徑
		
		public function biru_naka1() {
			addEventListener(Event.ADDED_TO_STAGE, init);
		}
		
		private function init3DEngine():void{
			for (var i = 0; i < floorArr.length(); i++ ) {
				var _view:BasicView = new BasicView(0, 0, true, true, "Target");
				var ff:MovieClip = this.getChildByName("f" + (i + 1)) as MovieClip;
				_view.x = -405;
				_view.y = 78 * i-340;
				_view.name = "view" + i;
				_view.camera.y = 300;
				_view.camera.z = -900;
				_view.viewport.buttonMode = true;
				addChildAt(_view, getChildIndex(ff) + 1);
			}
			
			this.addEventListener(Event.ENTER_FRAME, onEventRender3D);
		}
		
		private function init(e:Event) {
			logolist = mod.bland_XML.logo.(@category == citymod.biruArrEn[mod.now_3d]);
			floorArr = mod.bland_XML.floor.(@category == citymod.biruArrEn[mod.now_3d]);
			_btn_left.addEventListener(MouseEvent.MOUSE_DOWN, function(e:MouseEvent) { initKakudou(false); } );
			_btn_right.addEventListener(MouseEvent.MOUSE_DOWN, function(e:MouseEvent) { initKakudou(true); } );
			
			init3DEngine();
			makeLogo();
		}
		
		private function floorMove(b:Boolean):void {
			for (var i = 1; i <= floorArr.length(); i++) {
				var ff:MovieClip=this.getChildByName("f"+i) as MovieClip;
				if (b) {
					Tweener.addTween(ff.ss, { rotation:_kakudou[now_kakudou_num], time:1, transition:"linear" } );
				}else {
					_kakudou[now_kakudou_num] > 0	?	Tweener.addTween(ff.ss, { rotation:_kakudou[now_kakudou_num] - 360, time:1, transition:"linear" } ):
														Tweener.addTween(ff.ss, { rotation:_kakudou[now_kakudou_num] , time:1, transition:"linear" } );
				}
				
			}
			
		}
		
		private function moveLogo3D() {
			for (var i = 0; i < floorArr.length(); i++) {
				var _view:BasicView = getChildByName("view" + i) as BasicView;
				var logoRootNode:DisplayObject3D = _view.scene.getChildByName("_logoRootNode") as DisplayObject3D;
				var dang:Number = Math.PI * 2 / floorArr[i];
				Tweener.addTween(logoRootNode, { 
					rotationY: now_kakudou_num * dang * 180 / Math.PI -30, 
					time:1, 
					transition:"linear"
					} );
			}
		}
		
		private function initKakudou(b:Boolean) {
			if (b) {
				now_kakudou_num++;
				now_kakudou_num = now_kakudou_num < _kakudou.length? now_kakudou_num : now_kakudou_num - _kakudou.length;
				//now_kakudou += _kakudou[now_kakudou_num];
			}else {
				now_kakudou_num--;
				now_kakudou_num = now_kakudou_num < 0?now_kakudou_num + _kakudou.length:now_kakudou_num;
				//now_kakudou -= _kakudou[now_kakudou_num];
			}
			moveLogo3D();
			floorMove(b);
		}
		
		private function makeLogo() {
			var _start:int = 0;
			for (var i = 0; i < floorArr.length(); i++) {
				var dang:Number = Math.PI * 2 / floorArr[i];
				var _view:BasicView = getChildByName("view" + i) as BasicView;
				var logoRootNode:DisplayObject3D = new DisplayObject3D();
				logoRootNode.name = "_logoRootNode";
				_view.scene.addChild(logoRootNode);
				
				for (var j = 1; j <= floorArr[i]; j++) {
					var _ang:Number = j * dang;
					var _img:String = mod.rooturl + "/" + logolist[_start].img_path;			
					var _bmpMat:BitmapFileMaterial = new BitmapFileMaterial(_img);
					_bmpMat.doubleSided = true; //雙面模式
					_bmpMat.smooth = true; // 平滑化
					var _plane	:Plane = new Plane(_bmpMat, 100, 100, 2, 2);
					_plane.useOwnContainer = true;
					_plane.alpha = 0;
					_plane.x = Math.cos(_ang) * radius;
					_plane.z = Math.sin(_ang) * radius;
					//trace(_start,j,_kakudou[j - 1]);
					_plane.rotationY = 270 - (_ang * 180 / Math.PI);
					logoRootNode.addChild(_plane);
					Tweener.addTween(_plane,{
												alpha		: 1,
												time		: 0.3,
												transition	:"linear",
												delay		:0.5
											}
										);
					_start++;
				}
				logoRootNode.rotationY = -30;
			}
		}
		
		private function onEventRender3D(e:Event):void {
			for (var i = 0; i < floorArr.length(); i++) {
				var _view:BasicView = getChildByName("view" + i) as BasicView;
				_view.singleRender();
			}
		}
	}
}