// forked from ganad's gravitation package { import flash.events.MouseEvent; import flash.display.Shape; import flash.display.StageAlign; import flash.display.StageScaleMode; import flash.display.Bitmap; import flash.display.BitmapData; import flash.display.Sprite; import flash.events.Event; import flash.geom.ColorTransform; import flash.display.Sprite; /** * ... * @author ganad * @author Martin Heidegger */ public class Main extends Sprite { private static const AMOUNT_PLANETS: int = 600; public static const G: Number = 5.0; public var _sun:Sun; public var _planets:Vector.<Planet> = new Vector.<Planet>(); public function Main():void { if (stage) init(); else addEventListener(Event.ADDED_TO_STAGE, init); } private function init(e:Event = null):void { removeEventListener(Event.ADDED_TO_STAGE, init); stage.scaleMode = StageScaleMode.NO_SCALE; stage.align = StageAlign.TOP_LEFT; stage.frameRate = 40; createBackground(); createPlanets(AMOUNT_PLANETS); createSun(); addEventListener(Event.ENTER_FRAME, applyGravity); } private function createBackground(): void { stage.addEventListener(Event.RESIZE, drawBackground); drawBackground(); } private function drawBackground(e:Event=null): void { graphics.clear(); graphics.beginFill(0,1); graphics.drawRect(0, 0, stage.stageWidth, stage.stageHeight); } private function createPlanets(amount:int):void { for( var i: int = 0; i<amount; ++i) { addPlanet( randomBetween(60,180) | randomBetween(80,255) << 8 | randomBetween(150,255) << 16, randomBetween(1,40), randomBetween(5,10), randomBetween(-10,10), randomBetween(250,275), randomBetween(90,160) ) } /* addPlanet(1, 10, -10, 275, 150); addPlanet(1, 7, 3, 275, 150); addPlanet(40, 5, 5, 275, 100); addPlanet(20, 10, 0, 275, 150); */ } private function randomBetween(from: Number, to: Number): Number { return from + Math.random() * (to-from); } private function addPlanet(color: int, mass: int, vx:Number, vy:Number, x:Number, y:Number): void { var planet: Planet = new Planet(color, mass, vx, vy, x, y); _planets.push(planet); addChild(planet.line); } private function createSun(): void { var sun: Sun = new Sun(1000, 0, 0, 275, 200) addChild(sun.ball); _sun = sun; } private function applyGravity(e:Event = null):void { for (var i:int = 0; i < _planets.length; i++) { _planets[i].applyGravity(_sun, G); } } } } import flash.display.GraphicsGradientFill; import flash.display.IGraphicsPath; import flash.display.GraphicsPathCommand; import flash.display.GraphicsSolidFill; import flash.display.JointStyle; import flash.display.CapsStyle; import flash.display.LineScaleMode; import flash.display.GraphicsPath; import flash.display.GraphicsStroke; import flash.display.Shape; import flash.display.IGraphicsData; class StellarObject { public var vx:Number; public var vy:Number; public var x:Number = 0; public var y:Number = 0; public var mass:int; public function StellarObject(mass:int=50, vx:Number=40,vy:Number=0,x:Number=0,y:Number=0): void { this.mass = mass; this.vx = vx; this.vy = vy; this.x = x; this.y = y; } } class Sun extends StellarObject { private static const SUN_COLOR: int = 0xffff00; public var ball: Shape; public function Sun(mass:int=50, vx:Number=40,vy:Number=0,x:Number=0,y:Number=0): void { super(mass, vx, vy, x, y); ball = new Shape(); moveTo(x, y); } public function moveTo(x: Number, y: Number): void { this.x = x; this.y = y; ball.graphics.clear(); ball.graphics.beginFill(SUN_COLOR, 1); ball.graphics.drawCircle(x, y, 10); ball.graphics.endFill(); } } /** * ... * @author ganad */ class Planet extends StellarObject { public var line:MovingLine; public function Planet(color:int = 0xFF0000, mass:int=50, vx:Number=40,vy:Number=0,x:Number=0,y:Number=0) :void { super(mass, vx, vy, x, y); line = new MovingLine(color, x, y); } public function applyGravity(target: StellarObject, gravity: Number): void { var dx:Number = target.x-this.x; var dy:Number = target.y-this.y; var dist:Number = dx * dx + dy * dy; var angle:Number = Math.atan2(dy, dx); var F:Number = gravity * target.mass / dist; var vx:Number = F * Math.cos(angle); var vy:Number = F * Math.sin(angle); this.vx += vx; this.vy += vy; this.x += this.vx; this.y += this.vy; line.moveTo(this.x, this.y); } } class MovingLine extends Shape { private var _data: Vector.<IGraphicsData>; private var _paths: Vector.<GraphicsPath>; private var _hasMoved: Boolean = false; public function MovingLine(color: int, x: Number, y: Number) { createData(color, x, y, 4); } public function moveTo(x: Number, y: Number): void { for( var pathNo: int = 1; pathNo<_paths.length; ++pathNo) { var oldPath: GraphicsPath = _paths[pathNo-1]; var path: GraphicsPath = _paths[pathNo]; oldPath.data[0] = path.data[0]; oldPath.data[1] = path.data[1]; } if( !_hasMoved ) { path.data[0] = x; path.data[1] = y; _hasMoved = true; } path.data[0] = x; path.data[1] = y; graphics.clear(); graphics.drawGraphicsData(_data); } private function createStrokes(color: int, segments: int): Vector.<GraphicsStroke> { var alpha: Number = 1.0; var alphaDecay: Number = alpha/segments; var strokes: Vector.<GraphicsStroke> = new Vector.<GraphicsStroke>(segments); for( var i: int = 0; i<segments; ++i) { strokes[segments-i-1] = new GraphicsStroke(1, false, LineScaleMode.NONE, CapsStyle.NONE, JointStyle.MITER, 0, new GraphicsSolidFill(color, alpha) ); alpha -= alphaDecay; } return strokes; } private function createData(color: int, x: Number, y: Number, lines: int): void { var strokes: Vector.<GraphicsStroke> = createStrokes(color, lines); _paths = new Vector.<GraphicsPath>(lines+1); _data = new Vector.<IGraphicsData>(lines+_paths.length); var path: GraphicsPath = new GraphicsPath(new Vector.<int>(1), new Vector.<Number>(2)); path.commands[0] = GraphicsPathCommand.MOVE_TO; path.data[0] = x; path.data[1] = y; _paths[0] = path; _data[0] = path; for( var lineNo: int = 0, dataNo: int = 1; lineNo<lines; ++lineNo, dataNo+=2) { path = new GraphicsPath(new Vector.<int>(1), new Vector.<Number>(2)); _paths[lineNo+1] = path;; path.commands[0] = GraphicsPathCommand.LINE_TO; path.data[0] = x; path.data[1] = y; _data[dataNo] = strokes[lineNo]; _data[dataNo+1] = path; } } } gravitation (cleaned and uses vectors)