In my side scroller game, when the character is moving past a specific zone (on the left side of the world) the camera should start moving until the character is past the next zone (on the right side of the world). However, when I cross the first zone and is where the camera should move, it moves slower than the player, and after a while the character disappears off the screen.
My code for the camera (in C#):
int worldWidth = world.GetLength(0) * _TILE_WIDTH;
int resX = camera.Width / TILE_WIDTH;
int resY = camera.Height / TILE_HEIGHT;
Bitmap screenBmp = new Bitmap(camera.Width, camera.Height);
Graphics g = Graphics.FromImage(screenBmp);
// upper left corner of the camera in the world
Vector2D pCamera = new Vector2D(p.X + (p.PlayerSize.Width / 2) - (screenBmp.Width / 2), 0);
int oneMoreX_tile = 0; // draw one more tile off the screen?
if (p.X + (p.PlayerSize.Width / 2) < 0 + screenBmp.Width / 2) // past the left zone
{
pCamera.X = 0;
}
else if (p.X + (p.PlayerSize.Width / 2) >= worldWidth - screenBmp.Width / 2) // past the right zone
{
pCamera.X = worldWidth - screenBmp.Width;
}
else // between the zones
{
oneMoreX_tile = 1;
}
int xOffset = (int)pCamera.X % TILE_WIDTH;
int yOffset = (int)pCamera.Y % TILE_HEIGHT;
int startX_tile = (int)pCamera.X / TILE_WIDTH;
int startY_tile = (int)pCamera.Y / TILE_HEIGHT;
for (int i = 0; i < resX + oneMoreX_tile; i++)
{
for (int j = 0; j < resY; j++)
{
int tileValue = world[startX_tile + i, startY_tile + j];
// tile coord in tileset
int x = tileValue % tilesetWidth_tile;
int y = tileValue / tilesetWidth_tile;
// pixel coord in tileset (top left)
int x_px = x * TILE_WIDTH;
int y_px = y * TILE_HEIGHT;
g.DrawImage(tileset,
new Rectangle(i * TILE_WIDTH - xOffset, j * TILE_HEIGHT - yOffset, TILE_WIDTH, TILE_HEIGHT),
new Rectangle(x_px, y_px, TILE_WIDTH, TILE_HEIGHT),
GraphicsUnit.Pixel);
}
}
What I don't understand is that I should calculate where the camera should start from the character position, so the character should always be centered as long as the camera is moving (i.e. not at one of the sides). To me it looks like it should work, but I can't figure out why it don't.
I figured out what the problem was. It was not a problem with the camera calculation, but rather with drawing the player.
The player's coordinates is in pixels in the works ( between 0 and world.GetLength(0) * tile_width). So when I drew the player, I forgot to subtract the camera position so the player world stay inside the camera view. ¨
This is what my code to draw the player looks like now:
g.DrawImage(p.PlayerSpriteCharSet,
new RectangleF(p.X - (float)pCamera.X, p.Y - (float)pCamera.Y, p.PlayerSize.Width, p.PlayerSize.Height),
new Rectangle(new Point(tilesetX_px, tilesetY_px), p.PlayerSpriteSize),
GraphicsUnit.Pixel);