P.S. It needs the jdom api (www.jdom.org)
Code: Select all
import java.io.IOException;
import java.lang.reflect.Method;
import java.util.StringTokenizer;
import net.sf.jirr.E_LIGHT_TYPE;
import net.sf.jirr.E_MATERIAL_FLAG;
import net.sf.jirr.E_MATERIAL_TYPE;
import net.sf.jirr.ILightSceneNode;
import net.sf.jirr.ISceneManager;
import net.sf.jirr.ISceneNode;
import net.sf.jirr.ISceneNodeAnimator;
import net.sf.jirr.ITexture;
import net.sf.jirr.IVideoDriver;
import net.sf.jirr.IrrlichtDevice;
import net.sf.jirr.SColor;
import net.sf.jirr.SColorf;
import net.sf.jirr.vector3df;
import org.jdom.Document;
import org.jdom.Element;
import org.jdom.JDOMException;
import org.jdom.input.SAXBuilder;
public class SceneLoader {
private static final String LIGHTING = "Lighting";
private static final String TRANS_ADD = "trans_add";
private static final String TRANS_ALPHACH = "trans_alphach";
private static final String SOLID = "solid";
private static final String POINT = "Point";
private static final String ENUM = "enum";
private static final String LIGHT_TYPE = "LightType";
private static final String FLOAT = "float";
private static final String SPEED = "Speed";
private static final String RADIUS = "Radius";
private static final String CENTER = "Center";
private static final String ROTATION_ATTRIBUTE = "Rotation";
private static final String FLY_CIRCLE = "flyCircle";
private static final String ROTATION = "rotation";
private static final String TYPE_PROPERTY = "Type";
private static final String MATERIALS = "materials";
private static final String MESH_PROPERTY = "Mesh";
private static final String ANIMATORS = "animators";
private static final String PARTICLE_SYSTEM = "particleSystem";
private static final String LIGHT = "light";
private static final String BILL_BOARD = "billBoard";
private static final String CUBE = "cube";
private static final String MESH = "mesh";
private static final String SKY_BOX = "skyBox";
private static final String TYPE = "type";
private static final String VALUE_SEPARATOR = ",";
private static final String ATTRIBUTES = "attributes";
private static final String VALUE = "value";
private static final String NAME = "name";
private static final String STRING = "string";
private static final String INT = "int";
private static final String VECTOR3D = "vector3d";
private static final String BOOL = "bool";
private static final String TRUE = "true";
private static final String NON_VALIDATING_DTD = "http://apache.org/xml/features/nonvalidating/load-external-dtd";
private static final String SET_PREFIX = "set";
public static void loadScene(String sceneFilename, IrrlichtDevice device) throws JDOMException, IOException {
IVideoDriver driver = device.getVideoDriver();
ISceneManager smgr = device.getSceneManager();
Document document = getDocument(sceneFilename);
Element irrScene = document.getRootElement();
if (irrScene.getChild(ATTRIBUTES) != null) {
//Reading the root scene node attributes
Element attributes = irrScene.getChild(ATTRIBUTES);
ISceneNode root = smgr.getRootSceneNode();
readAttributes(attributes, root);
}
for (Object obj : irrScene.getChildren()) {
Element node = (Element)obj;
if (ATTRIBUTES.equals(node.getName())) {
continue;
}
Element attributes = node.getChild(ATTRIBUTES);
String type = node.getAttributeValue(TYPE);
ISceneNode sceneNode = null;
if (type.equals(SKY_BOX)) {
Element materials = node.getChild(MATERIALS);
ITexture left = getTexture(driver, (Element)materials.getChildren().get(0));
ITexture front = getTexture(driver, (Element)materials.getChildren().get(1));
ITexture right = getTexture(driver, (Element)materials.getChildren().get(2));
ITexture back = getTexture(driver, (Element)materials.getChildren().get(3));
ITexture top = getTexture(driver, (Element)materials.getChildren().get(4));
ITexture down = getTexture(driver, (Element)materials.getChildren().get(5));
sceneNode = smgr.addSkyBoxSceneNode(top, down, front, back, left, right);
} else if (type.equals(MESH)) {
String meshName = getStringValue(attributes, MESH_PROPERTY);
sceneNode = smgr.addAnimatedMeshSceneNode(smgr.getMesh(meshName));
readAttributes(attributes, sceneNode);
readMaterials(driver, node, sceneNode);
} else if (type.equals(CUBE)) {
sceneNode = smgr.addTestSceneNode();
readAttributes(attributes, sceneNode);
readMaterials(driver, node, sceneNode);
} else if (type.equals(BILL_BOARD)) {
sceneNode = smgr.addBillboardSceneNode();
readAttributes(attributes, sceneNode);
readMaterials(driver, node, sceneNode);
} else if (type.equals(LIGHT)) {
sceneNode = smgr.addLightSceneNode();
readAttributes(attributes, sceneNode);
readAttributes(attributes, ((ILightSceneNode)sceneNode).getLightData());
ILightSceneNode light = (ILightSceneNode)sceneNode;
String lightType = getValue(attributes, LIGHT_TYPE, ENUM);
if (lightType.equals(POINT)) {
light.getLightData().setType(E_LIGHT_TYPE.ELT_POINT);
} else {
light.getLightData().setType(E_LIGHT_TYPE.ELT_DIRECTIONAL);
}
} else if (type.equals(PARTICLE_SYSTEM)) {
sceneNode = smgr.addParticleSystemSceneNode();
readAttributes(attributes, sceneNode);
readMaterials(driver, node, sceneNode);
}
if (sceneNode != null) {
if (node.getChild(ANIMATORS) != null) {
Element animators = node.getChild(ANIMATORS);
for (Object o : animators.getChildren()) {
Element el = (Element)o;
String animType = getStringValue(el, TYPE_PROPERTY);
if (animType.equals(ROTATION)) {
vector3df rotation = getVector3DValue(el, ROTATION_ATTRIBUTE);
ISceneNodeAnimator anim = smgr.createRotationAnimator(rotation);
sceneNode.addAnimator(anim);
anim.drop();
} else if (animType.equals(FLY_CIRCLE)) {
vector3df center = getVector3DValue(el, CENTER);
float radius = getFloatValue(el, RADIUS);
float speed = getFloatValue(el, SPEED);
ISceneNodeAnimator anim = smgr.createFlyCircleAnimator(center, radius, speed);
sceneNode.addAnimator(anim);
anim.drop();
}
}
}
}
}
}
private static void readMaterials(IVideoDriver driver, Element node, ISceneNode sceneNode) {
if (node.getChild(MATERIALS) != null) {
Element materials = node.getChild(MATERIALS);
int index = 0;
for (Object o : materials.getChildren()) {
Element el = (Element)o;
sceneNode.setMaterialTexture(index, getTexture(driver, el));
readAttributes(el, sceneNode.getMaterial(index));
String materialType = getValue(el, TYPE_PROPERTY, ENUM);
if (materialType.equals(SOLID)) {
sceneNode.getMaterial(index).setMaterialType(E_MATERIAL_TYPE.EMT_SOLID);
} else if (materialType.equals(TRANS_ALPHACH)) {
sceneNode.getMaterial(index).setMaterialType(E_MATERIAL_TYPE.EMT_TRANSPARENT_ALPHA_CHANNEL);
} else if (materialType.equals(TRANS_ADD)) {
sceneNode.getMaterial(index).setMaterialType(E_MATERIAL_TYPE.EMT_TRANSPARENT_ADD_COLOR);
}
sceneNode.setMaterialFlag(E_MATERIAL_FLAG.EMF_LIGHTING, getBooleanValue(el, LIGHTING));
index++;
}
}
}
private static boolean getBooleanValue(Element attributes, String elementName) {
return TRUE.equals(getValue(attributes, elementName, BOOL));
}
private static String getStringValue(Element attributes, String elementName) {
return getValue(attributes, elementName, STRING);
}
private static String getValue(Element attributes, String elementName, String type) {
for (Object o : attributes.getChildren(type)) {
Element el = (Element)o;
if (el.getAttributeValue(NAME).equals(elementName)) {
return el.getAttributeValue(VALUE);
}
}
return "";
}
private static vector3df getVector3DValue(Element attributes, String elementName) {
String value = getValue(attributes, elementName, VECTOR3D);
StringTokenizer tokens = new StringTokenizer(value, VALUE_SEPARATOR);
float x = Float.parseFloat(tokens.nextToken());
float y = Float.parseFloat(tokens.nextToken());
float z = Float.parseFloat(tokens.nextToken());
return new vector3df(x, y, z);
}
private static float getFloatValue(Element attributes, String elementName) {
String value = getValue(attributes, elementName, FLOAT);
return Float.parseFloat(value);
}
private static ITexture getTexture(IVideoDriver driver, Element eTexture) {
String textureName = "";
for (Object o : eTexture.getChildren("texture")) {
Element te = (Element)o;
if ("Texture1".equals(te.getAttributeValue("name"))) {
textureName = te.getAttributeValue("value");
break;
}
}
return driver.getTexture(textureName);
}
private static void readAttributes(Element attributes, Object root) {
for (Object obj : attributes.getChildren()) {
Element child = (Element)obj;
String name = child.getAttributeValue(NAME);
String value = child.getAttributeValue(VALUE);
String methodName = SET_PREFIX + name;
Method method = getMethod(root, methodName);
if (method == null) {
continue;
}
if (child.getName().equals(STRING)) {
Object[] args = {value};
try {
method.invoke(root, args);
} catch (Exception e) {
e.printStackTrace();
}
} else if (child.getName().equals(INT)) {
Object[] args = {Integer.parseInt(value)};
try {
method.invoke(root, args);
} catch (Exception e) {
e.printStackTrace();
}
} else if (child.getName().equals(VECTOR3D)) {
StringTokenizer tokens = new StringTokenizer(value, VALUE_SEPARATOR);
float x = Float.parseFloat(tokens.nextToken());
float y = Float.parseFloat(tokens.nextToken());
float z = Float.parseFloat(tokens.nextToken());
Object[] args = {new vector3df(x, y, z)};
try {
method.invoke(root, args);
} catch (Exception e) {
e.printStackTrace();
}
} else if (child.getName().equals(BOOL)) {
Object[] args = {TRUE.equals(value)};
try {
method.invoke(root, args);
} catch (Exception e) {
e.printStackTrace();
}
} else if (child.getName().equals("colorf")) {
StringTokenizer tokens = new StringTokenizer(value, VALUE_SEPARATOR);
float x = Float.parseFloat(tokens.nextToken());
float y = Float.parseFloat(tokens.nextToken());
float z = Float.parseFloat(tokens.nextToken());
Object[] args = {new SColorf(x, y, z)};
try {
method.invoke(root, args);
} catch (Exception e) {
e.printStackTrace();
}
} else if (child.getName().equals("color")) {
int a = Integer.parseInt(value.substring(0, 2), 16);
int r = Integer.parseInt(value.substring(2, 4), 16);
int g = Integer.parseInt(value.substring(4, 6), 16);
int b = Integer.parseInt(value.substring(6, 8), 16);
Object[] args = {new SColor(a, r, g, b)};
try {
method.invoke(root, args);
} catch (Exception e) {
e.printStackTrace();
}
}
}
}
private static Method getMethod(Object obj, String methodName) {
for (Method method : obj.getClass().getMethods()) {
if (method.getName().equalsIgnoreCase(methodName)) {
return method;
}
}
return null;
}
private static Document getDocument(String filename) throws JDOMException, IOException {
SAXBuilder builder = new SAXBuilder();
builder.setFeature(NON_VALIDATING_DTD, false);
return builder.build(filename);
}
}
In order to use this class you'll just have to do something like that:
SceneLoader.loadScene("scenes/myscene.irr", device);