I finally got an animation working. It is a simple ninja man that walks jumps runs ect. I used the TestMilkJmeWrite to get it to work since it was a .ms3d object. It works great and I am stoked but it just runs through all of the animations one after another. I need to get it to only got through the jump phase (frames 0-29). How do I achieve this? I know this is a hard question to just answer so if there is a good tut on it I would appreciate the link/guidance. Thanks.
The Vector is a Collection. You can use whatever Collection you want like LinkedList or Hashmap.
So in the getKeyframeControllers method, we are adding the KeyframeController to our collection because we need to use them at a later time (to set the animation times).
Here is an example.
Node node = <getNodeFromImporter>;
Vector controllersV = new Vector();
// get keyframe controllers
getKeyframeControllers(node,controllersV);
// set times
setKeyFrameTimes(controllersV, 0f, 10f, KeyframeController.RT_WRP);
Does this make sense?
Its actually not that hard as long as you know when your animation times start and stop.
Here are the steps that you need to take
- Get the keyframe controllers (they should be imported and attached to your node object)
- Set the keyframe times for the node (you should do this in accordance with whatever animation action you want)
- getting the controllers
/**
* Gets all the keyframe controllers and adds them to the vector.
* @param node gets the controllers from the node.
* @param v the vector to add the controllers.
**/
private void getKeyframeControllers(Node node, Vector v){
for(int i = 0; i < node.getChildren().size(); i++){
v.add((KeyframeController) node.getChild(i).getController(0));
}
}
2. sets the controllers
/**
* Sets the animation time.
* @param v contains the controllers to set.
* @param timeIn the start time of the animation.
* @param timeOut the stop time of the animation.
**/
private void setKeyFrameTimes(Vector v, float timeIn, float timeOut, int repeatType){
for(int i = 0; i < v.size(); i++){
((KeyframeController)v.elementAt(i)).setNewAnimationTimes(timeIn,timeOut);
((KeyframeController)v.elementAt(i)).setRepeatType(repeatType);
}
}
I hope that helps
Yes that helps a lot, that is exactly what I was looking for! One thing though what is the vector for that is getting passed into the getKeyFrameControllers method? Is it a directional vector or some sort? Thanks for your help.
Thanks for your help, and sorry it is taking me so long to get back but we were in the middle of finals week here at school. Ok now everything you said makes sense but eclipse is giving me this error.
java.lang.ClassCastException: com.jmex.model.animation.JointController cannot be cast to com.jmex.model.animation.KeyframeController
at gameFiles.Animation.setKeyFrameTimes(Animation.java:54)
at gameFiles.Animation.simpleInitGame(Animation.java:44)
at com.jme.app.BaseSimpleGame.initGame(BaseSimpleGame.java:544)
at com.jme.app.BaseGame.start(BaseGame.java:74)
at gameFiles.Animation.main(Animation.java:29)
It is happening at this line in the code – v.add((KeyframeController) node.getChild(i).getController(0));
So apparently you can't case KeyframeController like that. What is the problem here?
Thanks for your help again sorry I am a noob with JME
Try casting to a JointController?
private void setKeyFrameTimes(Vector v, float timeIn, float timeOut, int repeatType){
for(int i = 0; i < v.size(); i++){
((JointController)v.elementAt(i)).setTimes(timeIn,timeOut);
((JointController)v.elementAt(i)).setRepeatType(repeatType);
}
}
Finally got it working. In case anyone wants to see the code here it is. Got it from somewhere else on the forums.
public void playAnimation(Node n){
JointController controller = (JointController) n.getController(0);
//animation
int startFrame=0, endFrame=14;
controller.setSpeed(.5f);
controller.setRotation(2, 4.3f, 1, 1, 1);
controller.setTimes(startFrame, endFrame);
//controller.setRepeatType(Controller.RT_CYCLE);
controller.setActive(true);
And here is how I am loading the model
private Node createNinja(){
try {
ResourceLocatorTool.addResourceLocator(
ResourceLocatorTool.TYPE_TEXTURE,
new SimpleResourceLocator(Animation.class
.getClassLoader().getResource("ninja/")));
} catch (URISyntaxException e1) {
logger.log(Level.WARNING, "unable to setup texture directory.", e1);
}
MilkToJme converter = new MilkToJme();
URL MSFile = Animation.class.getClassLoader().getResource(
"ninja/ninja.ms3d");
ByteArrayOutputStream BO = new ByteArrayOutputStream();
try {
converter.convert(MSFile.openStream(), BO);
} catch (IOException e) {
logger.info("IO problem writting the file!!!");
logger.info(e.getMessage());
System.exit(0);
}
Node i = null;
try {
i = (Node) BinaryImporter.getInstance().load(
new ByteArrayInputStream(BO.toByteArray()));
} catch (IOException e) {
logger.info("darn exceptions:" + e.getMessage());
}
i.setLocalScale(1f);
return i;
}