PV3D - Interactive Shaded Cube

Posted on March 8, 2009
Filed Under Actionscript 3.0, Papervision, experiments |

protoshader

Ryan and myself wanted to figure out how to create have an interactive cube which uses a ShadedMaterial (MovieMaterial + Shader). Problem was that when you had a shadedmaterial you didn’t get any interactiveScene3DEvent’s back, when you used only the MovieMaterial and set it to interactive=true everything worked fine, but in combination with a shader it created a problem. So I had a look at it today and came up with the following solution.

  1. package
  2. {
  3.  import flash.events.Event;
  4.  
  5.  import org.papervision3d.materials.shaders.PhongShader;
  6.  import org.papervision3d.materials.shaders.ShadedMaterial;
  7.  import org.papervision3d.events.InteractiveScene3DEvent;
  8.  import org.papervision3d.materials.MovieAssetMaterial;
  9.  import org.papervision3d.materials.utils.MaterialsList;
  10.  import org.papervision3d.objects.primitives.Cube;
  11.  import org.papervision3d.lights.PointLight3D;
  12.  import org.papervision3d.view.BasicView;
  13.  import org.papervision3d.core.proto.CameraObject3D;
  14.  import org.papervision3d.core.proto.MaterialObject3D;
  15.  import org.papervision3d.objects.DisplayObject3D;
  16.  import org.papervision3d.core.geom.renderables.Triangle3D;
  17.  
  18.  public class DemoShader extends BasicView
  19.  {
  20.   private var _clipsAndSides:Array;
  21.   private var _light:PointLight3D;
  22.   private var _cube:Cube;
  23.  
  24.   public function DemoShader()
  25.   {
  26.    // linked library assets and the cubeSides we want it to belong to
  27.    _clipsAndSides = [  {linkageId: "clip_1", cubeSide:"front" },
  28.         {linkageId: "clip_2", cubeSide:"back" },
  29.         {linkageId: "clip_3", cubeSide:"top" },
  30.         {linkageId: "clip_4", cubeSide:"bottom"},
  31.         {linkageId: "clip_5", cubeSide:"left"},
  32.         {linkageId: "clip_6", cubeSide:"right"}
  33.        ];
  34.  
  35.    // light
  36.    _light = new PointLight3D();
  37.    _light.z = camera.z;
  38.    _light.x = camera.x;
  39.    _light.y = 250;
  40.  
  41.    // place camera a bit higher up
  42.    camera.y = 500;
  43.  
  44.    viewport.buttonMode = true;
  45.    viewport.interactive = true;
  46.  
  47.    var mList:MaterialsList = new MaterialsList();
  48.    for (var i:int = 0; i < _clipsAndSides.length; i++)
  49.    {
  50.     var ma:MovieAssetMaterial = new MovieAssetMaterial(_clipsAndSides[i].linkageId);
  51.     var phongShader:PhongShader = new PhongShader(_light, 0xFFFFFF, 0×333333);
  52.     var shadedMaterial:ShadedMaterial = new ShadedMaterial(ma, phongShader);
  53.     shadedMaterial.interactive = true;
  54.     shadedMaterial.name = _clipsAndSides[i].linkageId;
  55.     mList.addMaterial(shadedMaterial, _clipsAndSides[i].cubeSide);
  56.    }
  57.  
  58.    _cube = new Cube(mList, 500, 500, 500, 2, 2, 2);
  59.    _cube.addEventListener(InteractiveScene3DEvent.OBJECT_CLICK, objectClicked);
  60.    scene.addChild(_cube);
  61.  
  62.    // render
  63.    addEventListener(Event.ENTER_FRAME, update);
  64.   }
  65.  
  66.   private function objectClicked(event:InteractiveScene3DEvent):void
  67.   {
  68.    switch(event.face3d.material.name)
  69.    {
  70.     case "clip_1":
  71.      trace("clip 1 clicked");
  72.      break;
  73.  
  74.     case "clip_2":
  75.      trace("clip 2 clicked");
  76.      break;
  77.  
  78.     case "clip_3":
  79.      trace("clip 3 clicked");
  80.      break;
  81.  
  82.     case "clip_4":
  83.      trace("clip 4 clicked");
  84.      break;
  85.  
  86.     case "clip_5":
  87.      trace("clip 5 clicked");
  88.      break;
  89.  
  90.     case "clip_6":
  91.      trace("clip 6 clicked");
  92.      break;
  93.    }
  94.   }
  95.  
  96.   private function update(event:Event):void
  97.   {
  98.    camera.lookAt(_cube);
  99.  
  100.    _cube.yaw(1.5); // y-axis
  101.    _cube.pitch(1.5); // x-axis
  102.  
  103.    singleRender();
  104.   }
  105.  }
  106. }

Hope everything is clear and if you have a better solution please comment a post!

Comments

7 Responses to “PV3D - Interactive Shaded Cube”

  1. Gackson on May 4th, 2009 12:25 pm

    This helps a lot, thx!

  2. Ryan on May 28th, 2009 3:18 pm

    Hey Jan —

    I forgot to ask you, do you notice a drop in the frame rate when you do this?

  3. Ryan on May 28th, 2009 3:42 pm

    After looking at my original code to yours I had some minor errors that probably caused some rendering errors.

    Have you ever worked with reflections. I’m going to play around and see if I can get a reflection from this cube.

  4. Ryan on June 2nd, 2009 6:03 pm

    Hey Jan –

    I noticed a weird problem when shading the cube. My shading will be jumpy as the cube is spinning. When a face is not directly in front, that face will be at it’s darkest. Then when it gets close to the front it jumps to the lightest value. You know of any reason for that?

    Thanks!

  5. aaa on January 7th, 2010 4:52 pm

    i like your header.swf very nice. thanks for the tutorial.

  6. Ray on March 10th, 2010 7:24 pm

    didnt work for meh…
    changes:

    var mList:MaterialsList = new MaterialsList();

    for (var i:int = 0; i < _clipsAndSides.length; i++)
    {
    var bg:Sprite = new Sprite();
    bg.graphics.clear();
    bg.graphics.beginFill(0xFafafa,1);
    bg.graphics.drawRect(0, 0, 100,100);
    bg.graphics.endFill();
    bg.buttonMode = true;
    var ma:MovieMaterial = new MovieMaterial(bg);
    var phongShader:PhongShader = new PhongShader(light, 0xFFFFFF, 0×333333);
    var shadedMaterial:ShadedMaterial = new ShadedMaterial(ma, phongShader);
    shadedMaterial.interactive = true;
    shadedMaterial.name = _clipsAndSides[i].linkageId;
    mList.addMaterial(shadedMaterial, _clipsAndSides[i].cubeSide);
    }

  7. keerthi on July 19th, 2010 10:11 am

    Nice tutorial, could u help to implement the same thing in android using open gl es, i want identify which face of the cube is touched.

Leave a Reply




-->