渲染到纹理不起作用

时间:2014-03-20 05:20:40

标签: actionscript-3 textures pixel-shader stage3d agal

我试图测试Stage3D的setRenderToTexture函数,但我的测试代码没有提供任何输出。我希望有人能告诉我为什么 - 我已经尝试了几乎所有工作。我创建的代码如下:

import flash.events.Event;
import flash.display.*;
import flash.display3D.*;
import flash.display3D.textures.Texture;
import AGALMiniAssembler;

//using stage size in several locations for simplicity - needs to be square, 2^n
[SWF(width='512', height='512', backgroundColor='0x000000', frameRate='60')]

//vars
var context0:Context3D;
var vBuff:VertexBuffer3D;
var iBuff:IndexBuffer3D;
var tex0:Texture;
var tex1:Texture;
var vShader:AGALMiniAssembler = new AGALMiniAssembler();
var fShader:AGALMiniAssembler = new AGALMiniAssembler();
var program:Program3D;

//create a square
var square:Shape = new Shape();
square.graphics.beginFill(0xaa00ff,1);
square.graphics.drawRect(10, 10, stage.stageWidth - 20, stage.stageHeight - 20);

//draw square to bitmapdata and create one blank bitmapdata
var tex0data:BitmapData = new BitmapData(stage.stageWidth,stage.stageHeight,false,0);
tex0data.draw(square);
var tex1data:BitmapData = new BitmapData(stage.stageWidth,stage.stageHeight,false,0);

//initialize stage3d
stage.stage3Ds[0].addEventListener(Event.CONTEXT3D_CREATE, initStage3D);
stage.stage3Ds[0].requestContext3D();

function initStage3D(e:Event):void {
    context0 = stage.stage3Ds[0].context3D;
    context0.configureBackBuffer(stage.stageWidth, stage.stageHeight, 0);

    //create buffers - simple quad
    var vBuff_vec:Vector.<Number> = new <Number>[-1, -1, 0, 0, 1,
                                                 -1, 1, 0, 0, 0,
                                                 1, 1, 0, 1, 0,
                                                 1, -1, 0, 1, 1];
    var iBuff_vec:Vector.<uint> = new <uint>[0, 1, 2, 0, 2, 3]
    vBuff = context0.createVertexBuffer(4, 5);
    vBuff.uploadFromVector(vBuff_vec, 0, 4);
    iBuff = context0.createIndexBuffer(6);
    iBuff.uploadFromVector(iBuff_vec, 0, 6);

    //load bitmapdata into textures - square to tex0 and blank to tex1
    tex0 = context0.createTexture(tex0data.width,tex0data.height,'bgra',false);
    tex0.uploadFromBitmapData(tex0data);    
    tex1 = context0.createTexture(tex1data.width, tex1data.height,'bgra',true);
    tex1.uploadFromBitmapData(tex1data);

    //create and upload simple shader program
    vShader.assemble('vertex', 'mov v0, va1 \n'+ //uv coords to v0
                                 'mov op, va0'); //output xyz coords
    fShader.assemble('fragment', 'tex oc, v0, fs0 <2d, linear, nomip>'); //output texture at fs0
    program = context0.createProgram();
    program.upload(vShader.agalcode, fShader.agalcode);
    context0.setProgram(program);

    //set buffers
    context0.setVertexBufferAt(0, vBuff, 0, 'float3');
    context0.setVertexBufferAt(1, vBuff, 3, 'float2');

    //prep rendering
    addEventListener(Event.ENTER_FRAME, render);
}

function render(e:Event):void {
    context0.clear();

    //render tex0 onto tex1
    context0.setRenderToTexture(tex1);
    context0.setTextureAt(0, tex0);
    context0.drawTriangles(iBuff);

    //render tex1 to back buffer and present
    context0.setTextureAt(0, tex1);
    context0.setRenderToBackBuffer();
    context0.drawTriangles(iBuff);
    context0.present();
}

编辑:我注意到更改空白位图的颜色确实会改变最终输出的颜色 - 它正在显示,但正方形未被渲染它。

1 个答案:

答案 0 :(得分:1)

最终想出来了!在纹理作为渲染目标可行之前必须采取一个微妙但重要的步骤 - 必须在切换渲染目标后清除它。按如下方式修改渲染功能会使程序按预期运行:

function render(e:Event):void {
    //render tex0 onto tex1
    context0.setRenderToTexture(tex1);
    context0.clear();
    context0.setTextureAt(0, tex0);
    context0.drawTriangles(iBuff);

    //render tex1 to back buffer and present
    context0.setTextureAt(0, tex1);
    context0.setRenderToBackBuffer();
    context0.clear();
    context0.drawTriangles(iBuff);
    context0.present();
}