Matrix3D Perspective Projection
http://www.neuroproductions.be/experiments/matrix3d-perspective-projection/
/**
* Copyright alexnotkin ( http://wonderfl.net/user/alexnotkin )
* MIT License ( http://www.opensource.org/licenses/mit-license.php )
* Downloaded from: http://wonderfl.net/c/sOP0
*/
// source code from http://www.neuroproductions.be/experiments/matrix3d-perspective-projection/
package {
import flash.display.Bitmap;
import flash.display.BitmapData;
import flash.display.Sprite;
import flash.display.StageAlign;
import flash.display.StageScaleMode;
import flash.display.TriangleCulling;
import flash.events.Event;
import flash.events.MouseEvent;
import flash.geom.Matrix3D;
import flash.geom.PerspectiveProjection;
import flash.geom.Point;
import flash.geom.Utils3D;
import flash.geom.Vector3D;
[SWF( frameRate="25", backgroundColor="#0")]
public class PerlinDrawingAPI extends Sprite
{
private var holder:Sprite =new Sprite()
private var rows:int =40
private var cols:int =50
private var indices:Vector.<int> = new Vector.<int>();
private var projectedVerts:Vector.<Number> = new Vector.<Number>();
private var uvts:Vector.<Number> = new Vector.<Number>();
private var vertices:Vector.<Number> = new Vector.<Number>();
private var anglecount:Number =0
private var count:Number =0
private var bmd:BitmapData
private var bmdFill:BitmapData
private var isPerlin:Boolean =true
public function PerlinDrawingAPI()
{
holder.scaleX=0.5
holder.scaleY =0.5
bmd =new BitmapData(cols,rows,false)
stage.align =StageAlign.TOP_LEFT
stage.scaleMode =StageScaleMode.NO_SCALE
this.addChild(holder)
prepTriangles();
this.addEventListener(Event.ENTER_FRAME,loopNoise);
stage.addEventListener(MouseEvent.MOUSE_DOWN,switchLoop)
}
private function switchLoop(e:Event):void
{
if (isPerlin)
{
isPerlin =false
this.removeEventListener(Event.ENTER_FRAME,loopNoise);
this.addEventListener(Event.ENTER_FRAME,loopSine);
}
else
{
isPerlin =true
this.addEventListener(Event.ENTER_FRAME,loopNoise);
this.removeEventListener(Event.ENTER_FRAME,loopSine);
}
}
public function loopSine(event:Event):void
{
projectedVerts = new Vector.<Number>();
uvts= new Vector.<Number>();
vertices = new Vector.<Number>();
var xPos:Number
var yPos:Number
var zPos:Number
anglecount+= 0.3
var angle:Number =anglecount
for (var i:int =0;i<rows-1;i++)
{
angle+=Math.PI /12
var angle2:Number =anglecount
for (var j:int =0;j<cols;j++)
{
xPos=(j*80)-(cols*80/2)
yPos=(i*80)-(rows*80/2)
angle2+=Math.PI /12
zPos =-1000+(Math.sin(angle)*200)+(Math.sin(angle2)*200)
vertices.push(xPos,yPos,zPos);
uvts.push(j/(cols-1),(rows-1+i)/(rows-1),zPos);
}
}
project()
}
public function loopNoise(event:Event):void
{
count-=1
projectedVerts = new Vector.<Number>();
uvts= new Vector.<Number>();
vertices = new Vector.<Number>();
var xPos:Number
var yPos:Number
var zPos:Number
var ofzetPoint:Point =new Point(0,count)
bmd.perlinNoise(40,40,3,1,false,true,7,true,[ofzetPoint,ofzetPoint,ofzetPoint])
for (var i:int =0;i<rows-1;i++)
{
for (var j:int =0;j<cols;j++)
{
var pixelVal:Number = bmd.getPixel(j,i)
var ofzetz : Number = pixelVal >> 16 & 0xFF
//var ofzetx : Number = pixelVal >> 8 & 0xFF
//var ofzety : Number = pixelVal >> 0 & 0xFF
xPos=(j*80)-(cols*80/2)//+((ofzetx*ofzetx)/20)
yPos=(i*80)-(rows*80/2)//+((ofzety*ofzety)/40)
zPos = -(ofzetz*ofzetz)/20
vertices.push(xPos,yPos,zPos);
uvts.push(j/(cols-1),(rows-1+i)/(rows-1),zPos);
}
}
project()
}
private function project():void
{
var vertices2D:Vector.<Number> = new Vector.<Number>();
var m:Matrix3D = new Matrix3D()
//
var pp:PerspectiveProjection =new PerspectiveProjection()
pp.focalLength =3
pp.fieldOfView =48
m = pp.toMatrix3D()
m.prependTranslation(0,0,1000)
var rotPoint:Vector3D =new Vector3D(0,0,1000)
var rotPoint2:Vector3D =new Vector3D(0,0,1000)
m.prependRotation((mouseY/15)-60,Vector3D.X_AXIS,rotPoint2)
m.prependRotation((mouseX-(stage.stageWidth/2))/10,Vector3D.Z_AXIS,rotPoint2)
Utils3D.projectVectors(m,vertices,vertices2D,uvts)
holder.graphics.clear();
holder.graphics.lineStyle(1,0x2eabff,1)
//holder.graphics.beginBitmapFill(bmdFill,null,true,true);
holder.graphics.drawTriangles(vertices2D,indices,uvts,TriangleCulling.NEGATIVE);
holder.graphics.endFill();
holder.x = stage.stageWidth/2;
holder.y = (stage.stageHeight/2)-80;
}
public function prepTriangles():void
{
for (var i:int =0;i<rows-1;i++)
{
for (var j:int =0;j<cols-1;j++)
{
if(i<rows && j<cols)
{
indices.push(i*cols+j+1, (i+1)*cols+j+1,(i+1)*cols+j);
indices.push(i*cols+j,i*cols+j+1,(i+1)*cols+j);
}
}
}
}
}
}