godot-tilemap
gamedev-skills/awesome-gamedev-agent-skills
Build and edit tile-based 2D levels in Godot 4.7 with TileMapLayer, collision, terrains, and runtime cell manipulation.
What is godot-tilemap?
Create and manage tile-based 2D levels in Godot 4.7 using TileMapLayer nodes and TileSet resources. Configure per-tile collision, navigation, custom data, and autotiling with terrain sets. Use this skill when designing tile grids, setting up tilesets, or reading/writing tiles from code.
- Paint and edit tiles in 2D levels using TileMapLayer nodes
- Define per-tile collision polygons, navigation layers, and custom data in TileSet editor
- Autotile with terrain sets for self-connecting tiles
- Read and write tile cells at runtime with local_to_map, set_cell, and get_cell_tile_data
- Convert mouse positions to grid cells and query tile properties
- Migrate deprecated TileMap nodes to multiple TileMapLayer nodes
How to install godot-tilemap
npx skills add https://github.com/gamedev-skills/awesome-gamedev-agent-skills --skill godot-tilemap- Godot 4.7 installed
- Basic understanding of Godot scene structure and GDScript
How to use godot-tilemap
- 1.Create a TileMapLayer node in your scene (one per visual/logical layer)
- 2.Create or assign a TileSet resource to the layer's tile_set property
- 3.Add an atlas source (texture) to the TileSet and slice it into tiles in the TileSet editor
- 4.Define tile data: physics layers for collision, custom data layers for per-tile properties, and terrain sets for autotiling
- 5.Paint tiles using the TileMap bottom panel (Paint/Line/Rectangle/Bucket modes)
- 6.Enable collision_enabled and navigation_enabled on the layer if needed
- 7.Use set_cell, get_cell_tile_data, and local_to_map in GDScript to manipulate and query tiles at runtime
Use cases
- Design a dungeon or platformer level by painting tiles on multiple layers
- Add custom per-tile properties (damage, is_ladder, is_spawn) and query them at runtime
- Implement terrain autotiling so grass, water, and stone edges connect automatically
- Procedurally place or erase tiles during gameplay (digging, building, destruction)
- Find all tiles with a specific property (e.g., spawn points) by iterating used cells
- Game developers building 2D tile-based games in Godot 4.7
- Level designers creating grid-based environments
- Programmers implementing runtime tilemap manipulation and tile queries
godot-tilemap FAQ
TileMap (deprecated in Godot 4.3) was a single node that held multiple layers. TileMapLayer is the new approach: one node per layer, each with its own TileSet. Group multiple TileMapLayer nodes under a parent Node2D to replicate the old multi-layer structure.
local_to_map expects local coordinates relative to the TileMapLayer node. If you pass global coordinates (e.g., from mouse input), convert them first with to_local(global_pos).
In the TileSet editor, create a custom data layer (e.g., 'damage' as int type), then assign values to each tile. At runtime, retrieve them with get_cell_tile_data(cell).get_custom_data('damage').
It returns null for empty cells or non-atlas sources. Always null-check before calling get_custom_data. Ensure the cell contains a tile from an atlas source.
Define a terrain set and terrain in the TileSet editor with proper bitmask peering, then use set_cells_terrain_connect(cells, terrain_set, terrain, true) to paint a region with automatic edge/corner tiles.
Full instructions (SKILL.md)
Source of truth, from gamedev-skills/awesome-gamedev-agent-skills.
name: godot-tilemap description: > Build and edit tile-based 2D levels in Godot 4.7 with TileMapLayer and TileSet: paint layers, set up collision/navigation/custom-data on tiles, autotile with terrain sets, and read/write cells from code (set_cell, get_cell_tile_data, local_to_map). Use when working with TileMapLayer nodes, .tres TileSets, autotiling, or migrating a deprecated TileMap node to TileMapLayer.
Godot TileMap (4.7 TileMapLayer)
Author tile-based levels with TileMapLayer + TileSet, add per-tile collision and
custom data, autotile with terrains, and manipulate cells at runtime. Targets
Godot 4.7, where TileMapLayer replaces the now-deprecated TileMap node.
When to use
- Use when designing 2D levels from a tile grid, configuring a
TileSet(collision, navigation, custom data, terrains), or reading/writing tiles from code. - Use when migrating a
TileMapnode (single node, many layers) to multipleTileMapLayernodes (one layer each).
When not to use: moving the player across the tiles → godot-2d-movement; general
physics bodies/raycasts → godot-physics; procedural map generation algorithms →
procedural-gen; level design practice → level-design.
Core workflow
- Add a
TileMapLayernode (one per visual/logical layer: background, walls, foreground). Each holds exactly one layer of tiles. - Create or assign a
TileSeton the layer'stile_setproperty. Add an atlas source (a texture sliced into tiles) in the TileSet editor. Save the TileSet as an external.tresso multiple layers/levels reuse it. - Add tile data in the TileSet editor: physics layers (collision polygons),
navigation layers, occlusion, and custom data layers (typed per-tile values like
damageoris_ladder). - Paint in the TileMap bottom panel (Paint/Line/Rectangle/Bucket). For self- connecting tiles, define a terrain set and paint with Connect/Path mode.
- Enable per-layer collision/navigation via the layer's
collision_enabled/navigation_enabledproperties. - Read/write from code with
local_to_map,set_cell,get_cell_source_id, andget_cell_tile_data(...).get_custom_data(...).
Patterns
1. Convert mouse position to a cell and read its custom data
extends TileMapLayer
func _unhandled_input(event: InputEvent) -> void:
if event is InputEventMouseButton and event.pressed:
# local_to_map expects local coords; convert from global first.
var cell := local_to_map(to_local(event.position))
var data := get_cell_tile_data(cell) # TileData or null
if data:
var dmg: int = data.get_custom_data("damage") # custom data layer
print("Cell %s deals %d damage" % [cell, dmg])
2. Place and erase tiles at runtime
# set_cell(coords, source_id, atlas_coords, alternative_tile = 0)
func place_wall(cell: Vector2i) -> void:
set_cell(cell, 0, Vector2i(2, 1)) # source 0, atlas tile at column 2, row 1
func dig(cell: Vector2i) -> void:
erase_cell(cell) # same as set_cell(cell, -1)
func clear_level() -> void:
clear() # remove every tile on this layer
3. Autotiling a region with a terrain set
# Paint a filled area with terrain `terrain` of terrain set `terrain_set`;
# Godot picks the correct edge/corner tiles to connect them.
func fill_with_grass(cells: Array[Vector2i]) -> void:
var terrain_set := 0
var grass_terrain := 0
set_cells_terrain_connect(cells, terrain_set, grass_terrain, true)
4. Iterate placed tiles (e.g. find all spawn tiles)
func find_spawns() -> Array[Vector2i]:
var spawns: Array[Vector2i] = []
for cell in get_used_cells():
var data := get_cell_tile_data(cell)
if data and data.get_custom_data("is_spawn"):
spawns.append(cell)
return spawns
Pitfalls
TileMapnode is deprecated in 4.3. UseTileMapLayernodes (one layer per node); group them under a parentNode2D. OldTileMapcalls that took alayerargument (set_cell(layer, ...)) do not apply toTileMapLayer.local_to_mapneeds local coordinates. Mouse/global positions must be converted withto_local(...)first, or cells will be offset.get_cell_tile_datareturnsnullfor empty cells or non-atlas sources — always null-check beforeget_custom_data.- Custom data is typed. A layer declared as
intreturnsint; reading it as the wrong type or referencing a non-existent layer name errors. Define the layer in the TileSet first. - Terrains need every combination defined.
set_cells_terrain_connectproduces odd results if the TileSet's terrain bitmask peering is incomplete. - Runtime edits are batched to end-of-frame. If you must read updated internals
immediately after
set_cell, callupdate_internals()(expensive — avoid in loops). - Collision not working? Check the layer's
collision_enabled, that the tile has a physics layer with a polygon, and that the TileSet's physics layer mask matches your bodies.
References
- For TileSet setup (atlas sources, physics/navigation/custom-data layers, terrain
bitmasks), scene tiles, Y-sorting, and runtime tile-data overrides
(
_use_tile_data_runtime_update), readreferences/tileset-and-terrains.md.
Related skills
godot-2d-movement— characters that walk on these tiles.godot-physics— collision layers/masks the tile collisions participate in.procedural-gen— generating tilemaps from noise/RNG.level-design/roguelike— design practice and grid-based genres.
Related skills
More from gamedev-skills/awesome-gamedev-agent-skills and the wider catalog.

godot-ui-control
Build responsive Godot 4.7 UIs with Control nodes, Containers, Themes, and keyboard/gamepad focus.

input-systems
Design game input as named actions with rebinding, multi-device support, deadzones, and feel features like buffering and coyote time.

itch-publish
Publish and update game builds on itch.io using butler CLI with efficient delta uploads.

level-design
Design playable levels through blockout-to-playable workflow: metrics, pacing, gating, and encounter design.

love2d-core
Set up and debug LÖVE 11.x games: the callback loop, delta-time movement, input, and screen states.

performance-optimization
Measure, find the bottleneck, apply the right fix—CPU pooling/allocation control or GPU batching/draw calls.