rendering to bitmap alternativa3d 8

David Jones
@david3jones
avatar-davidejones

I’ve worked on a couple of projects that have needed the rendered 3d scene to be rendered to a bitmap. One of them was for the top view on a car that can be driven around and another was to help out a friend of mine with his pixelated style 3d graphics. Anyway, I had created an example which shows how to roughly render a bitmap of the scene to the top left of the screen. I’ve used some bitmap cropping and other things but it seems to do the trick. Hopefully it will help you other guys out who are struggling with this. render to bitmap

package
{
    	import alternativa.engine3d.controllers.SimpleObjectController;
    	import alternativa.engine3d.core.Camera3D;
    	import alternativa.engine3d.core.Object3D;
    	import alternativa.engine3d.core.Resource;
    	import alternativa.engine3d.core.View;
    	import alternativa.engine3d.loaders.Parser3DS;
    	import alternativa.engine3d.loaders.ParserA3D;
    	import alternativa.engine3d.loaders.ParserCollada;
    	import alternativa.engine3d.loaders.ParserMaterial;
    	import alternativa.engine3d.loaders.TexturesLoader;
    	import alternativa.engine3d.materials.TextureMaterial;
    	import alternativa.engine3d.objects.Mesh;
    	import alternativa.engine3d.objects.Surface;
    	import alternativa.engine3d.resources.ExternalTextureResource;
    	import alternativa.engine3d.resources.Geometry;
    
    	import flash.display.Sprite;
    	import flash.display.Stage3D;
    	import flash.display.StageAlign;
    	import flash.display.StageScaleMode;
    	import flash.events.Event;
    	import flash.net.URLLoader;
    	import flash.net.URLLoaderDataFormat;
    	import flash.net.URLRequest;
    	
    	import flash.geom.Vector3D;
    	import alternativa.engine3d.primitives.Box;
    	import alternativa.engine3d.materials.FillMaterial;
    	
    	import flash.display.Bitmap;
    	import flash.display.BitmapData;
    	import flash.geom.Matrix;
    	import flash.geom.Rectangle;
    	import flash.geom.Point;
    	
    	[SWF(backgroundColor="#000000", frameRate="60", width="800", height="600")]
    
    	public class main extends Sprite 
    	{		
    		private var scene:Object3D = new Object3D();
    		private var camera:Camera3D;
    		private var controller:SimpleObjectController;
    		private var stage3D:Stage3D;
    		private var mybitmap:Bitmap;
    		
    		public function main():void
    		{
    			stage.align = StageAlign.TOP_LEFT;
    			stage.scaleMode = StageScaleMode.NO_SCALE;
    			
    			camera = new Camera3D(1, 1000);
    			camera.view = new View(stage.stageWidth, stage.stageHeight, false, 0, 0, 4);
    			addChild(camera.view);
    			addChild(camera.diagram);
    			
    			camera.x = -150;
    			camera.y = -150;
    			camera.z = 0;
    			camera.view.renderToBitmap = true;
    			controller = new SimpleObjectController(stage, camera, 200);
    			controller.lookAt(new Vector3D(0,0,0));
    			scene.addChild(camera);
    			
    			stage3D = stage.stage3Ds[0];
    			stage3D.addEventListener(Event.CONTEXT3D_CREATE, onContextCreate);
    			stage3D.requestContext3D();
    		}
    		
    		private function onContextCreate(e:Event):void {
    			stage3D.removeEventListener(Event.CONTEXT3D_CREATE, onContextCreate);
    			
    			mybitmap = new Bitmap();
    			mybitmap.smoothing = true;
    			mybitmap.bitmapData = camera.view.canvas;
    			
    			var b:Box = new Box(50, 50, 50, 1, 1, 1, false, null);
    			b.setMaterialToAllSurfaces(new FillMaterial(0xFF0000));
    			scene.addChild(b);
    			uploadResources(b.getResources(false, Geometry));
    			
    			stage.addEventListener(Event.ENTER_FRAME, onEnterFrame);
    			stage.addEventListener(Event.RESIZE, onResize);
    			onResize();
    			
    			stage.addChild(mybitmap);
    		}
    		
    		private function uploadResources(resources:Vector.):void {
    			for each (var resource:Resource in resources) {
    				resource.upload(stage3D.context3D);
    			}
    		}
    
    		private function onEnterFrame(e:Event):void {
    			controller.update();
    			camera.render(stage3D);
    			mybitmap.bitmapData = cropBitmapData(camera.view.canvas, 200, 130);
    		}
    		
    		private function onResize(e:Event = null):void {
    			camera.view.width = stage.stageWidth;
    			camera.view.height = stage.stageHeight;
    		}
    		
    		private function cropBitmapData(sourceBitmapData:BitmapData, width:Number, height:Number):BitmapData
            {
    			var ratio:Number = height/width;
    			var m:Matrix = new Matrix();
    			m.scale(width / sourceBitmapData.width, height / sourceBitmapData.height);
    			var bmp:BitmapData = new BitmapData(width, height, false, 0x000000);
    			bmp.draw(sourceBitmapData, m);
    			return bmp.clone();
    			bmp.dispose();
            }
    	}
}

You can download the example files here

Downloads

Comments

  • avatar-piotr-tracki
    # Piotr Tracki
    Hi, Could you show a bit more and explain how to use RenderToTexture to copy viewport on a small 3d plane placed and rotated somewhere in the scene? I see no simple example on the net. Only mirrors and complicated fullscreen post effects …
  • avatar-davidejones
    # davidejones
    The mirror example does pretty much exactly what you want. Basically you would create a custom material this is applied to your plane placed somewhere in scene. This material uses rendertotexture only difference is you don’t need to use a mirror camera or reposition the camera or anything like that as you don’t need a mirror view.
  • avatar-ali
    # Ali
    Thanks for the help - really useful One thing that’s troubling me is transparency when rendertobitmap is set to true. If I have many layered black objects with a low transparency (say 0.1 for instance) they appear to act like glass. The more the objects are layered the darker it gets until you get to black. With rendertobitmap set to true the layered objects look grey there is a certain amount of build up in transparency but only up to a max of 3 or 4 layers perhaps. I’m using fillmaterial btw, hope you can help
  • avatar-davidejones
    # davidejones

    Glad the post helped.

    I’m not sure about your problem, perhaps its to do with the inner workings of alternativa3d or stage3d that cause your problem. The render to bitmap should just take what is rendered so i don’t see how it would look different.

Comments are currently closed