hybrid-brush-04
...
@author bouze
// forked from bouze's hybrid-brush-03
// forked from bouze's hybrid-brush-02
// forked from bouze's hybrid-brush-01
package
{
import flash.display.GradientType;
import flash.display.Graphics;
import flash.display.Sprite;
import flash.events.Event;
import flash.geom.Matrix;
import flash.geom.Point;
/**
* ...
* @author bouze
*/
[SWF(frameRate="60", backgroundColor="#CCCC99")]
public class Main extends Sprite
{
private var drawLayer:Sprite;
private var particles:Array = new Array();
private var pNum:int = 40;
private var maxDistance:Number = 20;
private var friction:Number = 0.3;
public function Main()
{
init();
}
private function init():void
{
stage.quality = "LOW";
drawLayer = new Sprite();
addChild(drawLayer);
initParticles();
addEventListener(Event.ENTER_FRAME, update);
}
private function initParticles():void
{
var i:int;
for (i = 0; i < pNum; i++)
{
var sp:Sprite = new Sprite();
drawLayer.addChild( sp );
/*
var g:Graphics = sp.graphics;
g.lineStyle( 1 );
g.drawCircle( 0, 0, 4 );
drawLayer.addChild( sp );
*/
particles.push(
{
ref: sp,
x: mouseX,
y: mouseY,
dx: 0,
dy: 0
} );
}
}
private function move():void
{
var i:int;
for (i = 0; i < pNum; i++)
{
var p:Object = particles[ i ];
var pp:Object = particles[ i - 1 ];
if ( i == 0 )
{
p.x += ( mouseX - p.x ) * friction;
p.y += ( mouseY - p.y ) * friction;
}
else
{
p.x += ( pp.x - p.x ) * friction * ( pNum - i ) * 0.08;
p.y += ( pp.y - p.y ) * friction * ( pNum - i ) * 0.08;
}
}
}
private function draw():void
{
var i:int;
for (i = 0; i < pNum - 5; i++)
{
var g:Graphics = particles[ i ].ref.graphics;
var mtrx:Matrix = new Matrix();
mtrx = createLinearGradientMatrix( particles[ i ].x, particles[ i ].y, particles[ i + 2 ].x, particles[ i + 2 ].y)
g.clear();
g.beginGradientFill(GradientType.LINEAR, [ 0x660099, 0xFF0066 ], [ 0.4, 0.3 ], [ 0, 255 ], mtrx);
g.moveTo( particles[ i ].x, particles[ i ].y );
curveThrough3Pts(g, particles[ i ].x, particles[ i ].y, particles[ i + 1 ].x, particles[ i + 1 ].y, particles[ i + 2 ].x, particles[ i + 2 ].y );
curveThrough3Pts(g, particles[ i + 2 ].x, particles[ i + 2 ].y, particles[ i + 3 ].x, particles[ i + 3 ].y, particles[ i + 4 ].x, particles[ i + 4 ].y );
/*
g.lineTo( particles[ i + 1 ].x, particles[ i + 1 ].y );
g.lineTo( particles[ i + 2 ].x, particles[ i + 2 ].y );
g.lineTo( particles[ i + 3 ].x, particles[ i + 3 ].y );
g.lineTo( particles[ i + 4 ].x, particles[ i + 4 ].y );
g.lineTo( particles[ i + 5 ].x, particles[ i + 5 ].y );
*/
g.lineTo( particles[ i ].x, particles[ i ].y );
}
g.endFill();
}
/**
* 三点を通る二次元曲線
* via 詳説ActionScript 3.0(p.700)
*/
private function curveThrough3Pts
(
g:Graphics,
startX:Number,
startY:Number,
throughX:Number,
throughY:Number,
endX:Number,
endY:Number
):void
{
var controlX:Number = ( 2 * throughX ) - 0.5 * ( startX + endX );
var controlY:Number = ( 2 * throughY ) - 0.5 * ( startY + endY );
g.moveTo( startX, startY );
g.curveTo( controlX, controlY, endX, endY );
}
/**
* Make matrix for linear gradient
* via http://nutsu.com/blog/2009/020921_as_gradient_matrix.html
*/
private function createLinearGradientMatrix( x0:Number, y0:Number, x1:Number, y1:Number ):Matrix
{
var mtrx:Matrix = new Matrix();
mtrx.createGradientBox( 1, 1, 0, -0.5, -0.5 );
var vx:Number = x1 - x0;
var vy:Number = y1 - y0;
var w:Number = Math.sqrt( vx * vx + vy * vy );
var r:Number = Math.atan2( vy, vx );
var cx:Number = ( x0 + x1 ) / 2;
var cy:Number = ( y0 + y1 ) / 2;
mtrx.scale( w, 1 );
mtrx.rotate( r );
mtrx.translate( cx, cy );
return mtrx;
}
private function update(e:Event):void
{
move();
draw();
}
}
}