0
\$\begingroup\$

I have created an inventory in which you can select some objects that you can spawn. This is a button in a table in a inventory class. Spawning is done via left mouse button (just click on some position in the game screen). Another option is that you can also stop spawning by unselecting the selected object by clicking the same button as before (select/unselect). Issue is that when you click that button to unselect the object it also spawns it on the same position. Is there a way to ignore spawning when your click is inside the inventory ?

Here is inventory class. It is created in the main PlayScreen

private final Stage stage;
private final Label fpsCounter;
private ImageButton mineButton;
private ObjectSelector objectSelector;
private ClickListener mineButtonClickListener;

public Inventory(final SpriteBatch sb,
                 final InputMultiplexer inputMultiplexer,
                 final ObjectSelector objectSelector,
                 final float width,
                 final float height) {
    this.objectSelector = objectSelector;

    final Viewport viewport = new FitViewport(
            width,
            height,
            new OrthographicCamera()
    );
    stage = new Stage(viewport, sb);

    stage.addActor(buildObjectSelectionTable(width, height));
    inputMultiplexer.addProcessor(stage);
}

private Table buildObjectSelectionTable(final float width,
                                        final float height) {
    final Table table = new Table();
    table.center(); // Center table content
    table.setSize(width * 0.5f, height * 0.09f);
    table.setPosition(table.getWidth() / 2 , height * 0.01f);
    table.setZIndex(99);
    final Texture background = new Texture("menu.png");
    table.setBackground(new TextureRegionDrawable(new TextureRegion(background)));


    final Drawable over = new TextureRegionDrawable(
            new TextureRegion(new Texture("mine2_trans.png"))
    );

    final Drawable exit = new TextureRegionDrawable(
            new TextureRegion(new Texture("mine2.png"))
    );

    float v = table.getHeight() * 0.8f;
    over.setMinHeight(v);
    over.setMinWidth(v);

    exit.setMinHeight(v);
    exit.setMinWidth(v);

    ImageButton.ImageButtonStyle style = new ImageButton.ImageButtonStyle();
    style.imageOver = over;
    style.imageUp = over;
    style.imageDown = exit;
    style.imageCheckedOver = exit;
    style.imageCheckedDown = exit;
    style.imageDisabled = exit;

    mineButton = new ImageButton(style);
    mineButton.setSize(v, v);

    ImageButton imageButton2 = new ImageButton(over);
    mineButton.setSize(v, v);

    mineButtonClickListener = new ClickListener() {
        private boolean selected = false;

        @Override
        public void clicked(InputEvent inputEvent, float x, float y) {
            System.out.println("clicked " + System.currentTimeMillis());
            if (!selected) {
                selected = true;
                objectSelector.selectObject(
                        Gdx.input,
                        Mine.class,
                        Mine.getObjectWidth(),
                        Mine.getObjectHeight());
                mineButton.setDisabled(selected);
            } else {
                selected = false;
                mineButton.setDisabled(selected);
                objectSelector.unselectObject();
            }
        }
    };
    mineButton.addListener(mineButtonClickListener);

    table.add(mineButton).padLeft(10);
    table.add(imageButton2).padLeft(10);

    return table;
}

PlayScreen looks like this

public class PlayScreen implements Screen {
    .....
public PlayScreen(Game game) {
    this.game = game;
    camera = new OrthographicCamera();
    gamePort = new ScreenViewport(camera);

    // Create object selector
    objectSelection = new ObjectSelector<GameObject>(game.getBatch(), camera);

    // Set input listener
    inputListener = new InputListener(camera, objectSelection);
    inputMultiplexer.addProcessor(inputListener);

    // Create inventory scene
    inventory = new Inventory (
            game.getBatch(),
            inputMultiplexer,
            objectSelection,
            gamePort.getWorldWidth(),
            gamePort.getWorldHeight()
    );

    Gdx.input.setInputProcessor(inputMultiplexer);
}
    
@Override
public void render(float delta) {
    if (Gdx.input.isButtonPressed(Input.Buttons.LEFT)) {
        Vector2 position = PositionUtil.toUnProjectedVector2(camera, Gdx.input);
        objectSelection.spawn(position);
    }
}
\$\endgroup\$

1 Answer 1

0
\$\begingroup\$

Update:

Sorry, I did see your comment that the inventory is on screen at the same time, then forgot about it.

If they are both on screen at the same time, you are going to have to logically carve your screen up into a 'play area' and the 'inventory area', by knowing the x or y coordinates that each part occupies.

Then you will need to check that the cursor position generated by your input Vector2 is inside the play area. If it is not, you simply ignore the click.

And if you haven't done so already, this is the time you really want to think about separating your game internal (logical) resolution from your screen (display) resolution.

Original answer based on the wrong assumption that the inventory was an overlay:

Personally, I would add some sort of flag to the Playscreen class, such as boolean isInInventory = false;, then flick it to true when the inventory is opened. Then you can

if (Gdx.input.isButtonPressed(Input.Buttons.LEFT && !isInInventory)) {

to ignore the click in the main screen. Set it back to false when you exit the inventory. If you have multiple non-play screens (score, etc), you might want to flick the logic and use the boolean to indicate the game is in play mode.

\$\endgroup\$
5
  • 1
    \$\begingroup\$ I might go further and have an active game state variable, then check if (activeGameState == GameState.Play ) vs GameState.InventoryMenu / etc. That scales to any number of screens/states without separate boolean flags for each. \$\endgroup\$
    – DMGregory
    Sep 27, 2021 at 11:33
  • \$\begingroup\$ That works too, and is probably easier for readability. \$\endgroup\$
    – Skrrp
    Sep 27, 2021 at 12:12
  • \$\begingroup\$ Problem with that solution is that this menu is shown all the time. Think of it as a menu where you can select objects to spawn, something like in RTS games. \$\endgroup\$
    – mirzak
    Sep 30, 2021 at 6:32
  • \$\begingroup\$ @mirzak updated based on your comment. Sorry this took so long. \$\endgroup\$
    – Skrrp
    Oct 5, 2021 at 16:46
  • \$\begingroup\$ I appreciate the answer. I have thought of that solution already but the problem I have there is that as camera moves my inventory can be on different position. For example position [10, 10] is one in my inventory, then player moves the camera and now position [10, 10] is not in the inventory, but [10, -200] is and so on. I am not sure if there is something like on-hover event on buttons that could be used. I tried enter and exit listeners but they are not triggered. \$\endgroup\$
    – mirzak
    Oct 12, 2021 at 17:11

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .