sim.portrayal3d.simple.BranchGroupPortrayal3D Maven / Gradle / Ivy
Show all versions of mason Show documentation
/*
Copyright 2006 by Sean Luke and George Mason University
Licensed under the Academic Free License version 3.0
See the file "LICENSE" for more information
*/
package sim.portrayal3d.simple;
import com.sun.j3d.utils.geometry.*;
import sim.portrayal3d.*;
import sim.portrayal.*;
import javax.media.j3d.*;
import java.net.*;
import java.io.*;
import com.sun.j3d.loaders.*;
import com.sun.j3d.loaders.lw3d.*;
import com.sun.j3d.loaders.objectfile.*;
import com.sun.j3d.utils.picking.*;
/**
* Loads a Lightwave 3D scene file (.lwo or .lws extension) or a Wavefront object file (.obj extension) into a BranchGroup,
* then attaches this as a portrayal. All scene elements and attributes are loaded (fog, sound, etc. as well). Generally
* all geometry in the scene is loaded as a Shape3D. If an Appearance is specified in the constructor, it is applied to all
* Shape3D objects in the scene. Else they are left with the appearance specified in the file.
*
* You can also use other loaders for other scene file formats. NCSA Portfolio contains a large number of them, but
* it's not quite open source (free for academic, research, or internal business use). See the MASON website for a link
* to download and use the NCSA Portfolio library.
*/
public class BranchGroupPortrayal3D extends PrimitivePortrayal3D
{
public static BranchGroup getBranchGroupForResource(Class c, String resourceName) throws IllegalArgumentException, FileNotFoundException
{
return getBranchGroupForURL(c.getResource(resourceName));
}
public static BranchGroup getBranchGroupForURL(URL url) throws IllegalArgumentException, FileNotFoundException
{
String s = url.getPath().trim();
s = s.substring(s.length() - 4);
if (s.equalsIgnoreCase(".obj")) return new ObjectFile().load(url).getSceneGroup();
if (s.equalsIgnoreCase(".lws") ||
s.equalsIgnoreCase(".lwo")) return new Lw3dLoader().load(url).getSceneGroup();
throw new IllegalArgumentException("Invalid extension to file name in url (" + url + "), MASON requires '.obj' or '.lws' at present time.");
}
public static BranchGroup getBranchGroupForFile(String filename) throws IllegalArgumentException, FileNotFoundException
{
String s = filename.trim();
s = s.substring(s.length() - 4);
if (s.equalsIgnoreCase(".obj")) return new ObjectFile().load(filename).getSceneGroup();
if (s.equalsIgnoreCase(".lws")) return new Lw3dLoader().load(filename).getSceneGroup();
throw new IllegalArgumentException("Invalid extension to file name (" + filename + "), MASON requires '.obj' or '.lws' at present time.");
}
/** Constructs a BranchGroupPortrayal3D with the given scene file loader without changing its appearance, scale, or transform. */
public BranchGroupPortrayal3D(BranchGroup scene)
{
this(scene, 1.0f, null);
}
/** Constructs a BranchGroupPortrayal3D with the given scene file loader without changing its appearance, but scaling it. */
public BranchGroupPortrayal3D(BranchGroup scene, double scale)
{
this(scene, scale, null);
}
/** Constructs a BranchGroupPortrayal3D with the given scene file loader without changing its appearance, but transforming it. */
public BranchGroupPortrayal3D(BranchGroup scene, Transform3D transform)
{
this(scene, transform, null);
}
/** Constructs a BranchGroupPortrayal3D with the given scene file loader without transforming it or scaling it, but changing its appearance (unless the appearance is null). */
public BranchGroupPortrayal3D(BranchGroup scene, Appearance a)
{
this(scene, 1.0f, a);
}
/** Constructs a BranchGroupPortrayal3D with the given scene file loader by scaling it and changing its appearance (unless the appearance is null). */
public BranchGroupPortrayal3D(BranchGroup scene, double scale, Appearance a)
{
setScale(null, scale);
traverseForAttributes(scene);
group = scene;
appearance = a;
}
/** Constructs a BranchGroupPortrayal3D with the given scene file loader by transforming it and changing its appearance (unless the appearance is null). */
public BranchGroupPortrayal3D(BranchGroup scene, Transform3D transform, Appearance a)
{
setTransform(null, transform);
traverseForAttributes(scene);
group = scene;
appearance = a;
}
// traverses the BranchGroup and sets all Shape3D geometries and other attributes
// sufficient to allow proper picking. This is done during construction.
void traverseForAttributes(Node n)
{
if (n instanceof Shape3D)
{
Shape3D s = (Shape3D) n;
setShape3DFlags(s);
setPickableFlags(s);
PickTool.setCapabilities(s, PickTool.INTERSECT_FULL);
Geometry g = s.getGeometry();
if (g instanceof CompressedGeometry)
((CompressedGeometry)g).setCapability(CompressedGeometry.ALLOW_GEOMETRY_READ);
else if (g instanceof GeometryArray)
{
((GeometryArray)g).setCapability(GeometryArray.ALLOW_COUNT_READ);
((GeometryArray)g).setCapability(GeometryArray.ALLOW_FORMAT_READ);
}
}
else if (n instanceof Group)
{
Group g = (Group) n;
for(int i = 0; i < g.numChildren(); i++)
traverseForAttributes(g.getChild(i));
}
}
// traverses the BranchGroup and sets all Shape3D userdata and appearance (if non-null).
// This is done during getModel()
void traverseForUserDataAndAppearance(Node n, LocationWrapper wrapper)
{
if (n instanceof Shape3D)
{
Shape3D s = (Shape3D) n;
s.setUserData(wrapper);
if (appearance != null)
s.setAppearance(appearance);
}
else if (n instanceof Group)
{
Group g = (Group) n;
for(int i = 0; i < g.numChildren(); i++)
traverseForUserDataAndAppearance(g.getChild(i), wrapper);
}
}
// basically a copy of the same code in PrimitivePortrayal3D but with
// appearance setting removed and a change from O(n^2) to O(n) updates of userdata
public TransformGroup getModel(Object obj, TransformGroup j3dModel)
{
if (j3dModel==null)
{
j3dModel = new TransformGroup();
j3dModel.setCapability(Group.ALLOW_CHILDREN_READ);
// build a LocationWrapper for the object
LocationWrapper pickI = new LocationWrapper(obj, null, getCurrentFieldPortrayal());
Node g = (Node) (group.cloneTree(true));
if (transform != null)
{
TransformGroup tg = new TransformGroup();
tg.setTransform(transform);
tg.setCapability(TransformGroup.ALLOW_TRANSFORM_READ);
tg.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE);
tg.setCapability(Group.ALLOW_CHILDREN_READ);
tg.addChild(g);
g = tg;
}
j3dModel.addChild(g);
traverseForUserDataAndAppearance(j3dModel, pickI);
}
return j3dModel;
}
/** Unused: returns 0 always. */
protected int numShapes() { return 0; }
}