(I added "down" to
love.keypressed by the way.)
Code: Select all
elseif key == "down" then
if testMap(0, 1) then
player.grid_y = player.grid_y + 16
end
Now, on to
testMap!
Code: Select all
function testMap(x, y)
if tileString[(player.grid_y / 16) + y][(player.grid_x / 16) + x] == '-' then
return false
elseif tileString[(player.grid_y / 16) + y][(player.grid_x / 16) + x] == 'x' then
return false
end
return true
end
First of all, I'm not sure whether you want to be checking for "x", as it's the sky!
Instead of using tileString, try using TileTable. TileTable is structured like
TileTable[x][y], not like
TileTable[y][x].
I think this code will be easier to read if the tests are joined with
and, and the positions to test are stored in their own
local variables (
local meaning they won't be able to be seen outside the function they are defined in).
Code: Select all
function testMap(x, y)
local testX = player.grid_x / 16 + x
local testY = player.grid_y / 16 + y
if TileTable[testX][testY] == '-' or
TileTable[testX][testY] == '#' then
return false
end
return true
end
Well this
kind of works... but it crashes sometimes and doesn't seem to work quite right. So, what can we do? It may be helpful to know more about what's going on than what is shown on the screen. We can use Lua's
print function to print variable values to the screen. If you're using Windows, check out
t.console, otherwise you can run LÖVE from the command line to see output from
print.
Code: Select all
function testMap(x, y)
local testX = player.grid_x / 16 + x
local testY = player.grid_y / 16 + y
print('player.grid_y: '..player.grid_y)
print('player.grid_x: '..player.grid_x)
print('x: '..x)
print('y: '..y)
print('testX: '..testX)
print('testY: '..testY)
print('TileTable[testX][testY]: '..TileTable[testX][testY])
if TileTable[testX][testY] == '-' or
TileTable[testX][testY] == '#' then
return false
end
return true
end
The top-left corner of
TileTable is
TileTable[1][1].
Let's say player.grid_x is at 16 (the second tile from the left of the screen, also the starting position) and the player moves left. What happens?
Code: Select all
local testX = player.grid_x / 16 + x
testX will be 0... which isn't quite what we want. Let's add 1 to
testX and
testY.
Code: Select all
local testX = player.grid_x / 16 + x
local testY = player.grid_y / 16 + y
It works! Well, unless the player goes off the screen, meaning
TileTable[testX][testY] doesn't exist. To check this, we need to test whether
TileTable[testX][testY] is
true (which it will be if it isn't
nil or
false), and before that, whether
TileTable[testX] is true (because if
testX is out of range,
TileTable[testX][testY] will be looking for
testY in something which doesn't exist,
TileTable[testX].)
Code: Select all
function testMap(x, y)
local testX = player.grid_x / 16 + x + 1
local testY = player.grid_y / 16 + y + 1
print('player.grid_y: '..player.grid_y)
print('player.grid_x: '..player.grid_x)
print('x: '..x)
print('y: '..y)
print('testX: '..testX)
print('testY: '..testY)
if not TileTable[testX] or
not TileTable[testX][testY] then
print(string.format('TileTable[%s][%s] doesn\'t exist!', testX, testY))
else
print('TileTable[testX][testY]: '..TileTable[testX][testY])
end
if not TileTable[testX] or
not TileTable[testX][testY] or
TileTable[testX][testY] == '-' or
TileTable[testX][testY] == '#' then
return false
end
return true
end
(For more information on string.format as well as other string functions, check out
String Library Tutorial on the lua-users wiki.)
For understandability, instead of having the number
16 everywhere, you can give it a name and use that instead, perhaps in ALL CAPS to signify that it's a global variable which won't change.
You may or may not, depending on what the rest of your game will be like, also like to store the player's position as tile co-ordinates rather than an absolute position. For example, instead of the player being at
player.grid_x being 16 and
player.grid_y being 32, they would be 1 and 2 respectively.
Here are some changes you could make to do this:
Code: Select all
player = { grid_x = 2, grid_y = 2, act_x = 32, act_y = 32, speed = 10 }
Code: Select all
function updatePlayer(dt)
player.act_y = player.act_y - ((player.act_y - player.grid_y * TILESIZE) * player.speed * dt)
player.act_x = player.act_x - ((player.act_x - player.grid_x * TILESIZE) * player.speed * dt)
end
Code: Select all
function testMap(x, y)
local testX = player.grid_x + x
local testY = player.grid_y + y
Code: Select all
if testMap(0, -1) then
player.grid_y = player.grid_y - 1
end
etc.
Code: Select all
function love.draw()
drawMap()
love.graphics.rectangle("fill", player.act_x - TILESIZE, player.act_y - TILESIZE, TILESIZE, TILESIZE)
end
Depending on what else you're doing this might be easier. Or, it might not be.
I hope this helps!