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

Virtual Aquarium with MotionTrack

せっかくカメラ使ってるのでモーショントラッキングも入れてみました。
画面からちょっと離れた方がいい感じで動きます。
/**
 * Copyright mousepancyo ( http://wonderfl.net/user/mousepancyo )
 * MIT License ( http://www.opensource.org/licenses/mit-license.php )
 * Downloaded from: http://wonderfl.net/c/4F99
 */

// forked from mousepancyo's Virtual Aquarium
package
{
    import flash.display.Bitmap;
    import flash.display.BitmapData;
    import flash.display.Sprite;
    import flash.events.Event;
    import flash.geom.Vector3D;
    import flash.geom.Point;
    import flash.media.Camera;
    import flash.media.Video;
    import flash.net.URLRequest;
    import flash.system.Security;
    import flash.system.LoaderContext;
    
    import jp.progression.commands.*;
    import jp.progression.commands.lists.*;
    import jp.progression.commands.lists.LoaderList;
    import jp.progression.commands.net.*;
    import jp.progression.data.*;
    import jp.progression.events.*;
    
    
    [SWF(width="465", height="465", frameRate="30", backgroundColor="0xFFFFFF")]
    public class Main extends Sprite
    {
        
        private const WIDTH:Number = 465;
        private const HEIGHT:Number = 465;
        private const NUM_FISH:int = 7;
        private const DEFAULT_URL:String = "http://www.digifie.jp/assets/images/111005/";
        private const NUM_MATERIAL:int = 10;
        
        private var _cam:Camera;
        public var video:Video;
        private var _imgList:Array /*BitmapData*/ = [];
        
        private var container3D:Sprite;
        
        // Fish
        private var _fishList:Array = [];
        private var _motionValList:Array = [4, 3, 2, 5, 2, 3, 4];
        
        // Bubble & Weed
        private var _bubble1:Bubble;
        private var _bubble2:Bubble;
        private var _weed1:PolyImage;
        private var _weed2:PolyImage;
        private var _weed3:PolyImage;
        
        private var _px:Number = WIDTH * .5;
        private var _py:Number = HEIGHT * .5;
        
        // Tracker
        private var _tracker:Tracker;
        
        public function Main()
        {
            root.transform.perspectiveProjection.fieldOfView = 50;
            root.transform.perspectiveProjection.projectionCenter = new Point(WIDTH * .5, HEIGHT * .5);
            
            addChild(new Bitmap(new BitmapData(WIDTH, HEIGHT, false, 0x001432)));
            container3D = new Sprite();
            container3D.x = WIDTH * .5;    container3D.y = HEIGHT * .5;    container3D.z = -10;
            addChild(container3D);
            
            //
            bmdMultyLoad();
        }
        
        // Setup
        private function setup():void
        {    
            // Bubbles
            _bubble1 = new Bubble();  _bubble1.x = -200;  _bubble1.y = 470;    _bubble1.z = 10;
            _bubble2 = new Bubble();  _bubble2.x = 150;  _bubble2.y = 470;    _bubble2.z = 0;
            _bubble1.blendMode = _bubble2.blendMode = "add";
            container3D.addChild(_bubble1);  container3D.addChild(_bubble2);
            _bubble1.mouseChildren = _bubble2.mouseChildren = _bubble1.mouseEnabled = _bubble2.mouseEnabled = false;
            
            // Fish
            for(var i:int = 0; i<7; i++)
            {
                var n:int = (Math.random() * 7) | 0;
                var speed:Number = Math.random() * 3 + 1;
                var fish:Fish = new Fish(_imgList[i], 3, 2, .3 + (speed | 0) * .1, _motionValList[n]);    
                fish.id = i;    fish.scaleX = -1;     fish.speed =  speed;
                if(Math.random() < .5)
                {
                    fish.isTurn = true;
                }
                else
                {
                    fish.rotationY = 180;  fish.isTurn = false;
                }
                _fishList.push(fish);
                fish.x = (Math.random() * WIDTH * 2 - WIDTH) | 0;    fish.y = (Math.random() * HEIGHT - HEIGHT * .5) | 0;
                fish.z = - 10 * i; container3D.addChild(fish);
            }
            
            _weed1 = new Weed(_imgList[7], 2, 4, .3, 8);  _weed1.x = -300;  _weed1.y = -50;    _weed1.z = -90;
            _weed2 = new Weed(_imgList[8], 2, 4, .2, 7);  _weed2.x = -100;  _weed2.y = 0;    _weed2.z = 20;
            _weed3 = new Weed(_imgList[9], 2, 4, .2, 9);  _weed3.x = 80;  _weed3.y = -200;    _weed3.z = -120;
            container3D.addChild(_weed1);    container3D.addChildAt(_weed2, 1);    container3D.addChild(_weed3);
            
            addChild(new Water());
            //
            addEventListener(Event.ENTER_FRAME, update);
        }
        
        
        // ------------ Camera & Video ------------------------------------------------------------------/
        private function setupCamera():void
        {
            _cam = Camera.getCamera();
            _cam.setMode(640, 480, 30);
            video = new Video(_cam.width, _cam.height);
            video.attachCamera(_cam);
            video.scaleX = -1;
            video.x = 640 * .5;    video.y = -480 * .5;    video.z = 50;
            container3D.addChildAt(video, 0);
            //
            _tracker = new Tracker(WIDTH, HEIGHT, video);
            //addChild(_tracker);
            //
            setup();
        }
        
        
        // ------------ Multy Loader ------------------------------------------------------------------/
        private function bmdMultyLoad():void{
            var context:LoaderContext = new LoaderContext;
            context.checkPolicyFile = true;
            var loadList:LoaderList = new LoaderList();
            //
            for ( var i:int = 1; i < NUM_MATERIAL + 1; i++ )
            {
                loadList.addCommand(
                    new LoadBitmapData(new URLRequest(DEFAULT_URL + i + ".png"),
                        {cacheAsResource:true, context:context, resGroup:"image", resId:i}
                    )
                )
            }
            // Start
            loadList.onStart = function():void {
                trace( "start multy loader." );
            }
            // Progress
            loadList.onProgress = function():void {
                //trace( this.percent,"%" );
            }
            // Complete
            loadList.onComplete = function():void{
                trace( " files load complete." );
                //
                for( i = 1; i < NUM_MATERIAL + 1; i++ )
                {
                    var bmd:BitmapData = getResourceById(i.toString()).data;
                    //addChild(new Bitmap(bmd));
                    _imgList.push(bmd);
                }
                //
                setupCamera();
            };
            // Exec
            loadList.execute();
        }
        
        // ------------ Update ------------------------------------------------------------------/
        private function update(e:Event):void
        {
            _bubble1.update();    _bubble2.update();
            _weed1.update();    _weed2.update();    _weed3.update();
            
            //
            for(var i:int = 0; i<NUM_FISH; i++)
            {
                _fishList[i].update();
                movedFish(_fishList[i], _fishList[i].speed);
            }
            
            //
            if(_tracker.isMotion)
            {
                _px += (_tracker.trackPoint.x - _px) * .1;
                _py += (_tracker.trackPoint.y - _py) * .1;
            }
            else
            {
                _px += ((465 * .5) - _px) * .05;
                _py += ((465 * .5) - _py) * .05;
            }
            
            container3D.rotationY = -(_px - WIDTH * .5) * .25;
            container3D.rotationX = (_py - HEIGHT * .5) * .25;
            
        }
        
        
        // ------------ Moved Fish ------------------------------------------------------------------/
        private function movedFish(target:PolyImage, speed:Number):void
        {
            if(target.isTurn)
            {
                target.x += speed;
                if(target.x > WIDTH)
                {
                    target.addEventListener(Event.ENTER_FRAME, target.turn);
                }
            }
            else
            {
                target.x -= speed;
                if(target.x < -WIDTH)
                {
                    target.addEventListener(Event.ENTER_FRAME, target.turn);
                }
            }
        }
        
    }
}


