GameStateManager LibGDX

I started a project with libgdx and I have a GameStateManager for my GameStates Menu and Play.

If I run the project it shows a menu and then I can press the button to open Play GameState. The problem is when I finished the game it should show the menu state again, but I get a black screen. I have tested if render () method (with System.out ...) and render () method on the menu are running.

I don't understand why I get a black screen when I open the menu state again. This may not work because I am using Box2D in Play, but I donโ€™t know.

Here is the code:

This is the method in Play that should open the menu if the player is at the end:

public void playerEnded() {

    gsm.setState(GameStateManager.MENU);

}

      

Maybe you can tell me if I need to finish the box2d case or so. I hope someone can help me and if you want more code no problem.

+3


source to share


3 answers


Your custom GameStateManager should extend this class:

http://libgdx.badlogicgames.com/nightlies/docs/api/com/badlogic/gdx/Game.html

To change screens, you must use Game.setScreen



Each screen must be an implementation of the screen.

So the way it works in my libGDX projects is that GameScreen expands the screen and the MenuScreen expands the screen. This way I can change what is drawing on which screen.

It all goes back to interfaces and polymorphism, so if you don't get those concepts, just give them a quick Google and you will get an idea of โ€‹โ€‹what you need to do.

+2


source


Chances are you are defining

Stack<GameState> gameStates

      

in your GameStateManager to manage your GameStates.

If so, you can read a little about stack usage. Anyway, here's what you can do to solve your problem: I assume you have the following structure in your GamestateManager;

public void setState(int state){
    popState();
    pushState(state);
}
public void pushState(int state){
    gameStates.push(getState(state));
}
public void popState(){
    GameState g = gameStates.pop();
    g.dispose();
}

private GameState getState(int state){
    if(state == MENU) return new Menu(this);
    if(state == PLAY) return new Play(this);
    return null;
}

      

When you click the Start button on your GameState menu, you will want to launch Play-GameState. Now instead of using the setState method, which removes the top state (pop) and then pushes the new state. Try to use only pushState method. This will add your new Play-GameState on top of your GameState menu in the GameState-Stack.

When you're done playing, you can appear in Play-GameState and Menu-GameState appears again. But this time it will not instantiate a new object, but reuse the one you used when starting the game.



// in the Menu-GameState:
public void startPlay() {
    gsm.pushState(GameStateManager.PLAY);
}

// in the Play-GameState:
public void playerEnded() {
    gsm.popState();
}

      

This will not affect gameplay performance as you will only display and update your game with GameState on top of the Stack, for example:

public void update(float dt) {
    gameStates.peek().update(dt);
}

public void render() {
    gameStates.peek().render();
}

      

The peek method takes the GameState off the top of the stack, but leaves it there.

The only drawback is that the Menu-Gamestate will remain in memory during your Play-State.

Also, if this method works, you can still do it your own way, but you should check how your Menu-GameState is created and look for problems when it was created twice.

+1


source


I have implemented a similar StageManager in my game. If you are using viewports / cameras in your game, then it is likely that when you return to your menu state, the viewport will still be set in the game state viewport.

In my application, my State class had an activate () method that will be called whenever the state becomes active:

public void activate(){
  stage.getViewport().update(Gdx.graphics.getWidth(), Gdx.graphics.getHeight());
}

      

0


source







All Articles