| Package | flash.display3D |
| Class | public final class Context3DStencilAction |
| Inheritance | Context3DStencilAction Object |
| Language Version: | ActionScript 3.0 |
| Runtime Versions: | Flash Player 11, AIR 3 |
A stencil action specifies how the values in the stencil buffer should be changed.
Related API Elements
| Constant | Defined By | ||
|---|---|---|---|
| DECREMENT_SATURATE : String = "decrementSaturate" [static]
Decrement the stencil buffer value, clamping at 0, the minimum value. | Context3DStencilAction | ||
| DECREMENT_WRAP : String = "decrementWrap" [static]
Decrement the stencil buffer value. | Context3DStencilAction | ||
| INCREMENT_SATURATE : String = "incrementSaturate" [static]
Increment the stencil buffer value, clamping at 255, the maximum value. | Context3DStencilAction | ||
| INCREMENT_WRAP : String = "incrementWrap" [static]
Increment the stencil buffer value. | Context3DStencilAction | ||
| INVERT : String = "invert" [static]
Invert the stencil buffer value, bitwise. | Context3DStencilAction | ||
| KEEP : String = "keep" [static]
Keep the current stencil buffer value. | Context3DStencilAction | ||
| SET : String = "set" [static]
Replace the stencil buffer value with the reference value. | Context3DStencilAction | ||
| ZERO : String = "zero" [static]
Set the stencil buffer value to 0. | Context3DStencilAction | ||
DECREMENT_SATURATE | Constant |
public static const DECREMENT_SATURATE:String = "decrementSaturate"| Language Version: | ActionScript 3.0 |
| Runtime Versions: | Flash Player 11, AIR 3 |
Decrement the stencil buffer value, clamping at 0, the minimum value.
DECREMENT_WRAP | Constant |
public static const DECREMENT_WRAP:String = "decrementWrap"| Language Version: | ActionScript 3.0 |
| Runtime Versions: | Flash Player 11, AIR 3 |
Decrement the stencil buffer value. If the result is less than 0, the minimum value, then the buffer value is "wrapped around" to 255.
INCREMENT_SATURATE | Constant |
public static const INCREMENT_SATURATE:String = "incrementSaturate"| Language Version: | ActionScript 3.0 |
| Runtime Versions: | Flash Player 11, AIR 3 |
Increment the stencil buffer value, clamping at 255, the maximum value.
INCREMENT_WRAP | Constant |
public static const INCREMENT_WRAP:String = "incrementWrap"| Language Version: | ActionScript 3.0 |
| Runtime Versions: | Flash Player 11, AIR 3 |
Increment the stencil buffer value. If the result exceeds 255, the maximum value, then the buffer value is "wrapped around" to 0.
INVERT | Constant |
public static const INVERT:String = "invert"| Language Version: | ActionScript 3.0 |
| Runtime Versions: | Flash Player 11, AIR 3 |
Invert the stencil buffer value, bitwise.
For example, if the 8-bit binary number in the stencil buffer is: 11110000,
then the value is changed to: 00001111.
KEEP | Constant |
public static const KEEP:String = "keep"| Language Version: | ActionScript 3.0 |
| Runtime Versions: | Flash Player 11, AIR 3 |
Keep the current stencil buffer value.
SET | Constant |
public static const SET:String = "set"| Language Version: | ActionScript 3.0 |
| Runtime Versions: | Flash Player 11, AIR 3 |
Replace the stencil buffer value with the reference value.
ZERO | Constant |
public static const ZERO:String = "zero"| Language Version: | ActionScript 3.0 |
| Runtime Versions: | Flash Player 11, AIR 3 |
Set the stencil buffer value to 0.
- Clear stencil buffer to 0.
- Set stencil action to increment when the stencil test passes.
- Set the stencil reference value to 0.
- Draw the triangular mask. Wherever the triangle is drawn, the stencil test passes because the stencil buffer has been cleared to 0 and the reference value is 0. As a result, the stencil buffer is incremented to 1 where the triangle mask is drawn.
- Change the stencil action to keep so that subsequent draw operations do not change the stencil buffer.
- Draw a full screen rectangle (multicolored). Because the stencil reference value is still 0, the stencil test fails in the masked area. Thus, the rectangle draws everywhere except in the masked region.
- Change the stencil reference value to 1.
- Draw another full screen rectangle (red). Now the stencil test fails everywhere except the masked area, which was incremented to 1. Thus the rectangle only draws in the masked region.
Mouse over the example to see the main steps in sequence.
package
{
import com.adobe.utils.AGALMiniAssembler;
import flash.display.Sprite;
import flash.display.Stage3D;
import flash.display.StageAlign;
import flash.display.StageScaleMode;
import flash.display3D.Context3D;
import flash.display3D.Context3DBlendFactor;
import flash.display3D.Context3DCompareMode;
import flash.display3D.Context3DProgramType;
import flash.display3D.Context3DRenderMode;
import flash.display3D.Context3DStencilAction;
import flash.display3D.Context3DTriangleFace;
import flash.display3D.Context3DVertexBufferFormat;
import flash.display3D.IndexBuffer3D;
import flash.display3D.Program3D;
import flash.display3D.VertexBuffer3D;
import flash.events.Event;
import flash.events.KeyboardEvent;
import flash.events.MouseEvent;
import flash.events.TimerEvent;
import flash.geom.Rectangle;
import flash.text.TextField;
import flash.text.TextFormat;
import flash.ui.Keyboard;
import flash.utils.Timer;
public class Context3D_Stencil extends Sprite
{
public const viewWidth:Number = 350;
public const viewHeight:Number = 240;
private var stage3D:Stage3D;
private var renderContext:Context3D;
private var indexList:IndexBuffer3D;
private var vertexes:VertexBuffer3D;
private const VERTEX_SHADER:String =
"mov op, va0 \n" + //copy position to output
"mov v0, va1"; //copy color to varying variable v0
private const FRAGMENT_SHADER:String =
"mov oc, v0"; //Set the output color to the value interpolated from the three triangle vertices
private var vertexAssembly:AGALMiniAssembler = new AGALMiniAssembler();
private var fragmentAssembly:AGALMiniAssembler = new AGALMiniAssembler();
private var programPair:Program3D;
public function Context3D_Stencil()
{
stage3D = this.stage.stage3Ds[0];
stage3D.x = 10;
stage3D.y = 10;
//Add event listener before requesting the context
stage3D.addEventListener( Event.CONTEXT3D_CREATE, contextCreated );
stage3D.requestContext3D( Context3DRenderMode.AUTO );
//Compile shaders
vertexAssembly.assemble( Context3DProgramType.VERTEX, VERTEX_SHADER, false );
fragmentAssembly.assemble( Context3DProgramType.FRAGMENT, FRAGMENT_SHADER, false );
non3DSetup();
}
//Note, context3DCreate event can happen at any time, such as when the hardware resources are taken by another process
private function contextCreated( event:Event ):void
{
renderContext = Stage3D( event.target ).context3D;
trace( "3D driver: " + renderContext.driverInfo );
renderContext.enableErrorChecking = true; //Can slow rendering - only turn on when developing/testing
renderContext.configureBackBuffer( viewWidth, viewHeight, 2, true );
//Create vertex index list for the triangles
var triangles:Vector.<uint> = Vector.<uint>( [ 0, 3, 2,
0, 1, 3,
4, 7, 6,
4, 5, 7,
8, 9, 10
] );
indexList = renderContext.createIndexBuffer( triangles.length );
indexList.uploadFromVector( triangles, 0, triangles.length );
//Create vertexes
const dataPerVertex:int = 6;
var vertexData:Vector.<Number> = Vector.<Number>(
[
//x, y, z r,g,b format
-1, 1, 0, 1,0,0,
1, 1, 0, 0,0,1,
-1,-1, 0, 0,1,0,
1,-1, 0, 1,0,1,
-1, 1, 0, .5,0,0,
1, 1, 0, .5,0,0,
-1,-1, 0, .5,0,0,
1,-1, 0, .5,0,0,
0, .7,.1, 0,0,0,
-.7,-.7,.1, 0,0,0,
.7,-.7,.1, 0,0,0
]);
vertexes = renderContext.createVertexBuffer( vertexData.length/dataPerVertex, dataPerVertex );
vertexes.uploadFromVector( vertexData, 0, vertexData.length/dataPerVertex );
//Identify vertex data inputs for vertex program
renderContext.setVertexBufferAt( 0, vertexes, 0, Context3DVertexBufferFormat.FLOAT_3 ); //va0 is position
renderContext.setVertexBufferAt( 1, vertexes, 3, Context3DVertexBufferFormat.FLOAT_3 ); //va1 is color
//Upload programs to render context
programPair = renderContext.createProgram();
programPair.upload( vertexAssembly.agalcode, fragmentAssembly.agalcode );
renderContext.setProgram( programPair );
render();
}
private function render():void
{
//Clear, setting stencil to 0
renderContext.clear( .3, .3, .3, 1, 1, 0 );
//Draw stencil, incrementing the stencil buffer value
renderContext.setStencilReferenceValue( 0 );
renderContext.setStencilActions( Context3DTriangleFace.FRONT_AND_BACK,
Context3DCompareMode.EQUAL, Context3DStencilAction.INCREMENT_SATURATE );
if( state > 0 ) renderContext.drawTriangles( indexList, 12, 1 );
//Change stencil action when stencil passes so stencil buffer is not changed
renderContext.setStencilActions( Context3DTriangleFace.FRONT_AND_BACK,
Context3DCompareMode.EQUAL, Context3DStencilAction.KEEP );
//Draw quad -- doesn't draw where stencil has already drawn
if( state > 1 ) renderContext.drawTriangles( indexList, 0, 2 );
//Change the reference to 1 so this quad only draws into stenciled area
renderContext.setStencilReferenceValue( 1 );
if( state > 2 ) renderContext.drawTriangles( indexList, 6, 2 );
//Show the frame
renderContext.present();
}
//The rest of the code is for the example UI and timer
private function doState( event:TimerEvent ):void
{
switch (state)
{
case 0:
description.text = "Draw triangle with stencil action == increment";
state = 1;
break;
case 1:
description.text = "Draw the first plane where stencil == 0";
state = 2;
break;
case 2:
description.text = "Draw second plane where stencil == 1";
state = 3;
break;
case 3:
description.text = "Clear, setting stencil to 0";
state = 0;
break;
default:
description.text = "";
state = 0;
}
render();
}
private var state:int = 3;
private var stateTimer:Timer = new Timer( 1250 );
private var description:TextField = new TextField();
private function non3DSetup():void
{
//Setup timer to animate the stages of drawing the scene
stateTimer.addEventListener( TimerEvent.TIMER, doState );
this.stage.addEventListener( MouseEvent.MOUSE_OVER, function(event:Event):void{stateTimer.start()} );
this.stage.addEventListener( MouseEvent.MOUSE_OUT, function(event:Event):void{stateTimer.stop()} );
description.height = 30;
description.width = viewWidth;
this.addChild( description );
description.y = viewHeight + 15;
description.defaultTextFormat = new TextFormat( null, 18, 0xffffff );
description.text = "Mouse over to view.";
//Allows mouse-over events
var coverSprite:Sprite = new Sprite();
coverSprite.graphics.beginFill( 0, .01 )
coverSprite.graphics.lineTo( stage.stageWidth, 0 );
coverSprite.graphics.lineTo( stage.stageWidth, stage.stageHeight );
coverSprite.graphics.lineTo( 0, stage.stageHeight );
coverSprite.graphics.lineTo( 0, 0 );
this.addChild( coverSprite );
}
}
}
Mon Nov 28 2011, 06:48 AM -08:00
Hide Inherited Public Properties
Show Inherited Public Properties