quinta-feira, 17 de outubro de 2013

Actionscript 3D

Back in the days when i was working at a Marketing Company doing a 2D Artist job, i was hungry about programming but i didn't know how or where to start. I remember reading articles about John Carmack, Romero and the beginning of hardware accelerated graphics and imagining these guys in their extremely cool offices working on extremely cool machines, programming games and being the underground rockstars of the nerd world(my favorite world). So i decided that i needed to do something, and do something 3D! After spend a night with my scarce Actionscrip 2 knowledge and a lot of research on the Kirupa forums, i had done the first "3D" programming of my life: (Click HERE to open the flash, use WASD and Arrows).
If you have flash, just open a new document, click on the first frame, F9 and paste this:
MovieClip.prototype.glQuad = function(ax,ay,az,
           bx,by,bz,
           cx,cy,cz,
           dx,dy,dz,
           color) {
 
 p1 = new Object();
 p1.x = ax;
 p1.y = ay;
 p1.z = az;
 xy2d(p1);
 
 p2 = new Object();
 p2.x = bx;
 p2.y = by;
 p2.z = bz;
 xy2d(p2);
 
 p3 = new Object();
 p3.x = cx;
 p3.y = cy;
 p3.z = cz;
 xy2d(p3);
 
 p4 = new Object();
 p4.x = dx;
 p4.y = dy;
 p4.z = dz;
 xy2d(p4);
 
 mediaz = ((p1.z + p2.z + p3.z + p4.z)/4);
 
 if (isVisibleBetween(p1,p2,p3)){
  this.lineStyle(1, 0x000000, 100);
  this.moveTo(p1.x,p1.y);
  this.beginFill(color, 100);
  this.lineTo(p1.x,p1.y);
  this.lineTo(p2.x,p2.y);
  this.lineTo(p3.x,p3.y);
  this.lineTo(p4.x,p4.y);
  this.lineTo(p1.x,p1.y);
  this.endFill();
  this.swapDepths(Math.round(1000000-mediaz));
 }
 
 function xy2d (vertex:Object) {
  
  var sx = Math.sin(cameraView.rotationX*(Math.PI/180));
  var cx = Math.cos(cameraView.rotationX*(Math.PI/180));
  var sy = Math.sin(cameraView.rotationY*(Math.PI/180));
  var cy = Math.cos(cameraView.rotationY*(Math.PI/180));
  var sz = Math.sin(cameraView.rotationZ*(Math.PI/180));
  var cz = Math.cos(cameraView.rotationZ*(Math.PI/180));
  
  
  // rotation around x
  xy = cx*cameraView.y - sx*cameraView.z;
  xz = sx*cameraView.y + cx*cameraView.z;
  // rotation around y
  yz = cy*xz - sy*cameraView.x;
  yx = sy*xz + cy*cameraView.x;
  // rotation around z
  zx = cz*yx - sz*xy;
  zy = sz*yx + cz*xy;
  
  vertex.x = vertex.x - cameraView.x; //+ yx;
  vertex.y = vertex.y - cameraView.y;
  vertex.z = vertex.z - cameraView.z; //+ yz;
 
  limite = -500;
  if ( vertex.z < limite ) { vertex.z = limite; }
  
  focalLength = _root.fov;
  var scaleRatio = focalLength/(focalLength + vertex.z);
   
  vertex.x = (vertex.x - cameraView.x) * scaleRatio;
  vertex.y = (vertex.y - cameraView.y) * scaleRatio;

  vertex.x += pontoFugaInicial.x;
  vertex.y += pontoFugaInicial.y;

 };
  
 function isVisibleBetween(a,b,c){
  if (((b.y-a.y)/(b.x-a.x)-(c.y-a.y)/(c.x-a.x)<0)^(a.x<=b.x == a.x>c.x)){
   return true;
  }else{
   return false;
  }
 };

}

function glRedraw() {

 drawGl();
 controles();
  
}

function controles() {
 
 if (Key.isDown(Key.RIGHT)) { cameraView.rotationY += 10; } 
 if (Key.isDown(Key.LEFT)) { cameraView.rotationY -= 10;}  
 
 if (Key.isDown(65)) { cameraView.x -= 10; } //A
 if (Key.isDown(68)) { cameraView.x += 10; } //D
 if (Key.isDown(87)) { cameraView.z += 40; } //W
 if (Key.isDown(83)) { cameraView.z -= 40; } //S
 
 
 var movement = 0;
 if (Key.isDown(Key.UP)) { cameraView.y -= 10; }
 if (Key.isDown(Key.DOWN)) { cameraView.y += 10; }
 
 if (_root.debugz) {
  _root.debugz.text = "z: "+(cameraView.z);
  _root.debugy.text = "y: "+(cameraView.y);
  _root.debugx.text = "x: "+(cameraView.x);
 }
 
}

function drawGl() {
 
 //box1
 box.clear();
 box.glQuad(100,100,600,
      200,100,600,
      200,200,600,
      100,200,600,
      0xFFFFFF);
 box.glQuad(100,100,700,
      100,100,600,
      100,200,600,
      100,200,700,
      0xCCCCCC);
 box.glQuad(200,100,700,
      100,100,700,
      100,200,700,
      200,200,700,
      0xAAAAAA);
 box.glQuad(200,100,600,
      200,100,700,
      200,200,700,
      200,200,600,
      0xAAAAAA);
 box.glQuad(100,100,700,
      200,100,700,
      200,100,600,
      100,100,600,
      0xAAAAAA);
 
 
 //box2
 box2.clear();
 box2.glQuad(-100,100,900,
    0,100,900,
    0,200,900,
    -100,200,900,
      0xCC77AA);
 box2.glQuad(-100,100,1000,
    -100,100,900,
    -100,200,900,
    -100,200,1000,
      0xCC77AA);
 box2.glQuad(0,100,1000,
    -100,100,1000,
    -100,200,1000,
    0,200,1000,
      0xCC77AA);
 box2.glQuad(0,100,900,
    0,100,1000,
    0,200,1000,
    0,200,900,
      0xCC77AA);
 box2.glQuad(-100,100,1000,
    0,100,1000,
    0,100,900,
    -100,100,900,
      0xCC77AA);
 
 //sala
 sala.clear();
 sala.glQuad(-1000,200,7000,
    1000,200,7000,
    1000,200,-7000,
    -1000,200,-7000,
      0x457908);
 
}

function glLoad() {
 
 objeto = 0;
 strafe = 0;
 forward = 0;
 
 cameraView = new Object();
 cameraView.x = 0;
 cameraView.y = 0;
 cameraView.z = 0;
 cameraView.rotationX = 0;
 cameraView.rotationY = 0;
 cameraView.rotationZ = 0;
 
 pontoFugaInicial = new Object();
 pontoFugaInicial.x = (Stage.width/2);
 pontoFugaInicial.y = (Stage.height/2);
 
 if (_root.fuga) {
  _root.fuga._x = pontoFugaInicial.x;
  _root.fuga._y = pontoFugaInicial.y;
 }
 
 fov = 600;
 zAngle = 0;
 zmouse = 0;
 
 createEmptyMovieClip("box",1);
 createEmptyMovieClip("box2",2);
 createEmptyMovieClip("sala",3);
  
}

onLoad = glLoad;
onEnterFrame = glRedraw;

Nenhum comentário:

Postar um comentário