forked from: forked from: メタボール

by fukt forked from forked from: メタボール (diff: 2)
♥0 | Line 129 | Modified 2011-07-17 01:32:10 | MIT License
play

ActionScript3 source code

/**
 * Copyright fukt ( http://wonderfl.net/user/fukt )
 * MIT License ( http://www.opensource.org/licenses/mit-license.php )
 * Downloaded from: http://wonderfl.net/c/qY0i
 */

// forked from termat's forked from: メタボール
// forked from termat's メタボール
package
{
    import flash.display.Bitmap;
    import flash.display.BitmapData;
    import flash.display.Sprite;
    import flash.events.Event;

    [SWF(width = "460", height = "460", backgroundColor = "0x000000", fps = "30")] 
    public class Practice41 extends Sprite{
        private var bitmap:BitmapData;
        private var balls:Vector.<Metaball>;
        private var colors:Vector.<Array>;
        
        public function Practice41() {
            bitmap = new BitmapData(stage.stageWidth, stage.stageHeight, false, 0x000000);
            addChild(new Bitmap(bitmap));
            balls = new Vector.<Metaball>();
            colors = createColors();
            addEventListener(Event.ENTER_FRAME, update);
            for (var i:int = 0; i < 256; i++) addMetaball(240,240);
        }
        
        private function createColors():Vector.<Array>{
            var ret:Vector.<Array> = new Vector.<Array>();
            var r:int, g:int, b:int;
            for (var i:int=0;i<256;i++){
                r = g = b = 0;
                if (i >= 0) b = Math.min(255, 4 * i * 2);
                if (i >= 2) g = Math.min(255, 4 * (i / 4));
                if (i >= 4) r = Math.min(255, 4 * (i / 8));
                ret[i]=[r,g,b];
            }
            return ret;
        }
        
        private function update(e:Event):void {
            bitmap.fillRect(bitmap.rect, 0x000000);
            for each(var p:Metaball in balls) {
                p.draw(bitmap);    
                move(p);
            }
        }
        
        private function addMetaball(x:int, y:int):void {
            var m:Metaball = new Metaball(colors);
            m.x = x;    m.y = y;
            m.vx = 20 * Math.random()-10;
            m.vy = 20 * Math.random()-10;
            m.init();
            balls.push(m);
        }
        
        private function move(p:Metaball):void {
            var xx:int = p.x + p.vx;
            if (xx < 0) {
                p.x = xx * -1;    p.vx *= -1;
            }else if (xx> bitmap.width) {
                p.x = bitmap.width * 2 - xx;    p.vx *= -1;
            }else {
                p.x = xx;
            }
            xx = p.y + p.vy;
            if (xx < 0) {
                p.y = xx * -1;    p.vy *= -1;
            }else if (xx> bitmap.height) {
                p.y = bitmap.height * 2 - xx;    p.vy *= -1;
            }else {
                p.y = xx;
            }
        }
    }
}
import flash.display.BitmapData;
class Metaball {
    public var x:int, y:int,vx:int,vy:int;
    public var colors:Vector.<Array> ;
    private var pixels:Vector.<Pixel>;
    public var RADIUS:int=80;
    private var NUM_PIXELS:int;
        
    public function Metaball(c:Vector.<Array>){
        NUM_PIXELS=(2 * RADIUS) * (2 * RADIUS);
        pixels = new Vector.<Pixel>();
        for (var i:int = 0; i < NUM_PIXELS; i++) pixels[i] = new Pixel();
        colors=c;
    }
        
    public function init():void {
        var no:int;
        var c:int = 0;
        for (var i:int = -RADIUS; i < RADIUS; i++) {
            for (var j:int = -RADIUS; j < RADIUS; j++) {
                var z:Number = RADIUS * RADIUS - i * i - j * j;
                if (z < 0) {
                    no = 0;
                }else{
                    z = Math.sqrt(z);
                    var t:Number = z / RADIUS;
                    no = (int) (255 * (t * t * t * t));
                    no = Math.max(0, Math.min(no, 255));
                }
                pixels[c].dx = i;
                pixels[c].dy = j;
                pixels[c].no = no;
                c++;
            }
        }
    }
        
    public function draw(bitmap:BitmapData):void {
        for (var i:int = 0; i < NUM_PIXELS; i++) {
            var sx:int = x + pixels[i].dx;
            if (sx < 0 || sx > bitmap.width-1)continue;
            var sy:int = y + pixels[i].dy;
            if (sy < 0 || sy > bitmap.height-1)continue;
            var p:Array = getRgb(bitmap.getPixel(sx, sy));
            for (var j:int = 0; j < 3; j++) {
                p[j] += colors[pixels[i].no][j];
                if (p[j] > 255)p[j] = 255;
            }
            bitmap.setPixel(sx, sy, get16(p[0], p[1], p[2]));
        }
    }
    
    private function get16(rr:int,gg:int,bb:int):uint {
        return (rr << 16) + (gg << 8) + bb;
    }
    
    private function getRgb(c:uint):Array {
        var r:int = (c & 0xff0000) >> 16;
        var g:int = (c & 0xff00) >> 8;
        var b:int = (c & 0xff);
        return [r, g, b];
    }
}

class Pixel {
    public var dx:int;
    public var dy:int;
    public var no:int;
}