Compare commits
23 Commits
97de68e34b
...
Chunk
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
577b7576cf | ||
|
|
fa4b2c86b5 | ||
|
|
e8cef497d4 | ||
|
|
b3a12305da | ||
|
|
236e23177d | ||
|
|
4d94cc805d | ||
|
|
9c4b5431ee | ||
|
|
ba1c0f0c89 | ||
|
|
ef632d50ee | ||
|
|
5bcf25a461 | ||
|
|
1039479c47 | ||
|
|
62555b4526 | ||
|
|
a4af57ca6c | ||
|
|
5189bef537 | ||
|
|
eab4cbbcdc | ||
|
|
829963e080 | ||
|
|
82246dc0c6 | ||
|
|
3a5e0b395b | ||
|
|
feed65cf6d | ||
|
|
1883bcd78b | ||
|
|
3c1746d914 | ||
|
|
f091fba9f7 | ||
|
|
27f1dc71c0 |
@@ -77,3 +77,16 @@ function Camera:positionAt(x,y)
|
|||||||
self.pos.y = math.floor((y/self.height)*self.height)
|
self.pos.y = math.floor((y/self.height)*self.height)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
-- translate screen coordinates to game coordinates
|
||||||
|
function Camera:ptScreenToGame(pt)
|
||||||
|
return self.pos + pt
|
||||||
|
end
|
||||||
|
|
||||||
|
function Camera:mouseScreenPos()
|
||||||
|
return Point:new(love.mouse.getX(),love.mouse.getY()) / game.scale
|
||||||
|
end
|
||||||
|
|
||||||
|
-- return the mouse position as game coordinates
|
||||||
|
function Camera:mouseGamePos()
|
||||||
|
return self:ptScreenToGame(self:mouseScreenPos())
|
||||||
|
end
|
||||||
|
|||||||
51
code/chunk.lua
Normal file
51
code/chunk.lua
Normal file
@@ -0,0 +1,51 @@
|
|||||||
|
-- pieces of levels
|
||||||
|
|
||||||
|
Chunk = {all = {}}
|
||||||
|
Chunk.__index = Chunk
|
||||||
|
|
||||||
|
-- CLASS METHODS
|
||||||
|
|
||||||
|
-- box == nil for global chunks
|
||||||
|
function Chunk:new(filename, box)
|
||||||
|
local o = { filename = filename, box = box }
|
||||||
|
setmetatable(o, self)
|
||||||
|
self.all[o] = true
|
||||||
|
end
|
||||||
|
|
||||||
|
function Chunk:getExportList()
|
||||||
|
local r = {}
|
||||||
|
for chunk in pairs(self.all) do
|
||||||
|
table.insert(r, {chunk.filename, chunk.box})
|
||||||
|
end
|
||||||
|
return r
|
||||||
|
end
|
||||||
|
|
||||||
|
-- INSTANCE METHODS
|
||||||
|
|
||||||
|
function Chunk:containsPoint(pt)
|
||||||
|
return self.box == nil or self.box:containsPoint(pt)
|
||||||
|
end
|
||||||
|
|
||||||
|
function Chunk:load()
|
||||||
|
if self.loaded then
|
||||||
|
return
|
||||||
|
end
|
||||||
|
logPrint("loading chunk "..self.filename)
|
||||||
|
self.data = dofile(level_current.."/chunks/"..self.filename)
|
||||||
|
self.loaded = { rooms = {}, collisions = {} }
|
||||||
|
LevelTiles = self.data.tiles
|
||||||
|
indexLevelTiles()
|
||||||
|
optimizeTileObjects(self.loaded.collisions)
|
||||||
|
|
||||||
|
for _, v in ipairs(self.data.rooms or {}) do
|
||||||
|
local room = Collision:new(v[1],v[2],v[3],v[4])
|
||||||
|
table.insert(self.data.rooms, room)
|
||||||
|
table.insert(LoadedObjects.Rooms, room)
|
||||||
|
end
|
||||||
|
logPrint("loaded chunk with "..#self.loaded.collisions.." collisions")
|
||||||
|
end
|
||||||
|
|
||||||
|
function Chunk:save(chunkdir)
|
||||||
|
return love.filesystem.write(chunkdir.."/"..self.filename, "return "..serialize_lua_value(self.data))
|
||||||
|
end
|
||||||
|
|
||||||
@@ -88,3 +88,7 @@ function Collision:draw(color)
|
|||||||
love.graphics.setColor(0,1,90,0.5)
|
love.graphics.setColor(0,1,90,0.5)
|
||||||
love.graphics.rectangle("line",self.from.x-Camera.pos.x, self.from.y-Camera.pos.y, self.width, self.height)
|
love.graphics.rectangle("line",self.from.x-Camera.pos.x, self.from.y-Camera.pos.y, self.width, self.height)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
function Collision:asRect()
|
||||||
|
return Rect:fromCoords(self.from.x, self.from.y, self.to.x, self.to.y)
|
||||||
|
end
|
||||||
|
|||||||
@@ -1,17 +1,37 @@
|
|||||||
assert(editor == nil)
|
assert(editor == nil)
|
||||||
editor = {
|
editor = {
|
||||||
|
active = false,
|
||||||
room_mode = false,
|
room_mode = false,
|
||||||
--palette_mode = false,
|
|
||||||
palette = {
|
palette = {
|
||||||
active = false,
|
active = false,
|
||||||
scroll = Point:new(0, 0),
|
scroll = Point:new(0, 0),
|
||||||
},
|
},
|
||||||
|
multiselect = {
|
||||||
|
active = false,
|
||||||
|
sweeping = false,
|
||||||
|
box = nil,
|
||||||
|
},
|
||||||
pan = { fixed = false, speed = 3 },
|
pan = { fixed = false, speed = 3 },
|
||||||
}
|
}
|
||||||
|
|
||||||
function stepEditor()
|
function stepEditor()
|
||||||
|
|
||||||
animateTiles()
|
animateTiles()
|
||||||
|
|
||||||
|
local osweep = editor.multiselect.sweeping
|
||||||
|
editor.multiselect.sweeping = Keybind:checkDown(Keybind.editor.entity_select)
|
||||||
|
frameDebug("sweeping: "..tostring(editor.multiselect.sweeping))
|
||||||
|
if editor.multiselect.sweeping and not editor.multiselect.active then
|
||||||
|
print("multiselect enabled")
|
||||||
|
editor.multiselect.active = true
|
||||||
|
end
|
||||||
|
if not osweep and osweep ~= editor.multiselect.sweeping then
|
||||||
|
editor.multiselect.box = nil
|
||||||
|
end
|
||||||
|
if editor.multiselect.active then
|
||||||
|
doEditorMultiselect()
|
||||||
|
end
|
||||||
|
|
||||||
if Keybind:checkPressed(Keybind.editor.room_mode) then
|
if Keybind:checkPressed(Keybind.editor.room_mode) then
|
||||||
if love.keyboard.isDown("lshift") then
|
if love.keyboard.isDown("lshift") then
|
||||||
editor.room_mode = "delete"
|
editor.room_mode = "delete"
|
||||||
@@ -80,7 +100,7 @@ function stepEditor()
|
|||||||
if name_prompt.canceled then return end
|
if name_prompt.canceled then return end
|
||||||
Prompt:new({
|
Prompt:new({
|
||||||
name = "filename",
|
name = "filename",
|
||||||
input = "level.lua",
|
input = "unnamed_level",
|
||||||
func = function(file_prompt)
|
func = function(file_prompt)
|
||||||
if file_prompt.canceled then return end
|
if file_prompt.canceled then return end
|
||||||
exportLevel(name_prompt.input, file_prompt.input)
|
exportLevel(name_prompt.input, file_prompt.input)
|
||||||
@@ -89,13 +109,6 @@ function stepEditor()
|
|||||||
end,
|
end,
|
||||||
}):activate()
|
}):activate()
|
||||||
end
|
end
|
||||||
|
|
||||||
if Keybind:checkPressed(Keybind.debug.editor) then
|
|
||||||
editor_mode = not editor_mode
|
|
||||||
deselectSpawns()
|
|
||||||
createTileObjects()
|
|
||||||
restartGame()
|
|
||||||
end
|
|
||||||
end
|
end
|
||||||
|
|
||||||
function scrollEditor(y)
|
function scrollEditor(y)
|
||||||
@@ -128,6 +141,10 @@ function drawEditor()
|
|||||||
if editor.palette.active then
|
if editor.palette.active then
|
||||||
doEditorPalette()
|
doEditorPalette()
|
||||||
end
|
end
|
||||||
|
if editor.multiselect.box ~= nil then
|
||||||
|
frameDebug("drawing multiselect "..tostring(editor.multiselect.box))
|
||||||
|
drawEditorMultiselect()
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
function doEditorEdit()
|
function doEditorEdit()
|
||||||
@@ -204,7 +221,9 @@ function doEditorEdit()
|
|||||||
else
|
else
|
||||||
if Keybind:checkDown(Keybind.editor.entity_select) then
|
if Keybind:checkDown(Keybind.editor.entity_select) then
|
||||||
deselectSpawns()
|
deselectSpawns()
|
||||||
selectSpawns(mouse_x,mouse_y)
|
if editor.multiselect.box then
|
||||||
|
selectSpawns(editor.multiselect.box)
|
||||||
|
end
|
||||||
end
|
end
|
||||||
if Keybind:checkDown(Keybind.editor.entity_move) then
|
if Keybind:checkDown(Keybind.editor.entity_move) then
|
||||||
moveSpawns(mouse_x,mouse_y)
|
moveSpawns(mouse_x,mouse_y)
|
||||||
@@ -353,7 +372,21 @@ end
|
|||||||
|
|
||||||
function drawEditorRooms()
|
function drawEditorRooms()
|
||||||
for _, room in pairs(LoadedObjects.Rooms) do
|
for _, room in pairs(LoadedObjects.Rooms) do
|
||||||
love.graphics.setColor(0,0,100,1)
|
love.graphics.setColor(0,0,1,1)
|
||||||
love.graphics.rectangle("line",room.from.x-Camera.pos.x, room.from.y-Camera.pos.y, room.width, room.height)
|
room:asRect():draw("line")
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
function drawEditorMultiselect()
|
||||||
|
love.graphics.setColor(0,1,1,1)
|
||||||
|
editor.multiselect.box:draw("line")
|
||||||
|
end
|
||||||
|
|
||||||
|
function doEditorMultiselect()
|
||||||
|
local mousept = Camera:mouseGamePos()
|
||||||
|
if editor.multiselect.box == nil then
|
||||||
|
editor.multiselect.box = Rect:fromPoints(mousept, mousept)
|
||||||
|
elseif editor.multiselect.sweeping then
|
||||||
|
editor.multiselect.box.max = mousept
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|||||||
@@ -36,20 +36,30 @@ function Arrow:drawBackground()
|
|||||||
end
|
end
|
||||||
|
|
||||||
function Arrow:doPhysics()
|
function Arrow:doPhysics()
|
||||||
if not self:isCollidingAt(self.pos.x + self.vel.x, self.pos.y, LoadedObjects.Collisions) then
|
-- horizontal collision
|
||||||
self.pos.x = self.pos.x + self.vel.x
|
self:moveX(
|
||||||
else
|
self.vel.x,
|
||||||
self.stuck = true
|
function()
|
||||||
end
|
self.stuck = true
|
||||||
if not self:isCollidingAt(self.pos.x, self.pos.y + self.vel.y, LoadedObjects.Collisions) then
|
end
|
||||||
self.pos.y = self.pos.y + self.vel.y
|
)
|
||||||
else
|
|
||||||
self.stuck = true
|
if not self.stuck then
|
||||||
|
-- vertical collision
|
||||||
|
self:moveY(
|
||||||
|
self.vel.y,
|
||||||
|
function()
|
||||||
|
self.stuck = true
|
||||||
|
end
|
||||||
|
)
|
||||||
end
|
end
|
||||||
|
|
||||||
if self.stuck then
|
if self.stuck then
|
||||||
self.pos.x = self.pos.x + self.vel.x * (2/3)
|
self.pos.x = self.pos.x + self.vel.x * (2/3)
|
||||||
self.pos.y = self.pos.y + self.vel.y * (2/3)
|
self.pos.y = self.pos.y + self.vel.y * (2/3)
|
||||||
self.vel.x = 0
|
self.vel.x = 0
|
||||||
self.vel.y = 0
|
self.vel.y = 0
|
||||||
end
|
end
|
||||||
|
|
||||||
|
self:adjustLight()
|
||||||
end
|
end
|
||||||
|
|||||||
@@ -67,6 +67,13 @@ function CursedBook:doLogic()
|
|||||||
elseif self.status == 4 then
|
elseif self.status == 4 then
|
||||||
|
|
||||||
end
|
end
|
||||||
|
|
||||||
|
if self.isFlying then
|
||||||
|
local random_x = math.random(-4, 4)/100
|
||||||
|
local random_y = math.random(-4, 4)/100
|
||||||
|
self.vel.x = self.vel.x + random_x
|
||||||
|
self.vel.y = self.vel.y + random_y
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
function CursedBook:handleAnimation()
|
function CursedBook:handleAnimation()
|
||||||
@@ -101,15 +108,21 @@ function CursedBook:handleAnimation()
|
|||||||
end
|
end
|
||||||
|
|
||||||
function CursedBook:doPhysics()
|
function CursedBook:doPhysics()
|
||||||
if self.isFlying then
|
-- horizontal collision
|
||||||
local random_x = math.random(-4, 4)/100
|
self:moveX(
|
||||||
local random_y = math.random(-4, 4)/100
|
self.vel.x,
|
||||||
self.vel.x = self.vel.x + random_x
|
function()
|
||||||
self.vel.y = self.vel.y + random_y
|
self.vel.x = 0
|
||||||
end
|
end
|
||||||
-- move
|
)
|
||||||
|
-- vertical collision
|
||||||
self:moveWithCollision()
|
self:moveY(
|
||||||
|
self.vel.y,
|
||||||
|
function()
|
||||||
|
self.vel.y = 0
|
||||||
|
end
|
||||||
|
)
|
||||||
|
-- final position
|
||||||
self:adjustLight()
|
self:adjustLight()
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|||||||
@@ -34,7 +34,6 @@ function Fairy:new(x,y)
|
|||||||
end
|
end
|
||||||
|
|
||||||
function Fairy:doLogic()
|
function Fairy:doLogic()
|
||||||
|
|
||||||
if self:checkVisionLine(main_player,self.vision_range) then
|
if self:checkVisionLine(main_player,self.vision_range) then
|
||||||
|
|
||||||
self.target.x = main_player.pos.x + main_player.target_offset.x
|
self.target.x = main_player.pos.x + main_player.target_offset.x
|
||||||
@@ -63,31 +62,19 @@ function Fairy:doLogic()
|
|||||||
|
|
||||||
local distance_x = self.target.x - self.pos.x
|
local distance_x = self.target.x - self.pos.x
|
||||||
local distance_y = self.target.y - self.pos.y
|
local distance_y = self.target.y - self.pos.y
|
||||||
local angle = getAngleFromVector(distance_x,distance_y)
|
local angle = getAngleFromVector(vector(distance_x,distance_y))
|
||||||
local distance = math.sqrt(distance_x ^ 2 + distance_y ^ 2)
|
local distance = math.sqrt(distance_x ^ 2 + distance_y ^ 2)
|
||||||
|
|
||||||
if distance < self.range then
|
if distance < self.range then
|
||||||
self.vel.x = self.vel.x * 0.9
|
local random_x = math.random(-1, 1)
|
||||||
self.vel.y = self.vel.y * 0.9
|
local random_y = math.random(-1, 1)
|
||||||
|
self.vel.x = self.vel.x * 0.9 + random_x/10
|
||||||
|
self.vel.y = self.vel.y * 0.9 + random_y/10
|
||||||
else
|
else
|
||||||
self.vel.x = math.cos(angle)*self.speed
|
local random_x = math.random(-6, 6)
|
||||||
self.vel.y = math.sin(angle)*self.speed
|
local random_y = math.random(-6, 6)
|
||||||
end
|
self.vel.x = math.cos(angle)*self.speed + random_x/10
|
||||||
self.particle_timer = self.particle_timer + 1
|
self.vel.y = math.sin(angle)*self.speed + random_y/10
|
||||||
if self.particle_timer >= self.particle_time then
|
|
||||||
self.particle_timer = 0
|
|
||||||
|
|
||||||
local particle_data = {
|
|
||||||
animation = animation.particle.simple,
|
|
||||||
animation_speed = 1,
|
|
||||||
sprite_tint = hex2rgb("#fed100"),
|
|
||||||
sprite_alpha_fade = true,
|
|
||||||
direction = angle-math.rad(180+math.random(60)-30),
|
|
||||||
speed = 0.8*(distance/50),
|
|
||||||
speed_increase = -0.01,
|
|
||||||
time = 0.75
|
|
||||||
}
|
|
||||||
Particle:new(self.pos.x,self.pos.y,particle_data)
|
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
@@ -95,19 +82,42 @@ function Fairy:handleAnimation()
|
|||||||
self.body:animate()
|
self.body:animate()
|
||||||
--if self:isCollidingWith(main_player) then self.sprite_tint = {1,0,0} else self.sprite_tint = {1,1,1} end
|
--if self:isCollidingWith(main_player) then self.sprite_tint = {1,0,0} else self.sprite_tint = {1,1,1} end
|
||||||
self:draw(self.body)
|
self:draw(self.body)
|
||||||
|
|
||||||
|
self.particle_timer = self.particle_timer + 1
|
||||||
|
if self.particle_timer >= self.particle_time then
|
||||||
|
local vector = vector(self.vel.x,self.vel.y)
|
||||||
|
local angle = getAngleFromVector(vector)
|
||||||
|
self.particle_timer = 0
|
||||||
|
local particle_data = {
|
||||||
|
animation = animation.particle.simple,
|
||||||
|
animation_speed = 1,
|
||||||
|
sprite_tint = hex2rgb("#fed100"),
|
||||||
|
sprite_alpha_fade = true,
|
||||||
|
direction = angle-math.rad(180+math.random(60)-30),
|
||||||
|
speed = 1,
|
||||||
|
speed_increase = -0.01,
|
||||||
|
time = 0.75
|
||||||
|
}
|
||||||
|
Particle:new(self.pos.x,self.pos.y,particle_data)
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
function Fairy:doPhysics()
|
function Fairy:doPhysics()
|
||||||
local random_x = math.random(-4, 4)/10
|
-- horizontal collision
|
||||||
local random_y = math.random(-4, 4)/10
|
self:moveX(
|
||||||
|
self.vel.x,
|
||||||
self.vel.x = self.vel.x + random_x
|
function()
|
||||||
self.vel.y = self.vel.y + random_y
|
self.vel.x = 0
|
||||||
|
end
|
||||||
self:moveWithCollision()
|
)
|
||||||
self.vel.x = 0
|
-- vertical collision
|
||||||
self.vel.y = 0
|
self:moveY(
|
||||||
|
self.vel.y,
|
||||||
|
function()
|
||||||
|
self.vel.y = 0
|
||||||
|
end
|
||||||
|
)
|
||||||
|
-- final position
|
||||||
self:adjustLight()
|
self:adjustLight()
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|||||||
@@ -36,10 +36,6 @@ function HookAnchor:drawBackground()
|
|||||||
)
|
)
|
||||||
end
|
end
|
||||||
|
|
||||||
function HookAnchor:doPhysics()
|
|
||||||
end
|
|
||||||
|
|
||||||
|
|
||||||
function Fairy:debug()
|
function Fairy:debug()
|
||||||
Entity.debug(self)
|
Entity.debug(self)
|
||||||
end
|
end
|
||||||
|
|||||||
@@ -44,8 +44,9 @@ function Kupo:doLogic()
|
|||||||
self.target.y = main_player.pos.y - main_player.target_offset.y
|
self.target.y = main_player.pos.y - main_player.target_offset.y
|
||||||
local distance_x = self.target.x - self.pos.x
|
local distance_x = self.target.x - self.pos.x
|
||||||
local distance_y = self.target.y - self.pos.y
|
local distance_y = self.target.y - self.pos.y
|
||||||
|
|
||||||
local distance = math.sqrt(distance_x ^ 2 + distance_y ^ 2)
|
local distance = math.sqrt(distance_x ^ 2 + distance_y ^ 2)
|
||||||
local angle = getAngleFromVector(distance_x,distance_y)
|
local angle = getAngleFromVector(vector(distance_x,distance_y))
|
||||||
self.draw_bow = false
|
self.draw_bow = false
|
||||||
if distance <= self.range then
|
if distance <= self.range then
|
||||||
if self.hostile == true then
|
if self.hostile == true then
|
||||||
@@ -153,7 +154,3 @@ function Kupo:handleAnimation()
|
|||||||
)
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
function Kupo:doPhysics()
|
|
||||||
self:moveWithCollision()
|
|
||||||
end
|
|
||||||
|
|||||||
@@ -21,8 +21,14 @@ function Particle:new(x,y,particle_data)
|
|||||||
o.sprite_flip = particle_data.sprite_flip or o.sprite_flip
|
o.sprite_flip = particle_data.sprite_flip or o.sprite_flip
|
||||||
|
|
||||||
o.time = particle_data.time or nil
|
o.time = particle_data.time or nil
|
||||||
if o.time ~= nil then o.time = o.time * game.framerate end
|
if o.time ~= nil then
|
||||||
|
if particle_data.time_unit ~= nil
|
||||||
|
and particle_data.time_unit == "frames" then
|
||||||
|
o.time = o.time
|
||||||
|
else
|
||||||
|
o.time = o.time * game.framerate
|
||||||
|
end
|
||||||
|
end
|
||||||
o.timer = 0
|
o.timer = 0
|
||||||
|
|
||||||
o.vel = {
|
o.vel = {
|
||||||
@@ -83,26 +89,32 @@ function Particle:handleAnimation()
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
function Particle:doPhysics()
|
function Particle:doLogic()
|
||||||
-- adjust speed
|
-- adjust speed
|
||||||
if self.speed_increase ~= 0 then
|
if self.speed_increase ~= 0 then
|
||||||
self.speed = self.speed + self.speed_increase
|
self.speed = self.speed + self.speed_increase
|
||||||
self.vel.x = self.speed * math.cos(self.direction)
|
self.vel.x = self.speed * math.cos(self.direction)
|
||||||
self.vel.y = self.speed * math.sin(self.direction)
|
self.vel.y = self.speed * math.sin(self.direction)
|
||||||
end
|
end
|
||||||
-- move
|
|
||||||
self:moveWithCollision()
|
|
||||||
|
|
||||||
if self.light ~= nil then
|
|
||||||
self:adjustLight()
|
|
||||||
self.light.range = self.light_range * self.sprite_alpha/2
|
|
||||||
end
|
|
||||||
|
|
||||||
if self.time ~= nil then
|
if self.time ~= nil then
|
||||||
if self.timer >= self.time then self:kill() end
|
if self.timer >= self.time then self:kill() end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
function Particle:doPhysics()
|
||||||
|
-- horizontal collision
|
||||||
|
self:moveX(
|
||||||
|
self.vel.x
|
||||||
|
)
|
||||||
|
-- vertical collision
|
||||||
|
self:moveY(
|
||||||
|
self.vel.y
|
||||||
|
)
|
||||||
|
-- final position
|
||||||
|
self:adjustLight()
|
||||||
|
end
|
||||||
|
|
||||||
function Particle:debug()
|
function Particle:debug()
|
||||||
-- draw center CYAN
|
-- draw center CYAN
|
||||||
love.graphics.setColor(0,1,1)
|
love.graphics.setColor(0,1,1)
|
||||||
|
|||||||
@@ -155,7 +155,7 @@ function Player:doLogic()
|
|||||||
end
|
end
|
||||||
|
|
||||||
-- set dash values
|
-- set dash values
|
||||||
self.dashDirection = getAngleFromVector(horizontal, vertical)
|
self.dashDirection = getAngleFromVector(vector(horizontal, vertical))
|
||||||
self.dash_timer = math.floor(self.dash_time * game.framerate)
|
self.dash_timer = math.floor(self.dash_time * game.framerate)
|
||||||
end
|
end
|
||||||
else
|
else
|
||||||
@@ -232,10 +232,10 @@ function Player:doPhysics()
|
|||||||
-- hook state
|
-- hook state
|
||||||
if self.is_hooked then
|
if self.is_hooked then
|
||||||
self.move_x = 0
|
self.move_x = 0
|
||||||
local hook = vector(self.pos.x, self.pos.y, self.hook_anchor.x, self.hook_anchor.y)
|
local hook = vector(self.hook_anchor.x - self.pos.x, self.hook_anchor.y - self.pos.y)
|
||||||
local dist = math.min(getVectorValue(hook), self.hook_distance)
|
local dist = math.min(getVectorValue(hook), self.hook_distance)
|
||||||
|
|
||||||
local hook_angle = getAngleFromVector(hook[1],hook[2])-math.rad(180)
|
local hook_angle = getAngleFromVector(hook)-math.rad(180)
|
||||||
|
|
||||||
if Keybind:checkDown(Keybind.move.right) then
|
if Keybind:checkDown(Keybind.move.right) then
|
||||||
hook_angle = hook_angle - self.hook_swing_speed
|
hook_angle = hook_angle - self.hook_swing_speed
|
||||||
@@ -251,7 +251,8 @@ function Player:doPhysics()
|
|||||||
animation_speed = 0,
|
animation_speed = 0,
|
||||||
sprite_tint = hex2rgb("#fed100"),
|
sprite_tint = hex2rgb("#fed100"),
|
||||||
sprite_alpha = 0.5,
|
sprite_alpha = 0.5,
|
||||||
time = 0.05,
|
time = 4,
|
||||||
|
time_unit = "frames",
|
||||||
sprite_flip = {
|
sprite_flip = {
|
||||||
x = self.sprite_flip.x,
|
x = self.sprite_flip.x,
|
||||||
y = self.sprite_flip.y
|
y = self.sprite_flip.y
|
||||||
@@ -263,8 +264,13 @@ function Player:doPhysics()
|
|||||||
local pos_y = self.hook_anchor.y + dist * math.sin(hook_angle)
|
local pos_y = self.hook_anchor.y + dist * math.sin(hook_angle)
|
||||||
self.vel.x = self.vel.x + pos_x - self.pos.x
|
self.vel.x = self.vel.x + pos_x - self.pos.x
|
||||||
self.vel.y = self.vel.y + pos_y - self.pos.y
|
self.vel.y = self.vel.y + pos_y - self.pos.y
|
||||||
self.pos.x = pos_x
|
|
||||||
self.pos.y = pos_y
|
self:moveX(
|
||||||
|
pos_x - self.pos.x
|
||||||
|
)
|
||||||
|
self:moveY(
|
||||||
|
pos_y - self.pos.y
|
||||||
|
)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
||||||
@@ -275,24 +281,26 @@ function Player:doPhysics()
|
|||||||
end
|
end
|
||||||
|
|
||||||
-- horizontal collision
|
-- horizontal collision
|
||||||
if not self:isCollidingAt(self.pos.x + self.vel.x, self.pos.y, LoadedObjects.Collisions) then
|
self.wall_hit = 0
|
||||||
self.pos.x = self.pos.x + self.vel.x
|
self:moveX(
|
||||||
self.wall_hit = 0
|
self.vel.x,
|
||||||
else
|
function()
|
||||||
self.wall_hit = math.sign(self.vel.x)
|
self.wall_hit = math.sign(self.vel.x)
|
||||||
self.vel.x = 0
|
self.vel.x = 0
|
||||||
end
|
end
|
||||||
|
)
|
||||||
|
|
||||||
-- vertical collision
|
-- vertical collision
|
||||||
if not self:isCollidingAt(self.pos.x, self.pos.y + self.vel.y, LoadedObjects.Collisions) then
|
self:moveY(
|
||||||
self.pos.y = self.pos.y + self.vel.y
|
self.vel.y,
|
||||||
else
|
function()
|
||||||
if self.vel.y > 0 then
|
if self.vel.y > 0 then
|
||||||
self.is_on_ground = true
|
self.is_on_ground = true
|
||||||
self.dash_count = self.dash_amount
|
self.dash_count = self.dash_amount
|
||||||
|
end
|
||||||
|
self.vel.y = 0
|
||||||
end
|
end
|
||||||
self.vel.y = 0
|
)
|
||||||
end
|
|
||||||
|
|
||||||
-- if u collision w hazard, respawn
|
-- if u collision w hazard, respawn
|
||||||
if self:isCollidingAt(self.pos.x, self.pos.y, LoadedObjects.Hazards) then
|
if self:isCollidingAt(self.pos.x, self.pos.y, LoadedObjects.Hazards) then
|
||||||
@@ -326,10 +334,10 @@ function Player:handleAnimation()
|
|||||||
elseif self.vel.y < 0 then
|
elseif self.vel.y < 0 then
|
||||||
self.body = self.body:change(animation.nancy.jump)
|
self.body = self.body:change(animation.nancy.jump)
|
||||||
self.mask = self.mask:change(self.mask_type.jump)
|
self.mask = self.mask:change(self.mask_type.jump)
|
||||||
elseif self.vel.x + self.move_x ~= 0 then
|
elseif self.vel.x + self.move_x ~= 0 and not self.is_hooked then
|
||||||
self.body = self.body:change(animation.nancy.run)
|
self.body = self.body:change(animation.nancy.run)
|
||||||
self.mask = self.mask:change(self.mask_type.run)
|
self.mask = self.mask:change(self.mask_type.run)
|
||||||
else
|
elseif not self.is_hooked then
|
||||||
self.body = self.body:change(animation.nancy.idle)
|
self.body = self.body:change(animation.nancy.idle)
|
||||||
self.mask = self.mask:change(self.mask_type.idle)
|
self.mask = self.mask:change(self.mask_type.idle)
|
||||||
end
|
end
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ function Entity:new(x,y)
|
|||||||
local o = {}
|
local o = {}
|
||||||
|
|
||||||
o.pos = {x = x, y = y}
|
o.pos = {x = x, y = y}
|
||||||
|
o.move_remainder = {x = 0, y = 0}
|
||||||
o.vel = {x = 0, y = 0}
|
o.vel = {x = 0, y = 0}
|
||||||
|
|
||||||
o.direction = 0
|
o.direction = 0
|
||||||
@@ -69,24 +70,53 @@ end
|
|||||||
function Entity:doLogic()
|
function Entity:doLogic()
|
||||||
end
|
end
|
||||||
|
|
||||||
function Entity:move()
|
function Entity:moveX(amount, func)
|
||||||
self.pos.x = self.pos.x + self.vel.x
|
self.move_remainder.x = self.move_remainder.x + amount
|
||||||
self.pos.y = self.pos.y + self.vel.y
|
local move = math.round(self.move_remainder.x)
|
||||||
|
if move ~= 0 then
|
||||||
|
self.move_remainder.x = self.move_remainder.x - move
|
||||||
|
local sign = math.sign(move)
|
||||||
|
while math.round(move) ~= 0 do
|
||||||
|
if not self:isCollidingAt(
|
||||||
|
self.pos.x + sign,
|
||||||
|
self.pos.y,
|
||||||
|
LoadedObjects.Collisions
|
||||||
|
) then
|
||||||
|
self.pos.x = self.pos.x + sign
|
||||||
|
move = move - sign
|
||||||
|
if tostring(move) == "nan" then error() end
|
||||||
|
else
|
||||||
|
if func then
|
||||||
|
func()
|
||||||
|
end
|
||||||
|
break
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
function Entity:moveWithCollision()
|
function Entity:moveY(amount, func)
|
||||||
-- horizontal collision
|
self.move_remainder.y = self.move_remainder.y + amount
|
||||||
if not self:isCollidingAt(self.pos.x + self.vel.x, self.pos.y, LoadedObjects.Collisions) then
|
local move = math.round(self.move_remainder.y)
|
||||||
self.pos.x = self.pos.x + self.vel.x
|
if move ~= 0 then
|
||||||
else
|
self.move_remainder.y = self.move_remainder.y - move
|
||||||
self.vel.x = 0
|
local sign = math.sign(move)
|
||||||
end
|
while math.round(move) ~= 0 do
|
||||||
|
if not self:isCollidingAt(
|
||||||
-- vertical collision
|
self.pos.x,
|
||||||
if not self:isCollidingAt(self.pos.x, self.pos.y + self.vel.y, LoadedObjects.Collisions) then
|
self.pos.y + sign,
|
||||||
self.pos.y = self.pos.y + self.vel.y
|
LoadedObjects.Collisions
|
||||||
else
|
) then
|
||||||
self.vel.y = 0
|
self.pos.y = self.pos.y + sign
|
||||||
|
move = move - sign
|
||||||
|
if tostring(move) == "nan" then error() end
|
||||||
|
else
|
||||||
|
if func then
|
||||||
|
func()
|
||||||
|
end
|
||||||
|
break
|
||||||
|
end
|
||||||
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
@@ -120,8 +150,9 @@ function Entity:checkVisionLine(entity,range)
|
|||||||
|
|
||||||
local distance_x = target_x - self.pos.x
|
local distance_x = target_x - self.pos.x
|
||||||
local distance_y = target_y - self.pos.y
|
local distance_y = target_y - self.pos.y
|
||||||
|
local distance = vector(distance_x,distance_y)
|
||||||
|
|
||||||
local angle = getAngleFromVector(distance_x,distance_y)
|
local angle = getAngleFromVector(distance)
|
||||||
local distance = math.sqrt(distance_x ^ 2 + distance_y ^ 2)
|
local distance = math.sqrt(distance_x ^ 2 + distance_y ^ 2)
|
||||||
|
|
||||||
local is_colliding = true
|
local is_colliding = true
|
||||||
@@ -227,8 +258,9 @@ function Entity:checkVisionLineDebug(entity,range)
|
|||||||
|
|
||||||
local distance_x = target_x - self.pos.x
|
local distance_x = target_x - self.pos.x
|
||||||
local distance_y = target_y - self.pos.y
|
local distance_y = target_y - self.pos.y
|
||||||
|
local distance = vector(distance_x,distance_y)
|
||||||
|
|
||||||
local angle = getAngleFromVector(distance_x,distance_y)
|
local angle = getAngleFromVector(distance)
|
||||||
local distance = math.sqrt(distance_x ^ 2 + distance_y ^ 2)
|
local distance = math.sqrt(distance_x ^ 2 + distance_y ^ 2)
|
||||||
|
|
||||||
if distance < range then
|
if distance < range then
|
||||||
@@ -277,6 +309,9 @@ function Entity:debug()
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
function Entity:doPhysics()
|
||||||
|
end
|
||||||
|
|
||||||
function Entity:handleAnimation()
|
function Entity:handleAnimation()
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|||||||
@@ -53,10 +53,6 @@ function stepGame()
|
|||||||
initMenu("dialog",dialog_sequence.example)
|
initMenu("dialog",dialog_sequence.example)
|
||||||
end
|
end
|
||||||
|
|
||||||
if Keybind:checkPressed(Keybind.debug.editor) then
|
|
||||||
editor_mode = true
|
|
||||||
end
|
|
||||||
|
|
||||||
if Keybind:checkPressed(Keybind.debug.recording) then
|
if Keybind:checkPressed(Keybind.debug.recording) then
|
||||||
if DemoRecording then
|
if DemoRecording then
|
||||||
Demo:endRecord()
|
Demo:endRecord()
|
||||||
|
|||||||
@@ -20,7 +20,6 @@ function drawGameworldBackground()
|
|||||||
for i = 1, #LevelTiles do
|
for i = 1, #LevelTiles do
|
||||||
for j = 1, #LevelTiles[i] do
|
for j = 1, #LevelTiles[i] do
|
||||||
if LevelTiles[i][j].id ~= 0 then
|
if LevelTiles[i][j].id ~= 0 then
|
||||||
|
|
||||||
local depth = TileData[LevelTiles[i][j].id].depth
|
local depth = TileData[LevelTiles[i][j].id].depth
|
||||||
drawTile(
|
drawTile(
|
||||||
LevelTiles[i][j],
|
LevelTiles[i][j],
|
||||||
|
|||||||
129
code/in_out.lua
129
code/in_out.lua
@@ -1,90 +1,51 @@
|
|||||||
function exportLevel(levelname, filename)
|
function exportLevel(levelname, dirname)
|
||||||
love.filesystem.createDirectory("export")
|
dirname = "export/"..dirname
|
||||||
filename = filename or "output.lua"
|
|
||||||
if string.sub(filename, 1, 1) ~= "/" then
|
if love.filesystem.exists(dirname) then
|
||||||
filename = "export/"..filename
|
-- TODO: prompt to overwrite
|
||||||
|
error("file already exists")
|
||||||
|
end
|
||||||
|
|
||||||
|
local ok = love.filesystem.createDirectory(dirname)
|
||||||
|
if not ok then
|
||||||
|
logPrint("error creating directory")
|
||||||
end
|
end
|
||||||
exportFile = io.open(filename, "w+")
|
|
||||||
|
|
||||||
if exportFile then
|
|
||||||
logPrint("Exporting level \"".. levelname .. "\"...")
|
|
||||||
exportFile:write("return {")
|
|
||||||
|
|
||||||
logPrint("- level name")
|
logPrint("Exporting level \"".. levelname .. "\"...")
|
||||||
exportFile:write("\n name = \"" .. levelname .. "\",")
|
local exportTable = {}
|
||||||
|
exportTable.name = levelname
|
||||||
logPrint("- tileset")
|
exportTable.tileset = "library"
|
||||||
for k, v in pairs(tileset) do
|
exportTable.properties = LevelData.properties
|
||||||
if v == LevelData.tileset then
|
--exportTable.tiles = LevelTiles
|
||||||
exportFile:write("\n tileset = tileset." .. k .. ",")
|
--logPrint("- objects")
|
||||||
end
|
--exportTable.objects = { spawns = {}, rooms = {} }
|
||||||
end
|
--logPrint(" - spawns")
|
||||||
|
--for i, v in ipairs(LoadedObjects.Spawns) do
|
||||||
logPrint("- properties")
|
--exportTable.objects.spawns = {v.archetype.name,{},v.args}
|
||||||
exportFile:write("\n properties = {")
|
--end
|
||||||
logPrint(" - darkness: ".. tostring(LevelData.properties.darkness))
|
|
||||||
exportFile:write("\n darkness = " .. tostring(LevelData.properties.darkness))
|
--logPrint(" - rooms")
|
||||||
exportFile:write("\n },")
|
|
||||||
|
--for i, room in ipairs(LoadedObjects.Rooms) do
|
||||||
logPrint("- tiles")
|
--- table.insert(exportTable.objects.rooms,{room:asRect():getCoords()})
|
||||||
exportFile:write("\n tiles = {")
|
--end
|
||||||
local rows = #LevelTiles
|
exportTable.chunks = Chunk:getExportList()
|
||||||
for i = 1, #LevelTiles do
|
logPrint("Writing to file...")
|
||||||
if i > 1 then
|
local ok, err = love.filesystem.write(dirname.."/level.lua", "return "..serialize_lua_value(exportTable))
|
||||||
exportFile:write(", ")
|
|
||||||
end
|
if ok then
|
||||||
exportFile:write("\n { ")
|
logPrint("Saving chunks...")
|
||||||
for j = 1, #LevelTiles[i] do
|
local chunkdir = dirname.."/chunks"
|
||||||
if j ~= 1 then
|
love.filesystem.createDirectory(chunkdir)
|
||||||
exportFile:write(", ")
|
for chunk in pairs(Chunk.all) do
|
||||||
end
|
local ok, err = chunk:save(chunkdir)
|
||||||
exportFile:write(tostring(LevelTiles[i][j].id))
|
if not ok then error(err) end
|
||||||
end
|
end
|
||||||
exportFile:write("}")
|
logPrint("Exporting complete.")
|
||||||
logPrint(" - row "..i.."/"..rows.." "..math.floor(100*((i-1)*100/rows))/100 .."%")
|
else
|
||||||
end
|
-- TODO: clean up created files
|
||||||
exportFile:write("\n },")
|
logPrint("Exporting failed: "..err)
|
||||||
logPrint("- objects")
|
|
||||||
exportFile:write("\n objects = {")
|
|
||||||
logPrint(" - spawns")
|
|
||||||
exportFile:write("\n spawns = {")
|
|
||||||
for i, v in ipairs(LoadedObjects.Spawns) do
|
|
||||||
if i > 1 then
|
|
||||||
exportFile:write(",")
|
|
||||||
end
|
|
||||||
exportFile:write("\n {")
|
|
||||||
exportFile:write(v.archetype.type)
|
|
||||||
exportFile:write(",{")
|
|
||||||
for i=1, #v.args do
|
|
||||||
if i > 1 then
|
|
||||||
exportFile:write(",")
|
|
||||||
end
|
|
||||||
exportFile:write(v.args[i])
|
|
||||||
end
|
|
||||||
exportFile:write("}}")
|
|
||||||
end
|
|
||||||
exportFile:write("\n },")
|
|
||||||
logPrint(" - rooms")
|
|
||||||
exportFile:write("\n rooms = {")
|
|
||||||
for i, room in ipairs(LoadedObjects.Rooms) do
|
|
||||||
if i > 1 then
|
|
||||||
exportFile:write(",")
|
|
||||||
end
|
|
||||||
exportFile:write("\n {{")
|
|
||||||
exportFile:write(room.from.x)
|
|
||||||
exportFile:write(",")
|
|
||||||
exportFile:write(room.from.y)
|
|
||||||
exportFile:write("},{")
|
|
||||||
exportFile:write(room.to.x)
|
|
||||||
exportFile:write(",")
|
|
||||||
exportFile:write(room.to.y)
|
|
||||||
exportFile:write("}}")
|
|
||||||
end
|
|
||||||
exportFile:write("\n },")
|
|
||||||
exportFile:write("\n },")
|
|
||||||
logPrint("Exporting complete.")
|
|
||||||
exportFile:write("\n}")
|
|
||||||
exportFile:close()
|
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|||||||
@@ -17,6 +17,10 @@ Keybind.debug = {}
|
|||||||
Keybind.editor = {}
|
Keybind.editor = {}
|
||||||
Keybind.generic = {}
|
Keybind.generic = {}
|
||||||
|
|
||||||
|
function Keybind:isAvailable(action)
|
||||||
|
return not action.occupied
|
||||||
|
end
|
||||||
|
|
||||||
function Keybind:checkDown(action)
|
function Keybind:checkDown(action)
|
||||||
if DemoPlayback then
|
if DemoPlayback then
|
||||||
for _, demo_action in pairs(DemoAction[CurrentDemoFrame]) do
|
for _, demo_action in pairs(DemoAction[CurrentDemoFrame]) do
|
||||||
@@ -37,9 +41,11 @@ function Keybind:checkDown(action)
|
|||||||
if action.demo ~= nil then
|
if action.demo ~= nil then
|
||||||
Demo:recordAction(action.demo)
|
Demo:recordAction(action.demo)
|
||||||
end
|
end
|
||||||
|
action.occupied = true
|
||||||
return true
|
return true
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
action.occupied = false
|
||||||
return false
|
return false
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|||||||
104
code/level.lua
104
code/level.lua
@@ -1,7 +1,25 @@
|
|||||||
function loadLevelTiles()
|
function loadLevelTiles()
|
||||||
math.randomseed(3)
|
math.randomseed(3)
|
||||||
LevelData = dofile("data/levels/"..level_current)
|
level_current = "data/levels/level1"
|
||||||
|
LevelData = dofile(level_current.."/level.lua")
|
||||||
|
LoadedObjects.Collisions = {}
|
||||||
|
LoadedObjects.Platforms = {}
|
||||||
|
LoadedObjects.Ladders = {}
|
||||||
|
LoadedObjects.Hazards = {}
|
||||||
|
if type(LevelData.tileset) == "string" then
|
||||||
|
LevelData.tileset_name = LevelData.tileset
|
||||||
|
end
|
||||||
|
LevelData.tileset = tileset[LevelData.tileset_name]
|
||||||
|
|
||||||
|
getLevelTileData()
|
||||||
|
|
||||||
|
for _, v in ipairs(LevelData.chunks) do
|
||||||
|
Chunk:new(v[1], v[2])
|
||||||
|
end
|
||||||
|
local global_chunk = next(Chunk.all)
|
||||||
|
global_chunk:load()
|
||||||
|
LoadedObjects.Collisions = global_chunk.loaded.collisions
|
||||||
|
LevelTiles = global_chunk.data.tiles
|
||||||
--[[
|
--[[
|
||||||
on level format:
|
on level format:
|
||||||
|
|
||||||
@@ -12,26 +30,26 @@ function loadLevelTiles()
|
|||||||
overlay_depth = foreground/background overlay depth
|
overlay_depth = foreground/background overlay depth
|
||||||
type = collision type
|
type = collision type
|
||||||
]]
|
]]
|
||||||
getLevelTileData()
|
|
||||||
LevelTiles = LevelData.tiles
|
|
||||||
updateLevelDimensions()
|
updateLevelDimensions()
|
||||||
indexLevelTiles()
|
--
|
||||||
createTileObjects()
|
--createTileObjects()
|
||||||
createRoomObjects()
|
--createRoomObjects()
|
||||||
getSpawns()
|
--getSpawns()
|
||||||
end
|
end
|
||||||
|
|
||||||
function createRoomObjects()
|
function createRoomObjects()
|
||||||
LoadedObjects.Rooms = {}
|
LoadedObjects.Rooms = {}
|
||||||
for _, v in pairs(LevelData.objects.rooms) do
|
for _, v in pairs(LevelData.objects.rooms) do
|
||||||
table.insert(LoadedObjects.Rooms, Collision:new(v[1][1],v[1][2],v[2][1],v[2][2]))
|
table.insert(LoadedObjects.Rooms, Collision:new(v[1],v[2],v[3],v[4]))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
function getSpawns()
|
function getSpawns()
|
||||||
LoadedObjects.Spawns = {}
|
LoadedObjects.Spawns = {}
|
||||||
for _, v in pairs(LevelData.objects.spawns) do
|
for _, v in pairs(LevelData.objects.spawns) do
|
||||||
addSpawn(v[1],unpack(v[2]))
|
--addSpawn(v[1],unpack(v[2]))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
@@ -121,11 +139,8 @@ function reduceLevelCanvas(horizontal,vertical)
|
|||||||
end
|
end
|
||||||
|
|
||||||
function getLevelTileData()
|
function getLevelTileData()
|
||||||
for k, v in pairs(tileset) do
|
TileData = dofile("data/tileset/"..LevelData.tileset_name..".lua")
|
||||||
if v == LevelData.tileset then
|
|
||||||
TileData = dofile("data/tileset/"..k..".lua")
|
|
||||||
end
|
|
||||||
end
|
|
||||||
end
|
end
|
||||||
|
|
||||||
function reloadLevelTiles()
|
function reloadLevelTiles()
|
||||||
@@ -159,10 +174,10 @@ end
|
|||||||
|
|
||||||
function indexLevelTiles()
|
function indexLevelTiles()
|
||||||
TileIndex = {}
|
TileIndex = {}
|
||||||
|
local this_tileset = LevelData.tileset
|
||||||
-- index from tileset
|
-- index from tileset
|
||||||
local width = LevelData.tileset:getPixelWidth()/tile_properties.width
|
local width = this_tileset:getPixelWidth()/tile_properties.width
|
||||||
local height = LevelData.tileset:getPixelHeight()/tile_properties.height
|
local height = this_tileset:getPixelHeight()/tile_properties.height
|
||||||
for i = 0, height do
|
for i = 0, height do
|
||||||
for j = 0, width do
|
for j = 0, width do
|
||||||
TileIndex[i*width+j+1] = love.graphics.newQuad(
|
TileIndex[i*width+j+1] = love.graphics.newQuad(
|
||||||
@@ -170,7 +185,7 @@ function indexLevelTiles()
|
|||||||
i*tile_properties.height,
|
i*tile_properties.height,
|
||||||
tile_properties.width,
|
tile_properties.width,
|
||||||
tile_properties.height,
|
tile_properties.height,
|
||||||
LevelData.tileset:getDimensions()
|
this_tileset:getDimensions()
|
||||||
)
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
@@ -220,6 +235,9 @@ end
|
|||||||
function instanceTile(id)
|
function instanceTile(id)
|
||||||
local tile = {}
|
local tile = {}
|
||||||
|
|
||||||
|
if type(id) == "table" then
|
||||||
|
id = id.id
|
||||||
|
end
|
||||||
tile.id = id
|
tile.id = id
|
||||||
local Properties = TileData[tile.id]
|
local Properties = TileData[tile.id]
|
||||||
|
|
||||||
@@ -258,7 +276,7 @@ function drawGridDisplay()
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
function optimizeTileObjects()
|
function optimizeTileObjects(dest)
|
||||||
logPrint("Optimizing Objects...")
|
logPrint("Optimizing Objects...")
|
||||||
local unoptimized = 0
|
local unoptimized = 0
|
||||||
local isTileOptimized = {}
|
local isTileOptimized = {}
|
||||||
@@ -270,8 +288,9 @@ function optimizeTileObjects()
|
|||||||
end
|
end
|
||||||
for i = 1, #LevelTiles do
|
for i = 1, #LevelTiles do
|
||||||
for j = 1, #LevelTiles[i] do
|
for j = 1, #LevelTiles[i] do
|
||||||
if LevelTiles[i][j].id ~= 0 then
|
if LevelTiles[i][j].id ~= 0 and TileData[LevelTiles[i][j].id] then
|
||||||
local type = TileData[LevelTiles[i][j].id].type
|
local tile_dat = TileData[LevelTiles[i][j].id]
|
||||||
|
local type = tile_dat.type
|
||||||
if type == "whole" and not isTileOptimized[i][j] then
|
if type == "whole" and not isTileOptimized[i][j] then
|
||||||
isTileOptimized[i][j] = true
|
isTileOptimized[i][j] = true
|
||||||
local n = 1
|
local n = 1
|
||||||
@@ -337,29 +356,27 @@ function optimizeTileObjects()
|
|||||||
base_x + tile_properties.width * tile_properties.scale * n,
|
base_x + tile_properties.width * tile_properties.scale * n,
|
||||||
base_y + tile_properties.height * tile_properties.scale * m
|
base_y + tile_properties.height * tile_properties.scale * m
|
||||||
)
|
)
|
||||||
table.insert(LoadedObjects.Collisions,col)
|
table.insert(dest,col)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
logPrint("collisions optimized from " .. unoptimized .. " to " .. #LoadedObjects.Collisions)
|
--logPrint("collisions optimized from " .. unoptimized .. " to " .. #LoadedObjects.Collisions)
|
||||||
end
|
end
|
||||||
|
|
||||||
function createTileObjects()
|
-- currently broken
|
||||||
LoadedObjects.Collisions = {}
|
function createTileObjects(dest)
|
||||||
LoadedObjects.Platforms = {}
|
|
||||||
LoadedObjects.Ladders = {}
|
|
||||||
LoadedObjects.Hazards = {}
|
|
||||||
|
|
||||||
optimizeTileObjects()
|
|
||||||
|
optimizeTileObjects(dest.collisions)
|
||||||
|
|
||||||
for i = 1, #LevelTiles do
|
for i = 1, #LevelTiles do
|
||||||
for j = 1, #LevelTiles[i] do
|
for j = 1, #LevelTiles[i] do
|
||||||
if LevelTiles[i][j].id ~= 0 then
|
if LevelTiles[i][j].id ~= 0 then
|
||||||
|
local tile_dat = TileData[LevelTiles[i][j].id] or {}
|
||||||
local type = TileData[LevelTiles[i][j].id].type
|
local type = tile_dat.type
|
||||||
local light = TileData[LevelTiles[i][j].id].light
|
local light = tile_dat.light
|
||||||
local base_x = tile_properties.scale * j * tile_properties.width + tile_properties.scale * (level_properties.offset.x - tile_properties.height)
|
local base_x = tile_properties.scale * j * tile_properties.width + tile_properties.scale * (level_properties.offset.x - tile_properties.height)
|
||||||
local base_y = tile_properties.scale * i * tile_properties.height + tile_properties.scale * (level_properties.offset.y - tile_properties.height)
|
local base_y = tile_properties.scale * i * tile_properties.height + tile_properties.scale * (level_properties.offset.y - tile_properties.height)
|
||||||
|
|
||||||
@@ -372,6 +389,9 @@ function createTileObjects()
|
|||||||
)
|
)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
local col
|
||||||
|
local list = dest.collisions
|
||||||
|
|
||||||
-- wholes are handled in optimization now
|
-- wholes are handled in optimization now
|
||||||
--[[if type == "whole" then
|
--[[if type == "whole" then
|
||||||
local col = Collision:new(
|
local col = Collision:new(
|
||||||
@@ -383,33 +403,33 @@ function createTileObjects()
|
|||||||
table.insert(LoadedObjects.Collisions,col)
|
table.insert(LoadedObjects.Collisions,col)
|
||||||
else]]if type == "half_bottom" then
|
else]]if type == "half_bottom" then
|
||||||
|
|
||||||
local col = Collision:new(
|
col = Collision:new(
|
||||||
base_x,
|
base_x,
|
||||||
base_y + tile_properties.height/2 * tile_properties.scale,
|
base_y + tile_properties.height/2 * tile_properties.scale,
|
||||||
base_x + tile_properties.width * tile_properties.scale,
|
base_x + tile_properties.width * tile_properties.scale,
|
||||||
base_y + tile_properties.height * tile_properties.scale
|
base_y + tile_properties.height * tile_properties.scale
|
||||||
)
|
)
|
||||||
table.insert(LoadedObjects.Collisions,col)
|
|
||||||
|
|
||||||
elseif type == "half_top" then
|
elseif type == "half_top" then
|
||||||
|
|
||||||
local col = Collision:new(
|
col = Collision:new(
|
||||||
base_x,
|
base_x,
|
||||||
base_y ,
|
base_y ,
|
||||||
base_x + tile_properties.width * tile_properties.scale,
|
base_x + tile_properties.width * tile_properties.scale,
|
||||||
base_y + tile_properties.height/2 * tile_properties.scale
|
base_y + tile_properties.height/2 * tile_properties.scale
|
||||||
)
|
)
|
||||||
table.insert(LoadedObjects.Collisions,col)
|
|
||||||
|
|
||||||
elseif type == "half_right" then
|
elseif type == "half_right" then
|
||||||
|
|
||||||
local col = Collision:new(
|
col = Collision:new(
|
||||||
base_x + tile_properties.height/2 * tile_properties.scale,
|
base_x + tile_properties.height/2 * tile_properties.scale,
|
||||||
base_y,
|
base_y,
|
||||||
base_x + tile_properties.width * tile_properties.scale,
|
base_x + tile_properties.width * tile_properties.scale,
|
||||||
base_y + tile_properties.height * tile_properties.scale
|
base_y + tile_properties.height * tile_properties.scale
|
||||||
)
|
)
|
||||||
table.insert(LoadedObjects.Collisions,col)
|
|
||||||
|
|
||||||
elseif type == "half_left" then
|
elseif type == "half_left" then
|
||||||
|
|
||||||
@@ -580,7 +600,8 @@ function createTileObjects()
|
|||||||
|
|
||||||
end
|
end
|
||||||
|
|
||||||
elseif type == "ladder_right" then
|
-- TODO: fix ladders
|
||||||
|
--[[elseif type == "ladder_right" then
|
||||||
|
|
||||||
local ladder = Collision:new(
|
local ladder = Collision:new(
|
||||||
base_x + (tile_properties.width-4)* tile_properties.scale,
|
base_x + (tile_properties.width-4)* tile_properties.scale,
|
||||||
@@ -638,7 +659,7 @@ function createTileObjects()
|
|||||||
)
|
)
|
||||||
table.insert(LoadedObjects.Platforms,plat)
|
table.insert(LoadedObjects.Platforms,plat)
|
||||||
|
|
||||||
elseif type == "bottom_hazard" then
|
]]elseif type == "bottom_hazard" then
|
||||||
|
|
||||||
|
|
||||||
local hazard = Collision:new(
|
local hazard = Collision:new(
|
||||||
@@ -647,9 +668,10 @@ function createTileObjects()
|
|||||||
base_x + tile_properties.width * tile_properties.scale,
|
base_x + tile_properties.width * tile_properties.scale,
|
||||||
base_y + tile_properties.height * tile_properties.scale
|
base_y + tile_properties.height * tile_properties.scale
|
||||||
)
|
)
|
||||||
table.insert(LoadedObjects.Hazards,hazard)
|
list = dest.hazards
|
||||||
|
|
||||||
end
|
end
|
||||||
|
table.insert(list, col)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|||||||
@@ -8,20 +8,22 @@ function math.sign(x)
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
function vector(init_x, init_y, final_x, final_y)
|
function math.round(x)
|
||||||
local distance_x = final_x - init_x
|
return math.floor(x+0.5)
|
||||||
local distance_y = final_y - init_y
|
end
|
||||||
return {distance_x, distance_y}
|
|
||||||
|
function vector(x, y)
|
||||||
|
return {x = x, y = y}
|
||||||
end
|
end
|
||||||
|
|
||||||
function getVectorValue(vector)
|
function getVectorValue(vector)
|
||||||
return math.sqrt(vector[1] ^ 2 + vector[2] ^ 2)
|
return math.sqrt(vector.x ^ 2 + vector.y ^ 2)
|
||||||
end
|
end
|
||||||
|
|
||||||
function getAngleFromVector(x,y)
|
function getAngleFromVector(vector)
|
||||||
local reduce = 0
|
local reduce = 0
|
||||||
if x < 0 then
|
if vector.x < 0 then
|
||||||
reduce = math.rad(180)
|
reduce = math.rad(180)
|
||||||
end
|
end
|
||||||
return math.atan(y/x) - reduce
|
return math.atan(vector.y/vector.x) - reduce
|
||||||
end
|
end
|
||||||
|
|||||||
@@ -25,10 +25,7 @@ function isThereObjectAt(x,y,objectType)
|
|||||||
for _, object in pairs(objectType) do
|
for _, object in pairs(objectType) do
|
||||||
if object.is_disabled then
|
if object.is_disabled then
|
||||||
-- Dont calculate if dissabled
|
-- Dont calculate if dissabled
|
||||||
elseif x >= object.from.x
|
elseif object:asRect():containsPoint(Point:new(x, y)) then
|
||||||
and x <= object.to.x
|
|
||||||
and y >= object.from.y
|
|
||||||
and y <= object.to.y then
|
|
||||||
object.is_colliding = true
|
object.is_colliding = true
|
||||||
return true
|
return true
|
||||||
end
|
end
|
||||||
@@ -36,14 +33,6 @@ function isThereObjectAt(x,y,objectType)
|
|||||||
return false
|
return false
|
||||||
end
|
end
|
||||||
|
|
||||||
function isThereCollisionAt(x,y)
|
|
||||||
if x >= 0 and x < #CollisionTable
|
|
||||||
and y >= 0 and y < #CollisionTable[0] then
|
|
||||||
return CollisionTable[math.floor(y)][math.floor(x)]
|
|
||||||
end
|
|
||||||
return false
|
|
||||||
end
|
|
||||||
|
|
||||||
-- flags
|
-- flags
|
||||||
function setCollisionFlags()
|
function setCollisionFlags()
|
||||||
local Check = {
|
local Check = {
|
||||||
|
|||||||
86
code/rect.lua
Normal file
86
code/rect.lua
Normal file
@@ -0,0 +1,86 @@
|
|||||||
|
-- based of of plan9's Rectangle struct
|
||||||
|
-- rect.max is not counted as "in" the rectangle
|
||||||
|
Rect = {}
|
||||||
|
Rect.__index = Rect
|
||||||
|
|
||||||
|
function Rect:fromPoints(pt1, pt2)
|
||||||
|
local o = { min = pt1, max = pt2 }
|
||||||
|
setmetatable(o, self)
|
||||||
|
return o
|
||||||
|
end
|
||||||
|
|
||||||
|
function Rect:getPoints()
|
||||||
|
return self.min, self.max
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
function Rect:fromCoords(x1, y1, x2, y2)
|
||||||
|
return Rect:fromPoints(Point:new(x1, y1), Point:new(x2, y2))
|
||||||
|
end
|
||||||
|
|
||||||
|
function Rect:getCoords()
|
||||||
|
return self.min.x, self.min.y, self.max.x, self.max.y
|
||||||
|
end
|
||||||
|
|
||||||
|
-- clone refers to a deep copy
|
||||||
|
function Rect:clone()
|
||||||
|
return Rect:fromCoords(self.min.x, self.min.y, self.max.x, self.max.y)
|
||||||
|
end
|
||||||
|
|
||||||
|
-- make sure min and max refer to the correct corners
|
||||||
|
-- acts in place, returns self
|
||||||
|
function Rect:fix()
|
||||||
|
if self.min.x > self.max.x then
|
||||||
|
self.min.x, self.max.x = self.max.x, self.min.x
|
||||||
|
end
|
||||||
|
if self.min.y > self.max.y then
|
||||||
|
self.min.y, self.max.y = self.max.y, self.min.y
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
function Rect:width()
|
||||||
|
return self.max.x - self.min.x
|
||||||
|
end
|
||||||
|
|
||||||
|
function Rect:height()
|
||||||
|
return self.max.y - self.min.y
|
||||||
|
end
|
||||||
|
|
||||||
|
function Rect:size()
|
||||||
|
return Point:new(self:width(), self:height())
|
||||||
|
end
|
||||||
|
|
||||||
|
function Rect:__add(pt)
|
||||||
|
return Rect:fromPoints(self.min + pt, self.max + pt)
|
||||||
|
end
|
||||||
|
|
||||||
|
function Rect:corners()
|
||||||
|
return {
|
||||||
|
self.min:copy(), -- top left
|
||||||
|
Point:new(self.max.x, self.min.y), -- top right
|
||||||
|
Point:new(self.min.x, self.max.y), -- bottom left
|
||||||
|
self.max:copy(), -- bottom right
|
||||||
|
}
|
||||||
|
end
|
||||||
|
|
||||||
|
function Rect:containsPoint(pt)
|
||||||
|
return pt.x >= self.min.x
|
||||||
|
and pt.y >= self.min.y
|
||||||
|
and pt.x <= self.max.x
|
||||||
|
and pt.y <= self.max.y
|
||||||
|
end
|
||||||
|
|
||||||
|
function Rect:overlapsRect(other)
|
||||||
|
return self.min.x < other.max.x
|
||||||
|
and self.max.x > other.min.x
|
||||||
|
and self.min.y < other.max.y
|
||||||
|
and self.max.y > other.min.y
|
||||||
|
end
|
||||||
|
|
||||||
|
function Rect:draw(style)
|
||||||
|
love.graphics.rectangle(style, self.min.x - Camera.pos.x, self.min.y - Camera.pos.y, self:width(), self:height())
|
||||||
|
end
|
||||||
|
|
||||||
|
function Rect:__tostring()
|
||||||
|
return "Rect["..tostring(self.min).." "..tostring(self.max).."]"
|
||||||
|
end
|
||||||
@@ -7,6 +7,7 @@ require "data/sfx"
|
|||||||
require "code/locale"
|
require "code/locale"
|
||||||
|
|
||||||
-- support functions
|
-- support functions
|
||||||
|
require "code/serialize"
|
||||||
require "code/math"
|
require "code/math"
|
||||||
require "code/draw"
|
require "code/draw"
|
||||||
require "code/hex"
|
require "code/hex"
|
||||||
@@ -14,6 +15,8 @@ require "code/in_out"
|
|||||||
|
|
||||||
-- classes
|
-- classes
|
||||||
require "code/point"
|
require "code/point"
|
||||||
|
require "code/rect"
|
||||||
|
require "code/chunk"
|
||||||
require "code/objects"
|
require "code/objects"
|
||||||
require "code/level"
|
require "code/level"
|
||||||
require "code/camera"
|
require "code/camera"
|
||||||
|
|||||||
31
code/serialize.lua
Normal file
31
code/serialize.lua
Normal file
@@ -0,0 +1,31 @@
|
|||||||
|
local function quote(str, lvl)
|
||||||
|
--lvl = lvl or
|
||||||
|
local rp = "]"..(lvl or "").."]"
|
||||||
|
if string.match(str, rp) then
|
||||||
|
return quote(str, (lvl or "") .. "=")
|
||||||
|
end
|
||||||
|
|
||||||
|
return "["..(lvl or "").."["..str..rp
|
||||||
|
end
|
||||||
|
|
||||||
|
function serialize_lua_value(val)
|
||||||
|
if type(val) == "number" then
|
||||||
|
return tostring(val)
|
||||||
|
elseif type(val) == "string" then
|
||||||
|
-- TODO: use different quotes if ']]' appears in the value
|
||||||
|
return quote(val)
|
||||||
|
elseif type(val) == "table" then
|
||||||
|
local r = "{"
|
||||||
|
for k, v in pairs(val) do
|
||||||
|
r = r .. "[ "..serialize_lua_value(k).." ]="..serialize_lua_value(v)..","
|
||||||
|
end
|
||||||
|
return r .. "}"
|
||||||
|
elseif val == nil then
|
||||||
|
return "nil"
|
||||||
|
elseif val == false then
|
||||||
|
return "false"
|
||||||
|
elseif val == true then
|
||||||
|
return "true"
|
||||||
|
end
|
||||||
|
error("serialization failed")
|
||||||
|
end
|
||||||
@@ -20,7 +20,11 @@ function deselectSpawns()
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
function selectSpawns(x,y)
|
function selectSpawns(rect)
|
||||||
|
local x, y = rect:getPoints()
|
||||||
|
local select_rect = Rect:fromPoints(x-{x=Camera.pos.x,y=Camera.pos.y},y-{x=Camera.pos.x,y=Camera.pos.y})
|
||||||
|
select_rect:fix()
|
||||||
|
|
||||||
for _, spawn in pairs(LoadedObjects.Spawns) do
|
for _, spawn in pairs(LoadedObjects.Spawns) do
|
||||||
|
|
||||||
local offset_x, offset_y = spawn.archetype.display:getCenteredOffset()
|
local offset_x, offset_y = spawn.archetype.display:getCenteredOffset()
|
||||||
@@ -28,9 +32,9 @@ function selectSpawns(x,y)
|
|||||||
local top = spawn.args[2] - Camera.pos.y - offset_y
|
local top = spawn.args[2] - Camera.pos.y - offset_y
|
||||||
local right = spawn.args[1] - Camera.pos.x + offset_x
|
local right = spawn.args[1] - Camera.pos.x + offset_x
|
||||||
local bottom = spawn.args[2] - Camera.pos.y + offset_y
|
local bottom = spawn.args[2] - Camera.pos.y + offset_y
|
||||||
local x = (x / game.scale)
|
|
||||||
local y = (y / game.scale)
|
local spawn_rect = Rect:fromCoords(left, top, right, bottom)
|
||||||
if x >= left and y >= top and x <= right and y <= bottom then
|
if spawn_rect:overlapsRect(select_rect) then
|
||||||
spawn.selected = true
|
spawn.selected = true
|
||||||
end
|
end
|
||||||
|
|
||||||
@@ -47,10 +51,22 @@ function selectSpawns(x,y)
|
|||||||
end
|
end
|
||||||
|
|
||||||
function moveSpawns(x,y)
|
function moveSpawns(x,y)
|
||||||
|
local move_x = nil
|
||||||
|
local move_y = nil
|
||||||
for _, spawn in pairs(LoadedObjects.Spawns) do
|
for _, spawn in pairs(LoadedObjects.Spawns) do
|
||||||
if spawn.selected then
|
if spawn.selected then
|
||||||
spawn.args[1] = math.floor(x/game.scale)+Camera.pos.x
|
local difference_x = math.floor((x/game.scale)+Camera.pos.x) - spawn.args[1]
|
||||||
spawn.args[2] = math.floor(y/game.scale)+Camera.pos.y
|
local difference_y = math.floor((y/game.scale)+Camera.pos.y) - spawn.args[2]
|
||||||
|
if move_x == nil or Point.abs({x=difference_x,y=difference_y}) < Point.abs({x=move_x,y=move_y}) then
|
||||||
|
move_x = difference_x
|
||||||
|
move_y = difference_y
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
for _, spawn in pairs(LoadedObjects.Spawns) do
|
||||||
|
if spawn.selected then
|
||||||
|
spawn.args[1] = spawn.args[1] + move_x
|
||||||
|
spawn.args[2] = spawn.args[2] + move_y
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
@@ -72,6 +88,9 @@ function promptSpawnNew()
|
|||||||
for i=2, #result+1 do
|
for i=2, #result+1 do
|
||||||
print("arg #"..i-1)
|
print("arg #"..i-1)
|
||||||
args[i-1] = result[i]
|
args[i-1] = result[i]
|
||||||
|
if i < 4 then
|
||||||
|
args[i-1] = math.floor(args[i-1])
|
||||||
|
end
|
||||||
end
|
end
|
||||||
else
|
else
|
||||||
args = {0,0}
|
args = {0,0}
|
||||||
|
|||||||
13
code/ui.lua
13
code/ui.lua
@@ -5,16 +5,19 @@ function addElement(self)
|
|||||||
self.id = #UIElement
|
self.id = #UIElement
|
||||||
end
|
end
|
||||||
|
|
||||||
function drawTextBox(text,x,y,color,background_color)
|
function drawTextBox(text,x,y,style)
|
||||||
local color = color or {1,1,1,1}
|
local style = style or {}
|
||||||
local background_color = background_color or {0,0,0,1}
|
|
||||||
local c1, c2, c3, a = love.graphics.getColor()
|
local c1, c2, c3, a = love.graphics.getColor()
|
||||||
local width = locale_font:getWidth(text)
|
local width = locale_font:getWidth(text)
|
||||||
local height = locale_font:getHeight(text)
|
local height = locale_font:getHeight(text)
|
||||||
local margin = 5
|
|
||||||
|
local color = style.color or {1,1,1,1}
|
||||||
|
local background_color = style.background_color or {0,0,0,1}
|
||||||
|
local margin = style.margin or 5
|
||||||
|
|
||||||
local lines = 1
|
local lines = 1
|
||||||
for i in text:gmatch("\n") do
|
for i in text:gmatch("\n") do
|
||||||
lines = lines + 1
|
lines = lines + 1
|
||||||
end
|
end
|
||||||
|
|
||||||
love.graphics.setColor(unpack(color))
|
love.graphics.setColor(unpack(color))
|
||||||
|
|||||||
@@ -62,8 +62,10 @@ function Prompt:draw()
|
|||||||
self.name .. ": " .. self.input,
|
self.name .. ": " .. self.input,
|
||||||
self.pos.x,
|
self.pos.x,
|
||||||
self.pos.y,
|
self.pos.y,
|
||||||
self.color,
|
{
|
||||||
self.background_color
|
color = self.color,
|
||||||
|
background_color = self.background_color
|
||||||
|
}
|
||||||
)
|
)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|||||||
@@ -1,42 +0,0 @@
|
|||||||
return {
|
|
||||||
name = "Dev Level",
|
|
||||||
tileset = tileset.library,
|
|
||||||
properties = {
|
|
||||||
darkness = false
|
|
||||||
},
|
|
||||||
tiles = {
|
|
||||||
{ 1, 4, 0, 0, 0, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
|
|
||||||
{ 1, 4, 0, 0, 0, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
|
|
||||||
{ 1, 4, 0, 0, 0, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
|
|
||||||
{ 1, 4, 0, 0, 0, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
|
|
||||||
{ 1, 4, 0, 0, 0, 2, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14},
|
|
||||||
{ 1, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
|
|
||||||
{ 1, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
|
|
||||||
{ 1, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
|
|
||||||
{ 1, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
|
|
||||||
{ 1, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
|
|
||||||
{ 1, 13, 13, 13, 13, 13, 13, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
|
|
||||||
{ 1, 1, 1, 1, 1, 1, 1, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
|
|
||||||
{ 1, 1, 1, 1, 1, 1, 1, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
|
|
||||||
{ 1, 1, 1, 1, 1, 1, 1, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
|
|
||||||
{ 1, 1, 1, 1, 1, 1, 1, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
|
|
||||||
{ 1, 1, 1, 1, 1, 1, 1, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
|
|
||||||
{ 1, 1, 1, 1, 1, 1, 1, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
|
|
||||||
{ 1, 1, 1, 1, 1, 1, 1, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
|
|
||||||
{ 1, 1, 1, 1, 1, 1, 1, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
|
|
||||||
{ 1, 1, 1, 1, 1, 1, 1, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13},
|
|
||||||
{ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
|
|
||||||
{ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1}
|
|
||||||
},
|
|
||||||
objects = {
|
|
||||||
spawns = {
|
|
||||||
{Fairy,{100,88}},
|
|
||||||
{HookAnchor,{200,89,100}},
|
|
||||||
{HookAnchor,{400,89,120}}
|
|
||||||
},
|
|
||||||
rooms = {
|
|
||||||
{{96,64},{544,320}},
|
|
||||||
{{0,0},{112,176}}
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}
|
|
||||||
1
data/levels/level1/chunks/global.lua
Normal file
1
data/levels/level1/chunks/global.lua
Normal file
File diff suppressed because one or more lines are too long
1
data/levels/level1/level.lua
Normal file
1
data/levels/level1/level.lua
Normal file
@@ -0,0 +1 @@
|
|||||||
|
return {[ [[tileset]] ]=[[library]],[ [[chunks]] ]={[ 1 ]={[ 1 ]=[[global.lua]],},},[ [[name]] ]=[[unnamed]],[ [[properties]] ]={[ [[darkness]] ]=false,},}
|
||||||
18
main.lua
18
main.lua
@@ -6,9 +6,10 @@ function love.load()
|
|||||||
secs = 0
|
secs = 0
|
||||||
|
|
||||||
menu_type = "no"
|
menu_type = "no"
|
||||||
|
-- FIXME: this overrides a standard library!
|
||||||
debug = false
|
debug = false
|
||||||
debug_collision = false
|
debug_collision = false
|
||||||
editor_mode = false
|
--editor_mode = false
|
||||||
|
|
||||||
text_size = 1
|
text_size = 1
|
||||||
|
|
||||||
@@ -103,6 +104,15 @@ function love.update(dt)
|
|||||||
return
|
return
|
||||||
end
|
end
|
||||||
|
|
||||||
|
if Keybind:checkPressed(Keybind.debug.editor) then
|
||||||
|
if editor.active then
|
||||||
|
deselectSpawns()
|
||||||
|
createTileObjects()
|
||||||
|
restartGame()
|
||||||
|
end
|
||||||
|
editor.active = not editor.active
|
||||||
|
end
|
||||||
|
|
||||||
if love.keyboard.isDown("f7") then
|
if love.keyboard.isDown("f7") then
|
||||||
local test_prompt = Prompt:new({
|
local test_prompt = Prompt:new({
|
||||||
name = "test prompt",
|
name = "test prompt",
|
||||||
@@ -127,7 +137,7 @@ function love.update(dt)
|
|||||||
if menu_type ~= nil then stepMenu(menu_type) end
|
if menu_type ~= nil then stepMenu(menu_type) end
|
||||||
|
|
||||||
--editor
|
--editor
|
||||||
if editor_mode then
|
if editor.active then
|
||||||
stepEditor()
|
stepEditor()
|
||||||
else
|
else
|
||||||
stepGame()
|
stepGame()
|
||||||
@@ -136,7 +146,7 @@ end
|
|||||||
|
|
||||||
|
|
||||||
function love.wheelmoved(_, y)
|
function love.wheelmoved(_, y)
|
||||||
if editor_mode then
|
if editor.active then
|
||||||
scrollEditor(y)
|
scrollEditor(y)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
@@ -150,7 +160,7 @@ function love.draw()
|
|||||||
game_resize = false
|
game_resize = false
|
||||||
end
|
end
|
||||||
|
|
||||||
if editor_mode then
|
if editor.active then
|
||||||
drawEditor()
|
drawEditor()
|
||||||
else
|
else
|
||||||
drawGame()
|
drawGame()
|
||||||
|
|||||||
Reference in New Issue
Block a user