// forked from checkmate's Checkmate Vol.6 Amatuer // 2009/12/20 frameRate 調整、およびそれに伴う物理定数調整 package { import flash.display.Sprite; import flash.events.Event; [SWF(width = "465", height = "465", frameRate = "60", backgroundColor = "0xFFFFFF")] public class CheckmateAmatuer extends Sprite { private var circle1:LiquidCircle; private var circle2:LiquidCircle; private var star1:LiquidStar; private var star2:LiquidStar; public function CheckmateAmatuer() { /* コードでエッチなものごとを描写してください。 公序良俗は守ってください。 Represent something sexual by codes. DO NOT be offensive to public order and morals. */ const SIZE_CIRCLE:Number = 50.0; const SCALE_CIRCLE:Number = 2.0; const COLOR_CIRCLE:uint = 0xFFCC99; const SIZE_STAR:Number = 10.0; const SCALE_STAR:Number = 12.5; const COLOR_STAR:uint = 0xFFFF66; const DIST:uint = 50; const centerX:Number = stage.stageWidth / 2; const centerY:Number = stage.stageHeight / 2; circle1 = new LiquidCircle(SIZE_CIRCLE, SCALE_CIRCLE); circle1.x = centerX - DIST; circle1.y = centerY; addChild(circle1); circle2 = new LiquidCircle(SIZE_CIRCLE, SCALE_CIRCLE); circle2.x = centerX + DIST; circle2.y = centerY; addChild(circle2); star1 = new LiquidStar(SIZE_STAR, SCALE_STAR); star1.x = centerX - DIST; star1.y = centerY; addChild(star1); star2 = new LiquidStar(SIZE_STAR, SCALE_STAR); star2.x = centerX + DIST; star2.y = centerY; addChild(star2); var facadeCurveTo:FacadeCurveTo = new FacadeCurveTo(); facadeCurveTo.defineFill(COLOR_CIRCLE); circle1.drawFacade = facadeCurveTo; circle2.drawFacade = facadeCurveTo; var facadeLineTo:FacadeLineTo = new FacadeLineTo(); facadeLineTo.defineFill(COLOR_STAR); star1.drawFacade = facadeLineTo; star2.drawFacade = facadeLineTo; addEventListener(Event.ENTER_FRAME, enterFrameHandler); } private function enterFrameHandler(event:Event):void { circle1.update(); circle2.update(); star1.update(); star2.update(); } } } import flash.display.Graphics; import flash.display.Sprite; import flash.geom.Point; /** * 流動的な図形を描く(抽象クラス) * @author YOSHIDA, Akio (Aquioux) */ class Liquid extends Sprite { // DrawAPI ファサード public function set drawFacade(value:FacadeDraw):void { _drawFacade = value; _drawFacade.definePath(numOfPoint); _drawFacade.build(); } protected var _drawFacade:FacadeDraw; // ドローポイントの数 protected var numOfPoint:uint; // ドローポイントを格納する配列 protected var drawPoints:Array; function Liquid() {} // ドローポイントの座標を計算して、一時的な Vector に格納する protected function createCoordinate(radius:Number):Vector.<Number> { // サブクラスで定義 return null; } // drawPoint の生成 protected function createDrawPoints(vector:Vector.<Number>, length:Number, distOfReaction:Number):void { var first:DrawPoint; var prev:DrawPoint; var n:uint = numOfPoint; drawPoints = []; for (var i:int = 0; i < n; i++) { var drawPoint:DrawPoint = new DrawPoint(vector[i * 2], vector[i * 2 + 1], length, distOfReaction); drawPoints.push(drawPoint); prev = (i == 0) ? first = drawPoint : prev.next = drawPoint; } // 最後の drawPoint の next を最初の drawPoint に設定 drawPoint.next = first; // 配列の一番最初に、最後の drawPointl を追加 drawPoints.unshift(drawPoint); } // 更新 public function update():void { updatePosition(); // drawPoint の位置更新 updateData(); // 描画のための座標 Vector の更新 updateDraw(); // 描画 } // DrawPoint の位置更新 private function updatePosition():void { var posX:Number = this.mouseX; var posY:Number = this.mouseY; var dist:Number = Math.sqrt(posX * posX + posY * posY); const N:uint = numOfPoint; for (var i:int = 0; i < N; i++) { var drawPoint:DrawPoint = drawPoints[i]; drawPoint.update(posX, posY, dist); } } // 描画のための座標 Vector の更新 protected function updateData():void { // サブクラスで定義 } // 描画 private function updateDraw():void { var g:Graphics = this.graphics; g.clear(); g.drawGraphicsData(_drawFacade.graphicsData); } } import flash.display.Graphics; import flash.display.Sprite; import flash.geom.Point; /** * 流動的な円を描く * @author YOSHIDA, Akio (Aquioux) */ class LiquidCircle extends Liquid { function LiquidCircle(radius:Number = 50.0, rate:Number = 2.0) { numOfPoint = 8; createDrawPoints(createCoordinate(radius), radius * rate, radius * 0.9); } // ドローポイントの座標を計算して、一時的な Vector に格納する override protected function createCoordinate(radius:Number):Vector.<Number> { const RADIAN:Number = Math.PI * 2 / numOfPoint; var vector:Vector.<Number> = new Vector.<Number>(); var n:uint = numOfPoint; for (var i:int = 0; i < n; i++) { var p:Point = Point.polar(radius, RADIAN * i); vector.push(p.x, p.y); } vector.fixed = true; return vector; } // 描画のための座標 Vector の更新 override protected function updateData():void { var data:Vector.<Number> = _drawFacade.data; // moveTo var drawPoint:DrawPoint = drawPoints[0]; var anchorX:Number = (drawPoint.x + drawPoint.next.x) / 2; var anchorY:Number = (drawPoint.y + drawPoint.next.y) / 2; var idx:uint = 0; data[idx++] = anchorX; data[idx++] = anchorY; // curveTo var n:uint = drawPoints.length; for (var i:int = 0; i < n; i++) { drawPoint = drawPoint.next; anchorX = (drawPoint.x + drawPoint.next.x) / 2; anchorY = (drawPoint.y + drawPoint.next.y) / 2; data[idx++] = drawPoint.x; data[idx++] = drawPoint.y; data[idx++] = anchorX; data[idx++] = anchorY; } } } import flash.display.Graphics; import flash.display.Sprite; import flash.geom.Point; /** * 流動的な☆を描く * @author YOSHIDA, Akio (Aquioux) */ class LiquidStar extends Liquid { function LiquidStar(radius:Number = 50.0, rate:Number = 2.0) { numOfPoint = 10; createDrawPoints(createCoordinate(radius), radius * rate, radius * 4.9); var n:uint = drawPoints.length; for (var i:int = 0; i < n; i++) { if (i % 2) { drawPoints[i].convex = true; } } } // ドローポイントの座標を計算して、一時的な Vector に格納する override protected function createCoordinate(radius:Number):Vector.<Number> { const RADIAN:Number = Math.PI * 2 / numOfPoint; const OFFSETRADIAN:Number = Math.PI / 2; var vector:Vector.<Number> = new Vector.<Number>(); var n:uint = numOfPoint; for (var i:int = 0; i < n; i++) { var radius2:Number = (i % 2) ? radius / 2 : radius; var p:Point = Point.polar(radius2, RADIAN * i + OFFSETRADIAN); vector.push(p.x, p.y); } vector.fixed = true; return vector; } // 描画のための座標 Vector の更新 override protected function updateData():void { var data:Vector.<Number> = _drawFacade.data; // moveTo var idx:uint = 0; var drawPoint:DrawPoint = drawPoints[0]; data[idx++] = drawPoint.x; data[idx++] = drawPoint.y; // lineTo var n:uint = drawPoints.length; for (var i:int = 0; i < n; i++) { drawPoint = drawPoint.next; data[idx++] = drawPoint.x; data[idx++] = drawPoint.y; } } } /** * ドローポイント * LinkedList になっている * マウスの位置に応じて動く * @author YOSHIDA, Akio (Aquioux) */ class DrawPoint { // LinkedList public function get next():DrawPoint { return _next; } public function set next(value:DrawPoint):void { _next = value; } private var _next:DrawPoint; // 現在のX座標 public function get x():Number { return _x; } private var _x:Number; // 現在のY座標 public function get y():Number { return _y; } private var _y:Number; // 凸フラグ public function set convex(value:Boolean):void { _convex = value; } private var _convex:Boolean = false; private const SPRING:Number = 0.059; // 弾性 private const FRICTION:Number = 0.82; // 抵抗 private var vx:Number = 0; // ヴェロシティX座標 private var vy:Number = 0; // ヴェロシティY座標 private var localY:Number; // 既定X座標 private var localX:Number; // 既定Y座標 private var length:Number; // マウス反応時の伸長距離 private var distOfReaction:Number; // マウス反応距離 public function DrawPoint(x:Number, y:Number, length:Number, distOfReaction:Number) { _x = localX = x; _y = localY = y; this.length = length; this.distOfReaction = distOfReaction; } public function update(targetX:Number, targetY:Number, dist:Number):void { var flg:uint = (dist > distOfReaction) ? 1 : 0; var radian:Number = Math.atan2(targetY * flg - localY , targetX * flg - localX); var length2:Number = (_convex && flg == 0) ? length / 2 : length; var tx:Number = localX - Math.cos(radian) * length2; var ty:Number = localY - Math.sin(radian) * length2; vx += (tx - _x) * SPRING; vy += (ty - _y) * SPRING; vx *= FRICTION; vy *= FRICTION; _x += vx; _y += vy; } } import flash.display.GraphicsEndFill; import flash.display.GraphicsPath; import flash.display.GraphicsPathCommand; import flash.display.GraphicsSolidFill; import flash.display.GraphicsStroke; import flash.display.IGraphicsData; /** * GraphicsAPI Facade(抽象クラス) * @author YOSHIDA, Akio (Aquioux) */ class FacadeDraw{ // Graphics.drawGraphicsData の引数 public function get graphicsData():Vector.<IGraphicsData> { return _graphicsData; } protected var _graphicsData:Vector.<IGraphicsData>; // GraphicsPath の command public function get data():Vector.<Number> { return _data; } protected var _data:Vector.<Number>; protected var fill:GraphicsSolidFill; // 塗り protected var stroke:GraphicsStroke; // 線 protected var commands:Vector.<int>; // GraphicsPath の command public function FacadeDraw() {} // 塗りの定義 public function defineFill(color:uint, alpha:Number = 1.0):void { fill = new GraphicsSolidFill(color, alpha); } // 線の定義 public function defineStroke(thickness:Number, color:uint, alpha:Number):void { stroke = new GraphicsStroke(); stroke.thickness = thickness; stroke.fill = new GraphicsSolidFill(color, alpha); } // パスの定義 public function definePath(num:uint):void { // サブクラスで定義 } public function build():void { _graphicsData = new Vector.<IGraphicsData>(); _graphicsData.push(fill); //_graphicsData.push(stroke); _graphicsData.push(new GraphicsPath(commands, _data)); _graphicsData.push(new GraphicsEndFill()); } } import flash.display.GraphicsPathCommand; /** * Graphics.curveTo Facade * @author YOSHIDA, Akio (Aquioux) */ class FacadeCurveTo extends FacadeDraw { public function FacadeCurveTo() {} // パスの定義 override public function definePath(num:uint):void { // コマンド commands = new Vector.<int>(); commands.push(GraphicsPathCommand.MOVE_TO); for (var i:int = 0; i < num; i++) { commands.push(GraphicsPathCommand.CURVE_TO); } commands.fixed = true; // 座標 var len:uint = (num + 1) * 4 + 2; _data = new Vector.<Number>(len, true); } } import flash.display.GraphicsPathCommand; /** * Graphics.lineTo Facade * @author YOSHIDA, Akio (Aquioux) */ class FacadeLineTo extends FacadeDraw { public function FacadeLineTo() {} // パスの定義 override public function definePath(num:uint):void { // コマンド commands = new Vector.<int>(); commands.push(GraphicsPathCommand.MOVE_TO); for (var i:int = 0; i < num; i++) { commands.push(GraphicsPathCommand.LINE_TO); } commands.fixed = true; // 座標 var len:uint = (num + 1) * 2 + 2; _data = new Vector.<Number>(len, true); } } forked from: Checkmate Vol.6 Amatuerx(スライムな●と★)