AGALの勉強 | Photoshop CC Tutorials
ここにきてようやくAGALの勉強です。
他の皆さんはAGALを使ってどんどんすごいものを作られているというのに自分はこの有様です。(;^_^ A

今回、AGALの参考文献としてFlash界の第一人者の高輪知明さんの資料を拝見させていただきました。

この資料にはAS3とGPUの関係が分かりやすく図で表されていて読んでいて面白かったです。
さらに有難いことにclockmakerさんのUstreamサイトで配信動画が載せられていましたので
こちらでも勉強させていただきました。

■ 高輪知明さんの資料サイト
http://nutsu.com/blog-asset/study/120525_slide_stage3d.pdf

■ clockmakerさんの動画配信サイト
http://www.ustream.tv/recorded/22837047

まずは下の画像のようなものを作成してみました。
$ピック社長のブログ

プログラムは下記のようになります。
Main.as
package
{
import com.adobe.utils.*;
import flash.display.*;
import flash.display3D.*;
import flash.display3D.textures.Texture;
import flash.events.*;
import flash.geom.Matrix3D;
import flash.net.URLRequest;
import flash.system.LoaderContext;

[SWF(width="300", height="300", frameRate="60", backgroundColor="#000000")]
public class Main extends Sprite
{
private var context3d:Context3D;
private var vertBuffer:VertexBuffer3D;
private var indexBuffer:IndexBuffer3D;
private var program:Program3D;
private var texture:Texture;
private var textureData:BitmapData;

private var matrix:Matrix3D = new Matrix3D();

public function Main()
{
if (stage) init();
else addEventListener(Event.ADDED_TO_STAGE, init);
}

private function init(event:Event = null):void
{
removeEventListener(Event.ADDED_TO_STAGE, init);

initStage();
stage.stage3Ds[0].addEventListener( Event.CONTEXT3D_CREATE, initStage3d );
stage.stage3Ds[0].requestContext3D();

addEventListener(Event.ENTER_FRAME, onTick);
}

private function initStage():void
{
stage.scaleMode = StageScaleMode.NO_SCALE;
stage.align = StageAlign.TOP_LEFT;
}

private function initStage3d(event:Event):void
{
context3d = stage.stage3Ds[0].context3D;
context3d.configureBackBuffer(stage.stageWidth, stage.stageHeight, 1, true);

///////////////////////////////
// 頂点定義
var scale:Number = 3;
var vertices:Vector. = Vector.([
// x y z u v
0.0000/scale, 2.3006/scale, 0.0000, 0, 0,
0.7475/scale, 0.7860/scale, 0.0000, 0, 0,
2.4190/scale, 0.5431/scale, 0.0000, 0, 0,
1.2095/scale, -0.6359/scale, 0.0000, 0, 0,
1.4950/scale, -2.3006/scale, 0.0000, 0, 0,
0.0000/scale, -1.5146/scale, 0.0000, 0, 0,
-1.4950/scale, -2.3006/scale, 0.0000, 0, 0,
-1.2095/scale, -0.6359/scale, 0.0000, 0, 0,
-2.4190/scale, 0.5431/scale, 0.0000, 0, 0,
-0.7475/scale, 0.7860/scale, 0.0000, 0, 0
]);

// vertexBuffer
vertBuffer = context3d.createVertexBuffer(10, 5);
vertBuffer.uploadFromVector(vertices, 0, 10);
// indexBuffer
indexBuffer = context3d.createIndexBuffer(24);
indexBuffer.uploadFromVector (Vector.([1, 9, 0, 3, 1, 2, 5, 3, 4, 6, 7, 5, 7, 8, 9, 1, 3, 9, 9, 3, 5, 9, 5, 7]), 0, 24);
// texture
texture = context3d.createTexture(32, 32, Context3DTextureFormat.BGRA, true);
texture.uploadFromBitmapData(new BitmapData(32, 32, false, 0xffff00));

matrix.appendTranslation(0, 0, 0);

// シェーダに割り当てる
// va0 holds xyz
context3d.setVertexBufferAt(0, vertBuffer, 0, Context3DVertexBufferFormat.FLOAT_3);
// va1 holds uv
context3d.setVertexBufferAt(1, vertBuffer, 3, Context3DVertexBufferFormat.FLOAT_2);

generateMicroProg();

context3d.setTextureAt(0, texture);
context3d.setProgram(program);
}

private function generateMicroProg():void
{
///////////////////////////////
// シェーダプログラム
var vertexShaderAssembler : AGALMiniAssembler = new AGALMiniAssembler();
vertexShaderAssembler.assemble( Context3DProgramType.VERTEX,
"m44 op, va0, vc0\n" +
"mov v0, va1"
);

var fragmentShaderAssembler : AGALMiniAssembler= new AGALMiniAssembler();
fragmentShaderAssembler.assemble( Context3DProgramType.FRAGMENT,
"tex oc, v0, fs0<2d, clamp, nearest>"
);

program = context3d.createProgram();
program.upload( vertexShaderAssembler.agalcode, fragmentShaderAssembler.agalcode);
}

private function onTick(event:Event):void
{
///////////////////////////////
// 描画
if ( !context3d )
return;

context3d.clear ( 0, 0, 0, 1 );
matrix.appendTranslation(0, 0, 0);
// set vertex data from blank Matrix3D
context3d.setProgramConstantsFromMatrix(Context3DProgramType.VERTEX, 0, matrix, true);
context3d.setProgramConstantsFromVector(Context3DProgramType.FRAGMENT, 0, Vector.( [ 0, 0, 0, 1 ]) );

context3d.drawTriangles(indexBuffer);
context3d.present();
}
}
}