查看: 3682|回复: 0
打印 上一主题 下一主题

AGAL语法

[复制链接]

12

主题

1

听众

385

积分

设计实习生

Rank: 2

纳金币
385
精华
0

最佳新人

跳转到指定楼层
楼主
发表于 2013-5-18 02:18:46 |只看该作者 |倒序浏览
pstatus"> 本帖最后由 家熊 于 2013-5-18 02:24 编辑

AGAL(Adobe Graphics Assembly Language)是Adobe开发的图形汇编语言,汇编语言是仅高于计算机二进制机器码的低级语言,可以精确地操控机器硬件比如可编程显卡,PC的Dirext9、MAC的OpenGL以及移动设备中的OpenGL ES 2都是可编程显卡,并且都支持AGAL。通过Adobe官方提供的编译器AGALMiniAssembler(实际上是一个AS类库),我们可以通过字符串指令来获得一个AGAL二进制流,再通过context3D上传给显卡的编程管线。对于顶点以及片段的运算都是通过AGAL交由显卡来处理的,这就是传说中的GPU硬件加速。),最新的测试版flash player 11中提供了可调用显卡资源来渲染图形API,即Molehill。
va属性寄存器
  这些寄存器参考顶点着色器的VertexBuffer输入。因此,他们只能在顶点着色器中可用。
  要通过正确的索引分配一个VertexBuffer到一个特定的属性寄存器,使用方法
  Context3D:setVertexBufferAt()
  在着色器中,访问属性寄存器的语法:va<n>,其中<n>是属性寄存器的索引号。
  有一共有8个属性寄存器用于顶点着色器。
常量寄存器
  这些寄存器是用来从ActionScript传递参数到着色的。这是通过Context3D::setProgramConstants()系列函数来实现。
  在着色器中,这些寄存器的访问语法:
  vc<n>,用于顶点着色器
  fc<n>,用于像素着色器
  其中<n>是常量寄存器的索引值。
  有128个常量寄存器用于顶点着色器和28常量寄存器用于像素着色器。
临时寄存器
  这些寄存器在着色器中,可以用于临时计算。
  这些寄存器的访问语法:
  vt<n> (vertex),用于顶点着色器
  ft<n> (pixel),用于像素着色器
  <n>是寄存器编号。
  有8个用于顶点着色器,8个用于像素着色器。
输出寄存器
  输出寄存器是在顶点和像素着色器存储其计算输出。此输出用于顶点着色器是顶点的剪辑空间位置。用于像素着色器是该像素的颜色。
  访问这些寄存器运算的语法:
  op,用于顶点着色器
  oc,用于像素着色器
  但显然只能一个输出寄存器用于顶点和像素着色器
变寄存器
  这些寄存器用来从顶点着色器传递数据到像素着色器。传递数据被正确地插入图形芯片,从而使像素着色器接收到正确的正在处理的像素的值。
  以这种方式获取传递的典型数据是顶点颜色,或 纹理UV 坐标。
  这些寄存器可以被访问的语法v <n>,其中<n>是寄存器编号。
  有8个变寄存器可用。
纹理取样器
  纹理采样寄存器是用来基于UV坐标从纹理中获取颜色值。
  纹理是通过ActionScriptcall指定方法Context3D::setTextureAt()。
  纹理样本的使用语法是:fs<n> <flags>,其中<n>是取样指数,<flags>是由一个或多个标记,用于指定如何进行采样。
  <flags>是以逗号分隔的一组字符串,它定义:
  纹理尺寸。可以是:二维,三维,多维数据集
  纹理映射。可以是:nomip,mipnone,mipnearest,mipnone
  纹理过滤。可以是:最近点采样,线性
  纹理重复。可以是:重复,包装,夹取。
  因此,举例来说,一个标准的2D纹理没有纹理映射,并进行线性过滤,可以进行采样到临时寄存器FT1,使用以下命令:
  “tex ft1, v0, fs0 <2d,linear,nomip> “
  变寄存器v0持有插值的纹理 UVs。
////////////////////////////////////////////////////////////////////////////

AGAL Opcode 指令:


基本语法

[opcode] [destination] [source1] [source2 or sampler]
沒有使用到的栏位必必须设为 0 (应该是指 bytecode)
mov move        分量移动     移动 source1 到 destination
add  add         分量相加     destination = source1 + source2
sub  subtract    分量相減     destination = source1 - source2
mul  multiply    分量相乘     destination = source1 * source2
div  divide      分量相除     destination = source1 / source2
rcp  reciprocal  分量倒数     destination = 1 / source1
min  minimum     分量最小值    destination = minimum(source1 , source2)
max  maximum     分量最大值    destination = maximum(source1 , source2)
frc  fractional  分量取小数    destination = source1 - (float) floor(source1)
sqt  square      分量平方根    destination = sqrt(source1)
rsq  recip. root 分量平方根倒数 destination = 1 / sqrt(source1)
pow  power       分量指数      destination = pow(source1 , source2)
log  logarithm   2 为底分量对数 destination = log_2(source1)
exp  exponential 2 为底分量指数 destination = 2^source1
nrm  normalize   分量标准化    destination = normalize(source1)
sin  sine        分量正弦      destination = sin(source1)
cos  cosine      分量余弦      destination = cos(source1)

