Blender 2.61 + JME Nightly
Hello!
i want to split character animation into 2 animations: Top & Bottom
but it seem i do something wrong and i play with it like 4 hours… i need your help - i mean from people who done multichannel animations
http://i.imgur.com/Dj5Wb.jpg
track:

configuration of all animations look like this:

walkBottom (it dont share bones with walkTop):
http://i.imgur.com/joajw.jpg
walkTop (it dont share bones with walkBottom):
http://i.imgur.com/s80CZ.jpg
so when i look at Blender, it seem work, but when i look into SceneComposer or ingame, then:
- All animations override each other
for example walkTop have bottom bones position like in walkBottom first/last frame.
and walkBottom have bottom bones position like in walkTop first/last frame.
to be sure, ingame here is a code(becouse maybe SceneComposer always override):
[java]/*
- To change this template, choose Tools | Templates
- and open the template in the editor.
*/
package oxplay.assets.controls;
import com.jme3.animation.AnimChannel;
import com.jme3.animation.AnimControl;
import com.jme3.animation.AnimEventListener;
import com.jme3.animation.LoopMode;
import com.jme3.scene.Node;
import com.jme3.scene.Spatial;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.Map;
import java.util.HashMap;
import java.util.logging.Level;
import java.util.logging.Logger;
WorldElementControl is just a Extended Control(nothin to do with animations).
/**
*
-
@author oxplay
/
public abstract class AbstractAnimationControl extends WorldElementControl implements AnimEventListener {
private final static Logger logger = Logger.getLogger(AbstractAnimationControl.class.getName());
private Map<Integer, AnimChannel> channels = new HashMap<Integer, AnimChannel>();
public ArrayList<AnimControl> controls;
public AbstractAnimationControl() {
}
@Override
public void onSpatialSet() {
initAnimations(spatial);
}
private void initAnimations(Spatial spat) {
controls = findAnimControlSpatial(spat);
if (controls == null) {
logger.log(Level.SEVERE, “initAnimations can’t get control”);
}
for (Iterator<AnimControl> it = controls.iterator(); it.hasNext(){
AnimControl animControl = it.next();
animControl.addListener(this);
}
init();
}
public abstract void init();
public abstract void moveStart();
public abstract void moveEnd();
@Override
public void simpleUpdate(float tpf) {
}
public ArrayList<String> getAnimationList() {
ArrayList<String> animatiionList = new ArrayList<String>();
for (Iterator<AnimControl> it = controls.iterator(); it.hasNext(){
AnimControl animControl = it.next();
for (Iterator<String> it2 = animControl.getAnimationNames().iterator(); it2.hasNext(){
String animName = it2.next();
animatiionList.add(animName);
}
}
return animatiionList;
}
public boolean issetAnimation(String animation) {
boolean isset = false;
for (Iterator<AnimControl> it = controls.iterator(); it.hasNext(){
AnimControl animControl = it.next();
if (animControl.getAnimationNames().contains(animation)) {
isset = true;
}
}
return isset;
}
public ArrayList<AnimControl> findAnimControlSpatial(Spatial spatial) {
ArrayList<AnimControl> findControls = new ArrayList<AnimControl>();
if (spatial instanceof Node) {
Node findingnode = (Node) spatial;
for (int i = 0; i < findingnode.getQuantity(); i++) {
Spatial child = findingnode.getChild(i);
findControls.addAll(findAnimControlSpatial(child));
}
}
AnimControl foundControl = spatial.getControl(AnimControl.class);
if (foundControl != null) {
findControls.add(foundControl);
}
return findControls;
}
public void setAnim(String text, LoopMode mode, int channel, float speed) {
for (Iterator<AnimControl> it = controls.iterator(); it.hasNext(){
AnimControl animControl = it.next();
if (animControl != null && issetAnimation(text)) {
if (channels.get(channel) == null) {
channels.put(channel, animControl.createChannel());
channels.get(channel).setLoopMode(mode);
}
channels.get(channel).setAnim(text);
channels.get(channel).setSpeed(speed);
} else {
logger.log(Level.WARNING, “Animation: “+text+” do not exist!”);
}
}
}
}
[/java]
[java]/
- To change this template, choose Tools | Templates
- and open the template in the editor.
*/
package controls;
import com.jme3.animation.AnimChannel;
import com.jme3.animation.AnimControl;
import com.jme3.animation.LoopMode;
import com.jme3.scene.Spatial;
import com.jme3.scene.control.Control;
import java.util.Random;
import oxplay.assets.controls.AbstractAnimationControl;
/**
*
-
@author oxplay
*/
public class CharacterAnimationControl extends AbstractAnimationControl {
public static Random randomGenerator = new Random();
public boolean run = false;
@Override
public void init() {
setAnim("IdleTop1", LoopMode.Loop, 0, 1f);
}
@Override
public void onAnimCycleDone(AnimControl control, AnimChannel channel, String animName) {
if(animName.equals("IdleTop1") || animName.equals("IdleTop2")){
int value = randomGenerator.nextInt(10);
if(value <= 9){
channel.setAnim("IdleTop1");
} else {
channel.setAnim("IdleTop2");
}
}
}
@Override
public void onAnimChange(AnimControl control, AnimChannel channel, String animName) {
}
@Override
public void moveStart() {
if(run == false){
setAnim("WalkTop", LoopMode.Loop, 0, 1f);
setAnim("WalkBottom", LoopMode.Loop, 1, 1f);
} else {
setAnim("RunTop", LoopMode.Loop, 0, 1f);
setAnim("RunBottom", LoopMode.Loop, 1, 1f);
}
}
@Override
public void moveEnd() {
setAnim("IdleTop1", LoopMode.Loop, 0, 1f);
}
public void idle() {
setAnim("IdleTop1", LoopMode.Loop, 0, 1f);
}
public Control cloneForSpatial(Spatial spatial) {
throw new UnsupportedOperationException("Not supported yet.");
}
}
[/java]