Search in sources :

Example 36 with Animation

use of com.jme3.animation.Animation in project jmonkeyengine by jMonkeyEngine.

the class TestAnimationFactory method simpleInitApp.

@Override
public void simpleInitApp() {
    AmbientLight al = new AmbientLight();
    rootNode.addLight(al);
    DirectionalLight dl = new DirectionalLight();
    dl.setDirection(Vector3f.UNIT_XYZ.negate());
    rootNode.addLight(dl);
    // Create model
    Box box = new Box(1, 1, 1);
    Geometry geom = new Geometry("box", box);
    geom.setMaterial(assetManager.loadMaterial("Textures/Terrain/BrickWall/BrickWall.j3m"));
    Node model = new Node("model");
    model.attachChild(geom);
    Box child = new Box(0.5f, 0.5f, 0.5f);
    Geometry childGeom = new Geometry("box", child);
    childGeom.setMaterial(assetManager.loadMaterial("Textures/Terrain/BrickWall/BrickWall.j3m"));
    Node childModel = new Node("childmodel");
    childModel.setLocalTranslation(2, 2, 2);
    childModel.attachChild(childGeom);
    model.attachChild(childModel);
    TangentBinormalGenerator.generate(model);
    //creating quite complex animation witht the AnimationHelper
    // animation of 6 seconds named "anim" and with 25 frames per second
    AnimationFactory animationFactory = new AnimationFactory(6, "anim", 25);
    //creating a translation keyFrame at time = 3 with a translation on the x axis of 5 WU        
    animationFactory.addTimeTranslation(3, new Vector3f(5, 0, 0));
    //reseting the translation to the start position at time = 6
    animationFactory.addTimeTranslation(6, new Vector3f(0, 0, 0));
    //Creating a scale keyFrame at time = 2 with the unit scale.
    animationFactory.addTimeScale(2, new Vector3f(1, 1, 1));
    //Creating a scale keyFrame at time = 4 scaling to 1.5
    animationFactory.addTimeScale(4, new Vector3f(1.5f, 1.5f, 1.5f));
    //reseting the scale to the start value at time = 5
    animationFactory.addTimeScale(5, new Vector3f(1, 1, 1));
    //Creating a rotation keyFrame at time = 0.5 of quarter PI around the Z axis
    animationFactory.addTimeRotation(0.5f, new Quaternion().fromAngleAxis(FastMath.QUARTER_PI, Vector3f.UNIT_Z));
    //rotating back to initial rotation value at time = 1
    animationFactory.addTimeRotation(1, Quaternion.IDENTITY);
    //Creating a rotation keyFrame at time = 2. Note that i used the Euler angle version because the angle is higher than PI
    //this should result in a complete revolution of the spatial around the x axis in 1 second (from 1 to 2)
    animationFactory.addTimeRotationAngles(2, FastMath.TWO_PI, 0, 0);
    AnimControl control = new AnimControl();
    control.addAnim(animationFactory.buildAnimation());
    model.addControl(control);
    rootNode.attachChild(model);
    //run animation
    control.createChannel().setAnim("anim");
}
Also used : Geometry(com.jme3.scene.Geometry) AnimationFactory(com.jme3.animation.AnimationFactory) Quaternion(com.jme3.math.Quaternion) DirectionalLight(com.jme3.light.DirectionalLight) Node(com.jme3.scene.Node) Vector3f(com.jme3.math.Vector3f) Box(com.jme3.scene.shape.Box) AnimControl(com.jme3.animation.AnimControl) AmbientLight(com.jme3.light.AmbientLight)

Example 37 with Animation

use of com.jme3.animation.Animation in project jmonkeyengine by jMonkeyEngine.

the class TestPostWater method createFire.

