epic: refactor SDL2_Renderer usage to IRenderer and queued texture rendering

- Updated the testing guide to clarify the testing framework's organization and execution methods, improving user understanding.
- Refactored CMakeLists to include new platform-specific files, ensuring proper integration of the rendering backend.
- Modified main application files to utilize the new IRenderer interface, enhancing flexibility in rendering operations.
- Implemented deferred texture management in various components, allowing for more efficient graphics handling and improved performance.
- Introduced new methods for texture creation and updates, streamlining the rendering process across the application.
- Enhanced logging and error handling in the rendering pipeline to facilitate better debugging and diagnostics.
This commit is contained in:
scawful
2025-10-07 17:15:11 -04:00
parent 9e6f538520
commit 6c331f1fd0
101 changed files with 1401 additions and 2677 deletions

View File

@@ -15,7 +15,6 @@
#include "absl/strings/str_format.h"
#include "app/core/asar_wrapper.h"
#include "app/core/features.h"
#include "app/core/window.h"
#include "app/editor/overworld/map_properties.h"
#include "app/editor/overworld/tile16_editor.h"
#include "app/gfx/arena.h"
@@ -43,7 +42,6 @@
namespace yaze::editor {
using core::Renderer;
using namespace ImGui;
constexpr float kInputFieldSize = 30.f;
@@ -710,7 +708,8 @@ void OverworldEditor::RenderUpdatedMapBitmap(
current_bitmap.set_modified(true);
// Immediately update the texture to reflect changes
core::Renderer::Get().UpdateBitmap(&current_bitmap);
// TODO: Queue texture for later rendering.
// core::Renderer::Get().UpdateBitmap(&current_bitmap);
}
void OverworldEditor::CheckForOverworldEdits() {
@@ -1092,11 +1091,13 @@ absl::Status OverworldEditor::CheckForCurrentMap() {
// Ensure tile16 blockset is fully updated before rendering
if (tile16_blockset_.atlas.is_active()) {
Renderer::Get().UpdateBitmap(&tile16_blockset_.atlas);
// TODO: Queue texture for later rendering.
// Renderer::Get().UpdateBitmap(&tile16_blockset_.atlas);
}
// Update map texture with the traditional direct update approach
Renderer::Get().UpdateBitmap(&maps_bmp_[current_map_]);
// TODO: Queue texture for later rendering.
// Renderer::Get().UpdateBitmap(&maps_bmp_[current_map_]);
maps_bmp_[current_map_].set_modified(false);
}
@@ -1411,9 +1412,10 @@ absl::Status OverworldEditor::DrawAreaGraphics() {
overworld_.set_current_map(current_map_);
palette_ = overworld_.current_area_palette();
gfx::Bitmap bmp;
Renderer::Get().CreateAndRenderBitmap(0x80, kOverworldMapSize, 0x08,
overworld_.current_graphics(), bmp,
palette_);
// TODO: Queue texture for later rendering.
// Renderer::Get().CreateAndRenderBitmap(0x80, kOverworldMapSize, 0x08,
// overworld_.current_graphics(), bmp,
// palette_);
current_graphics_set_[current_map_] = bmp;
}
}
@@ -1483,17 +1485,19 @@ absl::Status OverworldEditor::LoadGraphics() {
// This avoids blocking the main thread with GPU texture creation
{
gfx::ScopedTimer gfx_timer("CreateBitmapWithoutTexture_Graphics");
Renderer::Get().CreateBitmapWithoutTexture(0x80, kOverworldMapSize, 0x40,
overworld_.current_graphics(),
current_gfx_bmp_, palette_);
// TODO: Queue texture for later rendering.
// Renderer::Get().CreateBitmapWithoutTexture(0x80, kOverworldMapSize, 0x40,
// overworld_.current_graphics(),
// current_gfx_bmp_, palette_);
}
LOG_DEBUG("OverworldEditor", "Loading overworld tileset (deferred textures).");
{
gfx::ScopedTimer tileset_timer("CreateBitmapWithoutTexture_Tileset");
Renderer::Get().CreateBitmapWithoutTexture(
0x80, 0x2000, 0x08, overworld_.tile16_blockset_data(),
tile16_blockset_bmp_, palette_);
// TODO: Queue texture for later rendering.
// Renderer::Get().CreateBitmapWithoutTexture(
// 0x80, 0x2000, 0x08, overworld_.tile16_blockset_data(),
// tile16_blockset_bmp_, palette_);
}
map_blockset_loaded_ = true;
@@ -1504,8 +1508,14 @@ absl::Status OverworldEditor::LoadGraphics() {
{
gfx::ScopedTimer tilemap_timer("CreateTilemap");
tile16_blockset_ =
gfx::CreateTilemap(tile16_blockset_data, 0x80, 0x2000, kTile16Size,
gfx::CreateTilemap(renderer_,tile16_blockset_data, 0x80, 0x2000, kTile16Size,
zelda3::kNumTile16Individual, palette_);
// Queue texture creation for the tile16 blockset atlas
if (tile16_blockset_.atlas.is_active() && tile16_blockset_.atlas.surface()) {
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::CREATE, &tile16_blockset_.atlas);
}
}
// Phase 2: Create bitmaps only for essential maps initially
@@ -1566,7 +1576,9 @@ absl::Status OverworldEditor::LoadGraphics() {
{
gfx::ScopedTimer initial_textures_timer("CreateInitialTextures");
for (int i = 0; i < initial_texture_count; ++i) {
Renderer::Get().RenderBitmap(maps_to_texture[i]);
// Queue texture creation/update for initial maps via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::CREATE, maps_to_texture[i]);
}
}
@@ -1588,7 +1600,10 @@ absl::Status OverworldEditor::LoadGraphics() {
priority = (map_world == current_world_) ? 5 : 15; // Current world = priority 5, others = 15
}
gfx::Arena::Get().QueueDeferredTexture(maps_to_texture[i], priority);
// Queue texture creation for remaining maps via Arena's deferred system
// Note: Priority system to be implemented in future enhancement
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::CREATE, maps_to_texture[i]);
}
if (core::FeatureFlags::get().overworld.kDrawOverworldSprites) {
@@ -1617,20 +1632,16 @@ absl::Status OverworldEditor::LoadSpriteGraphics() {
sprite_previews_[sprite.id()].Create(width, height, depth,
*sprite.preview_graphics());
sprite_previews_[sprite.id()].SetPalette(palette_);
Renderer::Get().RenderBitmap(&(sprite_previews_[sprite.id()]));
// TODO: Queue texture for later rendering.
// Renderer::Get().RenderBitmap(&(sprite_previews_[sprite.id()]));
}
return absl::OkStatus();
}
void OverworldEditor::ProcessDeferredTextures() {
// Use Arena's centralized progressive loading system
// This makes progressive loading available to all editors
auto batch = gfx::Arena::Get().GetNextDeferredTextureBatch(4, 2);
for (auto* bitmap : batch) {
if (bitmap && !bitmap->texture()) {
Renderer::Get().RenderBitmap(bitmap);
}
// Process queued texture commands via Arena's deferred system
if (renderer_) {
gfx::Arena::Get().ProcessTextureQueue(renderer_);
}
// Also process deferred map refreshes for modified maps
@@ -1682,8 +1693,9 @@ void OverworldEditor::EnsureMapTexture(int map_index) {
}
if (!bitmap.texture() && bitmap.is_active()) {
Renderer::Get().RenderBitmap(&bitmap);
// Note: Arena automatically removes from deferred queue when textures are created
// Queue texture creation for this map
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::CREATE, &bitmap);
}
}
@@ -1783,11 +1795,14 @@ void OverworldEditor::RefreshChildMapOnDemand(int map_index) {
map_index);
}
// CRITICAL FIX: Force COMPLETE texture recreation for immediate visibility
// UpdateBitmap() was still deferred - we need to force a full re-render
// Always recreate the texture to ensure immediate GPU update
Renderer::Get().RenderBitmap(&maps_bmp_[map_index]);
// Queue texture update to ensure changes are visible
if (maps_bmp_[map_index].texture()) {
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &maps_bmp_[map_index]);
} else {
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::CREATE, &maps_bmp_[map_index]);
}
}
// Handle multi-area maps (large, wide, tall) with safe coordination
@@ -1933,9 +1948,10 @@ void OverworldEditor::RefreshMultiAreaMapsSafely(int map_index,
}
maps_bmp_[sibling].set_modified(false);
// Update texture if it exists
// Queue texture update/creation
if (maps_bmp_[sibling].texture()) {
core::Renderer::Get().UpdateBitmap(&maps_bmp_[sibling]);
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &maps_bmp_[sibling]);
} else {
EnsureMapTexture(sibling);
}
@@ -2192,8 +2208,19 @@ absl::Status OverworldEditor::RefreshTile16Blockset() {
const auto tile16_data = overworld_.tile16_blockset_data();
gfx::UpdateTilemap(tile16_blockset_, tile16_data);
gfx::UpdateTilemap(renderer_, tile16_blockset_, tile16_data);
tile16_blockset_.atlas.SetPalette(palette_);
// Queue texture update for the atlas
if (tile16_blockset_.atlas.texture() && tile16_blockset_.atlas.is_active()) {
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &tile16_blockset_.atlas);
} else if (!tile16_blockset_.atlas.texture() && tile16_blockset_.atlas.is_active()) {
// Create texture if it doesn't exist yet
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::CREATE, &tile16_blockset_.atlas);
}
return absl::OkStatus();
}

