Captain’s log No.4, 2022-05-27T13:20:00Z
The Backbone (I guess)
T+4days
It’s been a while, huh? I’d lost time, lost motivation for this, but hadn’t lost interest.
To regain some motivation I wanted to overhaul the visual footprint of the project – easier to work on a pretty project than a placeholder-sprite-filled one.
Idea: sketch drawing! Works well with the nature of the project, since its sole purpose is to teach me the mechanics of game development and it would look interesting with a simplistic visual pattern. Crude geometric shapes made in half a second in Photoshop didn’t really sit with me.
Problem: It’s a lot easier to sketch by, well, sketching than by running my mouse across my desk, so I guess that part will still have to look crude until I can either borrow or buy a graphic tablet for my computer (which is a priority for academic purposes anyway).
T+3days
After about a year of not opening the project, I had to reacquaint myself with Defold (again) and with my project. I do not like to delete things, so while I was doing some necessary housework for bad ideas and bad code, I created a few ‘legacy’ folders and a lot of --[[comments]]--
. (some scripts have hundreds of lines and about 50 of them actually functioning un-commented)
I’ll probably have to delete all of it at some point. But that’s a future me problem.
T+2days
What now? Well I do need a main menu and could maybe use one of those intro sequences with massive logos saying “Built with Defold” and “Made by blackbird” (the name I usually go by online)
Now I’m sleepy.
T+1days_yesterday
I’ve missed programming. Even if after all this time 50% of it is looking up the Defold Manual, Examples and API. Some things do not change though – most of the time was still spent staring at the code and reading it slowly out loud, thinking where I’d gone wrong.
manager:controller#manager.script
-- i left out the init() function, because it does not really matter for this blog --
function on_message(self, message_id, message, sender)
if message_id == hash("load_menu") then
show(self, "#PRXY_main")
elseif message_id == hash("load_level") then
show(self, translate(self, message.gui_node))
elseif message_id == hash("proxy_loaded") then
self.current_proxy = sender
msg.post(sender, "enable")
elseif message_id == hash("proxy_unloaded") then
print("Unloaded ", sender)
end
end
function show(self, proxy)
if self.current_proxy then
msg.post(self.current_proxy, "unload")
self.current_proxy = nil
end
msg.post(proxy, "async_load")
--print("I done did it pardner")
end
--translate the gui node that initiated an action to a usable proxy name
function translate(self, gui_node)
return self.names[gui_node]
--[[ this was defined in init()
self.names = {["pong_box"] = "#PRXY_pong", }
]]--
end
The language I’d spent most time on in my life is Python. And Lua is just different enough to have me doubt the simplest expressions and peruse official Lua documentation.
for loops of all things got me beat.
why I am this confused with Lua
python
for i in range(1,10):
i += 1
for thing in list:
something(thing)
lua
for i=1,10,1 do
something(i)
end
for index, item in ipairs(list) do
something(item)
end
but what my brain wanted to do…
for i in 1..10 do
sth(i)
end
for item in list do
sth(item)
end
Don’t know why, don’t ask.
also pro-tip about local functions:
If you’re pedantic like me and want your function init(self)
at the top and don’t want to start scripts with local functions;
local func1
local func2
function init(self)
func1(a)
func2(b)
end
This works if you need to call these functions immediately. Because what I’d been doing before is:
function init(self)
--everything else i needed done immediately
local func1
local func2
func1(a)
end
This returns an error, because I tried to call a nil value at line 6. I guess local functions need more than a few lines’ time to get acquainted with everyone. Apparently works perfectly fine, so long as you don’t call the functions in the init() space.
The reason I brought these two issues up (the for loops and forward-announcing local functions) is because the main_menu.gui didn’t want to recognise the “touch” action. (I defined LMB as “touch”)
Now, I never intended this game to use the mouse anyway, so I started work on a system to allow the keyboard or controller.
Allowed controls
W A S D LCtrl
↑ ← ↓ → RCtrl
↑ ← ↓ → ▢
self.matrix
Please refer to the first screenshot under ‘T+2days’
self.matrix = {
{"pong_box", "lvl2_box", "lvl3_box", nil; },
{"lvl4_box", "lvl5_box", "lvl6_box", nil; },
{nil, nil, nil, "exit_box"; };
}
This nested list represents the rows and collumns in which the buttons are arranged. I can move vertically and horizontally with ease using self.matrix[x][y]
Oh, also! Apparently in Lua, indexes start at 1, not 0.
function reset(self) in 'manager:controller#manager.script'
In order to show which box was selected, I set all of the to alpha=0.7 and would only make the selected box fully opaque. Here’s where the confusingfor
loops come to play
inactive_alpha = 0.7
active_alpha = 1
function reset(self)
for i, rw in pairs(self.matrix) do
for ii, clm in pairs(rw) do
--reset each node to inactive_alpha=0.7
if clm then
gui.set_alpha(gui.get_node(clm), inactive_alpha)
end
end
end
end
Although I found the gui.set_alpha(node, number)
function on the API it didn’t exist? Autocomplete didn’t recognise it and it returned an error saying I tried to access nil value.
-- work-around
if clm then
local node = gui.get_node(clm)
local xyzw = gui.get_color(node)
xyzw.w = inactive_alpha
gui.set_color(node, xyzw)
end
-- if you use the action key on an active node then
msg.post("manager:controller#manager", "load_level", {gui_node = self.current})
-- from main:main_gui#main_gui
T-0days_today
ERROR:GAMEOBJECT: Instance 'manager:controller#manager' could not be found when dispatching message 'load_level' sent from main:/main_gui#main_gui
I swear, I’ll be learning how to use the msg.post()
function for the entirety of this project.
How the proxy is set up
both the main and manager collections are in the same directory
manager.collection is loaded immediately and never unloaded
-- function init(self) in 'manager:controller#manager.script'
function init(self)
msg.post(".", "acquire_input_focus")
self.current_proxy = nil
msg.post("#", "load_menu")
end
main.collection is immediatelly loaded
if I change the msg.post() in main_gui.gui_script:
msg.post("manager:controller#manager", "load_level", {gui_node = self.current})
or
msg.post(msg.url("manager:controller#manager"), "load_level", {gui_node = self.current})
-->ERROR:SCRIPT: /main/main_menu.gui_script:95: Could not send message 'load_level' from 'main:/main_gui#main_gui' to 'manager:controller#manager'.
-->stack traceback:
--> [C]:-1: in function post
msg.post(hash("manager:controller#manager"), "load_level", {gui_node = self.current})
-->ERROR:GAMEOBJECT: Instance 'manager:controller#manager' could not be found when dispatching message 'load_level' sent from main:/main_gui#main_gui
I do not see a reason, why the message can’t be delivered, since both collections are definitely loaded.
Anyway. I’m looking forward to working on this again for a few weeks until I inevitably dip again for months or years.
End log, 2022-05-27T14:53:00Z