I need little example

Hi, first of all I want to say thanks to Tonegod for this awesome gui.
And know i have question :
how AnimElement actually works ? How I can make animated character?
how quad’s I should set up set up and how i can make them move ?

maybe i’m asking to much, but I need somehow figure out.

And maybe you can explain little bit about collision detection in your framework ?

sorry for those abstract questions, but i think it would help not only for me :wink:

hey @SetasSan,

i have the same questions, i can look at it in a few days or we wait for an answer from tonegod =)

Hey guys… sorry for the wait. And sorry for the non-existant documentation on the 2D framework atm. I’m still sort-of in the process of integrating it into the library. There are so many ways this can be used. Let me see if I can put together a few examples… give me a few and I’ll post them here.

Actually now i need animate spaceship, i looked in you galaga. so in mine I want ship to change ship animation when arrows is pushed, I want Exhaust fallow engines.
Here is some files https://app.box.com/s/18phc5b0tjvsxxt5wl03

and for collision, how i can detect it if enemy ship shoots, and what type of object i should use for shoot. I gues it is not rigidBodyControl ? ;D ( i’m just joking)

If I succeed with this game, maybe i will get my first job in IT xD I’m tying get in game developing company . so I should make galaga replica. They sad i can choose any engine and any language for this task. so my choose was your engine ;D

2 Likes

Ok… starting with a little bit overview might be helpful.

All elements in the 2D frmework are Transformables.
AnimElement’s can contain many QuadData (4 verts, 2 faces) that act like an independant mesh, however, they are part of the parent AnimElement’s single mesh.
Since both the AnimElement and QuadData implement Transformable, you can use TemporalActions to manipulate their transform properties.

You have a couple choices as to how you use AnimElement…

  1. Extend AnimElement and define the Texture, TextureRegion(s) and QuadData internal to AnimElement or
  2. Create a new AnimElement and define this info after the fact.

Here is a small example of creating and using an AnimElement:

[java]
public class MyCharacter extends AnimElement {

public MyCharacter(Main main, Screen screen) {
	super(main.getAssetManager());
	
	setTexture(screen.createNewTexture("SOME_TEXTURE_PATH"));
	
	TextureRegion tr = this.addTextureRegion("region1", 0,592,144,144);
	tr.flip(false, true);
	
	QuadData qd = this.addQuad(
		"quad1", // hash key for retrieving QuadData later
		"region1", // name of texture region to use
		new Vector2f(50,50), // position
		new Vector2f(25,25) // origin (where transforms will center around
	);
	qd.setColor(ColorRGBA.White);
	qd.setDimensions(50,50); // Initially the quad is the size of the texture region
}

@Override
public void animElementUpdate(float tpf) {
	
}

}
[/java]

Meanwhile, back in the batcave (or your main class… etc)

[java]

@Override
public void simpleInitApp() {
	Screen screen = new Screen(this);
	guiNode.addControl(screen);
	
	AnimLayer gameLayer = screen.addAnimLayer("gameLayer");
	
	MyCharacter character = new MyCharacter(this, screen);
	gameLayer.addAnimElement("MyCharacter", character);
	
	ScaleByAction sa = new ScaleByAction();
	sa.setAmount(1f,1f);

	sa.setDuration(0.5f);
	sa.setInterpolation(Interpolation.bounceOut);

	screen.getAnimManager().addQueuedAction(sa, character.getQuad("quad1"), 0);
}

[/java]

2 Likes

thank you very much :wink:

1 Like
@SetasSan said: thank you very much ;)

Personally I think one of the coolest thing you can do is use the Pool class to create groups of reusable quads inside of a single animelement and then use Pool.getNextAvailable() and Pool.releaseObject(); to let the pool manage your resources.

Let me put together a quick example of this as it makes it really easy to manage.

Also, the Galaga example was written prior to starting to integrate the 2D framework, so you’ll see that I am managing the AnimElement’s update loops myself instead of using the Screen class to do it for me.

