Draw materials in tile atlas view

This commit is contained in:
kobewi 2023-06-06 14:42:27 +02:00
parent 0a0132ccf4
commit 16ac217aa0
2 changed files with 46 additions and 2 deletions

View File

@ -244,13 +244,16 @@ void TileAtlasView::_draw_base_tiles() {
for (int i = 0; i < tile_set_atlas_source->get_tiles_count(); i++) {
Vector2i atlas_coords = tile_set_atlas_source->get_tile_id(i);
// Different materials need to be drawn with different CanvasItems.
RID ci_rid = _get_canvas_item_to_draw(tile_set_atlas_source->get_tile_data(atlas_coords, 0), base_tiles_draw, material_tiles_draw);
for (int frame = 0; frame < tile_set_atlas_source->get_tile_animation_frames_count(atlas_coords); frame++) {
// Update the y to max value.
Rect2i base_frame_rect = tile_set_atlas_source->get_tile_texture_region(atlas_coords, frame);
Vector2 offset_pos = Rect2(base_frame_rect).get_center() + Vector2(tile_set_atlas_source->get_tile_data(atlas_coords, 0)->get_texture_origin());
// Draw the tile.
TileMap::draw_tile(base_tiles_draw->get_canvas_item(), offset_pos, tile_set, source_id, atlas_coords, 0, frame);
TileMap::draw_tile(ci_rid, offset_pos, tile_set, source_id, atlas_coords, 0, frame);
}
}
@ -286,6 +289,33 @@ void TileAtlasView::_draw_base_tiles() {
}
}
RID TileAtlasView::_get_canvas_item_to_draw(const TileData *p_for_data, const CanvasItem *p_base_item, HashMap<Ref<Material>, RID> &p_material_map) {
Ref<Material> mat = p_for_data->get_material();
if (mat.is_null()) {
return p_base_item->get_canvas_item();
} else if (p_material_map.has(mat)) {
return p_material_map[mat];
} else {
RID ci_rid = RS::get_singleton()->canvas_item_create();
RS::get_singleton()->canvas_item_set_parent(ci_rid, p_base_item->get_canvas_item());
RS::get_singleton()->canvas_item_set_material(ci_rid, mat->get_rid());
p_material_map[mat] = ci_rid;
return ci_rid;
}
}
void TileAtlasView::_clear_material_canvas_items() {
for (KeyValue<Ref<Material>, RID> kv : material_tiles_draw) {
RS::get_singleton()->free(kv.value);
}
material_tiles_draw.clear();
for (KeyValue<Ref<Material>, RID> kv : material_alternatives_draw) {
RS::get_singleton()->free(kv.value);
}
material_alternatives_draw.clear();
}
void TileAtlasView::_draw_base_tiles_texture_grid() {
Ref<Texture2D> texture = tile_set_atlas_source->get_texture();
if (texture.is_valid()) {
@ -370,6 +400,9 @@ void TileAtlasView::_draw_alternatives() {
TileData *tile_data = tile_set_atlas_source->get_tile_data(atlas_coords, alternative_id);
bool transposed = tile_data->get_transpose();
// Different materials need to be drawn with different CanvasItems.
RID ci_rid = _get_canvas_item_to_draw(tile_data, alternatives_draw, material_alternatives_draw);
// Update the y to max value.
Vector2i offset_pos;
if (transposed) {
@ -381,7 +414,7 @@ void TileAtlasView::_draw_alternatives() {
}
// Draw the tile.
TileMap::draw_tile(alternatives_draw->get_canvas_item(), offset_pos, tile_set, source_id, atlas_coords, alternative_id);
TileMap::draw_tile(ci_rid, offset_pos, tile_set, source_id, atlas_coords, alternative_id);
// Increment the x position.
current_pos.x += transposed ? texture_region_size.y : texture_region_size.x;
@ -405,6 +438,8 @@ void TileAtlasView::set_atlas_source(TileSet *p_tile_set, TileSetAtlasSource *p_
tile_set = p_tile_set;
tile_set_atlas_source = p_tile_set_atlas_source;
_clear_material_canvas_items();
if (!tile_set) {
return;
}
@ -695,3 +730,7 @@ TileAtlasView::TileAtlasView() {
alternatives_draw->connect("draw", callable_mp(this, &TileAtlasView::_draw_alternatives));
alternative_tiles_drawing_root->add_child(alternatives_draw);
}
TileAtlasView::~TileAtlasView() {
_clear_material_canvas_items();
}

View File

@ -89,7 +89,11 @@ private:
Control *base_tiles_drawing_root = nullptr;
Control *base_tiles_draw = nullptr;
HashMap<Ref<Material>, RID> material_tiles_draw;
HashMap<Ref<Material>, RID> material_alternatives_draw;
void _draw_base_tiles();
RID _get_canvas_item_to_draw(const TileData *p_for_data, const CanvasItem *p_base_item, HashMap<Ref<Material>, RID> &p_material_map);
void _clear_material_canvas_items();
Control *base_tiles_texture_grid = nullptr;
void _draw_base_tiles_texture_grid();
@ -164,6 +168,7 @@ public:
void queue_redraw();
TileAtlasView();
~TileAtlasView();
};
#endif // TILE_ATLAS_VIEW_H