简体   繁体   English

LibGDX:如何使平铺地图图块可点击?

[英]LibGDX: How to make tiled map tiles clickable?

如何为平铺地图中的切片添加单击侦听器,以便在使用鼠标选择切片时它会突出显示?

That's not supported directly by libGDX as the TiledMap stuff is only for rendering. libGDX不直接支持这一点,因为TiledMap的东西仅用于渲染。

You could easily create a Stage though, which will act as some kind of overlay-input-layer for your TiledMap. 您可以轻松创建一个Stage ,它将作为TiledMap的某种叠加输入层。 Just create an Actor for each tile which has the same size as position as that tile. 只需为每个图块创建一个Actor ,该图块的大小与该图块的位置相同。 Then you are able to add EventListener s to those actors to be able to recognize things like clicks on those actors. 然后,您可以将EventListener添加到这些actor中,以便能够识别诸如对这些actor的点击之类的内容。

Those actors should keep a reference to their "origin", namely TiledMapTileLayer.Cell . 这些演员应该保留对其“起源”的引用,即TiledMapTileLayer.Cell So you are able to go back from the actor to the cell anytime when processing those events. 因此,您可以在处理这些事件时随时从演员返回到单元格。

The following shows how you might do it: 以下显示了如何执行此操作:

This Actor is responsible to catch the events and keep the information about the tile it's based on: 该Actor负责捕获事件并保留有关它所基于的图块的信息:

public class TiledMapActor extends Actor {

    private TiledMap tiledMap;

    private TiledMapTileLayer tiledLayer;

    private TiledMapTileLayer.Cell cell;

    public TiledMapActor(TiledMap tiledMap, TiledMapTileLayer tiledLayer, TiledMapTileLayer.Cell cell) {
        this.tiledMap = tiledMap;
        this.tiledLayer = tiledLayer;
        this.cell = cell;
    }

}

This little listener can be attached to one of those actors and will do any kind of logic: 这个小听众可以附加到其中一个演员身上,并且可以做任何逻辑:

public class TiledMapClickListener extends ClickListener {

    private TiledMapActor actor;

    public TiledMapClickListener(TiledMapActor actor) {
        this.actor = actor;
    }

    @Override
    public void clicked(InputEvent event, float x, float y) {
        System.out.println(actor.cell + " has been clicked.");
    }
}

The following class actually creates the actors from a given map and wires them to the listeners: 以下类实际上从给定的地图创建actor并将它们连接到侦听器:

public class TiledMapStage extends Stage {

    private TiledMap tiledMap;

    public TiledMapStage(TiledMap tiledMap) {
        this.tiledMap = tiledMap;

        for (MapLayer layer : tiledMap.getLayers()) {
            TiledMapTileLayer tiledLayer = (TiledMapTileLayer)layer;
            createActorsForLayer(tiledLayer);
        }
    }

    private void createActorsForLayer(TiledMapTileLayer tiledLayer) {
        for (int x = 0; x < tiledLayer.getWidth(); x++) {
            for (int y = 0; y < tiledLayer.getHeight(); y++) {
                TiledMapTileLayer.Cell cell = tiledLayer.getCell(x, y);
                TiledMapActor actor = new TiledMapActor(tiledMap, tiledLayer, cell);
                actor.setBounds(x * tiledLayer.getTileWidth(), y * tiledLayer.getTileHeight(), tiledLayer.getTileWidth(),
                        tiledLayer.getTileHeight());
                addActor(actor);
                EventListener eventListener = new TiledMapClickListener(actor);
                actor.addListener(eventListener);
            }
        }
    }
}

Now the TiledMapStage will do all work for you. 现在, TiledMapStage将为您完成所有工作。 All you need to do is the following: 您需要做的就是以下内容:

Stage stage = new TiledMapStage(tiledMap);
Gdx.input.setInputProcessor(stage);

And in render(...) you need to call stage.act() . 在render(...)中,你需要调用stage.act() Remember to use the same Viewport for the stage as you are using to render the TiledMap. 请记住在舞台上使用相同的Viewport来渲染TiledMap。 Otherwise the input and your rendered map won't be aligned. 否则输入和渲染的地图将不对齐。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM