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

ペジェ曲線

3次までのペジェ曲線を描くサンプル
クリックした場所を制御点に加えていきます。
Get Adobe Flash player
by Horiuchi_H 30 Sep 2009
/**
 * Copyright Horiuchi_H ( http://wonderfl.net/user/Horiuchi_H )
 * MIT License ( http://www.opensource.org/licenses/mit-license.php )
 * Downloaded from: http://wonderfl.net/c/4ooa
 */

package 
{
	import flash.display.Graphics;
	import flash.display.Sprite;
	import flash.display.Stage;
	import flash.events.Event;
	import flash.events.MouseEvent;
	
	[SWF(width = 465, height = 465, frameRate = 60, backgroundColor = "#000000")]
	
	/**
	 * 3次までのペジェ曲線を描くサンプル
	 * クリックした場所を制御点に加えていきます。
	 */
	public class BezierCurve extends Sprite
	{
		private static const CURVE_POINT:int = 4;
		private static const DRAW_COUNT:Number = 100;
		
		private var clickPoints:Array = [];
		private var frame:Number = -1;
		
		private var g:Graphics;
		
		public function BezierCurve() {
			if (stage) init();
			else addEventListener(Event.ADDED_TO_STAGE, init);
		}
		
		private function init(e:Event = null):void {
			removeEventListener(Event.ADDED_TO_STAGE, init);
			// entry point
			g = this.graphics;
			
			this.stage.addEventListener(MouseEvent.CLICK, stageClickEventHandler);
			this.stage.addEventListener(Event.ENTER_FRAME, drawCurve);
		}
		
		
		private function stageClickEventHandler(event:MouseEvent):void {
			var point:/*Number*/Array = [event.stageX, event.stageY];
			frame = 0;
			
			if (clickPoints.length >= CURVE_POINT) {
				clearStage();
				clickPoints = [];
				frame = -1;
			}
			
			clickPoints.push(point);
			g.lineStyle(1, 0xffffff);
			g.drawCircle(point[0], point[1], 5.0);
			
			if (true) {
				// for debug
				g.lineStyle(1, 0x66666666);
				g.moveTo(clickPoints[0][0], clickPoints[0][1]);
				for (var i:int = 1; i < clickPoints.length; i++) {
					g.lineTo(clickPoints[i][0], clickPoints[i][1]);
				}
			}
			
			if (clickPoints.length > 1) {
				var from:/*Number*/Array = calcBezierCurvePoint(clickPoints, 0);
				g.lineStyle(2, 0x33cc66);
				g.moveTo(from[0], from[1]);
				for (var index:int = 1; index <= DRAW_COUNT; index++) {
					var to:/*Number*/Array = calcBezierCurvePoint(clickPoints, index / DRAW_COUNT);
					g.lineTo(to[0], to[1]);
					trace(to[0] + "," + to[1]);
				}
			}
		}
		
		private function clearStage():void {
			g.clear();
		}
		
		private function drawCurve(event:Event = null):void {
			if (frame < 0) return;
			if (frame >= DRAW_COUNT) return;
			
			var start:/*Number*/Array = calcBezierCurvePoint(clickPoints, frame / DRAW_COUNT);
			var end:/*Number*/Array = calcBezierCurvePoint(clickPoints, (frame + 1)/ DRAW_COUNT);
			g.lineStyle(1, 0xffffff);
			g.moveTo(start[0], start[1]);
			g.lineTo(end[0], end[1]);
			frame++;
		}
		
		private function calcBezierCurvePoint(points:Array, t:Number):/*Number*/Array {
			var ps:Array = points;
			while (ps.length > 1) {
				var next:Array = [];
				for (var index:int = 0; index < ps.length - 1; index++) {
					next[index] = calcCutoffPoint(ps[index], ps[index + 1], t);
				}
				ps = next;
			}
			return ps[0];
		}
		
		private function calcCutoffPoint(startPoint:/*Number*/Array, endPoint:/*Number*/Array, t:Number):/*Number*/Array {
			return [
				startPoint[0] + (endPoint[0] - startPoint[0]) * t,
				startPoint[1] + (endPoint[1] - startPoint[1]) * t,
			];
		}
	}
}