2017-03-26 2 views
0

Also hier ist mein Problem. Ich habe eine Gegnerklasse erstellt, die Sprite in libGDX mit einem Box2d-Körper zur Kollisionserkennung erweitert. Mein Code ruft die gegnerische Klasse dynamisch innerhalb des Spiels in einer Schleife auf, aber das Problem ist, dass wenn ich nach einer Kollision eine andere Animationssequenz benutze, um einen besiegten Gegner darzustellen, die Animationssequenz unterschiedliche Bildraten für verschiedene Instanzen derselben Klasse zeigt. Ich weiß nicht, warum das passiert.Mehrere Instanzen der gleichen Sprite-Klasse zeigen verschiedene Animation Frames in libGDX und box2d

Hier ist die Klasse, die in einer Schleife aufgerufen wird.

public class Spearman extends Enemies { 
    private Body spearman1; 
    private TextureAtlas atlas; 
    private Animation approaching,defeated; 
    private float time; 
    private TextureRegion spearmaninit; 

    private int spearmanstate=0; 


    public Spearman(Play_State state,float x, float y){ 
     super(state,x,y); 
     atlas=new TextureAtlas(); 
     atlas=Lone_Warrior1.getAtlas(3); 
     time=0f; 

     Array<TextureRegion> frames=new Array<TextureRegion>(); 
     for(int i=0;i<3;i++) 
     { 
      frames.add(new TextureRegion(atlas.findRegion("Spearman"+i))); 
     } 
     approaching=new Animation(0.15f,frames); 
     frames.clear(); 
     for(int i=0;i<5;i++) 
     { 
     frames.add(new       TextureRegion(atlas.findRegion("Spearmandefeated"+i))); 
     } 
     defeated=new Animation(2.2f,frames); 
     frames.clear(); 
     spearmaninit=new TextureRegion(atlas.findRegion("Spearman0")); 
     setBounds(getX(),getY(),200/ Lone_Warrior1.PPM,170/Lone_Warrior1.PPM); 
     setRegion(spearmaninit); 

    } 

    public void update(float dt){ 

     if(spearmanstate!=-1) { 
      setPosition(spearman1.getPosition().x - getWidth()/2,  (spearman1.getPosition().y - getHeight()/2)+13/Lone_Warrior1.PPM); 
      if (spearmanstate==0 && spearman1.getLinearVelocity().x>0) 
       spearmanstate=1; 
      if (spearmanstate==1 && spearman1.getLinearVelocity().x==0) { 
       Play_State.bodiesToRemove.add(spearman1); 
       Play_State.enemycounter++; 
       spearmanstate = -1; 

      } 
      if(spearmanstate==0) 
       spearman1.setLinearVelocity(-2f,0); 
      setRegion(getFrame(dt)); 
     } 
    } 
    public boolean check(){ 
     if(spearmanstate!=-1) 
      return true; 
    else 
     return false; 
    } 
    public TextureRegion getFrame(float dt){ 
     TextureRegion region=null; 
     region=approaching.getKeyFrame(time,true); 
     if(spearmanstate==1) 
      region=defeated.getKeyFrame(time); 
     /* if(!region.isFlipX()) 
     region.flip(true,false);*/ 
     time=time+dt; 
     return region; 

    } 

    @Override 
    public void defineEnemy() { 
     BodyDef bdef=new BodyDef(); 
     bdef.position.set(getX(),getY()); 
     bdef.type=BodyDef.BodyType.DynamicBody; 
     spearman1=Play_State.world.createBody(bdef); 

     FixtureDef fdef=new FixtureDef(); 
     PolygonShape War1=new PolygonShape(); 
     War1.setAsBox(60/Lone_Warrior1.PPM,60/Lone_Warrior1.PPM); 

     fdef.shape=War1; 
     fdef.filter.categoryBits=Lone_Warrior1.BIT_APPROACHING; 
       fdef.filter.maskBits=Lone_Warrior1.BIT_GROUND|Lone_Warrior1.BIT_RUN|Lone_Warrior  1.BIT_ATTACK; 
     spearman1.createFixture(fdef).setUserData("spearman1"); 

    } 

    } 

Die abstrakte Klasse, die die Spearman nennt:

public abstract class Enemies extends Sprite { 
    World world; 
    Body b2body; 
    public Enemies(){ 

    } 
    public Enemies(Play_State screen,float x, float y){ 
     this.world=screen.world; 
     setPosition(x,y); 
     defineEnemy(); 
    } 

    public abstract void defineEnemy(); 
    public abstract void update(float dt); 
    public abstract boolean check(); 
} 

Hier ist der Code, der die Klasse aufruft.

switch (a) { 
      case 1: 
       System.out.println("creating spearman"); 
       spearman.add(new Spearman(screen, (Lone_Warrior1.V_Width /Lone_Warrior1.PPM) + (Lone_Warrior1.x+``(i*500/Lone_Warrior1.PPM)), 100/  Lone_Warrior1.PPM)); 
       break; 
       } 
+0

Ich empfehle in hohem Grade, die Sprite-Kategorie nicht zu verwenden. Sprite ist eine TextureRegion-Unterklasse mit einem Hintergrund-Array, das eine ganze Reihe von Positions-, Orientierungs- und Farbdaten enthält. Es eignet sich nicht wirklich als Basisklasse für eine Spieleinheit, da es redundante Daten liefert und fehleranfällig ist. Erstellen Sie eine eigene Basisklasse, die auf eine TexturRegion ** oder ** Animation verweist und Felder für Position, Farbe, Ausrichtung usw. enthält. – Tenfour04

Antwort

0

Gelöst!

Ja, die Sprite-Klasse ist ein wenig mühsam für Frame-für-Frame-Animation, aber ich hatte schon viel von meinem Code getan und musste einen Patch-Job für dieses Problem finden, anstatt den gesamten Code neu schreiben zu müssen.

So, hier ist die Antwort:

time=currentState==previousState ? time+dt : 0; 
    previousState=currentState; 

Jedes Mal, wenn Sie sich die Zeit mit Delta-Zeit in der Update-Methode aktualisieren, stellen Sie sicher, zu überprüfen, ob die aktuelle Animationssequenz zum vorherigen gleich ist, wenn nicht, dann machen Zeit null, dann nach der Kollision würde die nächste Animation in der beabsichtigten Folge ablaufen. Versetzen Sie einfach einen Verfolger für den Zustand, in dem Sie sind.

Verwandte Themen