private void createFire() {
    /**
         * Uses Texture from jme3-test-data library!
         */
    ParticleEmitter fire = new ParticleEmitter("Emitter", ParticleMesh.Type.Triangle, 30);
    Material mat_red = new Material(assetManager, "Common/MatDefs/Misc/Particle.j3md");
    mat_red.setTexture("Texture", assetManager.loadTexture("Effects/Explosion/flame.png"));
    fire.setMaterial(mat_red);
    fire.setImagesX(2);
    // 2x2 texture animation
    fire.setImagesY(2);
    // red
    fire.setEndColor(new ColorRGBA(1f, 0f, 0f, 1f));
    // yellow
    fire.setStartColor(new ColorRGBA(1f, 1f, 0f, 0.5f));
    fire.getParticleInfluencer().setInitialVelocity(new Vector3f(0, 2, 0));
    fire.setStartSize(10f);
    fire.setEndSize(1f);
    fire.setGravity(0, 0, 0);
    fire.setLowLife(0.5f);
    fire.setHighLife(1.5f);
    fire.getParticleInfluencer().setVelocityVariation(0.3f);
    fire.setLocalTranslation(-600, 50, 300);
    fire.setQueueBucket(Bucket.Translucent);
    rootNode.attachChild(fire);
}
Also used : ParticleEmitter(com.jme3.effect.ParticleEmitter) ColorRGBA(com.jme3.math.ColorRGBA) Vector3f(com.jme3.math.Vector3f) Material(com.jme3.material.Material)

Example 38 with Animation

use of com.jme3.animation.Animation in project jmonkeyengine by jMonkeyEngine.

the class SceneLoader method buildAnimations.

