Webcam 3D objects texturing thanks to BitmapData
November 16th, 2005 by Kiroukou :: Resources, en :: RSS 2.0 :: trackbackAll the people who were interested by 3D has thought about the texturing thing. . We all hoped to be able to distort a bitmap to fits it on the 3D object's face. But who expected to be able to texture with a live video such as webcam?
People who have already looked at our examples files should know that Sandy gives the possibility to easily texture an object with your webcam video stream, and I will explain this point a bit more in this post
Since Flash8, as all of you already know, you are allowed to access to pixel with the BitmapData class. But the best thing is that Macromedia gave us the possibility to use this thing pretty much everywhere ! We have a complete MovieClip BitmapData relation which is really powerful. Moreover, you can use directly some transformations for the bitmap drawing.
We use this new feature in our API to texture a face. Basically we align the whole bitmap to fit it with our 3 points, and then use MovieClip.beginBitmapFill() to draw only what we need. So now, our TextureSkin class, which is the class used to texture Object3D, is basically a composition of a bitmapData with some face's points access.
You should be able to find the following part by yourself now
Since a Video object must be into a MovieClip, we just have to draw every time we want the Video's clip into our TextureSkin classbitmapData property with MovieClip.draw method , that's all And as we use a single bitmapData, it's not more CPU intensive than a BitmapData containing a static picture (well if we forgot the clip's draw into the bitmapdata for sure).
Here is the example :
and a picture for those who don't have a webcam :
And for those who don't have tried our API, here is the code needed to realize that :
-
import mb.sandy.core.data.*;
-
import flash.display.BitmapData;
-
import mb.sandy.primitive.*;
-
import mb.sandy.view.*;
-
import mb.sandy.core.transform.*;
-
import mb.sandy.core.*;
-
import mb.sandy.core.group.*;
-
import mb.sandy.skin.*;
-
import mb.sandy.event.*;
-
-
class Test extends Sandy
-
{
-
private var _ts:TextureSkin;
-
-
public function Test( mc:MovieClip )
-
{
-
super( mc );
-
// -- _mc.clip.vid is the link to our video object on the scene
-
_mc.clip.vid.attachVideo( Camera.get() );
-
}
-
-
public static function main( mc:MovieClip ):Void
-
{
-
var t:Test = new Test( mc );
-
t.start ();
-
}
-
-
public function start( Void ):Void
-
{
-
// -- object skin creation. Here a bitmapData
-
_ts = new TextureSkin( new BitmapData(200, 200) );
-
// The 3D object, here a simple box
-
var box:Box = new Box( 100, 50, 100);
-
// -- we attach the skin to the object
-
box.setSkin( _ts );
-
// -- we place our objet on the scene at x:0, y:0, z:550.
-
box.setPosition(0,0,550);
-
// -- we create the group (group of objects or of groups too)
-
var g:Group = new Group();
-
// -- we create a transformation to apply to our object, here a rotation ( parameters are axis, speed as angle in degrees)
-
var r:Transform3D = new Rotation3D( new Vector4(1,1,1), 2 );
-
// -- we create the transformGroup which manage all the transformations to aply to the objects of a group (here a single rotation)
-
var tg:TransformGroup = new TransformGroup();
-
// We add the rotation to the group
-
tg.addTransform( r );
-
// we compile it to be faster later
-
tg.compile();
-
// -- we attach the transformGroup to this group.
-
g.setTransformGroup( tg );
-
// -- we add the Box to our group
-
g.addObject( box );
-
// -- we add our group to our world object
-
_world.addGroup( g );
-
// -- we create some Frame call to wake the realtime rendering & texturing
-
var fcall:FrameCall = new FrameCall( this, "rendering" );
-
fcall.connect ();
-
var tcall:FrameCall = new FrameCall( this, "camTexturing" );
-
tcall.connect();
-
}
-
-
private function camTexturing( Void ):Void
-
{
-
// -- we just copy the movieclip containing the webcam stream into our texture bitmapdata.
-
_ts.texture.draw( _mc.clip );
-
}
-
-
private function rendering(Void):Void
-
{
-
// we render the world scene (here a simple group owning a simple object)
-
_world.render();
-
}
-
-
}
I hope you find this article interessting and please leave a comment if you have a question or if you want to notice something. Sorry if I made some English mistake, I'll do my best (feel free to correct me !)
Regards thomas


Some english modifications
Thanks François !