Also, I recently added an ExecuteAction class for delayed execution of methods using the AnimManager of screen. Very useful as well.

Your example is not working for me. I change just image path. do i need some light source or something ?
I thin i’m missing something in main class, because even if I do gameLayer.setColorMap(“someImage”), it’s shows nothing

So… setting an AnimElement up to work as managed resources (quads) requires a few classes:

Pool
PoolObjectFactory
AnimElement

First set up the pool object factories:

[java]
import com.jme3.math.Vector2f;
import tonegod.gui.framework.core.AnimElement;
import tonegod.gui.framework.core.QuadData;
import tonegod.gui.framework.core.util.PoolObjectFactory;

/**
*

  • @author t0neg0d
    */
    public class FooFactory implements PoolObjectFactory {
    AnimElement el;
    int index = 0;

    public FooFactory(AnimElement el) {
    this.el = el;
    }

    public QuadData newPoolObject() {
    QuadData foo = el.addQuad(“foo” + index, “Foo”, Vector2f.ZERO, Vector2f.ZERO);
    foo.setDimensions(0,0);
    foo.setIgnoreMouse(true);
    index++;
    return foo;
    }
    }
    [/java]

Another for bars:

[java]
import com.jme3.math.Vector2f;
import tonegod.gui.framework.core.AnimElement;
import tonegod.gui.framework.core.QuadData;
import tonegod.gui.framework.core.util.PoolObjectFactory;

/**
*

  • @author t0neg0d
    */
    public class BarFactory implements PoolObjectFactory {
    AnimElement el;
    int index = 0;

    public BarFactory(AnimElement el) {
    this.el = el;
    }

    public QuadData newPoolObject() {
    QuadData bar = el.addQuad(“bar” + index, “Bar”, Vector2f.ZERO, Vector2f.ZERO);
    bar.setDimensions(0,0);
    bar.setIgnoreMouse(true);
    index++;
    return bar;
    }
    }
    [/java]

An AnimElement to display the foo’s and bar’s you need during your game:

[java]
import com.jme3.math.Vector2f;
import tonegod.gui.core.Screen;
import tonegod.gui.framework.core.AnimElement;
import tonegod.gui.framework.core.QuadData;
import tonegod.gui.framework.core.util.Pool;

