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

architrave

Get Adobe Flash player
by ABA 25 Nov 2012
/**
 * Copyright ABA ( http://wonderfl.net/user/ABA )
 * MIT License ( http://www.opensource.org/licenses/mit-license.php )
 * Downloaded from: http://wonderfl.net/c/1BUD
 */

package {
    import flash.display.Sprite;
    [SWF(width="465", height="465", backgroundColor="0xffffff", frameRate="60")]
    public class Main extends Sprite  {
        public function Main():void  {
            initialize(this);
        }
    }
}
import flash.display.Graphics;
import flash.display.Shape;
import flash.events.Event;
import flash.events.MouseEvent;
import flash.geom.Matrix;
import flash.geom.Point;
import flash.geom.Vector3D;
import flash.text.TextField;
var main:Main;
var g:Graphics;
var screen:Screen;
var innerPolygon:Polygon;
var outerPolygon:Polygon;
var overlayg:Graphics;
function initialize(main:Main):void {
    this.main = main;
    var textField:TextField = new TextField;
    textField.text = "Click to try another combination.";
    textField.width = 200;
    main.addChild(textField);
    g = main.graphics;
    screen = new Screen;
    var overlayShape:Shape = new Shape;
    main.addChild(overlayShape);
    overlayg = overlayShape.graphics;
    setInnterOuterPolygons();
    main.stage.addEventListener(MouseEvent.CLICK, onClicked);
    main.addEventListener(Event.ENTER_FRAME, update);
}
function onClicked(e:MouseEvent):void {
    setInnterOuterPolygons();
}
var rollSpeed:Number;
function setInnterOuterPolygons():void {
    overlayg.clear();
    overlayg.lineStyle(1, 0);
    innerPolygon = new Polygon(30, 150, false);
    outerPolygon = new Polygon(20, 100, true);
    outerPolygon.addDots(0, 0);
    var c:Contact = new Contact;
    c.polygon = outerPolygon;
    c.side = outerPolygon.sides[1];
    c.distance = 0;
    c.onCorner = true;
    outerPolygon.contact = c;
    var ic:Contact = new Contact;
    ic.polygon = innerPolygon;
    ic.side = innerPolygon.sides[0];
    ic.distance = 0;
    outerPolygon.innerContact = ic;
    outerPolygon.calcAnglePrevNextOuter();
    rollSpeed = 0.02;
}
function update(e:Event):void {
    g.clear();
    g.lineStyle(1, 0);
    innerPolygon.setAngleAbtolute();
    innerPolygon.calcSidePoss();
    innerPolygon.draw();
    outerPolygon.calcPosFromContact();
    outerPolygon.calcSidePoss();
    outerPolygon.draw();
    outerPolygon.roll(rollSpeed);
    if (rollSpeed < 0.5) rollSpeed += 0.001;
}
class Polygon {
    public var pos:Point = new Point;
    public var sides:Vector.<Side> = new Vector.<Side>;
    public var contact:Contact = new Contact;
    public var innerContact:Contact = new Contact;
    public var angle:Number = 0;
    public var anglePrev:Number, angleNext:Number;
    public var dots:Vector.<Point> = new Vector.<Point>;
    public var dotsPrev:Vector.<Point> = new Vector.<Point>;
    public var cornerAngle:Number;
    public function Polygon(minSize:Number, maxSize:Number, isCounterclockwise:Boolean) {
        var size:Number = rand() * (maxSize - minSize) + minSize;
        var w:Number, h:Number;
        switch (int(rand() * 3)) {
        case 0:
            w = size;
            h = 0;
            setPolygon(32, size / 2, isCounterclockwise);
            break;
        case 1:
            w = size * (rand() + 0.2);
            h = size * (rand() + 0.2);
            setSquare(w, h, isCounterclockwise);
            break;
        case 2:
            var n:int = 3 + int(rand() * 2) * 2;
            w = size;
            h = 2 * size * sin(PI / n);
            setPolygon(n, size / 2, isCounterclockwise);
            break;
        }
        pos.x = screen.center.x - w / 2;
        pos.y = screen.center.y - h / 2;
    }
    public function setSquare(width:Number, height:Number, isCounterclockwise:Boolean):void {
        var firstSide:Side;
        var prevSide:Side;
        var side:Side;
        cornerAngle = PI / 2;
        for (var i:int = 0; i < 4; i++) {
            side = new Side;
            if (i == 0) side.isFirst = true;
            if (i % 2 == 0)    side.length = height;
            else side.length = width;
            side.angle = i * cornerAngle;
            if (isCounterclockwise) side.angle *= -1;
            side.angle = normalizeAngle(side.angle);
            if (prevSide) {
                prevSide.nextSide = side;
                side.prevSide = prevSide;
            }
            sides.push(side);
            if (!firstSide) firstSide = side;
            prevSide = side;
        }
        side.nextSide = firstSide;
        firstSide.prevSide = side;
    }
    public function setPolygon(number:int, radius:Number, isCounterclockwise:Boolean):void {
        var firstSide:Side;
        var prevSide:Side;
        var side:Side;
        cornerAngle = PI2 / number;
        for (var i:int = 0; i < number; i++) {
            side = new Side;
            if (i == 0) side.isFirst = true;
            side.length = 2 * radius * sin(PI / number);
            side.angle = i * cornerAngle;
            if (isCounterclockwise) side.angle *= -1;
            side.angle = normalizeAngle(side.angle);
            if (prevSide) {
                prevSide.nextSide = side;
                side.prevSide = prevSide;
            }
            sides.push(side);
            if (!firstSide) firstSide = side;
            prevSide = side;
        }
        side.nextSide = firstSide;
        firstSide.prevSide = side;
    }
    public function addDots(x:Number, y:Number):void {
        dots.push(new Point(y, x));
        dotsPrev.push(new Point(-99999, -99999));
    }
    public function calcAnglePrevNextInner():void {
        anglePrev = -innerPolygon.cornerAngle;
        angleNext = 0;
    }
    public function calcAnglePrevNextOuter():void {
        anglePrev = -outerPolygon.cornerAngle;
        angleNext = 0;
    }
    private function gotoPrev(overAngle:Number):void {
        if (contact.onCorner) {
            if (innerContact.distance < contact.side.prevSide.length) {
                contact.side = contact.side.prevSide;
                contact.distance = contact.side.length - innerContact.distance;
                contact.onCorner = false;
                innerContact.distance = 0;
                innerContact.onCorner = true;
            } else {
                contact.side = contact.side.prevSide;
                innerContact.distance -= contact.side.length;
            }
        } else {
            if (contact.distance < innerContact.side.prevSide.length) {
                innerContact.side = innerContact.side.prevSide;
                innerContact.distance = innerContact.side.length - contact.distance;
                innerContact.onCorner = false;
                contact.distance = 0;
                contact.onCorner = true;
            } else {
                contact.distance -= innerContact.side.length;
                innerContact.side = innerContact.side.prevSide;
            }
        }
        if (contact.onCorner) calcAnglePrevNextOuter();
        else calcAnglePrevNextInner();
        angle = angleNext + overAngle;
    }
    private function gotoNext(overAngle:Number):void {
        if (contact.onCorner) {
            if (innerContact.side.length - innerContact.distance < contact.side.length) {
                contact.distance = innerContact.side.length - innerContact.distance;
                contact.onCorner = false;
                innerContact.distance = 0;
                innerContact.onCorner = true;
                innerContact.side = innerContact.side.nextSide;
            } else {
                innerContact.distance += contact.side.length;
                contact.side = contact.side.nextSide;
            }
        } else {
            if (contact.side.length - contact.distance  < innerContact.side.length) {
                innerContact.distance = contact.side.length - contact.distance;
                innerContact.onCorner = false;
                contact.distance = 0;
                contact.onCorner = true;
                contact.side = contact.side.nextSide;
            } else {
                contact.distance += innerContact.side.length;
                innerContact.side = innerContact.side.nextSide;
            }
        }
        if (contact.onCorner) calcAnglePrevNextOuter();
        else calcAnglePrevNextInner();
        angle = anglePrev + overAngle;
    }
    public function roll(a:Number):void {
        angle += a;
        while (angle < anglePrev) gotoPrev(angle - anglePrev);
        while (angle >= angleNext) gotoNext(angle - angleNext);
    }
    private var sidePos:Vector3D = new Vector3D;
    public function calcSidePoss():void {
        var s:Side;
        s = sides[0];
        s.pos.x = sidePos.x = pos.x;
        s.pos.y = sidePos.y = pos.y;
        var a:Number = s.angleAbsolute;
        for (var i:int = 1; i < sides.length; i++) {
            s = sides[i - 1];
            sidePos.x += sin(a) * s.length;
            sidePos.y += cos(a) * s.length;
            a += (s.nextSide.angle - s.angle);
            s = sides[i];
            s.pos.x = sidePos.x;
            s.pos.y = sidePos.y;
            s.angleAbsolute = a;
        }
    }
    private var rollMat:Matrix = new Matrix;
    public function draw():void {
        var s:Side;
        s = sides[0];
        g.moveTo(s.pos.x, s.pos.y);
        for (var i:int = 1; i < sides.length; i++) {
            s = sides[i];
            g.lineTo(s.pos.x, s.pos.y);
        }
        s = sides[0];
        g.lineTo(s.pos.x, s.pos.y);
        if (!contact.side) return;
        rollMat.identity();
        rollMat.rotate(contact.side.prevSide.angle - innerContact.side.angle - angle);
        for (i = 0; i < dots.length; i++) {
            var rp:Point = rollMat.transformPoint(dots[i]);
            var dp:Point = dotsPrev[i];
            var df:Boolean = (dp.x > -9);
            if (df) overlayg.moveTo(dp.x, dp.y);
            dp.x = rp.x + pos.x;
            dp.y = rp.y + pos.y;
            if (df) overlayg.lineTo(dp.x, dp.y);
        }
    }
    public function setAngleAbtolute():void {
        sides[0].angleAbsolute = angle + sides[0].angle;
    }
    public function calcPosFromContact():void {
        var p:Vector3D = calcContactPos();
        var s:Side = contact.side;
        var a:Number = innerContact.side.angleAbsolute + angle;
        p.x -= sin(a) * contact.distance;
        p.y -= cos(a) * contact.distance;
        for (;; ) {
            if (s.isFirst) break;
            a -= (s.angle - s.prevSide.angle);
            s = s.prevSide;
            p.x -= sin(a) * s.length;
            p.y -= cos(a) * s.length;
        }
        s.angleAbsolute = a;
        pos.x = p.x;
        pos.y = p.y;
    }
    private var contactPos:Vector3D = new Vector3D;
    private function calcContactPos():Vector3D {
        var s:Side = innerContact.side;
        contactPos.x = s.pos.x + sin(s.angleAbsolute) * innerContact.distance;
        contactPos.y = s.pos.y + cos(s.angleAbsolute) * innerContact.distance;
        return contactPos;
    }
}
class Side {
    public var length:Number
    public var angle:Number;
    public var prevSide:Side;
    public var nextSide:Side;
    public var pos:Vector3D = new Vector3D;
    public var angleAbsolute:Number;
    public var isFirst:Boolean;
}
class Contact {
    public var polygon:Polygon;
    public var side:Side;
    public var distance:Number;
    public var onCorner:Boolean;
}
class Screen {
    public var size:Vector3D;
    public var center:Vector3D;
    function Screen() {
        size = new Vector3D(main.stage.stageWidth, main.stage.stageHeight);
        center = new Vector3D(size.x / 2, size.y / 2);
    }
}
var PI:Number = Math.PI;
var PI2:Number = Math.PI * 2;
var sin:Function = Math.sin;
var cos:Function = Math.cos;
var rand:Function = Math.random;
function normalizeAngle(angle:Number):Number {
    var r:Number = angle % PI2;
    if (r > PI) r -= PI2;
    else if (r < -PI) r += PI2;
    return r;
}