Reputation: 75
I am making a platformer where i am generating level with below code:
function LevelMaker.generateLevel3(width, height)
local tiles = {}
local objects = {}
local entities = {}
for y = 1, height do
table.insert(tiles, {})
for x = 1, width do
if y == 9 and (x > 5 and x < 12) then
table.insert(tiles[y], Tile(x, y, math.random(1, 3)))
elseif (y == 12) and (x > 11 and x < 30) then
table.insert(tiles[y], Tile(x, y, math.random(1, 3)))
elseif (y == 3) and (x == 13) then
table.insert(tiles[y], Tile(x, y, math.random(1, 3)))
elseif (y == 17) and (x > 15 and x < 28) then
table.insert(tiles[y], Tile(x, y, math.random(1, 3)))
elseif (y == 9) and (x > 31 and x < 35) then
table.insert(tiles[y], Tile(x, y, math.random(1, 3)))
elseif (y == 6) and (x > 25 and x < 29) then
table.insert(tiles[y], Tile(x, y, math.random(1, 3)))
elseif (y > 1 and y < 7) and (x == 26) then
table.insert(tiles[y], Tile(x, y, math.random(1, 3)))
elseif (y == 0) and (x > 3 and x < 10) then
table.insert(tiles[y], Tile(x, y, math.random(1, 3)))
elseif (y == 13) and (x > 22 and x < 30) then
table.insert(tiles[y], Tile(x, y, SKY))
table.insert(objects,
GameObject{
texture = 'spikes',
x = (x - 1) * TILE_SIZE, y = (y - 1) * TILE_SIZE,
width = TILE_SIZE, height = TILE_SIZE,
frame = 2,
collidable = true,
solid = true,
deadly = true
}
)
elseif (y == 3) and (x == 12) then
table.insert(tiles[y], Tile(x, y, SKY))
table.insert(objects,
GameObject{
texture = 'spikes',
x = (x - 1) * TILE_SIZE, y = (y - 1) * TILE_SIZE,
width = TILE_SIZE, height = TILE_SIZE,
frame = 4,
collidable = true,
solid = true,
deadly = true
}
)
elseif (y == 2 or y == 4) and (x == 13) then
table.insert(tiles[y], Tile(x, y, SKY))
table.insert(objects,
GameObject{
texture = 'spikes',
x = (x - 1) * TILE_SIZE, y = (y - 1) * TILE_SIZE,
width = TILE_SIZE, height = TILE_SIZE,
frame = y == 2 and 1 or 2,
collidable = true,
solid = true,
deadly = true
}
)
elseif (y == 8) and (x == 10 or x == 11) then
table.insert(tiles[y], Tile(x, y, SKY))
table.insert(objects,
GameObject{
texture = 'spikes',
x = (x - 1) * TILE_SIZE, y = (y - 1) * TILE_SIZE,
width = TILE_SIZE, height = TILE_SIZE,
frame = 1,
collidable = true,
solid = true,
deadly = true
}
)
elseif (y > 1 and y < 7) and (x == 25) then
table.insert(tiles[y], Tile(x, y, SKY))
table.insert(objects,
GameObject{
texture = 'spikes',
x = (x - 1) * TILE_SIZE, y = (y - 1) * TILE_SIZE,
width = TILE_SIZE, height = TILE_SIZE,
frame = 4,
collidable = true,
solid = true,
deadly = true
}
)
elseif (y == 8) and (x == 34) then
table.insert(tiles[y], Tile(x, y, SKY))
table.insert(objects,
GameObject{
texture = 'spikes',
x = (x - 1) * TILE_SIZE, y = (y - 1) * TILE_SIZE,
width = TILE_SIZE, height = TILE_SIZE,
frame = 1,
collidable = true,
solid = true,
deadly = true
}
)
elseif (y == 1) and (x > 3 and x < 10) then
table.insert(tiles[y], Tile(x, y, SKY))
table.insert(objects,
GameObject{
texture = 'spikes',
x = (x - 1) * TILE_SIZE, y = (y - 1) * TILE_SIZE,
width = TILE_SIZE, height = TILE_SIZE,
frame = 2,
collidable = true,
solid = true,
deadly = true
}
)
else
table.insert(tiles[y], Tile(x, y, SKY))
end
end
end
table.insert(objects,
GameObject{
texture = 'house',
x = (16 - 1) * TILE_SIZE, y = (13 - 1) * TILE_SIZE,
width = 36, height = 44,
frame = 1,
}
)
table.insert(objects,
GameObject{
texture = 'gems',
x = (28 - 1) * TILE_SIZE, y = (5 - 1) * TILE_SIZE,
width = 15, height = 11,
frame = {1,2,3,4,5},
}
)
local map = TileMap(width, height)
map.tiles = tiles
return GameLevel(entities, objects, map)
end
Is there a way to improve the same above code (improve time complexity) When the player dies over and over within 1-2 sec the game freezes. I want to load the level as fast as possible
Upvotes: 1
Views: 210
Reputation: 11191
What sticks out to me is that you're running two nested for loops over X and Y just to draw a couple lines, then checking whether the points are on the line using range checks to eventually place tiles; the only thing that seems to be randomized is the tile type, but not the tile position. You should store a list of lines and draw each line on the screen with randomized tiles:
for y = 1, height do -- prepare the grid
table.insert(tiles, {})
end
local lines = {{from = 6, to = 11, y = 9}, {from = ..., to = ...}, {...}, ...}
for _, line in pairs(lines) do -- draw lines
if line.y then
for x = line.from, line.to do
table.insert(tiles[line.y], Tile(x, line.y, math.random(1, 3)))
end
elseif line.x then
for y = line.from, line.to do
table.insert(tiles[y], Tile(line.x, y, math.random(1, 3)))
end
end
end
the fixed sky/spikes/house/gems tiles can benefit from the same technique; you'll have to store a line tile type with each line and use it instead of the random tile though. These seem to be static though - why can't you just reuse the old level and replace only the randomized tiles using the described "line drawing" technique?
Upvotes: 1