private void buildAnimations() {
    if (skeleton == null)
        return;
    if (animList == null || animList.list.size() == 0) {
        animList = new AnimationList();
        for (long layerId : alayerMap.keySet()) {
            FbxObject layer = alayerMap.get(layerId);
            animList.add(layer.name, layer.name, 0, -1);
        }
    }
    // Extract aminations
    HashMap<String, Animation> anims = new HashMap<String, Animation>();
    for (AnimInverval animInfo : animList.list) {
        float realLength = 0;
        float length = (animInfo.lastFrame - animInfo.firstFrame) / this.animFrameRate;
        float animStart = animInfo.firstFrame / this.animFrameRate;
        float animStop = animInfo.lastFrame / this.animFrameRate;
        Animation anim = new Animation(animInfo.name, length);
        // Search source layer for animation nodes
        long sourceLayerId = 0L;
        for (long layerId : alayerMap.keySet()) {
            FbxObject layer = alayerMap.get(layerId);
            if (layer.name.equals(animInfo.layerName)) {
                sourceLayerId = layerId;
                break;
            }
        }
        // Build bone tracks
        for (FbxNode limb : limbMap.values()) {
            // Animation channels may have different keyframes (non-baked animation).
            //   So we have to restore intermediate values for all channels cause of JME requires
            //   a bone track as a single channel with collective transformation for each keyframe
            // Sorted unique timestamps
            Set<Long> stamps = new TreeSet<Long>();
            FbxAnimNode animTranslation = limb.animTranslation(sourceLayerId);
            FbxAnimNode animRotation = limb.animRotation(sourceLayerId);
            FbxAnimNode animScale = limb.animScale(sourceLayerId);
            boolean haveTranslation = haveAnyChannel(animTranslation);
            boolean haveRotation = haveAnyChannel(animRotation);
            boolean haveScale = haveAnyChannel(animScale);
            // Collect keyframes stamps
            if (haveTranslation)
                animTranslation.exportTimes(stamps);
            if (haveRotation)
                animRotation.exportTimes(stamps);
            if (haveScale)
                animScale.exportTimes(stamps);
            if (stamps.isEmpty())
                continue;
            long[] keyTimes = new long[stamps.size()];
            int cnt = 0;
            for (long t : stamps) keyTimes[cnt++] = t;
            // Calculate keys interval by animation time interval
            int firstKeyIndex = 0;
            int lastKeyIndex = keyTimes.length - 1;
            for (int i = 0; i < keyTimes.length; ++i) {
                // Translate into seconds
                float time = (float) (((double) keyTimes[i]) * secondsPerUnit);
                if (time <= animStart)
                    firstKeyIndex = i;
                if (time >= animStop && animStop >= 0) {
                    lastKeyIndex = i;
                    break;
                }
            }
            int keysCount = lastKeyIndex - firstKeyIndex + 1;
            if (keysCount <= 0)
                continue;
            float[] times = new float[keysCount];
            Vector3f[] translations = new Vector3f[keysCount];
            Quaternion[] rotations = new Quaternion[keysCount];
            Vector3f[] scales = null;
            // Calculate keyframes times
            for (int i = 0; i < keysCount; ++i) {
                int keyIndex = firstKeyIndex + i;
                // Translate into seconds
                float time = (float) (((double) keyTimes[keyIndex]) * secondsPerUnit);
                times[i] = time - animStart;
                realLength = Math.max(realLength, times[i]);
            }
            // Load keyframes from animation curves
            if (haveTranslation) {
                for (int i = 0; i < keysCount; ++i) {
                    int keyIndex = firstKeyIndex + i;
                    FbxAnimNode n = animTranslation;
                    // Why do it here but not in other places? FBX magic?
                    Vector3f tvec = n.getValue(keyTimes[keyIndex], n.value).subtractLocal(n.value);
                    translations[i] = tvec.divideLocal(unitSize);
                }
            } else {
                for (int i = 0; i < keysCount; ++i) translations[i] = Vector3f.ZERO;
            }
            RotationOrder ro = RotationOrder.EULER_XYZ;
            if (haveRotation) {
                for (int i = 0; i < keysCount; ++i) {
                    int keyIndex = firstKeyIndex + i;
                    FbxAnimNode n = animRotation;
                    Vector3f tvec = n.getValue(keyTimes[keyIndex], n.value);
                    rotations[i] = ro.rotate(tvec);
                }
            } else {
                for (int i = 0; i < keysCount; ++i) rotations[i] = Quaternion.IDENTITY;
            }
            if (haveScale) {
                scales = new Vector3f[keysCount];
                for (int i = 0; i < keysCount; ++i) {
                    int keyIndex = firstKeyIndex + i;
                    FbxAnimNode n = animScale;
                    Vector3f tvec = n.getValue(keyTimes[keyIndex], n.value);
                    scales[i] = tvec;
                }
            }
            BoneTrack track = null;
            if (haveScale)
                track = new BoneTrack(limb.boneIndex, times, translations, rotations, scales);
            else
                track = new BoneTrack(limb.boneIndex, times, translations, rotations);
            anim.addTrack(track);
        }
        if (realLength != length && animInfo.lastFrame == -1) {
            Track[] tracks = anim.getTracks();
            if (tracks == null || tracks.length == 0)
                continue;
            anim = new Animation(animInfo.name, realLength);
            for (Track track : tracks) anim.addTrack(track);
        }
        anims.put(anim.getName(), anim);
    }
    animControl.setAnimations(anims);
}
Also used : FbxObject(com.jme3.scene.plugins.fbx.objects.FbxObject) HashMap(java.util.HashMap) Quaternion(com.jme3.math.Quaternion) FbxAnimNode(com.jme3.scene.plugins.fbx.objects.FbxAnimNode) FbxNode(com.jme3.scene.plugins.fbx.objects.FbxNode) TreeSet(java.util.TreeSet) BoneTrack(com.jme3.animation.BoneTrack) AnimInverval(com.jme3.scene.plugins.fbx.AnimationList.AnimInverval) Vector3f(com.jme3.math.Vector3f) Animation(com.jme3.animation.Animation) BoneTrack(com.jme3.animation.BoneTrack) Track(com.jme3.animation.Track)

Example 39 with Animation

use of com.jme3.animation.Animation in project jmonkeyengine by jMonkeyEngine.

the class SkeletonLoader method load.