View File

@@ -68,6 +68,7 @@ class OverworldEditor : public Editor, public gfx::GfxContext {
// MapPropertiesSystem will be initialized after maps_bmp_ and canvas are ready
}
void Initialize(gfx::IRenderer* renderer, Rom* rom);
void Initialize() override;
absl::Status Load() override;
absl::Status Update() final;
@@ -326,6 +327,7 @@ class OverworldEditor : public Editor, public gfx::GfxContext {
Rom* rom_;
gfx::IRenderer* renderer_;
Tile16Editor tile16_editor_{rom_, &tile16_blockset_};
GfxGroupEditor gfx_group_editor_;
PaletteEditor palette_editor_;

View File

@@ -138,7 +138,9 @@ absl::Status OverworldEditor::DrawScratchSpace() {
if (all_gfx_loaded_) {
palette_ = overworld_.current_area_palette();
current_slot.scratch_bitmap.SetPalette(palette_);
core::Renderer::Get().RenderBitmap(&current_slot.scratch_bitmap);
// Queue texture creation via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::CREATE, &current_slot.scratch_bitmap);
}
}
@@ -315,9 +317,9 @@ void OverworldEditor::UpdateScratchBitmapTile(int tile_x, int tile_y,
}
scratch_slot.scratch_bitmap.set_modified(true);
// Use batch operations for texture updates
scratch_slot.scratch_bitmap.QueueTextureUpdate(
core::Renderer::Get().renderer());
// Queue texture update via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &scratch_slot.scratch_bitmap);
scratch_slot.in_use = true;
}
@@ -360,7 +362,9 @@ absl::Status OverworldEditor::SaveCurrentSelectionToScratch(int slot) {
if (all_gfx_loaded_) {
palette_ = overworld_.current_area_palette();
scratch_spaces_[slot].scratch_bitmap.SetPalette(palette_);
core::Renderer::Get().RenderBitmap(
// Queue texture creation via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::CREATE,
&scratch_spaces_[slot].scratch_bitmap);
}
@@ -398,8 +402,6 @@ absl::Status OverworldEditor::SaveCurrentSelectionToScratch(int slot) {
scratch_spaces_[slot].in_use = true;
}
// Process all queued texture updates at once
gfx::Arena::Get().ProcessBatchTextureUpdates();
return absl::OkStatus();
}
@@ -433,7 +435,9 @@ absl::Status OverworldEditor::ClearScratchSpace(int slot) {
auto& data = scratch_spaces_[slot].scratch_bitmap.mutable_data();
std::fill(data.begin(), data.end(), 0);
scratch_spaces_[slot].scratch_bitmap.set_modified(true);
core::Renderer::Get().UpdateBitmap(&scratch_spaces_[slot].scratch_bitmap);
// Queue texture update via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &scratch_spaces_[slot].scratch_bitmap);
}
return absl::OkStatus();