// ------------ Water ------------------------------------------------------------------/

import flash.display.Sprite;

internal class Water extends Sprite
{
    
    public function Water()
    {
        this.graphics.beginFill(0x65BCD1, .4);
        this.graphics.drawRect(0, 0, 465, 465);
    }
}


// ------------ PolyImage ------------------------------------------------------------------/
//package 
//{
    import flash.display.Sprite;
    import flash.display.Shape;
    import flash.display.BitmapData;
    import flash.display.Bitmap;
    import flash.events.Event;
    import flash.geom.Point;
    
    internal class PolyImage extends Sprite
    {
        
        protected var _vertices:Vector.<Number> = new Vector.<Number>();
        protected var _indices:Vector.<int> = new Vector.<int>();
        protected var _uvData:Vector.<Number> = new Vector.<Number>();
        protected var _pX:Vector.<Number> = new Vector.<Number>();
        protected var _pY:Vector.<Number> = new Vector.<Number>();
        protected var _pointList:Vector.<Point> = new Vector.<Point>();
        protected var _bmd:BitmapData;
        protected var _bm:Bitmap;
        protected var _shape:Shape = new Shape();
        protected var _isRev:Boolean; // 反転用フラグ
        protected var _ofset:Number = 0; // ポイントのオフセット値
        protected var _acc:Number = 0.9;
        protected var _xLen:int;
        protected var _yLen:int;
        //
        public var isTurn:Boolean;
        public var isJump:Boolean;
        public var transformAccel:Number;
        public var maxDeformation:Number;
        public var id:int;
        public var speed:Number = 1;
        
        public function PolyImage(bmd:BitmapData, xlen:int, ylen:int)
        {
            _bmd = bmd;
            _xLen = xlen;
            _yLen = ylen;
            setup();
        }
        
        // ---------- Setup & CreateObject -------------------------------------/
        protected function setup():void
        {
            addChild(_shape);
            _shape.x = -50;
            //
            for (var i:int=0; i < _yLen; i++) {
                for (var j:int=0; j < _xLen; j++) {
                    _uvData.push(j / (_xLen-1), i / (_yLen-1));
                    _vertices.push(_bmd.width * j / (_xLen-1), _bmd.height * i / (_yLen-1));
                    _pX.push(_bmd.width * j / (_xLen-1));
                    _pY.push(_bmd.height * i / (_yLen-1));
                    
                    if (i != (_yLen - 1) && j != (_xLen - 1)) {
                        _indices.push(_xLen * i + j, _xLen * i + j + 1, _xLen * (i + 1) + j);
                        _indices.push(_xLen * i + j + 1, _xLen * (i + 1) + j, _xLen * (i + 1) + j + 1);
                    }
                }
            }
            
            for (i=0; i < _xLen * _yLen; i++) {
                var p:Point = new Point();
                p.x = _pX[i];
                p.y = _pY[i];
                _pointList.push(p);
                //
                /*var dot:Dot = new Dot(i)
                dot.x = _pX[i]
                dot.y = _pY[i]
                addChild(dot);*/
            }
            
            createTriangles(_vertices, _indices, _uvData);
        }
        
        
        // ---------- Motion Update -------------------------------------/
        public function update():void
        {
            doMotion();
        }
        
        
        // ---------- Do Motion (Overrideeble) -------------------------------------/
        protected function doMotion():void
        {
            // override
        }
        
        
        // ---------- Create Triangles (UV Mapping) -------------------------------------/
        internal function createTriangles(ver:Vector.<Number>, ind:Vector.<int>, uv:Vector.<Number>, cull:String = "none"):void
        {
            _shape.graphics.clear();
            //_shape.graphics.lineStyle(1, 0xFF0000, 0.5)
            _shape.graphics.beginBitmapFill(_bmd, null, true, true);
            _shape.graphics.drawTriangles(ver, ind, uv, cull);
            _shape.graphics.endFill();
        }
        
        
        // ---------- Turn -------------------------------------/
        public function turn(e:Event = null):void
        {
            if(isTurn){
                if(this.rotationY < 180){
                    this.rotationY += (30 + speed);
                }else{
                    isTurn = false;
                    this.rotationY = 180;
                    this.removeEventListener(Event.ENTER_FRAME, turn);
                }
            }else{
                if(this.rotationY > 0){
                    this.rotationY -= (30 + speed);
                }else{
                    isTurn = true;
                    this.rotationY = 0;
                    this.removeEventListener(Event.ENTER_FRAME, turn);
                }
            }
        }
        
    }