/**
*

  • @author t0neg0d
    */
    public class FooBars extends AnimElement {
    FooFactory fooFactory;
    Pool<QuadData> foos;
    BarFactory barFactory;
    Pool<QuadData> bars;

    public FooBars(Screen screen) {
    super(main.getAssetManager());
    this.screen = screen;

     setTexture(screen.createNewTexture("FOO_BAR_TEXTURE_PATH");
     
     addTextureRegion("foo", 657,25,126,126);
     addTextureRegion("bar", 513,25,126,126);
     
     fooFactory = new FooFactory(this);
     foos = new Pool(fooFactory, 45);
     barFactory = new BarFactory(this);
     bars = new Pool(barFactory, 45);
     
     initialize();
    

    }

    public QuadData getNextAvailableFoo() {
    return foos.getNextAvailable();
    }

    public void freeFoo(QuadData foo) {
    foos.freePoolObject(foo);
    }

    public QuadData getNextAvailableBar() {
    return bars.getNextAvailable();
    }

    public void freeBar(QuadData bar) {
    bars.freePoolObject(bar);
    }

    @Override
    public void animElementUpdate(float tpf) {

    }
    }
    [/java]

And that is pretty much it… no worrying about creating quads, managing quads, etc, etc. Just grab what you need ad free the resource when your done with it.

3 Likes
@SetasSan said: Your example is not working for me. I change just image path. do i need some light source or something ? I thin i'm missing something in main class, because even if I do gameLayer.setColorMap("someImage"), it's shows nothing

Ooops… forgot to put initialize(); at the bottom of the constructor. Was writing these from memory… sorry about that!

now it’s working. Awesome :wink:
And thank you for pool example

1 Like

Also note in the example above I set the dimensions to 0,0 to start… so you would call:

[java]
QuadData myFirstFoo = myFooBar.getNextAvailableFoo();
myFirstFoo.setDimensions(sozeXVal, someYVal);
myFirstFoo.update(0); // only need to call this if you are managing the AnimElement update loops yourself (i.e. not using screen).
[/java]

And when you done using it (i.e. the player blows up the foo, you would call:

[java]
myFooBar.freeFoo(myFirstFoo);
[/java]

To let the Pool know the resource is available for use again.

And to answer the above question about the AnimLayer… there is no visual component to the AnimLayer… it is a container for AnimElements that are also used to manage the update loops for you.

2 Likes

Oh! Also… if you want a fairly decent example of working with AnimElement, look at the ElementEmitter class… it’s a particle emitter built using an AnimElement to display the particles.

Ok I will :wink:
you are awesome person, so much help

2 Likes

Sorry for the barrage of posts, however, I didn’t get into using parent linkage (i.e. cascading transforms between quads contained in the same AnimElement. The bug enemy in the Galaga type game sets this up and can be used as a reference… Defining the linkage is easy… the confusing part is, the origin and placement becomes relative to it’s parent once the link is added. However, once you get the hang of it, it goes fairly quick.

Definately look at the bug enemy in the example game for how this works.

Hah! One last thing. If you are going to do a semi-direct copy of that game, I would suggest changing it to leverage screen’s new 2D framework functionality and update management as an exercise. It will reduce the code dramatically and make it far easier to understand… plus, once you finish it, you should be able to teach me how to use it properly :wink:

1 Like
@SetasSan said: Ok I will ;) you are awesome person, so much help

Well… I am at least a person feeling rather ashamed that I haven’t documented this yet >.<

thanks @t0neg0d for the information about the 2d framework. I try your code examples in a few days when i have more time to programm :slight_smile:

1 Like

I have one more question is it possible add separated images in ElementEmitter ?
with set Sprite I can add only one image.

And how i can set up collisionListener ?
should i access all quads emitter.getParticles().getQuads() and check a bullet position and enemy position ?

@SetasSan said: I have one more question is it possible add separated images in ElementEmitter ? with set Sprite I can add only one image.

And how i can set up collisionListener ?
should i access all quads emitter.getParticles().getQuads() and check a bullet position and enemy position ?

The one image can contain multiple sprites. I need to go look and see how you define the sprite images (as it’s a bit different from the actual particle emitter I put together)… one sec.

Ok, for basic animated sprites, you just call:

[java]
// Path to sprite image, number of sprite rows, number of sprites in each row, the target FPS for frame changes
ElementEmitter.setSprite(String spriteImagePath, int spriteRows, int spriteCols, int targetFPS);
[/java]

This will cycle through the images at the defined frames per second.

For more advanced sprite usage, use the SpriteInfluencer…

This allows for all sorts of different methods of animation:

SequentialAll - Shows all frames in sequential order at the defined FPS (I believe this is the default sprite setting for the emitter not using this influencer)
SequentialAllOverLife - Shows all frames in sequential order once over the life of the particle
SequentialDefinedOrder - Uses the defined frame order (2,7,3,10,12,12,7,etc) showing showing the frame sequence at the target FPS
SequentialDefinedOrderOverLife - Uses the defined frame order (2,7,3,10,12,12,7,etc) showing each defined frame once over the life of the particle
RandomAll - This shows all frames in random order at the target FPS
RandomAllOverLife - This shows all frames once over the life of the particle
RandomDefinedOrder - This allows you to define the sprite frames to use but shows them in random order at the defined target FPS.
RandomDefinedOrderOverLife - This allows you to define the sprite frames to use but shows them in random order once over the lifecycle of the particle.
SingleImage - Uses a single image from the frames (I believe you define which it uses)

EDIT: The 2D emitter doesn’t have physics collision like the regular emitter, however if you look at… um… one sec… HitCalculator.java in the Galaga game, you’ll see how I am doing this. All bullets are particles from an emitter

2 Likes