use of net.drewke.tdme.engine.model.Model in project tdme by andreasdr.
the class LevelEditorEntityLibrary method addTrigger.
/**
* Add a trigger
* @param name
* @param description
* @param width
* @param height
* @param depth
* @return level editor entity
* @throws Exception
*/
public LevelEditorEntity addTrigger(int id, String name, String description, float width, float height, float depth) throws Exception {
String cacheId = "leveleditor.trigger." + width + "mx" + height + "mx" + depth + "m";
LevelEditorEntity levelEditorEntity = null;
BoundingBox boundingBox = new BoundingBox(new Vector3(-width / 2f, 0f, -depth / 2f), new Vector3(+width / 2f, height, +depth / 2f));
Model model = PrimitiveModel.createModel(boundingBox, cacheId + "_bv");
levelEditorEntity = new LevelEditorEntity(id == ID_ALLOCATE ? allocateEntityId() : id, EntityType.TRIGGER, name, description, null, cacheId, model.getId().replace("\\", "_").replace("/", "_").replace(":", "_") + ".png", model, new Vector3());
levelEditorEntity.addBoundingVolume(0, new LevelEditorEntityBoundingVolume(0, levelEditorEntity));
levelEditorEntity.getBoundingVolumeAt(0).setupAabb(boundingBox.getMin(), boundingBox.getMax());
id = levelEditorEntity.getId();
// add trigger
addEntity(levelEditorEntity);
//
return levelEditorEntity;
}
use of net.drewke.tdme.engine.model.Model in project tdme by andreasdr.
the class Tools method setupEntity.
/**
* Set up entity in given engine with look from rotations and scale
* @param entity
* @param engine
* @param look from rotations
* @param scale
*/
public static void setupEntity(LevelEditorEntity entity, Engine engine, Transformations lookFromRotations, float scale) {
if (entity == null)
return;
// entity bounding box
BoundingBox entityBoundingBox = null;
// add model to engine
if (entity.getType() == EntityType.PARTICLESYSTEM) {
entityBoundingBox = new BoundingBox(new Vector3(-0.5f, 0f, -0.5f), new Vector3(0.5f, 3f, 0.5f));
Entity particleSystemObject = Level.createParticleSystem(entity.getParticleSystem(), "model", true);
if (particleSystemObject != null) {
engine.addEntity(particleSystemObject);
}
} else {
entityBoundingBox = entity.getModel().getBoundingBox();
Object3D modelObject = new Object3D("model", entity.getModel());
modelObject.setDynamicShadowingEnabled(true);
engine.addEntity(modelObject);
}
// create ground object
Model ground = createGroundModel((entityBoundingBox.getMax().getX() - entityBoundingBox.getMin().getX()) * 1f, (entityBoundingBox.getMax().getZ() - entityBoundingBox.getMin().getZ()) * 1f, entityBoundingBox.getMin().getY() - MathTools.EPSILON);
// add ground to engine
Object3D groundObject = new Object3D("ground", ground);
groundObject.setEnabled(false);
engine.addEntity(groundObject);
// add bounding volume if we have any
for (int i = 0; i < entity.getBoundingVolumeCount(); i++) {
LevelEditorEntityBoundingVolume boundingVolume = entity.getBoundingVolumeAt(i);
if (boundingVolume.getModel() == null)
continue;
Object3D modelBoundingVolumeObject = new Object3D("model_bv." + i, boundingVolume.getModel());
modelBoundingVolumeObject.setEnabled(false);
engine.addEntity(modelBoundingVolumeObject);
}
// set up lights
for (Light light : engine.getLights()) light.setEnabled(false);
Light light0 = engine.getLightAt(0);
light0.getAmbient().set(1.0f, 1.0f, 1.0f, 1.0f);
light0.getDiffuse().set(0.5f, 0.5f, 0.5f, 1f);
light0.getSpecular().set(1f, 1f, 1f, 1f);
light0.getPosition().set(entityBoundingBox.getMin().getX() + ((entityBoundingBox.getMax().getX() - entityBoundingBox.getMin().getX()) / 2f), //modelBoundingBox.getMax().getY(),
entityBoundingBox.getMin().getY() + ((entityBoundingBox.getMax().getY() - entityBoundingBox.getMin().getY()) / 2f), -entityBoundingBox.getMin().getZ() * 4f, 1f);
light0.getSpotDirection().set(0f, 0f, 0f).sub(new Vector3(light0.getPosition().getArray()));
light0.setConstantAttenuation(0.5f);
light0.setLinearAttenuation(0f);
light0.setQuadraticAttenuation(0f);
light0.setSpotExponent(0f);
light0.setSpotCutOff(180f);
light0.setEnabled(true);
// model dimension
Vector3 dimension = entityBoundingBox.getMax().clone().sub(entityBoundingBox.getMin());
// determine max dimension on each axis
float maxAxisDimension = computeMaxAxisDimension(entityBoundingBox);
// set up cam
Camera cam = engine.getCamera();
cam.setZNear(maxAxisDimension / 5000f);
cam.setZFar(maxAxisDimension);
// look at
Vector3 lookAt = entityBoundingBox.getMin().clone().add(dimension.clone().scale(0.5f));
cam.getLookAt().set(lookAt);
// look at -> look to vector
Vector3 lookAtToFromVector = new Vector3(0f, 0f, +(maxAxisDimension * 1.2f));
// apply look from rotations
Vector3 lookAtToFromVectorTransformed = new Vector3();
Vector3 lookAtToFromVectorScaled = new Vector3();
Vector3 upVector = new Vector3();
lookFromRotations.getTransformationsMatrix().multiply(lookAtToFromVector, lookAtToFromVectorTransformed);
lookAtToFromVectorScaled.set(lookAtToFromVectorTransformed).scale(scale);
lookFromRotations.getRotations().get(2).getQuaternion().multiply(new Vector3(0f, 1f, 0f), upVector);
// look from with rotations
Vector3 lookFrom = lookAt.clone().add(lookAtToFromVectorScaled);
cam.getLookFrom().set(lookFrom);
// up vector
cam.getUpVector().set(upVector);
}
use of net.drewke.tdme.engine.model.Model in project tdme by andreasdr.
the class ModelViewerView method loadModel.
/**
* Load model
* @param name
* @param description
* @param path name
* @param file name
* @param pivot
* @return level editor entity
* @throws Exception
*/
protected LevelEditorEntity loadModel(String name, String description, String pathName, String fileName, Vector3 pivot) throws Exception {
if (fileName.toLowerCase().endsWith(".dae")) {
Model model = DAEReader.read(modelFile.getParentFile().getCanonicalPath(), modelFile.getName());
LevelEditorEntity levelEditorEntity = new LevelEditorEntity(LevelEditorEntity.ID_NONE, LevelEditorEntity.EntityType.MODEL, name, description, null, pathName + File.separator + fileName, model.getId().replace("\\", "_").replace("/", "_").replace(":", "_") + ".png", model, pivot);
levelEditorEntity.setDefaultBoundingVolumes();
return levelEditorEntity;
} else if (fileName.toLowerCase().endsWith(".tm")) {
Model model = TMReader.read(modelFile.getParentFile().getCanonicalPath(), modelFile.getName());
LevelEditorEntity levelEditorEntity = new LevelEditorEntity(LevelEditorEntity.ID_NONE, LevelEditorEntity.EntityType.MODEL, name, description, null, pathName + File.separator + fileName, model.getId().replace("\\", "_").replace("/", "_").replace(":", "_") + ".png", model, pivot);
levelEditorEntity.setDefaultBoundingVolumes();
return levelEditorEntity;
} else if (fileName.toLowerCase().endsWith(".tmm")) {
LevelEditorEntity levelEditorEntity = ModelMetaDataFileImport.doImport(LevelEditorEntity.ID_NONE, pathName, fileName);
levelEditorEntity.setDefaultBoundingVolumes();
return levelEditorEntity;
}
return null;
}
use of net.drewke.tdme.engine.model.Model in project tdme by andreasdr.
the class DAEReader method readLevel.
/**
* Reads Collada DAE file level
* @param path name
* @param file name
* @throws Exception
* @return Model instance
*/
public static LevelEditorLevel readLevel(String pathName, String fileName) throws Exception {
// (re)create tm files folder
File tmFilesFolder = new File(pathName + "/" + fileName + "-models");
if (tmFilesFolder.exists()) {
tmFilesFolder.delete();
}
tmFilesFolder.mkdir();
// create level
LevelEditorLevel levelEditorLevel = new LevelEditorLevel();
LevelPropertyPresets.getInstance().setDefaultLevelProperties(levelEditorLevel);
// load dae xml document
DocumentBuilder builder = DocumentBuilderFactory.newInstance().newDocumentBuilder();
Document document = builder.parse(FileSystem.getInstance().getInputStream(pathName, fileName));
Element xmlRoot = document.getDocumentElement();
// authoring tool
AuthoringTool authoringTool = getAuthoringTool(xmlRoot);
// up vector and rotation order
UpVector upVector = getUpVector(xmlRoot);
RotationOrder rotationOrder = null;
switch(upVector) {
case Y_UP:
rotationOrder = RotationOrder.ZYX;
case Z_UP:
rotationOrder = RotationOrder.YZX;
}
levelEditorLevel.setRotationOrder(rotationOrder);
// parse scene from xml
String xmlSceneId = null;
Element xmlScene = getChildrenByTagName(xmlRoot, "scene").get(0);
for (Element xmlInstanceVisualscene : getChildrenByTagName(xmlScene, "instance_visual_scene")) {
xmlSceneId = xmlInstanceVisualscene.getAttribute("url").substring(1);
}
// check for xml scene id
if (xmlSceneId == null) {
throw new ModelFileIOException("No scene id found");
}
// parse visual scenes
Element xmlLibraryVisualScenes = getChildrenByTagName(xmlRoot, "library_visual_scenes").get(0);
for (Element xmlLibraryVisualScene : getChildrenByTagName(xmlLibraryVisualScenes, "visual_scene")) {
String xmlVisualSceneId = xmlLibraryVisualScene.getAttribute("id");
if (xmlVisualSceneId.equals(xmlSceneId)) {
// default FPS
float fps = 30f;
// parse frames per second
List<Element> xmlExtraNodes = getChildrenByTagName(xmlLibraryVisualScene, "extra");
if (xmlExtraNodes.isEmpty() == false) {
Element xmlExtraNode = xmlExtraNodes.get(0);
for (Element xmlTechnique : getChildrenByTagName(xmlExtraNode, "technique")) {
List<Element> xmlFrameRateNodes = getChildrenByTagName(xmlTechnique, "frame_rate");
if (xmlFrameRateNodes.isEmpty() == false) {
fps = Float.parseFloat(xmlFrameRateNodes.get(0).getTextContent());
break;
}
}
}
// visual scene root nodes
LevelEditorEntityLibrary entityLibrary = levelEditorLevel.getEntityLibrary();
LevelEditorEntity emptyEntity = null;
int nodeIdx = 0;
for (Element xmlNode : getChildrenByTagName(xmlLibraryVisualScene, "node")) {
// derive model name from node id
String modelName = xmlNode.getAttribute("id");
// replace blender _|-NUMBER, not sure if this is a good idea for all cases, we will see
modelName = modelName.replaceAll("[\\-\\_]{1}+[0-9]+$", "");
// replace number at the end still, not sure if this is a good idea for all cases, we will see
modelName = modelName.replaceAll("[0-9]+$", "");
// check if name is available, if not extend with numbers :DDD
boolean haveName = entityLibrary.getEntityCount() == 0;
if (haveName == false) {
for (int i = 0; i < 10000; i++) {
haveName = true;
String modelNameTry = modelName + (i == 0 ? "" : String.valueOf(i));
for (int entityIdx = 0; entityIdx < entityLibrary.getEntityCount(); entityIdx++) {
LevelEditorEntity entity = entityLibrary.getEntityAt(entityIdx);
if (entity.getName().equals(modelNameTry) == true) {
haveName = false;
break;
}
}
if (haveName == true) {
modelName = modelNameTry;
break;
}
}
}
// do we have a name now?
if (haveName == false) {
// nope, cant imagine this will happen
System.out.println("DAEReader::readLevel(): Skipping model '" + modelName + "' as no name could be created for it.");
continue;
}
// create model
Model model = new Model(pathName + File.separator + fileName + '-' + modelName, fileName + '-' + modelName, upVector, rotationOrder, null);
// import matrix
setupModelImportRotationMatrix(xmlRoot, model);
Matrix4x4 modelImportRotationMatrix = new Matrix4x4(model.getImportTransformationsMatrix());
setupModelImportScaleMatrix(xmlRoot, model);
// translation, scaling, rotation
Vector3 translation = new Vector3();
Vector3 scale = new Vector3();
Vector3 rotation = new Vector3();
Vector3 xAxis = new Vector3();
Vector3 yAxis = new Vector3();
Vector3 zAxis = new Vector3();
// set up local transformations matrix
Matrix4x4 nodeTransformationsMatrix = null;
List<Element> xmlMatrixElements = getChildrenByTagName(xmlNode, "matrix");
if (xmlMatrixElements.size() == 1) {
String xmlMatrix = xmlMatrixElements.get(0).getTextContent();
StringTokenizer t = new StringTokenizer(xmlMatrix, " \n\r");
//
nodeTransformationsMatrix = new Matrix4x4(Float.parseFloat(t.nextToken()), Float.parseFloat(t.nextToken()), Float.parseFloat(t.nextToken()), Float.parseFloat(t.nextToken()), Float.parseFloat(t.nextToken()), Float.parseFloat(t.nextToken()), Float.parseFloat(t.nextToken()), Float.parseFloat(t.nextToken()), Float.parseFloat(t.nextToken()), Float.parseFloat(t.nextToken()), Float.parseFloat(t.nextToken()), Float.parseFloat(t.nextToken()), Float.parseFloat(t.nextToken()), Float.parseFloat(t.nextToken()), Float.parseFloat(t.nextToken()), Float.parseFloat(t.nextToken())).transpose();
}
// check if we have node transformations matrix
if (nodeTransformationsMatrix == null) {
throw new ModelFileIOException("missing node transformations matrix for node " + xmlNode.getAttribute("id"));
}
// extract coordinate system axes
nodeTransformationsMatrix.getAxes(xAxis, yAxis, zAxis);
nodeTransformationsMatrix.getTranslation(translation);
nodeTransformationsMatrix.getScale(scale);
// normalize coordinate axes
xAxis.normalize();
yAxis.normalize();
zAxis.normalize();
// write back normalized x axis
nodeTransformationsMatrix.setAxes(xAxis, yAxis, zAxis);
// TODO: move me into Matrix4x4 decomposing code?
if ((upVector == UpVector.Y_UP && Vector3.computeDotProduct(Vector3.computeCrossProduct(xAxis, yAxis), zAxis) < 0.0f) || (upVector == UpVector.Z_UP && Vector3.computeDotProduct(Vector3.computeCrossProduct(xAxis, zAxis), yAxis) < 0.0f)) {
// negate axes
xAxis.scale(-1f);
yAxis.scale(-1f);
zAxis.scale(-1f);
// and write back to node transformation matrices
nodeTransformationsMatrix.setAxes(xAxis, yAxis, zAxis);
// scale
scale.scale(-1f);
}
// determine rotation
nodeTransformationsMatrix.computeEulerAngles(rotation);
// apply model import matrix
modelImportRotationMatrix.multiply(scale, scale);
modelImportRotationMatrix.multiply(rotation, rotation);
model.getImportTransformationsMatrix().multiply(translation, translation);
// set up frames per seconds
model.setFPS(fps);
// read sub groups
Group group = readVisualSceneNode(authoringTool, pathName, model, null, xmlRoot, xmlNode, fps);
if (group != null) {
group.getTransformationsMatrix().identity();
model.getSubGroups().put(group.getId(), group);
model.getGroups().put(group.getId(), group);
}
// set up joints
ModelHelper.setupJoints(model);
// fix animation length
ModelHelper.fixAnimationLength(model);
// prepare for indexed rendering
ModelHelper.prepareForIndexedRendering(model);
// check if empty model
EntityType entityType = EntityType.MODEL;
ModelStatistics modelStatistics = ModelUtilities.computeModelStatistics(model);
if (modelStatistics.getOpaqueFaceCount() == 0 && modelStatistics.getTransparentFaceCount() == 0) {
entityType = EntityType.EMPTY;
}
// level editor entity
LevelEditorEntity levelEditorEntity = null;
// model
if (entityType == EntityType.MODEL) {
// check if we have that model already
for (int i = 0; i < levelEditorLevel.getEntityLibrary().getEntityCount(); i++) {
LevelEditorEntity levelEditorEntityCompare = levelEditorLevel.getEntityLibrary().getEntityAt(i);
if (levelEditorEntityCompare.getType() != EntityType.MODEL)
continue;
if (ModelUtilities.equals(model, levelEditorEntityCompare.getModel()) == true) {
levelEditorEntity = levelEditorEntityCompare;
break;
}
}
// create level editor model, if not yet exists
if (levelEditorEntity == null) {
// save model
TMWriter.write(model, pathName + "/" + fileName + "-models", modelName + ".tm");
// create level editor entity
levelEditorEntity = entityLibrary.addModel(nodeIdx++, modelName, modelName, pathName + "/" + fileName + "-models", modelName + ".tm", new Vector3());
}
} else // empty
if (entityType == EntityType.EMPTY) {
if (emptyEntity == null) {
emptyEntity = entityLibrary.addEmpty(nodeIdx++, "Default Empty", "");
}
levelEditorEntity = emptyEntity;
} else {
System.out.println("DAEReader::readLevel(): unknown entity type. Skipping");
continue;
}
// level editor object transformations
Transformations levelEditorObjectTransformations = new Transformations();
levelEditorObjectTransformations.getTranslation().set(translation);
levelEditorObjectTransformations.getRotations().add(new Rotation(rotation.getArray()[rotationOrder.getAxis0VectorIndex()], rotationOrder.getAxis0()));
levelEditorObjectTransformations.getRotations().add(new Rotation(rotation.getArray()[rotationOrder.getAxis1VectorIndex()], rotationOrder.getAxis1()));
levelEditorObjectTransformations.getRotations().add(new Rotation(rotation.getArray()[rotationOrder.getAxis2VectorIndex()], rotationOrder.getAxis2()));
levelEditorObjectTransformations.getScale().set(scale);
levelEditorObjectTransformations.update();
// level editor object
LevelEditorObject object = new LevelEditorObject(xmlNode.getAttribute("id"), xmlNode.getAttribute("id"), levelEditorObjectTransformations, levelEditorEntity);
// add object to level
levelEditorLevel.addObject(object);
}
}
}
// save level
LevelFileExport.export(pathName + "/" + fileName + ".tl", levelEditorLevel);
//
return levelEditorLevel;
}
use of net.drewke.tdme.engine.model.Model in project tdme by andreasdr.
the class TMReader method read.
/**
* TDME model format reader
* @param path name
* @param file name
* @throws IOException
* @throws ModelIOException
* @return model
*/
public static Model read(String pathName, String fileName) throws IOException, ModelFileIOException {
InputStream is = null;
try {
is = FileSystem.getInstance().getInputStream(pathName, fileName);
// version major.minor = 1.0
String fileId = readString(is);
if (fileId == null || fileId.equals("TDME Model") == false) {
throw new ModelFileIOException("File is not a TDME model file, file id = '" + fileId + "'");
}
byte[] version = new byte[3];
version[0] = readByte(is);
version[1] = readByte(is);
version[2] = readByte(is);
if (version[0] != 1 || version[1] != 0 || version[2] != 0) {
throw new ModelFileIOException("Version mismatch, should be 1.0.0, but is " + version[0] + "." + version[1] + "." + version[2]);
}
// meta data
String name = readString(is);
// up vector, rotation order, bounding box
UpVector upVector = UpVector.valueOf(readString(is));
RotationOrder rotationOrder = RotationOrder.valueOf(readString(is));
BoundingBox boundingBox = new BoundingBox(new Vector3(readFloatArray(is)), new Vector3(readFloatArray(is)));
// create object
Model model = new Model(pathName + File.separator + fileName, fileName, upVector, rotationOrder, boundingBox);
// set additional data
model.setFPS(readFloat(is));
model.getImportTransformationsMatrix().set(readFloatArray(is));
// materials
int materialCount = readInt(is);
for (int i = 0; i < materialCount; i++) {
Material material = readMaterial(is);
model.getMaterials().put(material.getId(), material);
}
// sub groups
readSubGroups(is, model, null, model.getSubGroups());
//
return model;
} catch (IOException ioe) {
throw ioe;
} catch (ModelFileIOException mfioe) {
throw mfioe;
} finally {
if (is != null) {
is.close();
}
}
}
Aggregations