abs  absolute    分量负值      destination = -source1
sat  saturate    分量饱和值    destination = maximum(minimum(source1 , 1) , 0)

kil  kill / discard (fragment shader only)
如果单个标量源组件是小于零,片段将被丢弃,而不是绘制到帧缓冲器。
目标寄存器必须全部为0。


tex  texture sample (fragment shader only)
目的地=加载的纹理2源于1的坐标。 在这种来源2必须是在采样格式。


sge  set-if-greater-equal
   destination = source1 >= source2 ? 1 : 0

slt  set-if-less-than
   destination = source1 < source2 ? 1 : 0

crs  cross product 向量外积
   destination.x = source1.y * source2.z - source1.z * source2.y
   destination.y = source1.z * source2.x - source1.x * source2.z
   destination.z = source1.x * source2.y - source1.y * source2.x

dp3  dot product  向量內积
   destination = source1.x * source2.x + source1.y * source2.y + source1.z * source2.z

dp4  dot product  向量內积
   destination = source1.x * source2.x + source1.y * source2.y + source1.z * source2.z+ source1.w * source2.w

m33 multiply    3x3 矩阵相乘
   destination.x = (source1.x * source2[0].x) + (source1.y * source2[0].y) + (source1.z * source2[0].z)
   destination.y = (source1.x * source2[1].x) + (source1.y * source2[1].y) + (source1.z * source2[1].z)
   destination.z = (source1.x * source2[2].x) + (source1.y * source2[2].y) + (source1.z * source2[2].z)

m44 multiply    4x4 矩阵相乘
   destination.x = (source1.x * source2[0].x) + (source1.y * source2[0].y) + (source1.z * source2[0].z) + (source1.w * source2[0].w)
   destination.y = (source1.x * source2[1].x) + (source1.y * source2[1].y) + (source1.z * source2[1].z) + (source1.w * source2[1].w)
   destination.z = (source1.x * source2[2].x) + (source1.y * source2[2].y) + (source1.z * source2[2].z) + (source1.w * source2[2].w)
   destination.w = (source1.x * source2[3].x) + (source1.y * source2[3].y) + (source1.z * source2[3].z) + (source1.w * source2[3].w)

m34 multiply    3x4 矩阵相乘
   destination.x = (source1.x * source2[0].x) + (source1.y * source2[0].y) + (source1.z * source2[0].z) + (source1.w * source2[0].w)
   destination.y = (source1.x * source2[1].x) + (source1.y * source2[1].y) + (source1.z * source2[1].z) + (source1.w * source2[1].w)
   destination.z = (source1.x * source2[2].x) + (source1.y * source2[2].y) + (source1.z * source2[2].z) + (source1.w * source2[2].w)

从 AGALMiniAssembler 里面看到还有这些 opcode

ifz, inz, ife, ine, ifg, ifl, ieg, iel, els, eif, rep, erp, brk, sgn

不过实际测试在目前这版 Flash Player 尚未支持

Error: Error #3621: AGAL validation failed: Invalid opcode, ifg is not implemented in this version at
token 2 of fragment program.

AGAL 基本語法:


vc0, va0 作 4×4 矩阵转换后指定输出空间 (output clipspace)
m44 op, va0, vc
以上语法等于一下单独分量操作内积
dp4 op.x, va0, vc0
dp4 op.y, va0, vc1
dp4 op.z, va0, vc2
dp4 op.w, va0, vc3
从 va1 复制到 v0 给 fragment shader 使用
mov v0, va1
等于
mov v0, va1.xyzw
注意 xyzw 顺序
mov v0, va1.yxzw
实际上等于
mov v0.x, va1.y
mov v0.y, va1.x
mov v0.z, va1.z
mov v0.w, va1.w
///////////////////////////////////////////////////////////////////////
AS3中,编译AGAL指令须按照以下几个步骤:
1、创建AGALMiniAssembler类对象 (AGALMiniAssembler 是Adobe提供的用来将字符串格式的AGAL指令编译成二进制码的工具类),如:
var vertexShaderAssembler:AGALMiniAssembler = new AGALMiniAssembler();
var fragmentShaderAssembler:AGALMiniAssembler = new AGALMiniAssembler();
2、编译AGAL代码,如:
vertexShaderAssembler.assemble(Context3DProgramType.VERTEX,
      "m44 op, va0, vc0\n" +
      "mov v0, va0\n" +
      "mov v1, va1\n" +
      "mov v2, va2\n" );

fragmentShaderAssembler.assemble(Context3DProgramType.FRAGMENT,
     "tex ft0, v1, fs0<2d, repeat, miplinear>\n" +
     "mov oc, ft0\n" );
3、创建Shader,如:
var shaderProgramrogram3D = _context3D.createProgram();
4、将编译后的AGAL代码上载给Shader ,如:
shaderProgram.upload(vertexShaderAssembler.agalcode, fragmentShaderAssembler.agalcode);
分享到: QQ好友和群QQ好友和群 腾讯微博腾讯微博 腾讯朋友腾讯朋友 微信微信
转播转播0 分享淘帖0 收藏收藏0 支持支持0 反对反对0
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

手机版|纳金网 ( 闽ICP备2021016425号-2/3

GMT+8, 2024-11-27 18:36 , Processed in 0.109449 second(s), 28 queries .

Powered by Discuz!-创意设计 X2.5

© 2008-2019 Narkii Inc.

回顶部