Real reflections in Papervision3D!
You know I’m a fan of the Papervision BasicView, it’s just such a good entry point into Papervision – so easy to work with, and you can even extend it for your document class.
But how cool would it be if you could have something as simple as a BasicView, but that automatically created a reflection on the ground? Very cool! That’s how!
Which is exactly why I made a ReflectionView. You can pretty much just replace your BasicView with this new class.
At the moment it only works with reflections on an xz plane (ie the floor).
There are only two new things you need to consider :
surfaceHeight
This is the y position of the floor. You need to make sure none of your objects go underneath this or it’ll look weird!
setReflectionColor()
This function adjusts the color transform for the reflection by settings mutlipliers and offsets for red, green and blue, just like the colorTransform property of MovieClips.
By default this is set to darken the reflection but you can use it to lighten or even colorise it.
It’s very alpha, but very simple and very quick!
You can also add blur to the reflection by adding a filter to the reflection viewport :
viewportReflection.filters = [new BlurFilter(4,4,1)];
And if you want it to actually be transparent (if you’re using a floor plane for example) you can also add a ColorMatrixFilter to the viewportReflection filters.
I’m looking at improved effects to this with Andy’s help but I thought I’d at least get a basic version out there for you to play with.
Basic cube source code here :
package { import flash.events.Event; import org.papervision3d.cameras.Camera3D; import org.papervision3d.core.effects.view.ReflectionView; import org.papervision3d.materials.ColorMaterial; import org.papervision3d.materials.utils.MaterialsList; import org.papervision3d.objects.primitives.Cube; [SWF (width="640", height="480", backgroundColor="0x000000", frameRate="30")] public class ReflectionCubeSimple extends ReflectionView { private var cube : Cube; public function ReflectionCubeSimple() { super(640,480,false, false); //the height of the reflection plane surfaceHeight = -100; initCube(); camera.z = -400; addEventListener(Event.ENTER_FRAME, enterFrame); } public function initCube() : void { // create a materials list for the cube. var ml : MaterialsList = new MaterialsList(); ml.addMaterial(new ColorMaterial(0x880000), "all"); ml.addMaterial(new ColorMaterial(0x660000),"right"); ml.addMaterial(new ColorMaterial(0x440000),"bottom"); ml.addMaterial(new ColorMaterial(0xdd0000),"top"); ml.addMaterial(new ColorMaterial(0xdd0000),"left"); cube = new Cube(ml,100,100,100); // add the cube to the scene scene.addChild(cube); } public function enterFrame(e:Event) : void { // rotate the cube dependent on the mouse position cube.yaw((320-mouseX)*0.05); cube.y=(120-(mouseY/2)); if(cube.y<0) cube.y = 0; singleRender(); } } }
(Cue about a million CoverFlow type effects…
)
Related posts:




Hey Seb, thanks for the info. I’ve been trying to get the reflection to fade out into the floor. Kind of like an alpha gradient? Do you have any creative idea on how to do this off the top of your head?
[...] Seb Lee-Delisle » Blog Archive » Real reflections in Papervision3D!のブログが参考元ですが、RefrectionViewを継承すれば床に移りこんだ蝶が自動的に反映されます。 [...]
that’s really nice ..but i was wondering why if i put a clip underneath the reflektion disappears…i just wanted to put a gradient but i cant ..how to blur just the reflektions btw?
Thanks
Hi Seb
Any updates on this topic?
I’ve checked out the latest papervision revision and started using your ReflectionView, it’s a really great class. Would have saved me a lot of headaches on a previous project.
The particular topics I’m interested about is the possibility to create a falloff, apply effects to only the reflection (like a blur).
Hi guys,
I can see you’re all after creating a kind of drop off effect, there are a few ways we could approach this, but none of them are very easy
I expect it’d take some work on the renderer.
Bart, it’s easy to add a blur to the whole reflection, there’s a separate viewport in the ReflectionView class that you can apply effects to. From memory the viewport is called reflectionViewport, and you can set the filters like this :
reflectionViewport.filters = [new BlurFilter(4,4,1)];
Don’t forget that the blur filter is optimised for values that are exponents of 2, ie, 2, 4, 8, 16, 32 etc.
cheers!
Seb
Hi Seb,
I’m trying to extend the ReflectionView class but I’m getting this continuous error:
ERROR: lookAt error
What can be the reason?
Thanks
Hi Seb,
is it possible to avoid reflection on some displayObject3D while others do have reflection?
Thanks!
Hey, I’ve been checking out your blog, as well as over 400 other blogs over the past week (since I started my portfolio project at school) and have finally come up with some of your tutorials, other tuts, and put them together. Right now, here’s the demo of what I have:
http://www.geocities.com/bombermangraal/CubeTest.swf
As far as I know, I have a script to make the cube face the camera when a side is clicked, but don’t have one where you click outside of the cube and it goes back to its spinning self.
If it’s too much, then could you possibly give me tips on limiting the speed at which the cube spins via x, y, z?
haha silly me, I just read your code and used that to slow down my cube, thanks anyway!
sincerely,
Jim
Hi Seb,
great work! I just started using pv3dGW some days ago and while i definitely think that it is great in some way, it seems to be still a little raw in many areas – hopefully i can help in one way or the other in the upcoming christmas holidays.
That being said, I haven’t succeeded in using your ReflectionView as it just doesn’t display anthing. I also still haven’t found a good way to debug the issue, as pv3d gets a bit ugly when it comes to following inheritances – thank god it doesn’t seem to make much use of polymorphism.
I’m not sure if I could send you my code, because it gets its data from a server of our client, which i think i shouldn’t hand out to anyone.
Still i got some leads which I think you could maybe comment on:
1. I’m using Plane’s for everything, so i got no solid objects
2. The viewport is not set to scale with the stage, I instead scale it manually (which leads to another oddity, as culling seems to only work correct for the portion of the viewport in a quadratic area)
3. my surfaceheight is -1120 and my camera is set up with z=-1000, fov=60, near=10, far=5000, x=0, y=0 with the main display object being 1120 units in height and some thousand units in width
Got any ideas?
P.S. I could probably strip out those url’s which would leave my code not working because of no data, as that is being loaded from an external xml file.
@Joe
I think your plane is outside of your camera’s field of view.
@Jim
Thx for your answer -
How would i test for that? My normal viewport / planes just show up fine, and I already tried different heights for the surfaceheight, negative as well as positive, to no avail.
Hi Seb,
Using your example, but change the cube rotation with a camera movement (targeted to center) based on mouse position.
And there’s a bad effect, the second cube (in second viewport) seems to be late.
So i’ve made a little change for fixe it , just put your line super.singleRender(); as the first line of yours singleRenderer function in ReflectionView.
Thanks for your works.
Cheers
Hy everyone,
just found out, what was making the reflection not show up:
setChildIndex(viewportReflection,0);
I have a background image in my flash movie which covers the whole available space, so the reflection was in fact behind it. I’d suggest to change this part to swapping the index instead of plainly setting it to 0.
Merry Xmas
Next problem:
When i tilt the camera around the Y axis (i always confuse the words tilt / yaw / pitch so forgive me if I do it this time as well…) the reflection does not rotate the same way and it always seems to look at the camera, like a bilboard reflection…
Am i doing something wrong or is reflectionview not yet cut out for doing such reflections? Also, about a drop off: How would it be possible with the way reflectionview works at the moment? If i’d just overlay the viewport with a gradient mask it would not change with the rotation…
Any idea on one of those two problems?
Any update on the interactivity issues and reflection “lags”?
If I leave everything as is, I get interactivity when using reflectionview. However, if I orbit or move the camera, the reflection seems to be lagging.
If I move the line:
super.singleRender();
to the top of the singleRender() override function (ReflectionView.as) it seems to solve the reflection lag issue, but then interactivity goes mad. Kind of like if the “hot areas” are offset vertically.
I’ve been struggling with reflections for some time. Then the Merry Christmas post came out, and i noticed it used ReflectionView! Thanks so much!
I’m trying to figure out how to put a Plane down as the surface/ground. I first tried setting the y value of the plane below the surfaceHeight value, that didn’t work.
I saw your reply about using viewportReflection’s viewportObjectFilter, but i tried (try…catch) accessing it but it is null… maybe i need to research more…
I was then looking at the comment, and code: setChildIndex(viewportReflection,0) and was thinking that if the reflection is at childIndex of 0 and the normal viewport is above that, using myView.scene.addChild() will always put my plane above the reflection.
I’m sure im missing something, but it almost seems like i need a third viewport, below the reflection, if i want to simulate the reflection being “cast” or “above” my ground plane.
Let me know if you want code or if you can point me in the right direction.
Any help would be greatly appreciated! Thanks in advance!
Oh, also, i remember a talk you gave on particles back at FlashForward in Austin TX. I was blown away with your easy explanations and LOVED the plug-in media page, so much fun to playwith. Thanks for sharing with us flash mortals!
I’ve also been struggling with the reflections during the past days. When I move the camera the reflection does not sync properly.
Is this a known issue, seb?
For jason : just put the line super.singleRender(); as the first line of your singleRenderer function in ReflectionView. it works fine for me !
Fidiman: Yeah… I tried that before and it solves the reflection problem. However, if I do it, the mouse events go crazy for some reason (same problem as Paul). I’ve got some planes with mouse events and it seems as if the “hitareas” are above them
Chech if you’re set the ReflectionView as interactive or not when you call the super method
super(800,600,false, true);
the last parameter is to set the flag for interactivty..
Has ANYONE been able to get a Plane or any other do3d below/underneath the reflection/viewportReflection?
OK, i figured out a way to get an object (ground-plane) to appear below the reflection. And yes, I took Seb’s advice to use ViewportObjectFilter (see comment 59, above).
1. add a third viewport – viewportGround.
2. rearrange the viewports using setChildIndex(), placing viewportGround at zero
3. add another ‘render.renderScene()’ line to the singleRenderer() method
4. remove the ground-plane from both viewport and viewportReflection
5. remove all objects except the ground-plane from the viewportGround.
My earlier attempts at using ViewportObjectFilter were just improper usage/syntax.
Here’s a sample of what worked (to remove plane from viewportReflection):
viewportReflection.viewportObjectFilter = new ViewportObjectFilter(ViewportObjectFilterMode.EXCLUSIVE);
viewportReflection.viewportObjectFilter.addObject(plane);
On to the next feature/bug on my list…
Hi guys,
sorry I haven’t responded, I’m only just catching up with all this stuff.
The “lag” should be fixed now, so please test it and let me know how it works for you. Moving the singleRender function will cause problems with interactivity -from memory, interactivity only works on the last viewport rendered.
@darren_db glad you got that sorted, it sounds like a good solution.
Hey. This is working really good
, just what i was looking for too.
I have been trying to make the reflection taper of so that it is stronger in the beginning and then fades of. Should this be done with a ColorMatrixFilter? Anyone got an example of this?
This is really great, but doesnt work with renderlayers atm it seems :S
Hi Christian,
take a look at the ReflectionView class, it just makes a new viewport and renders a moved camera into that. I’m not sure what would happen with RenderLayers, but I can’t imagine that it’ll work
Maybe I’ll take a look when I get a chance, but I can’t imagine it’d be an easy update.
cheers!
Seb
Seems to work well with renderlayers except that the reflections graphics are never cleared. So every frame it adds more and more reflections.
Hi Seb,
First of all, thanks for all the hard work. This class is awesome!
Maybe you can also help me in my problem. I used this Reflection class, worked great so far but when i added filters on the vieport elements like blur, the reflectionViewport doesnt seem to get the same display.
Still looking for answers around other forums though. But hope you can shed some light into this.
Thanks!
[...] Papervision3D 2.0 GreatWhite revision 641 でReflectionViewってのが追加されてる。 サンプルとか詳しいことはこちら。 [...]
Hi Seb, thanks for this, a really useful class.
I know people have mentioned this already, but I haven’t seen any solutions…. I need to add some kind of falloff to the reflections, and before I start delving too deep, I thought I’d check here first.
You had mentioned that you were going to take a look at it, did you get anywhere? Maybe you could point me in the right direction, and I will of course contribute if I come up with a solution.
Drop-Offs
here’s a simple vertical alpha mask that simulates “drop-off” on the reflection.
add this function to ReflectionView:
protected function addDropOff():void
{
var shape:Sprite = new Sprite();
var mxBox:Matrix = new Matrix();
mxBox.createGradientBox( 640, 480 , Math.PI/2 , 0 , 0 );
shape.graphics.beginGradientFill(GradientType.LINEAR ,[0x000000, 0x000000], [0, 1], [0x00, 0x7E], mxBox);
shape.graphics.drawRect( 0, 0, 640, 480 );
shape.graphics.endFill();
shape.cacheAsBitmap=true;
viewportReflection.cacheAsBitmap = true;
viewportReflection.addChild(shape);
viewportReflection.mask = shape;
}
call it from the constructor (circa line 63):
ie change:
setReflectionColor(0.5,0.5,0.5);
to:
setReflectionColor(0.5,0.5,0.5);
addDropOff();
simple processor friendly solution – hope that helps anybody else looking
Hi Seb,
Amazing class ..yum yum.
I’ve juste question.
How can i insert a sprite in the reflectionViewport to have something like this.
http://embed.mibbit.com/up/gC9vpeL2.jpg.
Thank
Hello!
How can we get something like this – http://flashden.net/item/dynamic-thumbnail-scroller-image-browser/full_screen_preview/16048 with this class?
How can we add objects that we don’t want to have reflections ?
[...] -http://www.sebleedelisle.com/?p=196 [...]
Hi there,
How should we use this class if we’re already extending PaperBase in our project’s MainClass… I’ve tried extending PaperBase by ReflectionView, and it throws the following errors when compiling:
Error: A conflict exists with inherited definition org.papervision3d.view:AbstractView.viewport in namespace public.
Error: A conflict exists with inherited definition org.papervision3d.view:AbstractView.renderer in namespace public.
to be more specific with my problem, I am adding a load of Planes to a Page class which extends DisplayObject3D. I tried adding my Pages as children of an instance of ReflectionView but it is expecting a DisplayObject, not a DisplayObject3D!
Having an issue compiling this example in Flashdevelop with the latest build of p3d. Am getting an error in papervision3d\core\geom\Vertices3D.as:
Can not resolve a multiname reference unambiguously.
and also that Vertex3D is not a compile time constant.
possible conflict between versions of Vertex3D in geom and geom.renderables?
ok, rolled back to rev 869 and it’s working. definitely doesn’t seem to like 883.
(
Exactly what I’ve been looking for. Thanks for the article!
I’ve been working with ReflectionView for a few days now one problem I cant seem to sort out is the positioning of the reflection.
If I leave the viewport set to autoScale=true everything works fine. But I find the scene sits really high up on the screen.
If i set it to false the objects recenter and render based to my specified viewport height but the reflection stays auto-centered.
Any idea why… Ive tried adjusting the surfaceHeight but everything is still off kilt.
Well I did some searching found the culprit. It lies in the onAddedToStage function within ReflectionView
It’s set to call onStageResize whether autoScale is true or false. And since the onStageResize reads the stage.stageHeight it threw off the positioning so I just added a quick boolean check to onAddedToStage…
if (_autoScaleToStage)
{
stage.addEventListener(Event.RESIZE, onStageResize);
onStageResize();
}
Hi Seb –
Quick question about the reflection. In my probject I’m creating a cube with Bitmaps and a GouraudShader applied to it. I notice in the reflection, I see one face that is black and when the cube starts spinning it quickly looks normal like the main cube. Then as it spins instead of a smooth reflection it pops back to being black. Any ideas on why this would happen?
Thanks,
@mike, thanks for that, I’ll def check that out when I get a chance (not sure when that is though!)
@Ryan I can’t imagine that this will work very well with the shaders, sorry!
[...] as I was using his brilliant ReflectionView class that extends BasicView. View Seb’s post here to get started with reflections. One thing he doesn’t mention which I found very useful for [...]
Thanks for this class seb is looks to be exactly what I was looking for.
I have a question.
How can i put a movieclip above the papervision viewport ?
I know that i can do that if the class is extends Sprite but with extends ReflexionView, i dont know how to do that…
Thx
Thanks for the reflection class. Just got this up
http://www.fourstudio.co.uk/fourcomms/digital_intro.php
.T
[...] the animation is based on ReflectView an interesting class available for greatWhite after the merging of the two branches. All we have to do is to extend the ReflectionView and set the surfaceHeight of the reflection plane in this case: surfaceHeight = -212 the animation is based on this tutorial: http://www.sebleedelisle.com/?p=196 [...]
@Riccardo, There is ongoing improvements currently with lookAt, but these errors usually occur when the camera is in the same position as its target. Also, ReflectionView may be having problems while there is rotation refactoring going on!
@Andre, it is possible but you’re going to have to learn about the inner workings of the ReflectionView! It uses 2 viewports, one for the main view and one for the reflection. So you can filter out objects from the reflection by using the viewport.viewportObjectFilter property.
Hi Randy, I’m not sure what PaperBase is? ReflectionView works exactly like BasicView – you add DO3Ds to the scene, so you’d use scene.addChild(page). Hope this helps!
Seb