By Zevan | March 21, 2009
Actionscript:
-
var t:Number=0, cos:Number, sin:Number;
-
-
var canvas:BitmapData = new BitmapData(400,400,false, 0x000000);
-
addChild(new Bitmap(canvas));
-
-
var shape:Shape = new Shape();
-
with(shape.graphics) beginFill(0x568338, .2), drawCircle(0,0,10);
-
-
addEventListener(Event.ENTER_FRAME, onLoop);
-
function onLoop(evt:Event):void {
-
-
t += .1;
-
// -- low precision sine/cosine
-
//always wrap input angle to -PI..PI
-
if (t <-3.14159265){
-
t += 6.28318531;
-
}else{
-
if (t> 3.14159265)
-
t -= 6.28318531;
-
}
-
-
//compute sine
-
if (t <0){
-
sin = 1.27323954 * t + .405284735 * t * t;
-
}else{
-
sin = 1.27323954 * t - 0.405284735 * t * t;
-
}
-
-
//compute cosine: sin(t + PI/2) = cos(t)
-
t += 1.57079632;
-
if (t> 3.14159265){
-
t -= 6.28318531;
-
}
-
-
if (t <0){
-
cos = 1.27323954 * t + 0.405284735 * t * t
-
}else{
-
cos = 1.27323954 * t - 0.405284735 * t * t;
-
}
-
t -= 1.57079632;
-
-
// move the shape
-
shape.x = 200 + 100 * cos;
-
shape.y = 200 + 100 * sin;
-
-
// draw to the canvas
-
canvas.draw(shape, shape.transform.matrix);
-
}
This snippet draws a circle using low precision sine and cosine... you'll notice that its not a perfect looking circle:
Back in January I saw this blog post by Michael Baczynski over at http://lab.polygonal.de/. The blog post describes a technique for fast sine and cosine approximation - (I highly recommend giving it a read - very fun stuff).
It's worth noting that there is a higher precision sine and cosine that will likely draw a better looking circle but will be about half as fast. According to the original post ... the low precision technique is approximately 14x faster than using Math.cos()/Math.sin().
There some other really great posts over at polygonal go check them out.
Posted in Math, motion | Tagged actionscrpt, flash |
By Zevan | March 20, 2009
Actionscript:
-
function uniqueCompare(arr:Array, compare:Function):void {
-
var leng:int = arr.length;
-
for (var i:int = 0; i<leng; i++){
-
for (var j:int = i + 1; j<leng; j++){
-
compare(arr[i], arr[j]);
-
}
-
}
-
}
-
-
var numbers:Array = [1, 2, 3, 4, 5];
-
-
uniqueCompare(numbers, compareCallback);
-
-
function compareCallback(a:*, b:*):void {
-
trace("compare " + a + " to " + b);
-
}
-
-
/*
-
outputs:
-
compare 1 to 2
-
compare 1 to 3
-
compare 1 to 4
-
compare 1 to 5
-
compare 2 to 3
-
compare 2 to 4
-
compare 2 to 5
-
compare 3 to 4
-
compare 3 to 5
-
compare 4 to 5
-
*/
This snippet shows a function called uniqueCompare() that compares all elements in an array to all other elements in an array without repeating a comparison.
By Zevan | March 19, 2009
Actionscript:
-
var Box:Function = {
-
constructor : function(color:uint, w:Number, h:Number):void {
-
this.color = color;
-
this.s = new Shape();
-
with(this.s.graphics) beginFill(this.color), drawRect(0,0,w,h);
-
addChild(this.s);
-
-
this.setLoc = function(x:Number, y:Number):void{
-
this.s.x = x;
-
this.s.y = y;
-
}
-
}
-
}.constructor;
-
-
var box0:Object = new Box(0xFF0000, 100, 100);
-
-
box0.setLoc(100, 10);
-
-
var box1:Object = new Box(0x000000, 50, 50);
-
-
box1.setLoc(210, 10);
This snippet makes use of Object.constructor() to allow creation of Object instances using the new keyword. This is for fun only, I don't recommend this over actual Classes.
By Zevan | March 18, 2009
Actionscript:
-
[SWF(width = 400, height = 400)];
-
var canvas:BitmapData = new BitmapData(400,400, false, 0x000000);
-
var eraser:BitmapData = new BitmapData(400,400, true, 0x11000000);
-
addChild(new Bitmap(canvas));
-
-
var particles:Array = new Array();
-
for (var i:int = 0; i <500; i++){
-
particles.push(makeParticle());
-
}
-
-
addEventListener(Event.ENTER_FRAME, onLoop);
-
function onLoop(evt:Event):void {
-
canvas.copyPixels(eraser, eraser.rect, new Point(0,0), null, null, true);
-
for (var i:int = 0; i <particles.length; i++){
-
particles[i]();
-
}
-
}
-
-
function makeParticle():Function {
-
var dx:Number, dy:Number;
-
var x:Number = 200;
-
var y:Number = 200;
-
var vx:Number = Math.random() * 4 - 2;
-
var vy:Number = Math.random() * 4 - 2;
-
var ang:Number;
-
return function():void {
-
x += vx;
-
y += vy;
-
dx = 200 - x;
-
dy= 200 - y;
-
if (Math.sqrt((dx * dx) + (dy * dy))> 130){
-
ang = Math.atan2(dy, dx) / Math.PI * 180;
-
vx = Math.cos(ang);
-
vy = Math.sin(ang);
-
}
-
canvas.setPixel(x, y, 0xFFFFFF);
-
}
-
}
This is an interesting variation on yesterdays post. The result will looks like this...
Click to view swf...
I also decided to do a processing port of this with 3,000 particles:
Processing Version
The processing version eventually evolved into this:
Click for enlarged version...