View File

@@ -3,13 +3,12 @@
#include <array>
#include "absl/status/status.h"
#include "app/core/window.h"
#include "app/gfx/arena.h"
#include "app/gfx/bitmap.h"
#include "app/gfx/backend/irenderer.h"
#include "app/gfx/performance_profiler.h"
#include "app/gfx/snes_palette.h"
#include "app/gui/canvas.h"
#include "app/gui/icons.h"
#include "app/gui/input.h"
#include "app/gui/style.h"
#include "app/rom.h"
@@ -22,7 +21,6 @@
namespace yaze {
namespace editor {
using core::Renderer;
using namespace ImGui;
absl::Status Tile16Editor::Initialize(
@@ -34,14 +32,16 @@ absl::Status Tile16Editor::Initialize(
current_gfx_bmp_.Create(current_gfx_bmp.width(), current_gfx_bmp.height(),
current_gfx_bmp.depth(), current_gfx_bmp.vector());
current_gfx_bmp_.SetPalette(current_gfx_bmp.palette()); // Temporary palette
core::Renderer::Get().RenderBitmap(&current_gfx_bmp_);
// TODO: Queue texture for later rendering.
// core::Renderer::Get().RenderBitmap(&current_gfx_bmp_);
// Copy the tile16 blockset bitmap
tile16_blockset_bmp_.Create(
tile16_blockset_bmp.width(), tile16_blockset_bmp.height(),
tile16_blockset_bmp.depth(), tile16_blockset_bmp.vector());
tile16_blockset_bmp_.SetPalette(tile16_blockset_bmp.palette());
core::Renderer::Get().RenderBitmap(&tile16_blockset_bmp_);
// TODO: Queue texture for later rendering.
// core::Renderer::Get().RenderBitmap(&tile16_blockset_bmp_);
// Note: LoadTile8() will be called after palette is set by overworld editor
// This ensures proper palette coordination from the start
@@ -50,7 +50,8 @@ absl::Status Tile16Editor::Initialize(
current_tile16_bmp_.Create(kTile16Size, kTile16Size, 8,
std::vector<uint8_t>(kTile16PixelCount, 0));
current_tile16_bmp_.SetPalette(tile16_blockset_bmp.palette());
core::Renderer::Get().RenderBitmap(&current_tile16_bmp_);
// TODO: Queue texture for later rendering.
// core::Renderer::Get().RenderBitmap(&current_tile16_bmp_);
// Initialize enhanced canvas features with proper sizing
tile16_edit_canvas_.InitializeDefaults();
@@ -345,8 +346,9 @@ absl::Status Tile16Editor::RefreshTile16Blockset() {
// Mark atlas as modified to trigger regeneration
tile16_blockset_->atlas.set_modified(true);
// Update the atlas bitmap using the safer direct approach
core::Renderer::Get().UpdateBitmap(&tile16_blockset_->atlas);
// Queue texture update via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &tile16_blockset_->atlas);
util::logf("Tile16 blockset refreshed and regenerated");
return absl::OkStatus();
@@ -390,9 +392,10 @@ absl::Status Tile16Editor::UpdateBlocksetBitmap() {
}
}
// Mark the blockset bitmap as modified and use batch texture update
// Mark the blockset bitmap as modified and queue texture update
tile16_blockset_bmp_.set_modified(true);
tile16_blockset_bmp_.QueueTextureUpdate(nullptr); // Use batch operations
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &tile16_blockset_bmp_);
// Also update the tile16 blockset atlas if available
if (tile16_blockset_->atlas.is_active()) {
@@ -415,11 +418,9 @@ absl::Status Tile16Editor::UpdateBlocksetBitmap() {
}
tile16_blockset_->atlas.set_modified(true);
tile16_blockset_->atlas.QueueTextureUpdate(nullptr);
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &tile16_blockset_->atlas);
}
// Process all queued texture updates at once
gfx::Arena::Get().ProcessBatchTextureUpdates();
}
return absl::OkStatus();
@@ -515,8 +516,9 @@ absl::Status Tile16Editor::RegenerateTile16BitmapFromROM() {
}
}
// Render the updated bitmap
core::Renderer::Get().RenderBitmap(&current_tile16_bmp_);
// Queue texture creation via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::CREATE, &current_tile16_bmp_);
util::logf("Regenerated Tile16 bitmap for tile %d from ROM data",
current_tile16_);
@@ -606,9 +608,10 @@ absl::Status Tile16Editor::DrawToCurrentTile16(ImVec2 pos,
}
}
// Mark the bitmap as modified and update the renderer
// Mark the bitmap as modified and queue texture update
current_tile16_bmp_.set_modified(true);
core::Renderer::Get().UpdateBitmap(&current_tile16_bmp_);
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &current_tile16_bmp_);
// Update ROM data when painting to tile16
auto* tile_data = GetCurrentTile16Data();
@@ -893,8 +896,9 @@ absl::Status Tile16Editor::UpdateTile16Edit() {
}
}
// Render the display tile
core::Renderer::Get().RenderBitmap(&display_tile);
// Queue texture creation for display tile
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::CREATE, &display_tile);
// CRITICAL FIX: Handle tile painting with simple click instead of click+drag
// Draw the preview first
@@ -1273,7 +1277,9 @@ absl::Status Tile16Editor::LoadTile8() {
// Fallback to ROM palette
tile_bitmap.SetPalette(rom()->palette_group().overworld_main[0]);
}
core::Renderer::Get().RenderBitmap(&tile_bitmap);
// Queue texture creation via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::CREATE, &tile_bitmap);
} catch (const std::exception& e) {
util::logf("Error creating tile at (%d,%d): %s", tile_x, tile_y,
e.what());
@@ -1362,8 +1368,9 @@ absl::Status Tile16Editor::SetCurrentTile(int tile_id) {
current_tile16_bmp_.SetPalette(rom()->palette_group().overworld_main[0]);
}
// Render the bitmap
core::Renderer::Get().RenderBitmap(&current_tile16_bmp_);
// Queue texture creation via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::CREATE, &current_tile16_bmp_);
// Simple success logging
util::logf("SetCurrentTile: loaded tile %d successfully", tile_id);
@@ -1382,7 +1389,9 @@ absl::Status Tile16Editor::CopyTile16ToClipboard(int tile_id) {
clipboard_tile16_.Create(16, 16, 8, tile_data);
clipboard_tile16_.SetPalette(tile16_blockset_->atlas.palette());
}
core::Renderer::Get().RenderBitmap(&clipboard_tile16_);
// Queue texture creation via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::CREATE, &clipboard_tile16_);
clipboard_has_data_ = true;
return absl::OkStatus();
@@ -1396,7 +1405,9 @@ absl::Status Tile16Editor::PasteTile16FromClipboard() {
// Copy the clipboard data to the current tile16
current_tile16_bmp_.Create(16, 16, 8, clipboard_tile16_.vector());
current_tile16_bmp_.SetPalette(clipboard_tile16_.palette());
core::Renderer::Get().RenderBitmap(&current_tile16_bmp_);
// Queue texture creation via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::CREATE, &current_tile16_bmp_);
return absl::OkStatus();
}
@@ -1409,7 +1420,9 @@ absl::Status Tile16Editor::SaveTile16ToScratchSpace(int slot) {
// Create a copy of the current tile16 bitmap
scratch_space_[slot].Create(16, 16, 8, current_tile16_bmp_.vector());
scratch_space_[slot].SetPalette(current_tile16_bmp_.palette());
core::Renderer::Get().RenderBitmap(&scratch_space_[slot]);
// Queue texture creation via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::CREATE, &scratch_space_[slot]);
scratch_space_used_[slot] = true;
return absl::OkStatus();
@@ -1427,7 +1440,9 @@ absl::Status Tile16Editor::LoadTile16FromScratchSpace(int slot) {
// Copy the scratch space data to the current tile16
current_tile16_bmp_.Create(16, 16, 8, scratch_space_[slot].vector());
current_tile16_bmp_.SetPalette(scratch_space_[slot].palette());
core::Renderer::Get().RenderBitmap(&current_tile16_bmp_);
// Queue texture creation via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::CREATE, &current_tile16_bmp_);
return absl::OkStatus();
}
@@ -1471,7 +1486,9 @@ absl::Status Tile16Editor::FlipTile16Horizontal() {
current_tile16_bmp_.SetPalette(palette_);
current_tile16_bmp_.set_modified(true);
core::Renderer::Get().UpdateBitmap(&current_tile16_bmp_);
// Queue texture update via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &current_tile16_bmp_);
return absl::OkStatus();
}
@@ -1504,7 +1521,9 @@ absl::Status Tile16Editor::FlipTile16Vertical() {
current_tile16_bmp_.SetPalette(palette_);
current_tile16_bmp_.set_modified(true);
core::Renderer::Get().UpdateBitmap(&current_tile16_bmp_);
// Queue texture update via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &current_tile16_bmp_);
return absl::OkStatus();
}
@@ -1537,7 +1556,9 @@ absl::Status Tile16Editor::RotateTile16() {
current_tile16_bmp_.SetPalette(palette_);
current_tile16_bmp_.set_modified(true);
core::Renderer::Get().UpdateBitmap(&current_tile16_bmp_);
// Queue texture update via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &current_tile16_bmp_);
return absl::OkStatus();
}
@@ -1574,7 +1595,9 @@ absl::Status Tile16Editor::FillTile16WithTile8(int tile8_id) {
}
current_tile16_bmp_.set_modified(true);
core::Renderer::Get().UpdateBitmap(&current_tile16_bmp_);
// Queue texture update via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &current_tile16_bmp_);
return absl::OkStatus();
}
@@ -1590,7 +1613,9 @@ absl::Status Tile16Editor::ClearTile16() {
std::fill(data.begin(), data.end(), 0);
current_tile16_bmp_.set_modified(true);
core::Renderer::Get().UpdateBitmap(&current_tile16_bmp_);
// Queue texture update via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &current_tile16_bmp_);
return absl::OkStatus();
}
@@ -1633,7 +1658,9 @@ absl::Status Tile16Editor::PreviewPaletteChange(uint8_t palette_id) {
const auto& ow_main_pal_group = rom()->palette_group().overworld_main;
if (ow_main_pal_group.size() > palette_id) {
preview_tile16_.SetPaletteWithTransparent(ow_main_pal_group[0], palette_id);
core::Renderer::Get().UpdateBitmap(&preview_tile16_);
// Queue texture update via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &preview_tile16_);
preview_dirty_ = true;
}
@@ -1691,7 +1718,9 @@ absl::Status Tile16Editor::Undo() {
y_flip = previous_state.y_flip;
priority_tile = previous_state.priority;
core::Renderer::Get().UpdateBitmap(&current_tile16_bmp_);
// Queue texture update via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &current_tile16_bmp_);
undo_stack_.pop_back();
return absl::OkStatus();
@@ -1714,7 +1743,9 @@ absl::Status Tile16Editor::Redo() {
y_flip = next_state.y_flip;
priority_tile = next_state.priority;
core::Renderer::Get().UpdateBitmap(&current_tile16_bmp_);
// Queue texture update via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &current_tile16_bmp_);
redo_stack_.pop_back();
return absl::OkStatus();
@@ -1800,7 +1831,9 @@ absl::Status Tile16Editor::UpdateOverworldTilemap() {
}
tile16_blockset_->atlas.set_modified(true);
core::Renderer::Get().UpdateBitmap(&tile16_blockset_->atlas);
// Queue texture update via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &tile16_blockset_->atlas);
}
return absl::OkStatus();
@@ -1813,7 +1846,9 @@ absl::Status Tile16Editor::CommitChangesToBlockset() {
// Regenerate the tilemap data if needed
if (tile16_blockset_->atlas.modified()) {
core::Renderer::Get().UpdateBitmap(&tile16_blockset_->atlas);
// Queue texture update via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &tile16_blockset_->atlas);
}
// Update individual cached tiles
@@ -1857,7 +1892,9 @@ absl::Status Tile16Editor::CommitChangesToOverworld() {
}
tile16_blockset_->atlas.set_modified(true);
core::Renderer::Get().UpdateBitmap(&tile16_blockset_->atlas);
// Queue texture update via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &tile16_blockset_->atlas);
}
// Step 4: Notify the parent editor (overworld editor) to regenerate its blockset
@@ -2073,7 +2110,9 @@ absl::Status Tile16Editor::UpdateTile8Palette(int tile8_id) {
// }
current_gfx_individual_[tile8_id].set_modified(true);
Renderer::Get().UpdateBitmap(&current_gfx_individual_[tile8_id]);
// Queue texture update via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &current_gfx_individual_[tile8_id]);
util::logf("Updated tile8 %d with palette slot %d (palette size: %zu colors)",
tile8_id, current_palette_, display_palette.size());
@@ -2125,7 +2164,9 @@ absl::Status Tile16Editor::RefreshAllPalettes() {
// Apply the complete 256-color palette to the source bitmap (same as overworld)
current_gfx_bmp_.SetPalette(display_palette);
current_gfx_bmp_.set_modified(true);
core::Renderer::Get().UpdateBitmap(&current_gfx_bmp_);
// Queue texture update via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &current_gfx_bmp_);
util::logf(
"Applied complete 256-color palette to source bitmap (same as "
"overworld)");
@@ -2136,7 +2177,9 @@ absl::Status Tile16Editor::RefreshAllPalettes() {
// Use complete 256-color palette (same as overworld system)
current_tile16_bmp_.SetPalette(display_palette);
current_tile16_bmp_.set_modified(true);
core::Renderer::Get().UpdateBitmap(&current_tile16_bmp_);
// Queue texture update via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &current_tile16_bmp_);
}
// Update all individual tile8 graphics with complete 256-color palette
@@ -2146,7 +2189,9 @@ absl::Status Tile16Editor::RefreshAllPalettes() {
// The pixel data already contains correct color indices for the 256-color palette
current_gfx_individual_[i].SetPalette(display_palette);
current_gfx_individual_[i].set_modified(true);
core::Renderer::Get().UpdateBitmap(&current_gfx_individual_[i]);
// Queue texture update via Arena's deferred system
gfx::Arena::Get().QueueTextureCommand(
gfx::Arena::TextureCommandType::UPDATE, &current_gfx_individual_[i]);
}
}