| Crates.io | bevy_ecs_tiled |
| lib.rs | bevy_ecs_tiled |
| version | 0.9.5 |
| created_at | 2024-07-13 10:34:03.768696+00 |
| updated_at | 2025-09-23 21:24:50.555118+00 |
| description | A Bevy plugin for loading Tiled maps |
| homepage | https://github.com/adrien-bon/bevy_ecs_tiled |
| repository | https://github.com/adrien-bon/bevy_ecs_tiled |
| max_upload_size | |
| id | 1302227 |
| size | 691,302 |
bevy_ecs_tiled is a Bevy plugin for working with 2D tilemaps created using the Tiled map editor.
It leverages the official Tiled Rust bindings for parsing and loading Tiled map files, and uses the bevy_ecs_tilemap crate for efficient rendering.
This plugin aims to provide a simple and ergonomic workflow for integrating Tiled into your Bevy 2D games, letting you focus on game design while handling the technical details of map loading, rendering, and entity management.
Visibility and Transform are automatically propagated.Update your Bevy components directly from Tiled editor:

Use several maps to build a huge world:

This crate is documented in three places:
bevy_ecs_tiled book with design explanations, how-to guides and migrations guides.There is notably a FAQ that will hopefully answer most of your questions.
Add the required dependencies to your Cargo.toml file:
[dependencies]
bevy = "0.16"
bevy_ecs_tiled = "0.9"
To get started, add the plugin to your app and spawn a map entity.
All you need to do is spawn a TiledMap component with the map asset you want to load (e.g., your map.tmx file).
Make sure this map asset, along with any required dependencies (such as images or tilesets), is present in your local assets folder (by default, ./assets/).
use bevy::prelude::*;
use bevy_ecs_tiled::prelude::*;
fn main() {
App::new()
// Add Bevy's default plugins
.add_plugins(DefaultPlugins)
// Add the bevy_ecs_tiled plugin.
// bevy_ecs_tilemap::TilemapPlugin will be added automatically if needed
.add_plugins(TiledPlugin::default())
// Add your startup system and run the app
.add_systems(Startup, startup)
.run();
}
fn startup(
mut commands: Commands,
asset_server: Res<AssetServer>,
) {
// Spawn a 2D camera
commands.spawn(Camera2d);
// Load a map asset and retrieve its handle
let map_handle: Handle<TiledMapAsset> = asset_server.load("map.tmx");
// Spawn a new entity with the TiledMap component
commands.spawn(TiledMap(map_handle));
}
This simple example will load a map using the default settings.
You can customize how the map is loaded by listening to specific TiledEvent or adding various components to the map entity, such as:
TilemapAnchor — Controls the anchor point of the tilemap.TiledMapLayerZOffset — Adjusts the Z offset between map layers.TiledMapImageRepeatMargin — Control the margin for repeated images.TilemapRenderSettings — Configures rendering options.Transform — Sets the position, rotation, and scale of the map.Visibility — Controls the visibility of the map entity.use bevy::prelude::*;
use bevy_ecs_tiled::prelude::*;
fn spawn_map(
mut commands: Commands,
asset_server: Res<AssetServer>,
) {
commands
// Load a map and set its anchor point to the
// center instead of the default bottom-left
.spawn((
TiledMap(asset_server.load("map.tmx")),
TilemapAnchor::Center,
))
// Add an "in-line" observer to detect when
// the map has finished loading
.observe(
|trigger: Trigger<TiledEvent<MapCreated>>,
assets: Res<Assets<TiledMapAsset>>,
query: Query<(&Name, &TiledMapStorage), With<TiledMap>>| {
// We can access the map components via a regular query
let Ok((name, storage)) = query.get(trigger.event().origin) else {
return;
};
info!("=> Observer TiledMapCreated was triggered for map '{name}'");
// Or directly the underneath raw tiled::Map data
let Some(map) = trigger.event().get_map(&assets) else {
return;
};
info!("Loaded map: {:?}", map);
// Additionally, we can access Tiled items using the TiledMapStorage
// component: we can retrieve Tiled items entity and access
// their own components with another query (not shown here).
// This can be useful if you want for instance to create a resource
// based upon tiles or objects data but make it available only when
// the map is actually spawned.
for (id, entity) in storage.objects() {
info!(
"(map) Object ID {:?} was spawned as entity {:?}",
id, entity
);
}
}
);
}
For more advanced use cases, such as loading worlds, chunking, custom properties, or integrating with physics, see the examples directory in the repository.
You can also refer to the API documentation for details on all available components and configuration options.
| bevy | bevy_ecs_tilemap | bevy_ecs_tiled |
|---|---|---|
| 0.16 | 0.16 | 0.7 - 0.9 |
| 0.15 | 0.15 | 0.5 - 0.6 |
| 0.14 | 0.14 | 0.3 - 0.4 |
| 0.13 | main@e4f3cc6 | branch 0.2 |
| 0.12 | 0.12 | 0.1 |
If you can contribute, please do!
If you would like to contribute but don't know where to start, read this section in the book.
This work is licensed under the MIT license.
SPDX-License-Identifier: MIT