feat: Enhance Logging and Buffer Management in ROM and Editor Components
- Added critical logging for graphics buffer management in LoadAllGraphicsData to prevent data corruption during ROM loads. - Updated logging levels from INFO to DEBUG across various components for consistency and to reduce log verbosity. - Refactored texture creation and palette application logic to allow editors to manage their own rendering, improving flexibility and user experience. - Improved background buffer handling to ensure fresh bitmap creation only when necessary, optimizing performance. - Enhanced debugging output for canvas and performance tracking, aiding in better diagnostics during development.
This commit is contained in:
@@ -127,7 +127,7 @@ absl::Status YazeProject::Open(const std::string& project_path) {
|
||||
|
||||
#ifdef YAZE_ENABLE_JSON_PROJECT_FORMAT
|
||||
if (first_char == '{') {
|
||||
LOG_INFO("Project", "Detected JSON format project file");
|
||||
LOG_DEBUG("Project", "Detected JSON format project file");
|
||||
return LoadFromJsonFormat(project_path);
|
||||
}
|
||||
#endif
|
||||
@@ -889,19 +889,19 @@ absl::Status YazeProject::InitializeEmbeddedLabels() {
|
||||
resource_labels = zelda3::Zelda3Labels::ToResourceLabels();
|
||||
use_embedded_labels = true;
|
||||
|
||||
LOG_INFO("Project", "Initialized embedded labels:");
|
||||
LOG_INFO("Project", " - %d room names", resource_labels["room"].size());
|
||||
LOG_INFO("Project", " - %d entrance names", resource_labels["entrance"].size());
|
||||
LOG_INFO("Project", " - %d sprite names", resource_labels["sprite"].size());
|
||||
LOG_INFO("Project", " - %d overlord names", resource_labels["overlord"].size());
|
||||
LOG_INFO("Project", " - %d item names", resource_labels["item"].size());
|
||||
LOG_INFO("Project", " - %d music names", resource_labels["music"].size());
|
||||
LOG_INFO("Project", " - %d graphics names", resource_labels["graphics"].size());
|
||||
LOG_INFO("Project", " - %d room effect names", resource_labels["room_effect"].size());
|
||||
LOG_INFO("Project", " - %d room tag names", resource_labels["room_tag"].size());
|
||||
LOG_INFO("Project", " - %d tile type names", resource_labels["tile_type"].size());
|
||||
LOG_INFO("Project", " - %d overlord names", resource_labels["overlord"].size());
|
||||
LOG_INFO("Project", " - %d item names", resource_labels["item"].size());
|
||||
LOG_DEBUG("Project", "Initialized embedded labels:");
|
||||
LOG_DEBUG("Project", " - %d room names", resource_labels["room"].size());
|
||||
LOG_DEBUG("Project", " - %d entrance names", resource_labels["entrance"].size());
|
||||
LOG_DEBUG("Project", " - %d sprite names", resource_labels["sprite"].size());
|
||||
LOG_DEBUG("Project", " - %d overlord names", resource_labels["overlord"].size());
|
||||
LOG_DEBUG("Project", " - %d item names", resource_labels["item"].size());
|
||||
LOG_DEBUG("Project", " - %d music names", resource_labels["music"].size());
|
||||
LOG_DEBUG("Project", " - %d graphics names", resource_labels["graphics"].size());
|
||||
LOG_DEBUG("Project", " - %d room effect names", resource_labels["room_effect"].size());
|
||||
LOG_DEBUG("Project", " - %d room tag names", resource_labels["room_tag"].size());
|
||||
LOG_DEBUG("Project", " - %d tile type names", resource_labels["tile_type"].size());
|
||||
LOG_DEBUG("Project", " - %d overlord names", resource_labels["overlord"].size());
|
||||
LOG_DEBUG("Project", " - %d item names", resource_labels["item"].size());
|
||||
|
||||
return absl::OkStatus();
|
||||
} catch (const std::exception& e) {
|
||||
|
||||
@@ -6,9 +6,6 @@
|
||||
#include "util/sdl_deleter.h"
|
||||
#include "app/gfx/arena.h"
|
||||
#include "app/gui/style.h"
|
||||
#include "app/gui/theme_manager.h"
|
||||
#include "app/test/test_manager.h"
|
||||
#include "util/log.h"
|
||||
#include "imgui/backends/imgui_impl_sdl2.h"
|
||||
#include "imgui/backends/imgui_impl_sdlrenderer2.h"
|
||||
#include "imgui/imgui.h"
|
||||
@@ -59,15 +56,6 @@ absl::Status CreateWindow(Window& window, int flags) {
|
||||
// Apply original YAZE colors as fallback, then try to load theme system
|
||||
gui::ColorsYaze();
|
||||
|
||||
// Try to initialize theme system (will fallback to ColorsYaze if files fail)
|
||||
auto& theme_manager = gui::ThemeManager::Get();
|
||||
auto status = theme_manager.LoadTheme("YAZE Classic");
|
||||
if (!status.ok()) {
|
||||
// Theme system failed, stick with original ColorsYaze()
|
||||
LOG_WARN("Window", "Theme system failed, using original ColorsYaze(): %s",
|
||||
status.message().data());
|
||||
}
|
||||
|
||||
const int audio_frequency = 48000;
|
||||
SDL_AudioSpec want, have;
|
||||
SDL_memset(&want, 0, sizeof(want));
|
||||
|
||||
@@ -7,6 +7,7 @@
|
||||
#include "app/gui/canvas.h"
|
||||
#include "app/gui/input.h"
|
||||
#include "app/rom.h"
|
||||
#include "util/log.h"
|
||||
#include "app/zelda3/dungeon/object_drawer.h"
|
||||
#include "app/zelda3/dungeon/object_renderer.h"
|
||||
#include "app/zelda3/dungeon/room.h"
|
||||
@@ -106,13 +107,8 @@ void DungeonCanvasViewer::DrawDungeonCanvas(int room_id) {
|
||||
auto& bg1_bitmap = room.bg1_buffer().bitmap();
|
||||
bool needs_render = !bg1_bitmap.is_active() || bg1_bitmap.width() == 0;
|
||||
|
||||
printf("[DrawCanvas] Room %d: needs_render=%d, bg1_active=%d, blocks=%zu, objects=%zu\n",
|
||||
room_id, needs_render, bg1_bitmap.is_active(),
|
||||
room.blocks().size(), room.GetTileObjects().size());
|
||||
|
||||
// Render immediately if needed
|
||||
if (needs_render) {
|
||||
printf("[DrawCanvas] Rendering room %d graphics...\n", room_id);
|
||||
(void)LoadAndRenderRoomGraphics(room_id);
|
||||
}
|
||||
|
||||
@@ -683,30 +679,20 @@ void DungeonCanvasViewer::RenderRoomBackgroundLayers(int room_id) {
|
||||
auto& bg1_bitmap = room.bg1_buffer().bitmap();
|
||||
auto& bg2_bitmap = room.bg2_buffer().bitmap();
|
||||
|
||||
printf("[RenderLayers] Room %d: BG1 active=%d, texture=%p\n",
|
||||
room_id, bg1_bitmap.is_active(), (void*)bg1_bitmap.texture());
|
||||
|
||||
if (bg1_bitmap.is_active() && bg1_bitmap.width() > 0 && bg1_bitmap.height() > 0) {
|
||||
if (!bg1_bitmap.texture()) {
|
||||
printf("[RenderLayers] Creating BG1 texture...\n");
|
||||
core::Renderer::Get().RenderBitmap(&bg1_bitmap);
|
||||
}
|
||||
printf("[RenderLayers] Drawing BG1 bitmap: %dx%d, texture=%p\n",
|
||||
bg1_bitmap.width(), bg1_bitmap.height(), (void*)bg1_bitmap.texture());
|
||||
|
||||
|
||||
// DEBUG: Check SDL texture format
|
||||
Uint32 format;
|
||||
int access, w, h;
|
||||
if (SDL_QueryTexture(bg1_bitmap.texture(), &format, &access, &w, &h) == 0) {
|
||||
printf("[RenderLayers] BG1 texture format: %s (%u), access: %d, size: %dx%d\n",
|
||||
SDL_GetPixelFormatName(format), format, access, w, h);
|
||||
const char* format_name_cstr = SDL_GetPixelFormatName(format);
|
||||
}
|
||||
|
||||
|
||||
canvas_.DrawBitmap(bg1_bitmap, 0, 0, 1.0f, 255);
|
||||
} else {
|
||||
printf("[RenderLayers] BG1 not ready: active=%d, w=%d, h=%d\n",
|
||||
bg1_bitmap.is_active(), bg1_bitmap.width(), bg1_bitmap.height());
|
||||
}
|
||||
}
|
||||
|
||||
if (bg2_bitmap.is_active() && bg2_bitmap.width() > 0 && bg2_bitmap.height() > 0) {
|
||||
if (!bg2_bitmap.texture()) {
|
||||
|
||||
@@ -40,7 +40,7 @@ absl::Status DungeonRoomLoader::LoadAllRooms(std::array<zelda3::Room, 0x128>& ro
|
||||
static_cast<int>(std::thread::hardware_concurrency()));
|
||||
const int rooms_per_thread = (kTotalRooms + max_concurrency - 1) / max_concurrency;
|
||||
|
||||
LOG_INFO("Dungeon", "Loading %d dungeon rooms using %d threads (%d rooms per thread)",
|
||||
LOG_DEBUG("Dungeon", "Loading %d dungeon rooms using %d threads (%d rooms per thread)",
|
||||
kTotalRooms, max_concurrency, rooms_per_thread);
|
||||
|
||||
// Thread-safe data structures for collecting results
|
||||
|
||||
@@ -682,7 +682,7 @@ absl::Status EditorManager::Update() {
|
||||
// Ensure TestManager always has the current ROM
|
||||
static Rom* last_test_rom = nullptr;
|
||||
if (last_test_rom != current_rom_) {
|
||||
LOG_INFO("EditorManager",
|
||||
LOG_DEBUG("EditorManager",
|
||||
"EditorManager::Update - ROM changed, updating TestManager: %p -> "
|
||||
"%p",
|
||||
(void*)last_test_rom, (void*)current_rom_);
|
||||
@@ -2039,7 +2039,7 @@ absl::Status EditorManager::LoadRom() {
|
||||
for (auto& session : sessions_) {
|
||||
if (!session.rom.is_loaded()) {
|
||||
target_session = &session;
|
||||
LOG_INFO("EditorManager", "Found empty session to populate with ROM: %s",
|
||||
LOG_DEBUG("EditorManager", "Found empty session to populate with ROM: %s",
|
||||
file_name.c_str());
|
||||
break;
|
||||
}
|
||||
@@ -2067,7 +2067,7 @@ absl::Status EditorManager::LoadRom() {
|
||||
|
||||
// Update test manager with current ROM for ROM-dependent tests (only when tests are enabled)
|
||||
#ifdef YAZE_ENABLE_TESTING
|
||||
LOG_INFO("EditorManager", "Setting ROM in TestManager - %p ('%s')",
|
||||
LOG_DEBUG("EditorManager", "Setting ROM in TestManager - %p ('%s')",
|
||||
(void*)current_rom_,
|
||||
current_rom_ ? current_rom_->title().c_str() : "null");
|
||||
test::TestManager::Get().SetCurrentRom(current_rom_);
|
||||
@@ -2113,7 +2113,7 @@ absl::Status EditorManager::LoadAssets() {
|
||||
auto end_time = std::chrono::steady_clock::now();
|
||||
auto duration = std::chrono::duration_cast<std::chrono::milliseconds>(
|
||||
end_time - start_time);
|
||||
LOG_INFO("EditorManager", "ROM assets loaded in %lld ms", duration.count());
|
||||
LOG_DEBUG("EditorManager", "ROM assets loaded in %lld ms", duration.count());
|
||||
|
||||
return absl::OkStatus();
|
||||
}
|
||||
@@ -2273,7 +2273,7 @@ absl::Status EditorManager::OpenProject() {
|
||||
|
||||
// Update test manager with current ROM for ROM-dependent tests (only when tests are enabled)
|
||||
#ifdef YAZE_ENABLE_TESTING
|
||||
LOG_INFO("EditorManager", "Setting ROM in TestManager - %p ('%s')",
|
||||
LOG_DEBUG("EditorManager", "Setting ROM in TestManager - %p ('%s')",
|
||||
(void*)current_rom_,
|
||||
current_rom_ ? current_rom_->title().c_str() : "null");
|
||||
test::TestManager::Get().SetCurrentRom(current_rom_);
|
||||
@@ -2537,7 +2537,7 @@ void EditorManager::RemoveSession(size_t index) {
|
||||
sessions_[index].custom_name = "[CLOSED SESSION]";
|
||||
sessions_[index].filepath = "";
|
||||
|
||||
LOG_INFO("EditorManager", "Marked session as closed: %s (index %zu)",
|
||||
LOG_DEBUG("EditorManager", "Marked session as closed: %s (index %zu)",
|
||||
session_name.c_str(), index);
|
||||
toast_manager_.Show(
|
||||
absl::StrFormat("Session marked as closed: %s", session_name),
|
||||
|
||||
@@ -78,7 +78,7 @@ void OverworldEditor::Initialize() {
|
||||
absl::Status OverworldEditor::Load() {
|
||||
gfx::ScopedTimer timer("OverworldEditor::Load");
|
||||
|
||||
LOG_INFO("OverworldEditor", "Loading overworld.");
|
||||
LOG_DEBUG("OverworldEditor", "Loading overworld.");
|
||||
if (!rom_ || !rom_->is_loaded()) {
|
||||
return absl::FailedPreconditionError("ROM not loaded");
|
||||
}
|
||||
@@ -100,7 +100,7 @@ absl::Status OverworldEditor::Load() {
|
||||
// Force refresh of the current overworld map to show changes
|
||||
RefreshOverworldMap();
|
||||
|
||||
LOG_INFO("OverworldEditor", "Overworld editor refreshed after Tile16 changes");
|
||||
LOG_DEBUG("OverworldEditor", "Overworld editor refreshed after Tile16 changes");
|
||||
return absl::OkStatus();
|
||||
});
|
||||
|
||||
@@ -807,7 +807,7 @@ void OverworldEditor::CheckForOverworldEdits() {
|
||||
auto tile_data = gfx::GetTilemapData(tile16_blockset_, tile16_id);
|
||||
if (!tile_data.empty()) {
|
||||
RenderUpdatedMapBitmap(tile_position, tile_data);
|
||||
LOG_INFO("OverworldEditor",
|
||||
LOG_DEBUG("OverworldEditor",
|
||||
"CheckForOverworldEdits: Updated bitmap at position (%d,%d) "
|
||||
"with tile16_id=%d",
|
||||
x, y, tile16_id);
|
||||
@@ -824,7 +824,7 @@ void OverworldEditor::CheckForOverworldEdits() {
|
||||
// This is commented out for now, will come back to later.
|
||||
// ow_map_canvas_.mutable_selected_tiles()->clear();
|
||||
// ow_map_canvas_.mutable_points()->clear();
|
||||
LOG_INFO("OverworldEditor",
|
||||
LOG_DEBUG("OverworldEditor",
|
||||
"CheckForOverworldEdits: Rectangle selection applied and cleared");
|
||||
}
|
||||
}
|
||||
@@ -1469,7 +1469,7 @@ absl::Status OverworldEditor::Save() {
|
||||
absl::Status OverworldEditor::LoadGraphics() {
|
||||
gfx::ScopedTimer timer("LoadGraphics");
|
||||
|
||||
LOG_INFO("OverworldEditor", "Loading overworld.");
|
||||
LOG_DEBUG("OverworldEditor", "Loading overworld.");
|
||||
// Load the Link to the Past overworld.
|
||||
{
|
||||
gfx::ScopedTimer load_timer("Overworld::Load");
|
||||
@@ -1477,7 +1477,7 @@ absl::Status OverworldEditor::LoadGraphics() {
|
||||
}
|
||||
palette_ = overworld_.current_area_palette();
|
||||
|
||||
LOG_INFO("OverworldEditor", "Loading overworld graphics (optimized).");
|
||||
LOG_DEBUG("OverworldEditor", "Loading overworld graphics (optimized).");
|
||||
|
||||
// Phase 1: Create bitmaps without textures for faster loading
|
||||
// This avoids blocking the main thread with GPU texture creation
|
||||
@@ -1488,7 +1488,7 @@ absl::Status OverworldEditor::LoadGraphics() {
|
||||
current_gfx_bmp_, palette_);
|
||||
}
|
||||
|
||||
LOG_INFO("OverworldEditor", "Loading overworld tileset (deferred textures).");
|
||||
LOG_DEBUG("OverworldEditor", "Loading overworld tileset (deferred textures).");
|
||||
{
|
||||
gfx::ScopedTimer tileset_timer("CreateBitmapWithoutTexture_Tileset");
|
||||
Renderer::Get().CreateBitmapWithoutTexture(
|
||||
@@ -1499,7 +1499,7 @@ absl::Status OverworldEditor::LoadGraphics() {
|
||||
|
||||
// Copy the tile16 data into individual tiles.
|
||||
auto tile16_blockset_data = overworld_.tile16_blockset_data();
|
||||
LOG_INFO("OverworldEditor", "Loading overworld tile16 graphics.");
|
||||
LOG_DEBUG("OverworldEditor", "Loading overworld tile16 graphics.");
|
||||
|
||||
{
|
||||
gfx::ScopedTimer tilemap_timer("CreateTilemap");
|
||||
@@ -1517,7 +1517,7 @@ absl::Status OverworldEditor::LoadGraphics() {
|
||||
constexpr int kSpecialWorldEssential =
|
||||
zelda3::kSpecialWorldMapIdStart + kEssentialMapsPerWorld;
|
||||
|
||||
LOG_INFO("OverworldEditor",
|
||||
LOG_DEBUG("OverworldEditor",
|
||||
"Creating bitmaps for essential maps only (first %d maps per world)",
|
||||
kEssentialMapsPerWorld);
|
||||
|
||||
@@ -2049,7 +2049,7 @@ void OverworldEditor::ForceRefreshGraphics(int map_index) {
|
||||
// Clear blockset cache
|
||||
current_blockset_ = 0xFF;
|
||||
|
||||
LOG_INFO("OverworldEditor", "ForceRefreshGraphics: Map %d marked for refresh", map_index);
|
||||
LOG_DEBUG("OverworldEditor", "ForceRefreshGraphics: Map %d marked for refresh", map_index);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2097,7 +2097,7 @@ void OverworldEditor::RefreshSiblingMapGraphics(int map_index, bool include_self
|
||||
// Call RefreshChildMapOnDemand() directly instead of RefreshOverworldMapOnDemand()
|
||||
RefreshChildMapOnDemand(sibling);
|
||||
|
||||
LOG_INFO("OverworldEditor", "RefreshSiblingMapGraphics: Refreshed sibling map %d", sibling);
|
||||
LOG_DEBUG("OverworldEditor", "RefreshSiblingMapGraphics: Refreshed sibling map %d", sibling);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -2520,7 +2520,7 @@ absl::Status OverworldEditor::ApplyZSCustomOverworldASM(int target_version) {
|
||||
"ROM is already version %d or higher", current_version));
|
||||
}
|
||||
|
||||
LOG_INFO("OverworldEditor", "Applying ZSCustomOverworld ASM v%d to ROM...",
|
||||
LOG_DEBUG("OverworldEditor", "Applying ZSCustomOverworld ASM v%d to ROM...",
|
||||
target_version);
|
||||
|
||||
// Initialize Asar wrapper
|
||||
@@ -2540,7 +2540,7 @@ absl::Status OverworldEditor::ApplyZSCustomOverworldASM(int target_version) {
|
||||
// Use GetResourcePath to handle app bundles and various deployment scenarios
|
||||
std::string asm_file_path = util::GetResourcePath(asm_file_name);
|
||||
|
||||
LOG_INFO("OverworldEditor", "Using ASM file: %s", asm_file_path.c_str());
|
||||
LOG_DEBUG("OverworldEditor", "Using ASM file: %s", asm_file_path.c_str());
|
||||
|
||||
// Verify file exists
|
||||
if (!std::filesystem::exists(asm_file_path)) {
|
||||
@@ -2581,17 +2581,17 @@ absl::Status OverworldEditor::ApplyZSCustomOverworldASM(int target_version) {
|
||||
RETURN_IF_ERROR(UpdateROMVersionMarkers(target_version));
|
||||
|
||||
// Log symbols found during patching
|
||||
LOG_INFO("OverworldEditor", "ASM patch applied successfully. Found %zu symbols:",
|
||||
LOG_DEBUG("OverworldEditor", "ASM patch applied successfully. Found %zu symbols:",
|
||||
result.symbols.size());
|
||||
for (const auto& symbol : result.symbols) {
|
||||
LOG_INFO("OverworldEditor", " %s @ $%06X", symbol.name.c_str(),
|
||||
LOG_DEBUG("OverworldEditor", " %s @ $%06X", symbol.name.c_str(),
|
||||
symbol.address);
|
||||
}
|
||||
|
||||
// Refresh overworld data to reflect changes
|
||||
RETURN_IF_ERROR(overworld_.Load(rom_));
|
||||
|
||||
LOG_INFO("OverworldEditor", "ZSCustomOverworld v%d successfully applied to ROM",
|
||||
LOG_DEBUG("OverworldEditor", "ZSCustomOverworld v%d successfully applied to ROM",
|
||||
target_version);
|
||||
return absl::OkStatus();
|
||||
|
||||
@@ -2618,7 +2618,7 @@ absl::Status OverworldEditor::UpdateROMVersionMarkers(int target_version) {
|
||||
(*rom_)[zelda3::OverworldCustomAreaSpecificBGEnabled] = 0x01;
|
||||
(*rom_)[zelda3::OverworldCustomMainPaletteEnabled] = 0x01;
|
||||
|
||||
LOG_INFO("OverworldEditor", "Enabled v2+ features: Custom BG colors, Main palettes");
|
||||
LOG_DEBUG("OverworldEditor", "Enabled v2+ features: Custom BG colors, Main palettes");
|
||||
}
|
||||
|
||||
if (target_version >= 3) {
|
||||
@@ -2628,7 +2628,7 @@ absl::Status OverworldEditor::UpdateROMVersionMarkers(int target_version) {
|
||||
(*rom_)[zelda3::OverworldCustomTileGFXGroupEnabled] = 0x01;
|
||||
(*rom_)[zelda3::OverworldCustomMosaicEnabled] = 0x01;
|
||||
|
||||
LOG_INFO("OverworldEditor",
|
||||
LOG_DEBUG("OverworldEditor",
|
||||
"Enabled v3+ features: Subscreen overlays, Animated GFX, Tile GFX "
|
||||
"groups, Mosaic");
|
||||
|
||||
@@ -2652,11 +2652,11 @@ absl::Status OverworldEditor::UpdateROMVersionMarkers(int target_version) {
|
||||
}
|
||||
}
|
||||
|
||||
LOG_INFO("OverworldEditor", "Initialized area size data for %zu areas",
|
||||
LOG_DEBUG("OverworldEditor", "Initialized area size data for %zu areas",
|
||||
large_areas.size());
|
||||
}
|
||||
|
||||
LOG_INFO("OverworldEditor", "ROM version markers updated to v%d", target_version);
|
||||
LOG_DEBUG("OverworldEditor", "ROM version markers updated to v%d", target_version);
|
||||
return absl::OkStatus();
|
||||
}
|
||||
|
||||
|
||||
@@ -384,7 +384,7 @@ void SettingsEditor::DrawAIAgentSettings() {
|
||||
std::filesystem::path path(log_file_path);
|
||||
if (std::filesystem::exists(path)) {
|
||||
std::filesystem::remove(path);
|
||||
LOG_INFO("Settings", "Log file cleared: %s", log_file_path);
|
||||
LOG_DEBUG("Settings", "Log file cleared: %s", log_file_path);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -40,6 +40,25 @@ void BackgroundBuffer::DrawTile(const TileInfo& tile, uint8_t* canvas,
|
||||
int tile_x = (tile.id_ % 16) * 8; // 16 tiles per row, 8 pixels per tile
|
||||
int tile_y = (tile.id_ / 16) * 8; // Each row is 16 tiles
|
||||
|
||||
// DEBUG: For floor tiles, check what we're actually reading
|
||||
static int debug_count = 0;
|
||||
if (debug_count < 4 && (tile.id_ == 0xEC || tile.id_ == 0xED || tile.id_ == 0xFC || tile.id_ == 0xFD)) {
|
||||
printf("[DrawTile] Floor tile 0x%02X at sheet pos (%d,%d), palette=%d, mirror=(%d,%d)\n",
|
||||
tile.id_, tile_x, tile_y, tile.palette_, tile.horizontal_mirror_, tile.vertical_mirror_);
|
||||
printf("[DrawTile] First row (8 pixels): ");
|
||||
for (int i = 0; i < 8; i++) {
|
||||
int src_index = tile_y * 128 + (tile_x + i);
|
||||
printf("%d ", tiledata[src_index]);
|
||||
}
|
||||
printf("\n[DrawTile] Second row (8 pixels): ");
|
||||
for (int i = 0; i < 8; i++) {
|
||||
int src_index = (tile_y + 1) * 128 + (tile_x + i);
|
||||
printf("%d ", tiledata[src_index]);
|
||||
}
|
||||
printf("\n");
|
||||
debug_count++;
|
||||
}
|
||||
|
||||
// Dungeon graphics are 3BPP: 8 colors per palette (0-7, 8-15, 16-23, etc.)
|
||||
// NOT 4BPP which would be 16 colors per palette!
|
||||
// Clamp palette to 0-10 (90 colors / 8 = 11.25, so max palette is 10)
|
||||
@@ -78,32 +97,33 @@ void BackgroundBuffer::DrawBackground(std::span<uint8_t> gfx16_data) {
|
||||
buffer_.resize(tiles_w * tiles_h);
|
||||
}
|
||||
|
||||
// CRITICAL: Always create a fresh bitmap for each DrawBackground call
|
||||
// This ensures we're rendering the current tilemap state, not stale data
|
||||
printf("[BG:DrawBackground] Creating fresh bitmap for rendering\n");
|
||||
bitmap_.Create(width_, height_, 8, std::vector<uint8_t>(width_ * height_, 0));
|
||||
|
||||
// DEBUG: Check if gfx16_data has actual graphics
|
||||
if (gfx16_data.size() < 100) {
|
||||
printf("[BG:DrawBackground] WARNING: gfx16_data is too small (%zu bytes)\n", gfx16_data.size());
|
||||
} else {
|
||||
// Sample first 32 bytes
|
||||
printf("[BG:DrawBackground] gfx16_data size=%zu, first 32 bytes: ", gfx16_data.size());
|
||||
for (size_t i = 0; i < 32 && i < gfx16_data.size(); i++) {
|
||||
printf("%02X ", gfx16_data[i]);
|
||||
}
|
||||
printf("\n");
|
||||
// NEVER recreate bitmap here - it should be created by DrawFloor or initialized earlier
|
||||
// If bitmap doesn't exist, create it ONCE with zeros
|
||||
if (!bitmap_.is_active() || bitmap_.width() == 0) {
|
||||
bitmap_.Create(width_, height_, 8, std::vector<uint8_t>(width_ * height_, 0));
|
||||
}
|
||||
|
||||
// For each tile on the tile buffer
|
||||
int drawn_count = 0;
|
||||
int skipped_count = 0;
|
||||
int non_floor_count = 0;
|
||||
for (int yy = 0; yy < tiles_h; yy++) {
|
||||
for (int xx = 0; xx < tiles_w; xx++) {
|
||||
uint16_t word = buffer_[xx + yy * tiles_w];
|
||||
// Prevent draw if tile == 0xFFFF since it's 0 indexed
|
||||
if (word == 0xFFFF) continue;
|
||||
if (word == 0xFFFF) {
|
||||
skipped_count++;
|
||||
continue;
|
||||
}
|
||||
auto tile = gfx::WordToTileInfo(word);
|
||||
|
||||
// Count floor tiles vs non-floor
|
||||
if (tile.id_ >= 0xEE && tile.id_ <= 0xFF) {
|
||||
// This looks like a floor tile (based on DrawFloor's 14EE pattern)
|
||||
} else if (word != 0) {
|
||||
non_floor_count++;
|
||||
}
|
||||
|
||||
// Calculate pixel offset for tile position (xx, yy) in the 512x512 bitmap
|
||||
// Each tile is 8x8, so pixel Y = yy * 8, pixel X = xx * 8
|
||||
// Linear offset = (pixel_y * width) + pixel_x = (yy * 8 * 512) + (xx * 8)
|
||||
@@ -124,6 +144,11 @@ void BackgroundBuffer::DrawBackground(std::span<uint8_t> gfx16_data) {
|
||||
void BackgroundBuffer::DrawFloor(const std::vector<uint8_t>& rom_data,
|
||||
int tile_address, int tile_address_floor,
|
||||
uint8_t floor_graphics) {
|
||||
// Create bitmap ONCE at the start if it doesn't exist
|
||||
if (!bitmap_.is_active() || bitmap_.width() == 0) {
|
||||
bitmap_.Create(width_, height_, 8, std::vector<uint8_t>(width_ * height_, 0));
|
||||
}
|
||||
|
||||
auto f = (uint8_t)(floor_graphics << 4);
|
||||
|
||||
// Create floor tiles from ROM data
|
||||
@@ -155,7 +180,6 @@ void BackgroundBuffer::DrawFloor(const std::vector<uint8_t>& rom_data,
|
||||
uint16_t word6 = gfx::TileInfoToWord(floorTile6);
|
||||
uint16_t word7 = gfx::TileInfoToWord(floorTile7);
|
||||
uint16_t word8 = gfx::TileInfoToWord(floorTile8);
|
||||
|
||||
for (int xx = 0; xx < 16; xx++) {
|
||||
for (int yy = 0; yy < 32; yy++) {
|
||||
SetTileAt((xx * 4), (yy * 2), word1);
|
||||
|
||||
@@ -7,6 +7,7 @@
|
||||
#include <sstream>
|
||||
|
||||
#include "app/gfx/memory_pool.h"
|
||||
#include "util/log.h"
|
||||
|
||||
namespace yaze {
|
||||
namespace gfx {
|
||||
@@ -43,7 +44,7 @@ void PerformanceProfiler::EndTimer(const std::string& operation_name) {
|
||||
if (timer_iter == active_timers_.end()) {
|
||||
// During shutdown, silently ignore missing timers to avoid log spam
|
||||
if (!is_shutting_down_) {
|
||||
SDL_Log("Warning: EndTimer called for operation '%s' that was not started",
|
||||
LOG_DEBUG("PerformanceProfiler", "EndTimer called for operation '%s' that was not started",
|
||||
operation_name.c_str());
|
||||
}
|
||||
return;
|
||||
|
||||
@@ -22,7 +22,7 @@ void CanvasPerformanceIntegration::Initialize(const std::string& canvas_id) {
|
||||
// Initialize performance profiler integration
|
||||
dashboard_ = &gfx::PerformanceDashboard::Get();
|
||||
|
||||
LOG_INFO("CanvasPerformance",
|
||||
LOG_DEBUG("CanvasPerformance",
|
||||
"Initialized performance integration for canvas: %s",
|
||||
canvas_id_.c_str());
|
||||
}
|
||||
@@ -34,7 +34,7 @@ void CanvasPerformanceIntegration::StartMonitoring() {
|
||||
frame_timer_active_ = true;
|
||||
frame_timer_ = std::make_unique<gfx::ScopedTimer>("canvas_frame_" + canvas_id_);
|
||||
|
||||
LOG_INFO("CanvasPerformance", "Started performance monitoring for canvas: %s",
|
||||
LOG_DEBUG("CanvasPerformance", "Started performance monitoring for canvas: %s",
|
||||
canvas_id_.c_str());
|
||||
}
|
||||
|
||||
@@ -57,7 +57,7 @@ void CanvasPerformanceIntegration::StopMonitoring() {
|
||||
frame_timer_active_ = false;
|
||||
}
|
||||
|
||||
LOG_INFO("CanvasPerformance", "Stopped performance monitoring for canvas: %s",
|
||||
LOG_DEBUG("CanvasPerformance", "Stopped performance monitoring for canvas: %s",
|
||||
canvas_id_.c_str());
|
||||
}
|
||||
|
||||
@@ -363,12 +363,12 @@ void CanvasPerformanceIntegration::AnalyzePerformance() {
|
||||
|
||||
// Log trends
|
||||
if (std::abs(frame_time_trend) > 1.0) {
|
||||
LOG_INFO("CanvasPerformance", "Canvas %s: Frame time trend: %.2f ms/sample",
|
||||
LOG_DEBUG("CanvasPerformance", "Canvas %s: Frame time trend: %.2f ms/sample",
|
||||
canvas_id_.c_str(), frame_time_trend);
|
||||
}
|
||||
|
||||
if (std::abs(memory_trend) > 1.0) {
|
||||
LOG_INFO("CanvasPerformance", "Canvas %s: Memory trend: %.2f MB/sample",
|
||||
LOG_DEBUG("CanvasPerformance", "Canvas %s: Memory trend: %.2f MB/sample",
|
||||
canvas_id_.c_str(), memory_trend);
|
||||
}
|
||||
}
|
||||
@@ -536,7 +536,7 @@ void CanvasPerformanceManager::RegisterIntegration(
|
||||
const std::string& canvas_id,
|
||||
std::shared_ptr<CanvasPerformanceIntegration> integration) {
|
||||
integrations_[canvas_id] = integration;
|
||||
LOG_INFO("CanvasPerformance",
|
||||
LOG_DEBUG("CanvasPerformance",
|
||||
"Registered performance integration for canvas: %s",
|
||||
canvas_id.c_str());
|
||||
}
|
||||
@@ -604,7 +604,7 @@ void CanvasPerformanceManager::ClearAllIntegrations() {
|
||||
integration->StopMonitoring();
|
||||
}
|
||||
integrations_.clear();
|
||||
LOG_INFO("CanvasPerformance", "Cleared all canvas performance integrations");
|
||||
LOG_DEBUG("CanvasPerformance", "Cleared all canvas performance integrations");
|
||||
}
|
||||
|
||||
} // namespace canvas
|
||||
|
||||
@@ -31,7 +31,7 @@ void CanvasUsageTracker::SetUsageMode(CanvasUsage usage) {
|
||||
// Record mode change interaction
|
||||
RecordInteraction(CanvasInteraction::kModeChange, GetUsageModeName(usage));
|
||||
|
||||
LOG_INFO("CanvasUsage", "Canvas %s: Usage mode changed to %s",
|
||||
LOG_DEBUG("CanvasUsage", "Canvas %s: Usage mode changed to %s",
|
||||
canvas_id_.c_str(), GetUsageModeName(usage).c_str());
|
||||
}
|
||||
}
|
||||
@@ -267,7 +267,7 @@ void CanvasUsageTracker::EndSession() {
|
||||
// Save final stats
|
||||
SaveCurrentStats();
|
||||
|
||||
LOG_INFO("CanvasUsage", "Canvas %s: Session ended. Duration: %s, Operations: %d",
|
||||
LOG_DEBUG("CanvasUsage", "Canvas %s: Session ended. Duration: %s, Operations: %d",
|
||||
canvas_id_.c_str(),
|
||||
FormatDuration(std::chrono::duration_cast<std::chrono::milliseconds>(
|
||||
std::chrono::steady_clock::now() - session_start_)).c_str(),
|
||||
@@ -352,7 +352,7 @@ CanvasUsageManager& CanvasUsageManager::Get() {
|
||||
void CanvasUsageManager::RegisterTracker(const std::string& canvas_id,
|
||||
std::shared_ptr<CanvasUsageTracker> tracker) {
|
||||
trackers_[canvas_id] = tracker;
|
||||
LOG_INFO("CanvasUsage", "Registered usage tracker for canvas: %s", canvas_id.c_str());
|
||||
LOG_DEBUG("CanvasUsage", "Registered usage tracker for canvas: %s", canvas_id.c_str());
|
||||
}
|
||||
|
||||
std::shared_ptr<CanvasUsageTracker> CanvasUsageManager::GetTracker(const std::string& canvas_id) {
|
||||
@@ -421,7 +421,7 @@ void CanvasUsageManager::ClearAllTrackers() {
|
||||
tracker->ClearHistory();
|
||||
}
|
||||
trackers_.clear();
|
||||
LOG_INFO("CanvasUsage", "Cleared all canvas usage trackers");
|
||||
LOG_DEBUG("CanvasUsage", "Cleared all canvas usage trackers");
|
||||
}
|
||||
|
||||
} // namespace canvas
|
||||
|
||||
@@ -85,7 +85,7 @@ bool LoadROMPaletteGroups(Rom* rom, CanvasPaletteManager& palette_manager) {
|
||||
}
|
||||
|
||||
palette_manager.palettes_loaded = true;
|
||||
LOG_INFO("Canvas", "Loaded %zu ROM palette groups",
|
||||
LOG_DEBUG("Canvas", "Loaded %zu ROM palette groups",
|
||||
palette_manager.rom_palette_groups.size());
|
||||
return true;
|
||||
|
||||
@@ -116,7 +116,7 @@ bool ApplyPaletteGroup(gfx::Bitmap* bitmap,
|
||||
}
|
||||
|
||||
Renderer::Get().UpdateBitmap(bitmap);
|
||||
LOG_INFO("Canvas", "Applied palette group %d, index %d to bitmap",
|
||||
LOG_DEBUG("Canvas", "Applied palette group %d, index %d to bitmap",
|
||||
group_index, palette_index);
|
||||
return true;
|
||||
|
||||
|
||||
@@ -23,6 +23,7 @@
|
||||
#include "app/gfx/snes_palette.h"
|
||||
#include "app/gfx/snes_tile.h"
|
||||
#include "app/snes.h"
|
||||
#include "util/log.h"
|
||||
#include "util/hex.h"
|
||||
#include "util/log.h"
|
||||
#include "util/macro.h"
|
||||
@@ -178,6 +179,11 @@ absl::StatusOr<std::array<gfx::Bitmap, kNumGfxSheets>> LoadAllGraphicsData(
|
||||
SDL_Renderer *renderer = Renderer::Get().renderer();
|
||||
const bool renderer_ready = renderer != nullptr;
|
||||
|
||||
// CRITICAL: Clear the graphics buffer before loading to prevent corruption!
|
||||
// Without this, multiple ROM loads would accumulate corrupted data.
|
||||
rom.mutable_graphics_buffer()->clear();
|
||||
LOG_DEBUG("Graphics", "Cleared graphics buffer, loading %d sheets", kNumGfxSheets);
|
||||
|
||||
for (uint32_t i = 0; i < kNumGfxSheets; i++) {
|
||||
if (i >= 115 && i <= 126) { // uncompressed sheets
|
||||
sheet.resize(Uncompressed3BPPSize);
|
||||
@@ -201,22 +207,30 @@ absl::StatusOr<std::array<gfx::Bitmap, kNumGfxSheets>> LoadAllGraphicsData(
|
||||
|
||||
if (bpp3) {
|
||||
auto converted_sheet = gfx::SnesTo8bppSheet(sheet, 3);
|
||||
|
||||
graphics_sheets[i].Create(gfx::kTilesheetWidth, gfx::kTilesheetHeight,
|
||||
gfx::kTilesheetDepth, converted_sheet);
|
||||
if (graphics_sheets[i].is_active()) {
|
||||
if (i > 115) {
|
||||
// Apply sprites palette
|
||||
graphics_sheets[i].SetPaletteWithTransparent(
|
||||
rom.palette_group().global_sprites[0], 0);
|
||||
} else {
|
||||
graphics_sheets[i].SetPaletteWithTransparent(
|
||||
rom.palette_group().dungeon_main[0], 0);
|
||||
}
|
||||
}
|
||||
|
||||
// DON'T apply palettes here! Each editor (Dungeon, Graphics, GfxGroup)
|
||||
// should apply its own palette when displaying sheets.
|
||||
// This allows users to preview sheets with different palettes in each editor.
|
||||
// The bitmap data is stored as indexed (8bpp), and palettes are applied
|
||||
// at texture creation time by each editor.
|
||||
|
||||
// if (graphics_sheets[i].is_active()) {
|
||||
// if (i > 115) {
|
||||
// graphics_sheets[i].SetPaletteWithTransparent(
|
||||
// rom.palette_group().global_sprites[0], 0);
|
||||
// } else {
|
||||
// graphics_sheets[i].SetPaletteWithTransparent(
|
||||
// rom.palette_group().dungeon_main[0], 0);
|
||||
// }
|
||||
// }
|
||||
|
||||
if (!defer_render && renderer_ready) {
|
||||
graphics_sheets[i].CreateTexture(renderer);
|
||||
}
|
||||
// Don't create textures here either - let editors create them with their palettes
|
||||
// if (!defer_render && renderer_ready) {
|
||||
// graphics_sheets[i].CreateTexture(renderer);
|
||||
// }
|
||||
|
||||
for (int j = 0; j < graphics_sheets[i].size(); ++j) {
|
||||
rom.mutable_graphics_buffer()->push_back(graphics_sheets[i].at(j));
|
||||
|
||||
@@ -273,7 +273,7 @@ absl::Status Overworld::ConfigureMultiAreaMap(int parent_index, AreaSizeEnum siz
|
||||
"Wide and Tall areas require ZSCustomOverworld v3+");
|
||||
}
|
||||
|
||||
LOG_INFO("Overworld", "ConfigureMultiAreaMap: parent=%d, current_size=%d, new_size=%d, version=%d",
|
||||
LOG_DEBUG("Overworld", "ConfigureMultiAreaMap: parent=%d, current_size=%d, new_size=%d, version=%d",
|
||||
parent_index, static_cast<int>(overworld_maps_[parent_index].area_size()),
|
||||
static_cast<int>(size), asm_version);
|
||||
|
||||
@@ -383,7 +383,7 @@ absl::Status Overworld::ConfigureMultiAreaMap(int parent_index, AreaSizeEnum siz
|
||||
}
|
||||
}
|
||||
|
||||
LOG_INFO("Overworld", "Configured %s area: parent=%d, old_siblings=%zu, new_siblings=%zu",
|
||||
LOG_DEBUG("Overworld", "Configured %s area: parent=%d, old_siblings=%zu, new_siblings=%zu",
|
||||
(size == AreaSizeEnum::LargeArea) ? "Large" :
|
||||
(size == AreaSizeEnum::WideArea) ? "Wide" :
|
||||
(size == AreaSizeEnum::TallArea) ? "Tall" : "Small",
|
||||
|
||||
Reference in New Issue
Block a user