//}


import flash.display.Sprite;
import flash.display.Shape;
import flash.text.TextField;

class Dot extends Sprite{
    public function Dot(n:int){
        var shape:Shape = new Shape();
        addChild(shape);
        shape.graphics.beginFill(0xFF0000, 0.5);
        shape.graphics.drawCircle(0,0,5);
        shape.graphics.endFill();
        //
        var tx:TextField = new TextField();
        addChild(tx);
        tx.text = n.toString();
    }
}


// ------------ Weed ------------------------------------------------------------------/
//package 
//{
    
    import flash.display.BitmapData;
    
    internal class Weed extends PolyImage {
        
        public var accel:Number = 3;
        //public var transformAccel:Number = 2;
        
        public function Weed(bmd:BitmapData, xlen:int = 2, ylen:int = 3, accel:Number = .5, maxDef:Number = 10)
        {
            super(bmd, xlen, ylen);
            transformAccel = accel;
            maxDeformation = maxDef;
        }
        
        protected override function doMotion():void
        {
            var nX:int = 0;
            var nY:int = 0;
            
            if(_isRev){
                _ofset += transformAccel;
                if(_ofset > maxDeformation){
                    _ofset = maxDeformation;
                    _isRev = false;
                }
            }else{
                _ofset -= transformAccel;
                if(_ofset < -maxDeformation){
                    _ofset = -maxDeformation;
                    _isRev = true;
                }
            }
            
            for (var i:int=0; i < _vertices.length; i++) {
                if (i % 2 != 1) {
                    if (nX < _pointList.length) {
                        var ofsetX:Number;
                        if(nX %2 == 0){
                            ofsetX = _ofset * nX * maxDeformation * .075;
                        }else{
                            ofsetX = _ofset * -nX * maxDeformation * .075;
                        }
                        //
                        if(nX >= _xLen) ofsetX *= -1;
                        //
                        _vertices[i] = _pointList[nX].x + ofsetX;
                        nX++;
                    }
                } else {
                    if (nY < _pointList.length) {
                        var ofsetY:Number;
                        if(nY %4 == 0){
                            ofsetY = _ofset * -2;
                        }else if(nY %3 == 0){
                            ofsetY = _ofset;
                        }else if(nY %2 == 0){
                            ofsetY = _ofset * -1;
                        }else{
                            ofsetY = _ofset * 2;
                        }
                        //
                        if(nY >= _xLen) ofsetY *= -1;
                        //
                        _vertices[i] = _pointList[nY].y + ofsetY;
                        nY++;
                    }
                }
            }
            
            createTriangles(_vertices, _indices, _uvData);
        }
        
    }
    
