【问题标题】:Libgdx Camera/Viewport/TiledMapLibgdx 相机/视口/TiledMap
【发布时间】:2017-05-18 13:56:22
【问题描述】:

我正在尝试基于 TiledMap(带有相机和视口)制作游戏。 我的游戏应该被缩放,始终填满整个屏幕(没有黑条)[就像在 Banana Kong 中一样]。我找到了ExtendViewport 应该可以解决这个问题(我认为)。

在尝试了很多事情之后,我没有找到正确的解决方案。地图总是缩放到小或/和错误的位置。当我在计算机上缩放窗口时,它应该用 Tiled Map 填充整个高度,然后用 TiledMap 的可绘制部分填充屏幕的整个长度(并提到纵横比)。

到目前为止,这是我的代码,如何使它工作?

public class LoadingScreen implements Screen {
//Reference to MainGameClass
private MainGameClass game;

//Camera and Viewport
private OrthographicCamera gamecam;
private Viewport gamePort;

//Tiled MaP
private TmxMapLoader maploader;
private TiledMap map;
private OrthogonalTiledMapRenderer renderer;

public LoadingScreen(MainGameClass game) {
    this.game = game;

    //Camera and Viewport
    gamecam = new OrthographicCamera();
    gamePort = new ExtendViewport(MainGameClass.WIDTH, MainGameClass.HEIGHT, gamecam);

    //Tiledmap
    maploader = new TmxMapLoader();
    map = maploader.load("MarioBros.tmx");
    renderer = new OrthogonalTiledMapRenderer(map, 1);
    gamecam.setToOrtho(false);
}

@Override
public void show() {

}

public void update(float dt) {
    //gamecam.position.x += 1;
    gamecam.update();
    renderer.setView(gamecam);
}

@Override
public void render(float delta) {
    update(delta);

    //Clear Game Screen with black
    Gdx.gl.glClearColor(0,0,0,1);
    Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT);

    renderer.render();

    //Begin GameBatch
    game.batch.setProjectionMatrix(gamecam.combined);
}

@Override
public void resize(int width, int height) {
    gamePort.update(width,height);
    gamecam.setToOrtho(false);
}

@Override
public void pause() {

}

@Override
public void resume() {

}

@Override
public void hide() {

}

@Override
public void dispose() {

}
}

希望有人能帮忙

编辑 1:

手机的高度应始终填充整个关卡高度。那么你看到的地图的长度也应该总是填满整个屏幕。所以在手机上拉得更多你可以看到更多的关卡,关卡的高度总是和手机一样高。

此外,当我用鼠标手动缩放 PC 上的窗口时,应该更新视图!

【问题讨论】:

  • MainGameClass.WIDTHHEIGHT 的值以及地图的tileWidthtileHeight 的值和图块中的地图大小是多少?
  • MainGameClass.WIDTH 是屏幕/窗口高度,所以这里是 480px,tileWidth/Height 是 16px,它的 Tiles 高 6,长 60。
  • MainGameClass.WIDTHHEIGHT 是常数值?
  • 是的,它的常数
  • 这些常量的值?

标签: android libgdx viewport orthographic


【解决方案1】:
tileWidth=16;
tileHeight=16;

Total Tiles on map (10 * 6 screen) * 6; // on screen 10 * 6 tiles

所以相机视口尺寸应该是:

viewportWidth= 10 * 16 ;
viewportHeight= 6 * 16 ;

cam=new OrthographicCamera();
cam.setToOrtho(false,viewportWidth,viewportHeight);

TmxMapLoader tmxMapLoader=new TmxMapLoader();
TiledMap tiledMap=tmxMapLoader.load("untitled.tmx");

tiledMapRenderer=new OrthoCachedTiledMapRenderer(tiledMap);
tiledMapRenderer.setView(cam);

渲染

tiledMapRenderer.render();

我建议使用最少 15 * 10 每个屏幕/页面的瓦片,瓦片宽度或瓦片高度为 32 像素。当你增加没有。在游戏中您将获得更高的精度。

编辑

你可以这样使用ExtendViewport

public class MyTest extends ApplicationAdapter {

    OrthogonalTiledMapRenderer renderer;
    OrthographicCamera cam;
    ExtendViewport viewport;

    float viewportWidth,viewportHeight;

    @Override
    public void create() {

        viewportWidth=16*10;
        viewportHeight=6*16;

        cam=new OrthographicCamera();
        viewport=new ExtendViewport(viewportWidth,viewportHeight,cam);

        TmxMapLoader loader=new TmxMapLoader();
        TiledMap map=loader.load("untitled1.tmx");

        renderer=new OrthogonalTiledMapRenderer(map);
        renderer.setView(cam);
    }

    @Override
    public void render() {

        Gdx.gl.glClearColor(1,1,1,1);
        Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT);

        renderer.setView(cam);
        renderer.render();
    }

    @Override
    public void resize(int width, int height) {
        viewport.update(width,height,false);
        viewport.getCamera().position.set(viewportWidth/2f,viewportHeight/2f,0);
        viewport.getCamera().update();
    }
}

【讨论】:

  • 为什么视口宽度是16*10?
  • 只用相机也可以吗?没有像你的第一篇文章那样的视口
  • 16 是 tileWidth,我假设你在屏幕上横向有 10 个图块,所以你总共有 6 页(每页 10 个图块 * 6 页)所以总共 60 个图块是地图宽度
【解决方案2】:

将视口限制在地图区域需要几个步骤。

首先,我们需要计算出地图的全宽,这样我们才能知道要显示多少地图。

int totalMapWidth = totalHorizontalTiles * pixelPerTile;
int totalMapHeight = totalVerticalTiles * pixelPerTile;

现在我们有了我们想要的视口大小的地图大小,以便我们可以与我们的 totalMapWidth 和 totalMapHeight 进行比较。

viewport.getWorldWidth();  // our viewport width
viewport.getWorldHeight(); // our viewport height

最后我们需要相机的缩放值。

float zoom = camera.zoom;

通过以上所有数据,我们可以评估应用缩放后的视口宽度。

float evalWidth = viewport.getWorldWidth() * cam.zoom;
float evalHeight= viewport.getWorldHeight() * cam.zoom;

最后一步是将相机位置固定到地图区域内的位置。

cam.position.x = MathUtils.clamp(cam.position.x, evalWidth / 2f, 
                    totalMapWidth - evalWidth / 2f);
cam.position.y = MathUtils.clamp(cam.position.y, evh / 2f,
                                    totalMapHeight - evh / 2f);

当以合理的水平缩放时,这应该会停止相机显示地图之外的区域。如果用户缩小得太远以至于地图小于视口宽度或高度,则将显示外部区域。为了阻止这种情况,您还需要通过限制缩放来限制缩放级别。

float minZoom = 0.1f; // this is the zoomed in value
float maxZoom = 1; // this is zoomed out level

现在夹住相机

camera.zoom = Math.clamp(camera.zoom, minZoom,maxZoom);

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-04-04
    • 1970-01-01
    • 2013-01-23
    • 2016-06-11
    相关资源
    最近更新 更多