This commit is contained in:
2026-08-10 22:13:21 -05:00
parent 30e09a40c4
commit a8444b25ad
11 changed files with 330 additions and 155 deletions
+140 -54
View File
@@ -8,7 +8,7 @@ start = "start"
greeter = """
fn init(me) {
log(`hello from object — player at ${Player.x}, ${Player.y}`);
set_tile(2); // change my glyph to ☻ — proves the write path
set_tile(""); // change my glyph — proves the write path
say("Hello there,\\ntraveller!");
log(`Player health: ${Player.health}`);
}
@@ -37,15 +37,15 @@ fn init(me) {
}
}
// move() costs 250 ms, so the object steps ~4 cells/sec no matter how often
// tick() runs. Queue.length() avoids piling up moves; blocked() avoids walking
// into a wall (or another object's already-queued move this tick).
// tick() runs. The engine only calls tick() once this object's queue has drained,
// so a whole dance can be queued up front without piling up.
fn tick(me, dt) {
move(East);
move(South);
move(North);
move(East);
say("Hey!", 0.5);
delay(me, 0.5);
me.delay(0.5);
move(West);
move(South);
move(North);
@@ -159,7 +159,7 @@ fn bump(me, _dir) {
yammerer = """
fn tick(me, dt) {
say("blahblahblah", 2.0);
delay(2);
delay(2.0);
}
"""
@@ -175,8 +175,8 @@ fn tick(me, dt) {
}
"""
# A trigger script: no glyph, not solid — it just watches for the player stepping
# onto its cell and logs. Triggers are placed via [[boards.NAME.triggers]].
# A sensor script: no glyph, off the grid — it just watches for the player stepping
# onto its cell and logs. Sensors are placed via [[boards.NAME.sensors]].
tripwire = """
fn enter(me, dir) {
if Player.x == me.x && Player.y == me.y {
@@ -185,7 +185,7 @@ fn enter(me, dir) {
}
"""
[boards.start.map]
[boards.start]
name = "Starting Room"
width = 60
height = 25
@@ -193,23 +193,24 @@ height = 25
# grass/dirt/stone/water floor is not representable with one floor attribute).
floor = { biome = "grass" }
# The single grid: all solids and most non-solids (terrain, the player, objects and
# the portal). A space is always a transparent empty cell, so the floor shows through.
[boards.start.grid]
content = """
# The grid holds every solid: terrain, crates, the player and scripted objects. A
# space is a transparent empty cell, so the floor shows through. Portals and sensors
# are *not* here — they sit alongside the grid (see the arrays further down), because
# the player has to be able to share their cell.
grid = """
############################################################
# #
# o #
# oS #
# #
# 1 #
# #
# )######( B #
# # #
# +++ # v #
# # v #
# # #
# | #
# #
# V oo G - @ #
# V oo - @ #
# /# #
# t #
# #
@@ -223,52 +224,99 @@ content = """
# #
############################################################
"""
[boards.start.grid.palette]
"#" = { kind = "wall", tile = "#", fg = "#808080", bg = "#606060" }
"+" = { kind = "banana", tile = "#", fg = "#808080", bg = "#606060" } # unknown kind -> ErrorBlock demo
"o" = { kind = "crate", tile = 254, fg = "#aaaaaa", bg = "#000000" }
"-" = { kind = "hcrate", tile = 29, fg = "#aaaaaa", bg = "#000000" }
"|" = { kind = "vcrate", tile = 18, fg = "#aaaaaa", bg = "#000000" }
">" = { kind = "pusher_east" }
"^" = { kind = "pusher_north" }
"@" = { kind = "player" }
"1" = { kind = "portal", name = "to_house", target_map = "house", target_entry = "from_start" }
"G" = { kind = "object", tile = "#", fg = "#aa3333", bg = "#000000", solid = false, script_name = "greeter" }
"V" = { kind = "object", tile = 1, fg = "#33aa33", bg = "#000000", script_name = "mover" }
"M" = { kind = "object", tile = 15, fg = "#ffdd88", bg = "#000000", solid = true, name = "muffin", script_name = "muffin" }
"B" = { kind = "object", tile = 240, fg = "#cc9944", bg = "#000000", solid = true, name = "noticeboard", script_name = "noticeboard" }
"S" = { kind = "object", tile = 240, fg = "#cc9944", bg = "#000000", solid = true, name = "shifter", script_name = "shifter" }
"/" = { kind = "spinner_cw" }
"t" = { kind = "gem" }
"v" = { kind = "transporter_south" }
")" = { kind = "transporter_east" }
"(" = { kind = "transporter_west" }
[boards.start.palette]
"#" = { type = "builtin", kind = "wall", tile = "#", fg = "#808080", bg = "#606060" }
"o" = { type = "builtin", kind = "crate", tile = 254, fg = "#aaaaaa", bg = "#000000" }
"-" = { type = "builtin", kind = "hcrate", tile = 29, fg = "#aaaaaa", bg = "#000000" }
"|" = { type = "builtin", kind = "vcrate", tile = 18, fg = "#aaaaaa", bg = "#000000" }
">" = { type = "builtin", kind = "pusher_east" }
"^" = { type = "builtin", kind = "pusher_north" }
"/" = { type = "builtin", kind = "spinner_cw" }
"t" = { type = "builtin", kind = "gem" }
"v" = { type = "builtin", kind = "transporter_south" }
")" = { type = "builtin", kind = "transporter_east" }
"(" = { type = "builtin", kind = "transporter_west" }
"@" = { type = "player" }
# Triggers: invisible, non-solid, script-only objects placed off the grid. This one
# watches for the player and logs when they reach its cell.
[[boards.start.triggers]]
# The dancer: walks a fixed loop, and teleports back to where it started if the
# board Registry remembers a previous position.
[boards.start.palette.V]
type = "object"
script = "mover"
enter = "block"
tile = 1
fg = "#33aa33"
bg = "#000000"
[boards.start.palette.M]
type = "object"
script = "muffin"
name = "muffin"
enter = "block"
tile = 15
fg = "#ffdd88"
bg = "#000000"
[boards.start.palette.B]
type = "object"
script = "noticeboard"
name = "noticeboard"
enter = "block"
tile = 240
fg = "#cc9944"
bg = "#000000"
[boards.start.palette.S]
type = "object"
script = "shifter"
name = "shifter"
enter = "block"
tile = 240
fg = "#cc9944"
bg = "#000000"
[[boards.start.portals]]
x = 2
y = 5
name = "to_house"
target_board = "house"
target_name = "from_start"
# The greeter is a sensor, not a grid object: it is visible but does not block, so
# stepping onto it fires its `enter` hook. (A non-solid grid object no longer
# exists — every object in the grid is solid.)
[[boards.start.sensors]]
x = 36
y = 12
script = "greeter"
draw_layer = "Below" # capitalized: DrawLayer's variants are not renamed
glyph = { tile = "#", fg = "#aa3333", bg = "#000000" }
# An invisible tripwire, deliberately placed *under* the hcrate at (40,12): you have
# to shove the crate west before you can stand here and set it off.
[[boards.start.sensors]]
x = 40
y = 12
script_name = "tripwire"
script = "tripwire"
[boards.house.map]
[boards.house]
name = "The House"
width = 60
height = 25
dark = true
# A single fixed floor glyph across the whole board.
floor = { tile = 176, fg = "#888888", bg = "#444444" }
# A single fixed floor glyph across the whole board. There are no light sources
# here, so the board is lit only by the player's own torch (SIGHT_RADIUS, 10).
floor = { glyph = { tile = 176, fg = "#888888", bg = "#444444" } }
# The single grid: terrain, the player, objects and the return portal.
[boards.house.grid]
content = """
# The grid: terrain, the player and objects. The return portal is off-grid, below.
grid = """
############################################################
# #
# K ###F### #
# # # #
# ####### #
# 1 #
# #
# #
# ######### T #
# # # T #
@@ -289,12 +337,50 @@ content = """
# #
############################################################
"""
[boards.house.grid.palette]
"#" = { kind = "wall", tile = 178, fg = "#888888", bg = "#555555" }
"@" = { kind = "player" }
"1" = { kind = "portal", name = "from_start", target_map = "start", target_entry = "to_house" }
"K" = { kind = "object", tile = 240, fg = "#aa7733", bg = "#3d1c00", solid = true, name = "bookshelf", script_name = "bookshelf" }
"F" = { kind = "object", tile = 15, fg = "#ff8800", bg = "#220000", solid = true, name = "fireplace", script_name = "fireplace" }
"C" = { kind = "object", tile = 240, fg = "#ccaa44", bg = "#222200", solid = true, name = "chest", script_name = "chest" }
"T" = { kind = "object", tile = 1, fg = "#99ff44", bg = "#000000", solid = true, script_name = "yammerer" }
[boards.house.palette]
"#" = { type = "builtin", kind = "wall", tile = 178, fg = "#888888", bg = "#555555" }
"@" = { type = "player" }
[boards.house.palette.K]
type = "object"
script = "bookshelf"
name = "bookshelf"
enter = "block"
tile = 240
fg = "#aa7733"
bg = "#3d1c00"
[boards.house.palette.F]
type = "object"
script = "fireplace"
name = "fireplace"
enter = "block"
tile = 15
fg = "#ff8800"
bg = "#220000"
[boards.house.palette.C]
type = "object"
script = "chest"
name = "chest"
enter = "block"
tile = 240
fg = "#ccaa44"
bg = "#222200"
# Seven of these, so it stays unnamed — object names must be board-unique.
[boards.house.palette.T]
type = "object"
script = "yammerer"
enter = "block"
tile = 1
fg = "#99ff44"
bg = "#000000"
[[boards.house.portals]]
x = 56
y = 5
name = "from_start"
target_board = "start"
target_name = "to_house"