//}


// ------------ Fish ------------------------------------------------------------------/
//package
//{
    
    import flash.display.BitmapData;
    
    internal class Fish extends PolyImage {
        
        public var accel:Number = 3;
        //public var isTurn:Boolean;
        
        public function Fish(bmd:BitmapData, xlen:int = 3, ylen:int = 2, accel:Number = 1, maxDef:Number = 8)
        {
            super(bmd, xlen, ylen);
            transformAccel = accel;
            maxDeformation = maxDef;
        }
        
        protected override function doMotion():void
        {
            var nX:int = 0;
            var nY:int = 0;
            
            if(_isRev){
                _ofset += transformAccel;
                if(_ofset > maxDeformation){
                    _ofset = maxDeformation;
                    _isRev = false;
                }
            }else{
                _ofset -= transformAccel;
                if(_ofset < -maxDeformation){
                    _ofset = -maxDeformation;
                    _isRev = true;
                }
            }
            
            for (var i:int=0; i < _vertices.length; i++) {
                if (i % 2 != 1) {
                    if (nX < _pointList.length) {
                        var ofsetX:Number;
                        if(nX %2 == 0){
                            ofsetX = _ofset * nX * .5;
                        }else{
                            ofsetX = _ofset * -nX * .5;
                        }
                        //
                        if(nX >= _xLen) ofsetX *= -1;
                        //
                        _vertices[i] = _pointList[nX].x + ofsetX;
                        nX++;
                    }
                } else {
                    if (nY < _pointList.length) {
                        var ofsetY:Number;
                        if(nY %2 == 0){
                            ofsetY = _ofset;
                        }else{
                            ofsetY = _ofset * -1;
                        }
                        //
                        if(nY >= _xLen) ofsetY *= -1;
                        //
                        _vertices[i] = _pointList[nY].y + ofsetY;
                        nY++;
                    }
                }
            }
            
            createTriangles(_vertices, _indices, _uvData);
        }
        
        //     
    }
//}


// ------------ Bubble ------------------------------------------------------------------/
//package 
//{
    
    import flash.display.Sprite;
    import flash.display.Shape;
    
    internal class Bubble extends Sprite
    {
        private var _bubles:Array = [];
        private var _particles:Array = [];
        private var _startX:Number;
        private var _startY:Number;
        
        public function Bubble()
        {
            this.mouseEnabled = false;
        }
        
        private function createParticle():void
        {
            var p:Particle = new Particle();
            var radius:Number = Math.random() * Math.sqrt(Math.random()) * 3.5;
            var angle:Number = Math.random() * (Math.PI) * 2;
            //
            p.vx = Math.cos(angle) * radius;
            p.vy = Math.sin(angle) * radius;
            p.scale = Math.random() * .1;
            _particles.push(p);
            //
            var bubble:BubbleMaterial = new BubbleMaterial();
            addChild(bubble);
            _bubles.push(bubble);
        }
        
        
        private function emitte():void
        {
            var n:int = Math.random() * 1 + .2;
            _startX = 0;
            _startY = 0;
            while (n--) createParticle();
        }
        
        
        public function update():void
        {
            var n:int = _particles.length;
            while (n--) {
                var v:Number = Math.random() * 0.15 + 0.85;
                var p:Particle = _particles[n];
                var ranx:Number = Math.random() * 2 - 1;
                var rany:Number = Math.random() * - 1;
                p.vx += ranx;
                p.vy += rany;
                p.vx *= v;
                p.vy *= v;
                p.x += p.vx;
                p.y += p.vy;
                //
                _bubles[n].x = p.x;  _bubles[n].y = p.y;
                //
                if(p.scale <= .6) p.scale += .01
                if (p.y < -768){
                    _particles.splice(n, 1);
                    removeChild(_bubles[n]);
                    _bubles.splice(n, 1);
                }
            }
            //
            emitte();
        }
        
        //
        public function removed():void
        {
            var l:int = _bubles.length;
            for(var i:int; i<l; i++)
            {
                removeChild(_bubles[i]);
            }
            _bubles = [];
            _particles = [];
        }
        
    }    
