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

IK実験うにょうにょ forked from: IK実験

IK実験
クリックで追加。
あまり綺麗に曲がってくれない・・・・。
Get Adobe Flash player
by nemu90kWw 09 May 2009
// forked from Nao_u's IK実験
//
// IK実験
//
// クリックで追加。
// あまり綺麗に曲がってくれない・・・・。
//
//
package {
    import flash.display.Sprite;
    import flash.events.*;
	import flash.ui.Mouse;
    [SWF(width="465", height="465", backgroundColor="0xFFFFFF", frameRate="45")]
    public class FlashTest extends Sprite {
        public function FlashTest() {
            Main = this;
            initialize();
            stage.addEventListener(Event.ENTER_FRAME,update);
            stage.addEventListener(MouseEvent.MOUSE_DOWN,  onClick);
            stage.addEventListener(MouseEvent.MOUSE_MOVE, function(e:Event):void{Mouse.hide();});
        }
    }
}

import flash.display.Sprite;
import flash.text.*;
import flash.events.*;
import flash.geom.*;
var SCREEN_W:Number = 465, SCREEN_H:Number = 465;
var Main:Sprite;
var Text:TextField

var IkAry:Array = new Array;

function initialize():void{
    Text = new TextField();
    Text.text = "";
    Text.autoSize = "left";
    Main.addChild(Text);

    IkAry.push( new IkBase(100, 150, 10 ) );
    IkAry.push( new IkBase(400,  20, 13 ) );
//    IkAry.push( new IkBase(400, 420,  7 ) );
}

function onClick(event:MouseEvent):void{
    IkAry.push( new IkBase(Main.stage.mouseX, Main.stage.mouseY,  6+Math.random()*7 ) );

    if( IkAry.length > 6 ){
        IkAry.splice( 0, 1 );
    }
}

function update(e :Event):void{
    graphicClear();

    var ik:IkBase;
    for( var i:int=0; i<50; i++ ) {
        for each( ik in IkAry ) ik.update();
    }
    for each( ik in IkAry ) ik.draw();
}

class Node{
    public var x:Number;
    public var y:Number;
    public var speed:Number = 0;
    public var Rot:Number = 0;
    public var length:Number = 0;
    public function Node( ){

    }
}

class IkBase{
    public var Length:Number = 25.0;
    public var Base:Point = new Point(0,0);
    public var Target:Point = new Point(0,0);
    public var Nodes:Vector.<Node> = new Vector.<Node>;

    public function IkBase( x:Number, y:Number, num:int ){
        Base.x = x;
        Base.y = y;
        for( var i:int=0; i<num; i++ ) Nodes[i] = new Node();
    }

    // 内積
    public function dot( p0:Point, p1:Point ):Number{
        return p0.x*p1.x + p0.y*p1.y
    }

    public function update():void{
        Target.x = Main.stage.mouseX;
        Target.y = Main.stage.mouseY;

        var rotMax:Number = 0.00005;

        // 先端ノード
        var sn:Node = Nodes[Nodes.length-1]
        for( var i:int=Nodes.length-2; i>=0; i-- ){
            n = Nodes[i]
            var tv:Point = new Point();
            var sv:Point = new Point();
            var rv:Point = new Point();
            var lv:Point = new Point();
            // 間接から目標に向いたベクトル
            tv.x = Target.x - n.x;
            tv.y = Target.y - n.y;

            // 間接から先端に向いたベクトル
            sv.x = sn.x - n.x;
            sv.y = sn.y - n.y;

            // 右回りのベクトル
              rv.x = sv.x * Math.cos( rotMax ) + sv.y * Math.sin( rotMax );
            rv.y =-sv.x * Math.sin( rotMax ) + sv.y * Math.cos( rotMax );

            // 左回りのベクトル
              lv.x = sv.x * Math.cos(-rotMax ) + sv.y * Math.sin(-rotMax );
            lv.y =-sv.x * Math.sin(-rotMax ) + sv.y * Math.cos(-rotMax );

            var ds:Number = dot( tv, sv );
            var dr:Number = dot( tv, rv );
            var dl:Number = dot( tv, lv );
            if( ds < dr && ds < dl ){
                // 回らない
              }else if( dr > dl ){
                n.speed += rotMax / (Nodes.length-i);
            }else{
                n.speed -= rotMax / (Nodes.length-i);
            }
            n.Rot += n.speed;
            n.speed /= 1.005;
            n.length = (n.length*1000 + Length) / 1001;
        }

        Nodes[0].x = Base.x;
        Nodes[0].y = Base.y;
        var pn:Node = Nodes[0];
        var n:Node;
        for( i=1; i<Nodes.length; i++ ){
            n = Nodes[i];
            n.x = n.length * Math.sin( pn.Rot );
            n.y = n.length * Math.cos( pn.Rot );
            n.x += pn.x;
            n.y += pn.y;
            pn = n;
        }


    }
    public function draw():void{
        var pn:Node = Nodes[0];
        for( var i:int=1; i<Nodes.length; i++ ){
            var n:Node = Nodes[i];
            drawLine( pn.x, pn.y, n.x, n.y, 7.5, 0x808020 );
            pn = n;
        }

        drawCircle( Target.x, Target.y, 12, 0xe04000 );
        for each( n in Nodes ) drawCircle( n.x, n.y, 8, 0xe0d000 );
        drawCircle( Base.x, Base.y, 12, 0xb0a000 );
    }
}


function graphicClear():void{
    Main.graphics.clear();
    Main.graphics.lineStyle(1.2,0xb0b040);
    Main.graphics.moveTo( SCREEN_W/2,          0 );
    Main.graphics.lineTo( SCREEN_W/2,   SCREEN_H );
    Main.graphics.moveTo(          0, SCREEN_H/2 );
    Main.graphics.lineTo(   SCREEN_W, SCREEN_H/2 );
}

function drawLine( sx:Number, sy:Number, ex:Number, ey:Number, size:Number, col:int ):void{
    Main.graphics.lineStyle(size,col);
    Main.graphics.moveTo( sx, sy );
    Main.graphics.lineTo( ex, ey );
}

function drawCircle( x:Number, y:Number, size:Number, col:int ):void{
    Main.graphics.lineStyle(1.4,0x000000);
    Main.graphics.beginFill(col,1);
    Main.graphics.drawCircle(x,y,size);
    Main.graphics.endFill();
}