表示位置を直して形も変えた

by nabe forked from 1つのSpriteに表示してhitAreaは別々 (diff: 128)
♥0 | Line 182 | Modified 2010-02-28 11:39:08 | MIT License
play

ActionScript3 source code

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

// forked from nabe's 1つのSpriteに表示してhitAreaは別々
// forked from nabe's 別々のSpriteに描画
// forked from nabe's 1つのSpriteに描画
package {
	import flash.display.DisplayObject;
	import flash.display.Graphics;
	import flash.display.SimpleButton;
	import flash.display.Sprite;
	import flash.events.Event;
	import flash.events.MouseEvent;
	import flash.geom.*;
    [SWF(width="465", height="465", backgroundColor="0", frameRate="24")]
	public class Main extends Sprite {
		private var fx:Number;
		private var fy:Number;
		public function Main ():void {
			addEventListener(Event.ADDED_TO_STAGE, init_);
		}
		private function init_(e:Event):void {
			removeEventListener(Event.ADDED_TO_STAGE, init_);
			var w_:int = stage.stageWidth * 0.5;
			var h_:int = stage.stageHeight * 0.5;
			x = w_;
			y = h_;
			append_(w_ * (Math.random() - 0.5), h_ * (Math.random() - 0.5));
			addEventListener(Event.ENTER_FRAME, update_);
			stage.addEventListener(MouseEvent.CLICK, click_);
		}
		private function click_(e:MouseEvent):void {
		//クリックした位置に子を追加する。
			append_(mouseX, mouseY);
		}
		private function append_(x_:Number, y_:Number):void {
		//子を追加する。
			const useMask_:Boolean = true;
			//子SpriteにhitAreaを設定するか?
			addChild(new Cube(x_, y_, useMask_));
		}
		private function update_(e:Event):void {
		//アニメーション。
			const split_:Boolean = false;
			//子SpriteでBitmapFillするか?
			var g_:Graphics
			g_ = graphics;
			g_.clear();
			var n_:int = this.numChildren;
			for (var i_:int = 0; i_ < n_; ++i_) {
				var cube_:Cube = this.getChildAt(i_) as Cube;
				if (!cube_) continue;
				if (split_) {
					g_ = cube_.graphics;
					g_.clear();
				}
				cube_.update_(g_);
			}
		}
	}
}

