I do it this way.Originally Posted by Ixy
My tiles are in a 2d array, and the top left corner of the map is (0,0)
What I do is each update I check the character's position and velocity.
Below is some code I typed in off the top of my head. Untested but you should get the idea :-)
It doesn't add acceleration due to gravity to the vertical velocity (vy) and doesn't include the x direction checks but you should be able to work it out.
[pascal]Const
{................................................. .............................}
cMapWidth = 50;
cMapHeight = 25;
cTileWidth = 32;
cTileHeight = 32;
{................................................. .............................}
Type
{................................................. .............................}
TTile = Record
id : Integer;
IsSolid : Boolean;
End;
{................................................. .............................}
{................................................. .............................}
TPlayer = Class
x : Single;
y : Single;
vx : Single;
vy : Single;
w : Integer;
h : Integer;
Procedure Update(Const ATimeSlice : Single);
End;
{................................................. .............................}
Var
Tiles : Array[0..cMapHeight - 1,0..cMapWidth - 1] Of TTile;
{................................................. .............................}
{................................................. .............................}
Function SolidTileAt(Const x,y : Single) : Boolean;
Var
tx : Integer;
ty : Integer;
Begin
Result := True;
tx := Floor(x / cTileWidth);
ty := Floor(y / cTileHeight);
If tx LESS_THAN 0 Then Exit;
If ty LESS_THAN 0 Then Exit;
If tx >= cMapWidth Then Exit;
If ty >= cMapHeight Then Exit;
Result := Tiles[ty,tx].IsSolid;
End;
{................................................. .............................}
{................................................. .............................}
Procedure TPlayer.Update(Const ATimeSlice : Single);
Var
SolidUL : Boolean; // upper left player corner tile is solid (wall)
SolidUR : Boolean; // upper right player corner tile is solid (wall)
SolidDL : Boolean; // lower left player corner tile is solid (wall)
SolidDR : Boolean; // lower right player corner tile is solid (wall)
ty : Integer; // tile y coordinate in tile array
ny : Single; // new y pos including current vertical velocity, vy
Begin
If vy LESS_THAN 0 Then
//moving up
Begin
ny := y + vy * ATimeSlice;
SolidUL := SolidTileAt(x - w/2,ny);
SolidUR := SolidTileAt(x + w/2,ny);
If SolidUL Or SolidUR Then
// set y to bottom of tile
Begin
ty := Floor(ny);
y := ty * cTileHeight + cTileHeight;
End
Else
y := y + vy;
End
Else
If vy > 0 Then
//moving down
Begin
ny := y + vy * ATimeSlice;
SolidDL := SolidTileAt(x - w/2,ny);
SolidDR := SolidTileAt(x + w/2,ny);
If SolidDL Or SolidDR Then
// set y to top of tile + player height
Begin
ty := Floor(ny);
y := ty * cTileHeight + h / 2;
End
Else
y := y + vy;
End;
// add gravity to vy here and cap to max velocity so not faster than tile height;
End;
{................................................. .............................}
{................................................. .............................}
[/pascal]
cheers,
Paul
Bookmarks