//}

//
import flash.display.Sprite;
import flash.display.Shape;

internal class BubbleMaterial extends Sprite
{
    public function BubbleMaterial()
    {
        var n:int = Math.random() * 10 | 0;
        var sp:Shape = new Shape();
        //
        sp.graphics.beginFill(0xFFFFFF, .25);
        sp.graphics.drawCircle(-n * .3, -n * .3, n * .5);
        sp.graphics.endFill();
        sp.graphics.lineStyle(1.5, 0xFFFFFF, .35);
        sp.graphics.drawCircle(0, 0, n);
        sp.rotation = Math.random() * 180 | 0;
        //
        addChild(sp);
    }
}

//
import flash.geom.Point;

internal class Particle extends Point
{
    public var vx:Number = 0
    public var vy:Number = 0
    public var scale:Number = 0;
    public var c:uint = 0xFFFFFF;
}



//package 
//{
    
    import flash.display.BlendMode;
    import flash.filters.BlurFilter;
    import flash.display.BitmapData;
    import flash.geom.Matrix;
    import flash.geom.Point;
    import flash.geom.Rectangle;
    import flash.media.Video;
    import flash.display.Bitmap;
    import flash.display.Sprite;
    import flash.events.TimerEvent;
    import flash.utils.Timer;
    
    internal class Tracker extends Sprite
    {
        
        private var _w:Number;
        private var _h:Number;
        
        public var trackPoint:Point = new Point();
        
        public var _previous:BitmapData;
        public var _current:BitmapData;
        private var _px:Number;
        private var _py:Number;
        
        private var _blur:BlurFilter = new BlurFilter(64,64);
        private var _vid:Video;
        private var _mirror:Matrix;
        private var _point:Point = new Point();
        private var _area:Rectangle;
        public var isMotion:Boolean = false;
        
        public function Tracker(w:Number, h:Number, vid:Video)
        {
            _w = w;
            _h = h;
            _vid = vid;
            _mirror = new Matrix();
            _mirror.scale( -1, 1);

            var ofsetX:Number = _vid.width - (vid.width - 465) * .5
            _mirror.translate(ofsetX, 0);
            
            _current = new BitmapData(465, 465, false, 0x000000);
            _previous = _current.clone();
            
            addChild(new Bitmap(_previous));
            
            //
            var timer:Timer = new Timer(200);
            timer.addEventListener(TimerEvent.TIMER, trackerUpdate);
            timer.start();
        }
        
        private function trackerUpdate(e:TimerEvent):void
        {
            track();
            trackPoint.x = _px;
            trackPoint.y = _py;
        }
        
        private function track():void
        {
            _current.draw(_vid, _mirror);
            _current.draw(_previous, null, null, BlendMode.DIFFERENCE);
            _current.applyFilter(_current, _current.rect, _point, _blur);
            _current.threshold(_current, _current.rect, _point, ">",  0xFF333333, 0xFFFFFFFF);
            _previous.draw(_vid, _mirror);
            
            _area = _current.getColorBoundsRect(0xFFFFFFFF,0xFFFFFFFF,true);
            isMotion = ( _area.width > ( _current.width / 100) * 5 || _area.height > (_current.height / 100) * 5 );
            
            if (isMotion)
            {
                _px = _area.x + _area.width * .5;
                _py = _area.y + _area.height * .5;
            }
            
            /*graphics.clear();
            graphics.lineStyle(1, 0xFF0000, .5);
            graphics.drawRect(_area.x, _area.y, _area.width, _area.height);*/
        }
    }
    
//}