import flash.display.Bitmap;
import flash.display.BitmapData;
import flash.display.GradientType;
import flash.display.Graphics;
import flash.display.Shape;
import flash.display.TriangleCulling;
import flash.events.MouseEvent;
import flash.geom.Matrix;
import flash.geom.Matrix3D;
import flash.geom.PerspectiveProjection;
import flash.geom.Point;
import flash.geom.Utils3D;
import flash.geom.Vector3D;
import flash.display.Sprite;
import flash.events.Event;
class Cube extends Sprite {
	private var vertices3D:Vector.<Number> = new Vector.<Number>;
	private var vertices2D:Vector.<Number> = new Vector.<Number>;
	private var indices:Vector.<int> = new Vector.<int>;
	private var uvtData:Vector.<Number> = new Vector.<Number>;
	private var texture_:BitmapData;
	private var sum_rot:Matrix3D;
	private var add_rot:Matrix3D;
	private var trans_:Vector3D;
	private var pers_:Matrix3D;
	private var useMask_:Boolean;
	public function Cube(x_:Number, y_:Number, useMask_:Boolean):void {
		this.useMask_ = useMask_;
		trans_ = new Vector3D(x_, y_, 1000);
		addEventListener(Event.ADDED_TO_STAGE, init_);
	}
	private function init_(e:Event):void {
		removeEventListener(Event.ADDED_TO_STAGE, init_);

		var m_:Matrix3D = root.transform.perspectiveProjection.toMatrix3D();
		var p_:Vector3D = m_.transformVector(new Vector3D(1, 1, 1000, 1));
		trans_.x *= p_.z / p_.x;
		trans_.y *= p_.z / p_.y;

		data_();
		addEventListener(MouseEvent.CLICK, remove_);
		if (useMask_) {
			var mask_:Sprite = new Sprite;
			mask_.mouseEnabled = false;
			hitArea = mask_;
			mask_.visible = false;
			addChild(mask_);
		}
	}
	public function update_(g_:Graphics):void {
		move_();
		draw_(g_, true);
		if (useMask_) {
			var m_:Graphics = hitArea.graphics;
			m_.clear();
			draw_(m_, false);
		}
	}
	private function data_():void {
	//回転の用意。
		sum_rot = new Matrix3D;
		add_rot = new Matrix3D;
		var axis_:Vector3D = new Vector3D(Math.random() - 0.5, Math.random() - 0.5, Math.random() - 0.5);
		axis_.normalize();
		add_rot.appendRotation((Math.random() - 0.5) * 10, axis_);
	//投影の用意。
		pers_ = root.transform.perspectiveProjection.toMatrix3D();
	//テクスチャの用意。
		texture_ = newTexture_(400, 300, 10);
	//分割数
		const unum:int = 8;
		const vnum:int = 6;
		const r_:int = 100;
		var b0:int = 0;
		var b1:int = 0;
		for (var u_:int = 0; u_ <= unum; ++u_) {
			var upos:Number = u_ / unum;
			var urad:Number = Math.PI * 2 * upos;
			var xpos:Number = r_ * Math.cos(urad);
			var zpos:Number = r_ * Math.sin(urad);
			for (var v_:int = 0; v_ <= vnum; ++v_) {
				var vpos:Number = v_ / vnum;
				var vrad:Number = -Math.PI * vpos;
				var ypos:Number = r_ * Math.cos(vrad);
				var ysin:Number = Math.sin(vrad);
				uvtData.push(upos, vpos, 0);
				vertices3D.push(xpos * ysin, ypos, zpos * ysin);
			}
			if (u_ == 0) continue;
			b0 = b1;
			b1 += vnum + 1;
			for (var i_:int = 1; i_ < vnum; ++i_) {
				indices.push(
					b0 + i_ - 1, b1 + i_ + 0, b0 + i_ + 0,
					b0 + i_ + 0, b1 + i_ + 0, b1 + i_ + 1
				);
			}
		}
	}
	private function move_():void {
	//座標を更新する。
		sum_rot.append(add_rot);
		var mat:Matrix3D = sum_rot.clone();
		mat.appendTranslation(trans_.x, trans_.y, trans_.z);
		mat.append(pers_);
		Utils3D.projectVectors(mat, vertices3D, vertices2D, uvtData);
	}
	private function draw_(g_:Graphics, show_:Boolean):void {
	//渡された画面に描画する。
		if (show_) {
		//表示用。
			g_.beginBitmapFill(texture_, null, false, true);
			g_.drawTriangles(vertices2D, indices, uvtData, TriangleCulling.POSITIVE);
		} else {
		//マスク用。
			g_.beginFill(0xFFCCCC);
			g_.drawTriangles(vertices2D, indices, null, TriangleCulling.POSITIVE);
		}
		g_.endFill();
	}
	private function remove_(e:Event):void {
	//クリックすると消える。
		parent.removeChild(this);
		e.stopPropagation();
	}
	private function newTexture_ (width_:int, height_:int, size_:int):BitmapData {
	//ピンク色の方眼紙。
		var s_:Shape = new Shape;
		var g_:Graphics = s_.graphics;
		g_.clear();
		g_.lineStyle(1, 0xFF0000);
	//縦線。
		for (var x_:int = 0; x_ < width_; x_ += size_) {
			g_.moveTo(x_, 0);
			g_.lineTo(x_, height_);
		}
	//横線。
		for (var y_:int = 0; y_ < height_; y_ += size_) {
			g_.moveTo(0, y_);
			g_.lineTo(width_, y_);
		}
	//ビットマップに転記する。
		var r_:BitmapData = new BitmapData(width_, height_, false, 0xFFCCCC);
		r_.draw(s_);
		return r_;
	}
}