Flash Stage3D Cheat Sheet

Temas: Flash Stratos
Juan Mellado, 22 Noviembre, 2011 - 22:51

WebGL Cheat SheetEl lanzamiento de la versión definitiva de Flash 11 hace unas pocas semanas trajo consigo el tan esperado Stage3D, anteriormente conocido como Molehill. O lo que es lo mismo, la posibilidad de aprovechar las capacidades de las GPUs desde Flash. En principio es una alternativa más a otras opciones disponibles actualmente como WebGL, aunque el anuncio por parte de Adobe de renunciar a seguir desarrollando Flash para móviles en favor de su plataforma AIR nos ha dejado despistados a un montón de gente. Pero decisiones empresariales aparte, el API está ahí fuera y es hora de echarle un vistazo.

Siguiendo mi costumbre, he elaborado una pequeña cheat sheet para que me sirva de referencia, igual que la que hice para WebGL.

Lo primero que llama la atención es que es una API de muy bajo nivel. Los que hayan utilizado alguna vez OpenGL, WebGL o DirectX se sentirán cómodos. Pero sinceramente, me esperaba una jerarquía de clases que ofreciera una funcionalidad de más alto nivel para la gestión de escenas, cámaras, colisiones o carga de modelos. Pero no, las clases que hay son para el acceso a bastante bajo nivel. De hecho, ni siquiera han incluido en el runtime el compilador de shaders.

Pero vayamos por partes, las clases básicas de entrada al API son Stage3D y Context3D. La primera clase representa la superficie sobre la que se dibuja, de forma similar al Stage de toda la vida, y que permite además instanciar la segunda clase a través de un evento (para las situaciones de pérdida de contexto). El contexto 3D es el que permite instanciar al resto de clases como los buffers de índices, vértices, texturas o shaders.

public class Example extends Sprite{
  private var stage3D:Stage3D;
  private var context3D:Context3D;

  public function Example(){
    stage3D = this.stage.stage3Ds[0];
    stage3D.addEventListener(Event.CONTEXT3D_CREATE, onContext3DCreate);
    stage3D.requestContext3D(Context3DRenderMode.AUTO);
  }

  private function onContext3DCreated(event:Event):void{
    context3D = Stage3D(event.target).context3D;
  }
...

Context3D es la clase base, muy similar a otras APIs, y permite, entre cosas, establecer el estado del render con las clásicas opciones de configuración del z-buffer, blending o stencil, y el envío al driver de la orden de dibujado de triángulos.

Otras clases básicas son VertexBuffer3D, IndexBuffer3D, Texture, CubeTexture y Program3D. Pero tienen muy poca funcionalidad, apenas dos o tres métodos para inicializar su contenido desde fuentes de distintos tipos como arrays o matrices. El resto de clases son básicamente enumerados con las constantes típicas como Context3DTextureFormat, Context3DVertexBufferFormat, Context3DBlendFactor o Context3DStencilAction. En total son unas nueve clases de este último tipo, pero no ofrecen mayor funcionalidad aparte de exponer las constantes.

var triangles:Vector.<uint> = Vector.<uint>( [ ... ] );
...
indexList = context3D.createIndexBuffer(triangles.length);
indexList.uploadFromVector(triangles, 0, triangles.length);
...           
context3D.setCulling(Context3DTriangleFace.BACK);
...

Por lo que respecta a los shaders, Adobe ha definido un lenguaje propio (otro más) de muy bajo nivel llamado AGAL (Adobe Graphics Assembly Language). Es realmente ensamblador, por lo que las operaciones son de muy bajo nivel. Las instrucciones son opcodes que manipulan directamente los distintos tipos de registros habituales (attribute, constant, temporary, output, varying, sampler).

private const VERTEX_SHADER:String =
  "mov v0, va1"; //Color (v0: varying 0 <= va1: attribute 1)
  "m44 op, va0, vc0 \n" + //Perspectiva (op: output position, vc0: constant 0)
       
private const FRAGMENT_SHADER:String =
  "mov oc, v0"; //oc: output color

El array de bytecodes correspondiente a un shader puede generarse en tiempo de diseño mediante Pixel Bender 3D, que es una ampliación de la versión 2D de Pixel Bender, una tecnología de Adobe para el procesamiento óptimo de imágenes y vídeos independiente de la plataforma hardware utilizada basada en el uso de ficheros XML. Aunque afortunadamente los shaders también pueden compilarse de una forma más conveniente en tiempo de ejecución mediante una clase de utilidad externa llamada AGALMiniAssembler.

private var vertexAssembly:AGALMiniAssembler = new AGALMiniAssembler();
private var fragmentAssembly:AGALMiniAssembler = new AGALMiniAssembler();
private var programPair:Program3D;
...
vertexAssembly.assemble(Context3DProgramType.VERTEX, VERTEX_SHADER, false);
fragmentAssembly.assemble(Context3DProgramType.FRAGMENT, FRAGMENT_SHADER, false);
...
programPair = renderContext.createProgram();
programPair.upload(vertexAssembly.agalcode, fragmentAssembly.agalcode);

Por lo que respecta al bucle principal habitual de Flash, no parece requerir modificación, pudiéndose seguir utilizando el evento ENTER_FRAME por ejemplo.

  ...
  this.stage.addEventListener(Event.ENTER_FRAME, render);
}

private function render(event:Event):void{
  ...
  context3D.drawTriangles(indexList, 0, 12);
  context3D.present();
}

En definitiva, una API más, una opción más a tener en cuenta a la hora de representar 3D en el navegador. Quizás de muy bajo nivel para el concepto que suele tenerse en la cabeza de Flash, percepción que la aparición de ActionScript 3 empezó a modificar y que Stage3D no hace más que confirmar.

Para terminar, revisando la web de Flash, he encontrado un enlace a un proyecto de la propia Adobe llamado Proscenium. Una librería gráfica de alto nivel, a modo de engine 3D, que están desarrollando sobre Stage3D. El inconveniente es que está aún en fase de desarrollo y no tiene soporte, aunque ya permite crear primitivas básicas, cargar modelos de objetos, e incluso gestionar colisiones. No sé como acabará, pero supongo que pretenderá ser una alternativa a motores desarrollados de forma independiente, como por ejemplo el popular Away3D y otros, que la propia Adobe parece estar apoyando.

¿No encontró lo que buscaba?

Utilice el buscador para encontrar más páginas en esta web o en toda Internet.
 
Web www.inmensia.com