Add set_cell_gid write API to lib-core.maps
Validates layer name against VALID_LAYER_NAMES, bounds-checks the target cell, auto-allocates the layer table if the caller writes to a previously-empty layer. Marks the map as dirty for callers that track in-memory mutations.
This commit is contained in:
52
init.lua
52
init.lua
@@ -12,6 +12,15 @@ local map_registry = {} -- map_id -> Map
|
|||||||
local tilemap_registry = {} -- full_tilemap_id -> Tilemap
|
local tilemap_registry = {} -- full_tilemap_id -> Tilemap
|
||||||
local current_map_id = nil
|
local current_map_id = nil
|
||||||
|
|
||||||
|
-- Internal: resolve and return map by id, or raise.
|
||||||
|
local function require_map(map_id)
|
||||||
|
local id = map_id or current_map_id
|
||||||
|
if not id then error("maps: no current map set") end
|
||||||
|
local m = map_registry[id]
|
||||||
|
if not m then error(string.format("maps: no map registered with id '%s'", id)) end
|
||||||
|
return m
|
||||||
|
end
|
||||||
|
|
||||||
-- =====================================================================
|
-- =====================================================================
|
||||||
-- Packed-u32 GID encoding (Schema-v2)
|
-- Packed-u32 GID encoding (Schema-v2)
|
||||||
-- Bit-Layout:
|
-- Bit-Layout:
|
||||||
@@ -628,6 +637,49 @@ function M.cell_gid(layer_name, x, y, map_id)
|
|||||||
return m.layers[layer_name].tiles[y * m.size.w + x + 1] or 0
|
return m.layers[layer_name].tiles[y * m.size.w + x + 1] or 0
|
||||||
end
|
end
|
||||||
|
|
||||||
|
-- =====================================================================
|
||||||
|
-- Write APIs (v0.4.0)
|
||||||
|
-- =====================================================================
|
||||||
|
|
||||||
|
-- Helper: gather valid layer names for error messages.
|
||||||
|
local function get_valid_layer_names_list()
|
||||||
|
local names = {}
|
||||||
|
for name, _ in pairs(VALID_LAYER_NAMES) do
|
||||||
|
table.insert(names, name)
|
||||||
|
end
|
||||||
|
table.sort(names)
|
||||||
|
return names
|
||||||
|
end
|
||||||
|
|
||||||
|
-- Internal: get-or-allocate a layer table for in-place writes.
|
||||||
|
local function get_or_alloc_layer(map, layer_name)
|
||||||
|
if not VALID_LAYER_NAMES[layer_name] then
|
||||||
|
error(string.format("maps: unknown layer '%s' (valid: %s)",
|
||||||
|
layer_name, table.concat(get_valid_layer_names_list(), ", ")))
|
||||||
|
end
|
||||||
|
local layer = map.layers[layer_name]
|
||||||
|
if not layer then
|
||||||
|
local cell_count = map.size.w * map.size.h
|
||||||
|
local tiles = {}
|
||||||
|
for i = 1, cell_count do tiles[i] = 0 end
|
||||||
|
layer = { tiles = tiles }
|
||||||
|
map.layers[layer_name] = layer
|
||||||
|
end
|
||||||
|
return layer
|
||||||
|
end
|
||||||
|
|
||||||
|
function M.set_cell_gid(layer_name, x, y, gid, map_id)
|
||||||
|
local map = require_map(map_id)
|
||||||
|
if x < 0 or y < 0 or x >= map.size.w or y >= map.size.h then
|
||||||
|
error(string.format("maps.set_cell_gid: cell (%d,%d) out of bounds for size %dx%d",
|
||||||
|
x, y, map.size.w, map.size.h))
|
||||||
|
end
|
||||||
|
local layer = get_or_alloc_layer(map, layer_name)
|
||||||
|
local idx = y * map.size.w + x + 1
|
||||||
|
layer.tiles[idx] = gid
|
||||||
|
map._dirty = true
|
||||||
|
end
|
||||||
|
|
||||||
function M.is_indoor(x, y, map_id)
|
function M.is_indoor(x, y, map_id)
|
||||||
local id = map_id or current_map_id
|
local id = map_id or current_map_id
|
||||||
if not id then error("maps.is_indoor: no current map") end
|
if not id then error("maps.is_indoor: no current map") end
|
||||||
|
|||||||
Reference in New Issue
Block a user