8#include "absl/strings/str_format.h"
17#include "imgui/imgui.h"
25using internal::PaletteRowLayout;
30 size_t& out_offset,
int& out_length) {
31 if (palette.
empty()) {
35 const auto layout = GetPaletteRowLayout(group_name, palette.
size());
37 GetPaletteRowCount(palette.
size(), layout.colors_per_row);
38 const int clamped_row = std::clamp(row_index, 0, std::max(0, max_rows - 1));
39 const int row_offset = clamped_row * layout.colors_per_row;
40 const size_t offset =
static_cast<size_t>(
41 row_offset + (layout.has_explicit_transparent ? 1 : 0));
43 layout.colors_per_row - (layout.has_explicit_transparent ? 1 : 0);
44 length = std::clamp(length, 1, 15);
46 if (offset >= palette.
size()) {
50 if (offset + length > palette.
size()) {
51 length =
static_cast<int>(palette.
size() - offset);
56 return out_length > 0;
70 ImGui::TextDisabled(tr(
"Load a ROM to manage palettes"));
85 ImGui::TextDisabled(tr(
"Load a ROM to manage palettes"));
86 return absl::OkStatus();
97 return absl::OkStatus();
150 if (ImGui::Combo(tr(
"Group"),
152 kPaletteGroupAddressesKeys,
153 IM_ARRAYSIZE(kPaletteGroupAddressesKeys))) {
160 if (ImGui::InputInt(tr(
"Palette"), &palette_idx)) {
169 if (ImGui::InputInt(tr(
"Sub-Palette"), &sub_idx)) {
173 HOVER_HINT(
"Sub-palette row (0-7 for SNES 128-color palettes)");
184 if (!palette_group_result) {
185 ImGui::TextDisabled(tr(
"Invalid palette group"));
189 auto palette_group = *palette_group_result;
191 ImGui::TextDisabled(tr(
"Invalid palette index"));
197 auto palette_group_name =
199 auto layout = GetPaletteRowLayout(palette_group_name, palette.size());
201 int colors_per_row = layout.colors_per_row;
202 int total_colors =
static_cast<int>(palette.size());
203 int num_rows = GetPaletteRowCount(palette.size(), colors_per_row);
208 for (
int row = 0; row < num_rows; row++) {
209 for (
int col = 0; col < colors_per_row; col++) {
210 int idx = row * colors_per_row + col;
211 if (idx >= total_colors)
217 auto& color = palette[idx];
218 ImVec4 im_color(color.rgb().x / 255.0f, color.rgb().y / 255.0f,
219 color.rgb().z / 255.0f, 1.0f);
222 bool in_sub_palette =
224 std::optional<gui::StyleVarGuard> pal_border_var;
225 std::optional<gui::StyleColorGuard> pal_border_color;
226 if (in_sub_palette) {
227 pal_border_var.emplace(ImGuiStyleVar_FrameBorderSize, 2.0f);
231 std::string
id = absl::StrFormat(
"##PalColor%d", idx);
232 if (ImGui::ColorButton(
id.c_str(), im_color,
233 ImGuiColorEditFlags_NoTooltip, ImVec2(18, 18))) {
239 pal_border_color.reset();
240 pal_border_var.reset();
242 if (ImGui::IsItemHovered()) {
243 ImGui::BeginTooltip();
244 ImGui::Text(tr(
"Index: %d (Row %d, Col %d)"), idx, row, col);
245 ImGui::Text(tr(
"SNES: $%04X"), color.snes());
246 ImGui::Text(tr(
"RGB: %d, %d, %d"),
static_cast<int>(color.rgb().x),
247 static_cast<int>(color.rgb().y),
248 static_cast<int>(color.rgb().z));
255 ImGui::Text(tr(
"Sub-palette Row:"));
256 for (
int i = 0; i < std::min(8, num_rows); i++) {
261 std::optional<gui::StyleColorGuard> sel_guard;
265 if (ImGui::SmallButton(absl::StrFormat(
"%d", i).c_str())) {
278 ImGui::BeginDisabled(no_sheets);
279 if (ImGui::Button(
ICON_MD_BRUSH " Apply to Current Sheet")) {
282 ImGui::EndDisabled();
283 if (no_sheets && ImGui::IsItemHovered(ImGuiHoveredFlags_AllowWhenDisabled)) {
284 ImGui::SetTooltip(tr(
"Open a graphics sheet first"));
286 HOVER_HINT(
"Apply palette to the currently selected sheet");
295 HOVER_HINT(
"Apply palette to all active graphics sheets");
300 " Apply to %zu Selected",
307 HOVER_HINT(
"Apply palette to all selected sheets in browser");
318 HOVER_HINT(
"Force refresh of current sheet graphics");
325 auto palette_group_name =
327 auto palette_group_result =
329 if (!palette_group_result)
332 auto palette_group = *palette_group_result;
337 if (palette.empty()) {
342 if (sheet.is_active() && sheet.surface()) {
343 size_t palette_offset = 0;
344 int palette_length = 0;
345 if (ComputePaletteSlice(palette_group_name, palette,
347 palette_offset, palette_length)) {
348 sheet.SetPaletteWithTransparent(palette, palette_offset, palette_length);
350 sheet.SetPaletteWithTransparent(
351 palette, 0, std::min(7,
static_cast<int>(palette.size())));
361 auto palette_group_name =
363 auto palette_group_result =
365 if (!palette_group_result)
368 auto palette_group = *palette_group_result;
373 if (palette.empty()) {
376 size_t palette_offset = 0;
377 int palette_length = 0;
378 const bool has_slice = ComputePaletteSlice(
380 palette_offset, palette_length);
384 if (sheet.is_active() && sheet.surface()) {
386 sheet.SetPaletteWithTransparent(palette, palette_offset,
389 sheet.SetPaletteWithTransparent(
390 palette, 0, std::min(7,
static_cast<int>(palette.size())));
std::set< uint16_t > selected_sheets
uint16_t current_sheet_id
std::set< uint16_t > open_sheets
uint64_t sub_palette_index
uint64_t palette_group_index
absl::Status Update()
Legacy Update method for backward compatibility.
void DrawPresets()
Draw quick preset buttons.
GraphicsEditorState * state_
void Draw(bool *p_open) override
Draw the palette controls UI (WindowContent interface)
void ApplyPaletteToSheet(uint16_t sheet_id)
Apply current palette to specified sheet.
void DrawPaletteDisplay()
Draw the current palette display.
void DrawApplyButtons()
Draw apply buttons.
void Initialize()
Initialize the panel.
void ApplyPaletteToAllSheets()
Apply current palette to all active sheets.
void DrawPaletteGroupSelector()
Draw palette group selection.
zelda3::GameData * game_data_
auto mutable_gfx_sheets()
Get mutable reference to all graphics sheets.
void NotifySheetModified(int sheet_index)
Notify Arena that a graphics sheet has been modified.
Represents a palette of colors for the Super Nintendo Entertainment System (SNES).
static float GetComboWidth()
static float GetStandardInputWidth()
#define ICON_MD_LANDSCAPE
#define ICON_MD_CHECKLIST
#define ICON_MD_ACCOUNT_BOX
#define ICON_MD_FORMAT_PAINT
#define HOVER_HINT(string)
bool ComputePaletteSlice(std::string_view group_name, const gfx::SnesPalette &palette, int row_index, size_t &out_offset, int &out_length)
int GetPaletteRowCount(std::size_t palette_size, int colors_per_row)
PaletteRowLayout GetPaletteRowLayout(std::string_view group_name, std::size_t palette_size)
constexpr const char * kPaletteGroupAddressesKeys[]
ImVec4 GetSelectedColor()
void TextWithSeparators(const absl::string_view &text)
constexpr uint32_t kNumGfxSheets
PaletteGroup * get_group(const std::string &group_name)
auto palette(int i) const
gfx::PaletteGroupMap palette_groups