public Object load(InputStream in) throws IOException {
    try {
        // Added by larynx 25.06.2011
        // Android needs the namespace aware flag set to true 
        // Kirill 30.06.2011
        // Now, hack is applied for both desktop and android to avoid
        // checking with JmeSystem.
        SAXParserFactory factory = SAXParserFactory.newInstance();
        factory.setNamespaceAware(true);
        XMLReader xr = factory.newSAXParser().getXMLReader();
        xr.setContentHandler(this);
        xr.setErrorHandler(this);
        InputStreamReader r = new InputStreamReader(in);
        xr.parse(new InputSource(r));
        if (animations == null) {
            animations = new ArrayList<Animation>();
        }
        AnimData data = new AnimData(skeleton, animations);
        skeleton = null;
        animations = null;
        return data;
    } catch (SAXException ex) {
        IOException ioEx = new IOException("Error while parsing Ogre3D dotScene");
        ioEx.initCause(ex);
        fullReset();
        throw ioEx;
    } catch (ParserConfigurationException ex) {
        IOException ioEx = new IOException("Error while parsing Ogre3D dotScene");
        ioEx.initCause(ex);
        fullReset();
        throw ioEx;
    }
}
Also used : InputSource(org.xml.sax.InputSource) InputStreamReader(java.io.InputStreamReader) Animation(com.jme3.animation.Animation) IOException(java.io.IOException) ParserConfigurationException(javax.xml.parsers.ParserConfigurationException) XMLReader(org.xml.sax.XMLReader) SAXParserFactory(javax.xml.parsers.SAXParserFactory) SAXException(org.xml.sax.SAXException)

Example 40 with Animation

use of com.jme3.animation.Animation in project jmonkeyengine by jMonkeyEngine.

the class MeshLoader method compileModel.

private Node compileModel() {
    Node model = new Node(meshName + "-ogremesh");
    for (int i = 0; i < geoms.size(); i++) {
        Geometry g = geoms.get(i);
        Mesh m = g.getMesh();
        // New code for buffer extract
        if (sharedMesh != null && usesSharedMesh.get(i)) {
            m.extractVertexData(sharedMesh);
        }
        model.attachChild(geoms.get(i));
    }
    if (animData != null) {
        for (int i = 0; i < geoms.size(); i++) {
            Geometry g = geoms.get(i);
            Mesh m = geoms.get(i).getMesh();
            //FIXME the parameter is now useless.
            //It was !HADWARE_SKINNING before, but since toggleing 
            //HW skinning does not happen at load time it was always true.
            //We should use something similar as for the HWBoneIndex and 
            //HWBoneWeight : create the vertex buffers empty so that they 
            //are put in the cache, and really populate them the first time 
            //software skinning is used on the mesh.
            m.generateBindPose(true);
        }
        // Put the animations in the AnimControl
        HashMap<String, Animation> anims = new HashMap<String, Animation>();
        ArrayList<Animation> animList = animData.anims;
        for (int i = 0; i < animList.size(); i++) {
            Animation anim = animList.get(i);
            anims.put(anim.getName(), anim);
        }
        AnimControl ctrl = new AnimControl(animData.skeleton);
        ctrl.setAnimations(anims);
        model.addControl(ctrl);
        // Put the skeleton in the skeleton control
        SkeletonControl skeletonControl = new SkeletonControl(animData.skeleton);
        // This will acquire the targets from the node
        model.addControl(skeletonControl);
    }
    return model;
}
Also used : HashMap(java.util.HashMap) Animation(com.jme3.animation.Animation) SkeletonControl(com.jme3.animation.SkeletonControl) AnimControl(com.jme3.animation.AnimControl)

Aggregations

Vector3f (com.jme3.math.Vector3f)18 Animation (com.jme3.animation.Animation)12 Quaternion (com.jme3.math.Quaternion)12 AnimControl (com.jme3.animation.AnimControl)11 BoneTrack (com.jme3.animation.BoneTrack)10 HashMap (java.util.HashMap)9 Bone (com.jme3.animation.Bone)8 SpatialTrack (com.jme3.animation.SpatialTrack)7 TempVars (com.jme3.util.TempVars)6 Material (com.jme3.material.Material)5 Track (com.jme3.animation.Track)4 ParticleEmitter (com.jme3.effect.ParticleEmitter)4 DirectionalLight (com.jme3.light.DirectionalLight)4 Geometry (com.jme3.scene.Geometry)4 Node (com.jme3.scene.Node)4 ArrayList (java.util.ArrayList)4 AmbientLight (com.jme3.light.AmbientLight)3 ColorRGBA (com.jme3.math.ColorRGBA)3 Transform (com.jme3.math.Transform)3 Spatial (com.jme3.scene.Spatial)3