简体   繁体   中英

LibGDX - Camera scaling does not work

I have a problem with LibGDX. I am trying to create an application, and for ease of use I want to draw everything at a fixed resolution (1920x1080).

To do this, I am trying to create a FitViewport and an OrthographicCamera so that the viewport always fits nicely to the screen size, and everything automatically scales.

In my Screen class I create such a viewport and a camera:

AbstractScreen() {
    camera = new OrthographicCamera(Constants.VIRTUAL_WIDTH, Constants.VIRTUAL_HEIGHT);
    viewport = new FitViewport(Constants.VIRTUAL_WIDTH, Constants.VIRTUAL_HEIGHT, camera);
}

(where VIRTUAL_WIDTH is 1920 and VIRTUAL_HEIGHT is 1080)

Now, when I try to render an image that is 1920x1080px, only one third of that image is drawn!

Here is a screenshot of what should be drawn: screenshot

Here is the image that should be fully drawn: image

public abstract class AbstractScreen implements Screen {

    private Viewport viewport;
    private OrthographicCamera camera;

    protected SpriteBatch spriteBatch;

    AbstractScreen() {
        camera = new OrthographicCamera(Constants.VIRTUAL_WIDTH, Constants.VIRTUAL_HEIGHT);
        viewport = new FitViewport(Constants.VIRTUAL_WIDTH, Constants.VIRTUAL_HEIGHT, camera);

        spriteBatch = new SpriteBatch();
    }

    @Override
    public void show() {
        viewport.apply();
    }

    @Override
    public void render(float delta) {
        Gdx.gl.glClearColor(0, 0, 0, 1);
        Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT);

        camera.update();
        spriteBatch.setProjectionMatrix(camera.combined);
    }

    @Override
    public void resize(int width, int height) {
        viewport.update(width, height);
    }

    @Override
    public void pause() {

    }

    @Override
    public void resume() {

    }

    @Override
    public void hide() {

    }

    @Override
    public void dispose() {

    }
}

And here is the actual screen implementation:

class LoadingScreen extends AbstractScreen {

    private SpriteBatch spriteBatch;
    private Texture texture;

    @Override
    public void show() {
        super.show();
        spriteBatch = new SpriteBatch();
        texture = new Texture("textures/test.png");
    }

    @Override
    public void render(float delta) {
        super.render(delta);

        spriteBatch.begin();

        spriteBatch.draw(texture, 0, 0);

        spriteBatch.end();
    }
}

Thank you!

Your LoadingScreen is creating its own SpriteBatch named spriteBatch , which hides the spriteBatch in the AbstractScreen superclass.

So your LoadingScreen.render() calls super.render() , which sets up the appropriate projection matrix in AbstractScreen.spriteBatch , but then you are using LoadingScreen.spriteBatch to draw with.

So remove the spriteBatch field in LoadingScreen, and don't instantiate it there. Make the spriteBatch in AbstractScreen protected so you can access it from the subclass.

By the way, SpriteBatches must be disposed in dispose() or you will leak memory. Better yet, don't instantiate SpriteBatch inside your Screen. Instantiate a single SpriteBatch in your Game and pass it to your Screen's constructor so everything can share the same instance, rather that wasting time disposing and instantiating new ones every time you switch screens. SpriteBatch is a heavy object.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

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