Add tile_at_layer and route legacy tile_at to surface layer

Introduces M.tile_at_layer(layer_name, x, y, map_id) for direct per-layer
tile lookup with proper atlas resolution. Refactors the v2 branch of M.tile_at
to delegate to tile_at_layer("surface", ...) instead of duplicating the GID
decode logic inline.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
Axel Meyer
2026-05-21 15:48:07 +02:00
parent 880c67fef3
commit 15fd68670e

View File

@@ -344,6 +344,20 @@ function M.tile_size(map_id)
return map_registry[id].tile_size
end
function M.tile_at_layer(layer_name, x, y, map_id)
local id = map_id or current_map_id
if not id then error("maps.tile_at_layer: no current map") end
local m = map_registry[id]
if x < 0 or x >= m.size.w or y < 0 or y >= m.size.h then return nil end
if not m.layers or not m.layers[layer_name] then return nil end
local gid = m.layers[layer_name].tiles[y * m.size.w + x + 1] or 0
if gid == 0 then return nil end
local atlas_idx, tile_id, _rot = decode_gid(gid)
local atlas = m.atlases[atlas_idx + 1]
if not atlas then return nil end
return atlas.tiles[tile_id]
end
-- Arity-flex sugar: tile_at(tx, ty) uses current_map_id; tile_at(map_id, tx, ty)
-- is explicit. Both forms accept nil map_id and fall back to current_map_id.
function M.tile_at(a, b, c)
@@ -361,21 +375,12 @@ function M.tile_at(a, b, c)
if not m then
error(string.format("maps.tile_at: unknown map-id '%s'", tostring(map_id)))
end
if tx < 0 or tx >= m.size.w or ty < 0 or ty >= m.size.h then
return nil
end
-- v2 path: read from surface layer using GID encoding
-- v2 path: query surface layer for back-compat
if m.schema_version == 2 then
local surface = m.layers and m.layers.surface
if not surface then return nil end
local gid = surface.tiles[ty * m.size.w + tx + 1]
if not gid or gid == 0 then return nil end
local atlas_index, tile_id, _ = decode_gid(gid)
local atlas = m.atlases[atlas_index + 1]
if not atlas then return nil end
return atlas.tiles[tile_id]
return M.tile_at_layer("surface", tx, ty, map_id)
end
-- v1 legacy path (should not be reached after M.load auto-upgrades, kept for M.create)
-- v1 path (legacy): kept for any non-upgraded maps that bypass M.load
if tx < 0 or tx >= m.size.w or ty < 0 or ty >= m.size.h then return nil end
local palette_id = m.tiles[ty * m.size.w + tx + 1]
return m.tilemap.tiles[palette_id]
end