Graphics2D.translate problem [SOLVED]

I am using a camera/viewport for my screen which always centers around the player. Right now I always offset the coordinates for everything so get drawn on the screen when they should be visible. This methods seems very inelegant and I want to use the translate() method of g2d. My problem is, that it doesn’t work at all. If I move the player towards the edge of the screen it just ignores my translate and draws everything at it’s original coordinates. Maybe I’m just translating wrong.


public class Game implements Runnable{

  private void render() {
		Graphics2D g = (Graphics2D) bs.getDrawGraphics();
		g.setBackground(Color.black);
		g.clearRect(0, 0, WIDTH, HEIGHT);
		g.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_OFF);
		render(g);
		g.dispose();
		bs.show(); // the bufferstrategy
		
	}

	private void render(Graphics2D g) {
		screen.render(g);
	}
}

public class GameScreen {
  public void render(Graphics2D g) {
		g.translate(Math.round(cam.camX), Math.round(cam.camY));
		mc.render(g);
		player.render(g);
		hud.render(g);
		g.translate(-(Math.round(cam.camX)), -(Math.round(cam.camY)));
	}
}

public class Player {
  g.drawImage(current, Math.round(x /*- cam.camX*/), Math.round(y /*- cam.camY*/), null); //commented out my usual offset
}

I am translating at the game screen because other screens don’t need the translation.

NOTE: My inelegant method works perfectly which is basically a translation.

EDIT: I am using java2D/swing/awt if that’s of any importance

Hmmm…

Been a while since I used Graphics2D.

What does it draw at the moment?

I’m looking at the second g.translate(…)

When I used Graphics2D I never had to do that.

IMO, I think what’s happening is this:

Translate to the coords of the player.
Draw the player relative to the new coords.
Translate back to 0,0

Result: Player is 2x as far away from the centre

Wait a second!
I don’t see any render method for the player!
There is your problem!

I see that it still compiles properly according to you…

What I did with translations is:


int offsetX = -player.x + screenWidth/2;
int offsetY = -player.y + screenHeight/2;
g.translate(offsetX, offsetY);
render(g);
// etc.

I think that should work and you can edit it to centre on the player (add size offsets) etc.

Well, actually I already have an offset which is camX and camY. I left out how I calculate it above.


private void calcCamPos() {
		if (follow.getX() - screenWidth/2 < 0) {
			camX = 0;
		} else if (follow.getX() + screenWidth/2 > mapWidth) {
			camX = mapWidth - screenWidth;
		} else {
			camX = follow.getX() - screenWidth/2;
		}
		
		
		if (follow.getY() - screenHeight/2 < 0) { 
			camY = 0;
		} else if (follow.getY() + screenHeight/2 > mapHeight) {
			camY = mapHeight - screenHeight;
		} else {
			camY = follow.getY() - screenHeight/2;
		}
	}

If I use translate() with camX and camY now it just doesn’t translate the coordinates. Everything gets drawn at the original coordinates and not at the translated ones. I don’t see any difference right now between having translate() and having it commented out. No effect at all.


x - camX
y - camY

This is where everything gets drawn at the correct position. It’s commented out in my player render(). But I don’t want to calculate it for everything I draw, although of course I know someone has to calculate it. That is the job of translate() or do I just understand this method wrong?

Okay, your code confuses me, but I think I might know what’s wrong

You say that you render the player at (x = camX), (y = camY)?
However if you translate by -camX, -camY, then you are drawing the player at 0, 0

AFAIK, you only need to translate once for what you seem to be trying to do.
Try this:


g.translate(-camX, -camY);
render(g);

Also, in your offsets, the player position should be made negative, and the screen height/width should be ADDED to the negative position.

Of course, g.translate can use different formulas for the same effect, but I find this easiest to code.

Haha, yes the minus was the problem. I just understood the parameters wrong. I thought camX and camY were the new (0,0) of the screen instead of the offset for each drawing. Funnily enough I did it the right way on my own but couldn’t supply a method with the right parameters. Thank you very much!

EDIT: camX and camY are the coordinates for the upper left corner of my view port. Sorry, if I didn’t explain that or it seemed confusing.