Files
anm2ed/src/imgui.h

2586 lines
85 KiB
C++

#pragma once
#include "clipboard.h"
#include "dialog.h"
#include "editor.h"
#include "ffmpeg.h"
#include "preview.h"
#include "generate_preview.h"
#include "resources.h"
#include "settings.h"
#include "snapshots.h"
#include "tool.h"
#include "window.h"
#define IMGUI_IMPL_OPENGL_LOADER_CUSTOM
#define IMGUI_ENABLE_DOCKING
#define IM_VEC2_CLASS_EXTRA \
inline bool operator==(const ImVec2& rhs) const { return x == rhs.x && y == rhs.y; } \
inline bool operator!=(const ImVec2& rhs) const { return !(*this == rhs); } \
inline ImVec2 operator+(const ImVec2& rhs) const { return ImVec2(x + rhs.x, y + rhs.y); } \
inline ImVec2 operator-(const ImVec2& rhs) const { return ImVec2(x - rhs.x, y - rhs.y); } \
inline ImVec2 operator*(const ImVec2& rhs) const { return ImVec2(x * rhs.x, y * rhs.y); } \
inline ImVec2 operator*(float s) const { return ImVec2(x * s, y * s); } \
friend inline ImVec2 operator*(float s, const ImVec2& v) { return ImVec2(v.x * s, v.y * s); } \
inline ImVec2& operator+=(const ImVec2& rhs) { x += rhs.x; y += rhs.y; return *this; } \
inline ImVec2& operator-=(const ImVec2& rhs) { x -= rhs.x; y -= rhs.y; return *this; } \
inline ImVec2& operator*=(float s) { x *= s; y *= s; return *this; } \
inline ImVec2(const vec2& v) : x(v.x), y(v.y) {} \
inline operator vec2() const { return vec2(x, y); }
#define IM_VEC4_CLASS_EXTRA \
inline bool operator==(const ImVec4& rhs) const { return x == rhs.x && y == rhs.y && z == rhs.z && w == rhs.w; } \
inline bool operator!=(const ImVec4& rhs) const { return !(*this == rhs); } \
inline ImVec4 operator+(const ImVec4& rhs) const { return ImVec4(x + rhs.x, y + rhs.y, z + rhs.z, w + rhs.w); } \
inline ImVec4 operator-(const ImVec4& rhs) const { return ImVec4(x - rhs.x, y - rhs.y, z - rhs.z, w - rhs.w); } \
inline ImVec4 operator*(const ImVec4& rhs) const { return ImVec4(x * rhs.x, y * rhs.y, z * rhs.z, w * rhs.w); } \
inline ImVec4 operator*(float s) const { return ImVec4(x * s, y * s, z * s, w * s); } \
friend inline ImVec4 operator*(float s, const ImVec4& v) { return ImVec4(v.x * s, v.y * s, v.z * s, v.w * s); } \
inline ImVec4& operator+=(const ImVec4& rhs) { x += rhs.x; y += rhs.y; z += rhs.z; w += rhs.w; return *this; } \
inline ImVec4& operator-=(const ImVec4& rhs) { x -= rhs.x; y -= rhs.y; z -= rhs.z; w -= rhs.w; return *this; } \
inline ImVec4& operator*=(float s) { x *= s; y *= s; z *= s; w *= s; return *this; } \
inline ImVec4(const vec4& v) : x(v.x), y(v.y), z(v.z), w(v.w) {} \
inline operator vec4() const { return vec4(x, y, z, w); }
#include <imgui/imgui.h>
#include <imgui/imgui_internal.h>
#include <imgui/backends/imgui_impl_sdl3.h>
#include <imgui/backends/imgui_impl_opengl3.h>
#define IMGUI_CHORD_NONE (ImGuiMod_None)
#define IMGUI_EVENTS_FOOTER_HEIGHT 40
#define IMGUI_FRAME_BORDER 2.0f
#define IMGUI_LOG_DURATION 3.0f
#define IMGUI_LOG_PADDING 10.0f
#define IMGUI_PLAYHEAD_LINE_COLOR IM_COL32(UCHAR_MAX, UCHAR_MAX, UCHAR_MAX, UCHAR_MAX)
#define IMGUI_TRIGGERS_EVENT_COLOR IM_COL32(UCHAR_MAX, UCHAR_MAX, UCHAR_MAX, 128)
#define IMGUI_PLAYHEAD_LINE_WIDTH 2.0f
#define IMGUI_SPRITESHEETS_FOOTER_HEIGHT 65
#define IMGUI_TIMELINE_FRAME_MULTIPLE 5
#define IMGUI_TIMELINE_MERGE
#define IMGUI_TOOL_COLOR_PICKER_DURATION 0.25f
#define IMGUI_CONFIRM_POPUP_ROW_COUNT 2
#define IMGUI_CHORD_REPEAT_TIME 0.25f
#define IMGUI_ACTION_FRAME_CROP "Frame Crop"
#define IMGUI_ACTION_FRAME_MOVE "Frame Move"
#define IMGUI_ACTION_ANIMATION_SWAP "Animation Swap"
#define IMGUI_ACTION_TRIGGER_MOVE "Trigger At Frame"
#define IMGUI_ACTION_ITEM_SWAP "Item Swap"
#define IMGUI_ACTION_FRAME_DELAY "Frame Delay"
#define IMGUI_ACTION_DRAW "Draw"
#define IMGUI_ACTION_ERASE "Erase"
#define IMGUI_ACTION_MOVE "Move"
#define IMGUI_ACTION_SCALE "Scale"
#define IMGUI_ACTION_ROTATE "Rotate"
#define IMGUI_ACTION_CROP "Crop"
#define IMGUI_ACTION_ADD_SPRITESHEET "Add Spritesheet"
#define IMGUI_ACTION_REPLACE_SPRITESHEET "Replace Spritesheet"
#define IMGUI_ACTION_OPEN_FILE "Open File"
#define IMGUI_SET_ITEM_PROPERTIES_POPUP "Item Properties"
#define IMGUI_POPUP_FLAGS ImGuiWindowFlags_NoMove
#define IMGUI_POPUP_MODAL_FLAGS ImGuiWindowFlags_NoMove | ImGuiWindowFlags_AlwaysAutoResize
#define IMGUI_LOG_NO_ANM2_PATH "Please save the .anm2 to a path first!"
#define IMGUI_LOG_FILE_OPEN_FORMAT "Opened anm2: {}"
#define IMGUI_LOG_FILE_SAVE_FORMAT "Saved anm2 to: {}"
#define IMGUI_LOG_SPRITESHEET_RELOAD "Reloaded selected spritesheets"
#define IMGUI_LOG_RENDER_ANIMATION_FRAMES_SAVE_FORMAT "Saved rendered frames to: {}"
#define IMGUI_LOG_RENDER_ANIMATION_SAVE_FORMAT "Saved rendered animation to: {}"
#define IMGUI_LOG_RENDER_ANIMATION_NO_ANIMATION_ERROR "No animation selected; rendering cancelled."
#define IMGUI_LOG_RENDER_ANIMATION_NO_FRAMES_ERROR "No frames to render; rendering cancelled."
#define IMGUI_LOG_RENDER_ANIMATION_DIRECTORY_ERROR "Invalid directory! Make sure it exists and you have write permissions."
#define IMGUI_LOG_RENDER_ANIMATION_PATH_ERROR "Invalid path! Make sure it's valid and you have write permissions."
#define IMGUI_LOG_RENDER_ANIMATION_FFMPEG_PATH_ERROR "Invalid FFmpeg path! Make sure you have it installed and the path is correct."
#define IMGUI_LOG_RENDER_ANIMATION_FFMPEG_ERROR "FFmpeg could not render animation! Check paths or your FFmpeg installation."
#define IMGUI_LOG_SPRITESHEET_SAVE_FORMAT "Saved spritesheet #{} to: {}"
#define IMGUI_LOG_DRAG_DROP_ERROR "Invalid file for dragging/dropping!"
#define IMGUI_LOG_ANIMATION_PASTE_ERROR "Failed to parse clipboard text as an animation."
#define IMGUI_LOG_FRAME_PASTE_ERROR "Failed to parse clipboard text as a frame."
#define IMGUI_LOG_RELOAD_SPRITESHEET "Reloaded spritesheet(s)."
#define IMGUI_NONE "None"
#define IMGUI_ANIMATION_DEFAULT_FORMAT "(*) {}"
#define IMGUI_BUFFER_MAX UCHAR_MAX
#define IMGUI_INVISIBLE_LABEL_MARKER "##"
#define IMGUI_ITEM_SELECTABLE_EDITABLE_LABEL "## Editing"
#define IMGUI_LOG_FORMAT "## Log {}"
#define IMGUI_LOG_REDO_FORMAT "Redo: {}"
#define IMGUI_LOG_UNDO_FORMAT "Undo: {}"
#define IMGUI_OPENGL_VERSION "#version 330"
#define IMGUI_POSITION_FORMAT "Position: ({:8}, {:8})"
#define IMGUI_SPRITESHEET_FORMAT "#{} {}"
#define IMGUI_SPRITESHEET_ID_FORMAT "#{}"
#define IMGUI_TIMELINE_ITEM_CHILD_FORMAT "#{} {}"
#define IMGUI_LAYER_FORMAT "#{} {}"
#define IMGUI_NULL_FORMAT "#{} {}"
#define IMGUI_TIMELINE_FRAME_LABEL_FORMAT "## {}"
#define IMGUI_SELECTABLE_INPUT_INT_FORMAT "#{}"
#define IMGUI_TIMELINE_ANIMATION_NONE "Select an animation to show timeline..."
#define IMGUI_HOTKEY_CHANGE "Input new hotkey..."
#define IMGUI_LABEL_HOTKEY_FORMAT " ({})"
#define IMGUI_TOOLTIP_HOTKEY_FORMAT "\n(Hotkey: {})"
#define IMGUI_INVISIBLE_FORMAT "## {}"
#define IMGUI_RENDERING_FFMPEG_INFO_THRESHOLD 0.95f
#define IMGUI_TRIGGERS_FONT_SCALE 2.0
const ImVec2 IMGUI_TIMELINE_FRAME_SIZE = {12, 36};
const ImVec2 IMGUI_TIMELINE_FRAME_ATLAS_OFFSET = {ATLAS_SIZE_SMALL.x * 0.25f, (IMGUI_TIMELINE_FRAME_SIZE.y * 0.5f) - (ATLAS_SIZE_SMALL.y * 0.5f)};
const ImVec2 IMGUI_TIMELINE_ITEM_SELECTABLE_SIZE = {150, 0};
const ImVec2 IMGUI_TIMELINE_ITEM_SIZE = {300, IMGUI_TIMELINE_FRAME_SIZE.y};
const ImVec4 IMGUI_TIMELINE_FRAME_COLOR = {0.0f, 0.0f, 0.0f, 0.125};
const ImVec4 IMGUI_TIMELINE_FRAME_MULTIPLE_COLOR = {0.113, 0.184, 0.286, 0.125};
const ImVec4 IMGUI_TIMELINE_HEADER_FRAME_COLOR = {0.113, 0.184, 0.286, 0.5};
const ImVec4 IMGUI_TIMELINE_HEADER_FRAME_MULTIPLE_COLOR = {0.113, 0.184, 0.286, 1.0};
const ImVec4 IMGUI_TIMELINE_HEADER_FRAME_INACTIVE_COLOR = {0.113, 0.184, 0.286, 0.125};
const ImVec4 IMGUI_TIMELINE_HEADER_FRAME_MULTIPLE_INACTIVE_COLOR = {0.113, 0.184, 0.286, 0.25};
const ImVec4 IMGUI_ACTIVE_COLOR = {1.0, 1.0, 1.0, 1.0};
const ImVec4 IMGUI_INACTIVE_COLOR = {1.0, 1.0, 1.0, 0.25};
const ImVec2 IMGUI_SPRITESHEET_PREVIEW_SIZE = {50.0, 50.0};
const ImVec2 IMGUI_TOOLTIP_OFFSET = {16, 8};
const vec2 IMGUI_SPRITESHEET_EDITOR_CROP_FORGIVENESS = {1, 1};
const ImGuiKey IMGUI_INPUT_DELETE = ImGuiKey_Delete;
const ImGuiKey IMGUI_INPUT_LEFT = ImGuiKey_LeftArrow;
const ImGuiKey IMGUI_INPUT_RIGHT = ImGuiKey_RightArrow;
const ImGuiKey IMGUI_INPUT_UP = ImGuiKey_UpArrow;
const ImGuiKey IMGUI_INPUT_DOWN = ImGuiKey_DownArrow;
const ImGuiKey IMGUI_INPUT_SHIFT = ImGuiMod_Shift;
const ImGuiKey IMGUI_INPUT_CTRL = ImGuiMod_Ctrl;
const ImGuiKey IMGUI_INPUT_ZOOM_IN = ImGuiKey_1;
const ImGuiKey IMGUI_INPUT_ZOOM_OUT = ImGuiKey_2;
const ImGuiKey IMGUI_INPUT_ENTER = ImGuiKey_Enter;
const ImGuiKey IMGUI_INPUT_RENAME = ImGuiKey_F2;
const ImGuiKey IMGUI_INPUT_DEFAULT = ImGuiKey_Home;
const ImGuiMouseButton IMGUI_MOUSE_DEFAULT = ImGuiMouseButton_Middle;
enum ImguiPopupType
{
IMGUI_POPUP_NONE,
IMGUI_POPUP_BY_ITEM,
IMGUI_POPUP_CENTER_WINDOW
};
enum ImguiPopupState
{
IMGUI_POPUP_STATE_CLOSED,
IMGUI_POPUP_STATE_OPEN,
IMGUI_POPUP_STATE_CONFIRM,
IMGUI_POPUP_STATE_CANCEL
};
struct ImguiColorSet
{
ImVec4 normal{};
ImVec4 active{};
ImVec4 hovered{};
ImVec4 border{};
bool is_normal() const { return normal != ImVec4(); }
bool is_active() const { return active != ImVec4(); }
bool is_hovered() const { return hovered != ImVec4(); }
bool is_border() const { return border != ImVec4(); }
};
struct ImguiLogItem
{
std::string text;
f32 timeRemaining;
};
struct Imgui
{
Dialog* dialog = nullptr;
Resources* resources = nullptr;
Anm2* anm2 = nullptr;
Anm2Reference* reference = nullptr;
Editor* editor = nullptr;
Preview* preview = nullptr;
GeneratePreview* generatePreview = nullptr;
Settings* settings = nullptr;
Snapshots* snapshots = nullptr;
Clipboard* clipboard = nullptr;
SDL_Window* window = nullptr;
SDL_GLContext* glContext = nullptr;
std::string pendingPopup{};
ImguiPopupType pendingPopupType = IMGUI_POPUP_NONE;
ImVec2 pendingPopupPosition{};
std::vector<ImguiLogItem> log;
Anm2 saveAnm2;
SDL_SystemCursor cursor;
SDL_SystemCursor pendingCursor;
bool isCursorSet = false;
bool isContextualActionsEnabled = true;
bool isQuit = false;
bool isTryQuit = false;
};
static inline void imgui_snapshot(Imgui* self, const std::string& action = SNAPSHOT_ACTION)
{
self->snapshots->action = action;
Snapshot snapshot = snapshot_get(self->snapshots);
snapshots_undo_push(self->snapshots, &snapshot);
}
static void imgui_log_push(Imgui* self, const std::string& text)
{
self->log.push_back({text, IMGUI_LOG_DURATION});
log_imgui(text);
}
static inline void imgui_anm2_new(Imgui* self)
{
anm2_reference_clear(self->reference);
anm2_free(self->anm2);
anm2_new(self->anm2);
}
static inline void imgui_file_open(Imgui* self)
{
dialog_anm2_open(self->dialog);
}
static inline void imgui_file_save(Imgui* self)
{
if (self->anm2->path.empty())
dialog_anm2_save(self->dialog);
else
{
anm2_serialize(self->anm2, self->anm2->path);
imgui_log_push(self, std::format(IMGUI_LOG_FILE_SAVE_FORMAT, self->anm2->path));
}
self->saveAnm2 = *self->anm2;
}
static inline void imgui_file_new(Imgui* self)
{
std::string path = self->anm2->path;
imgui_anm2_new(self);
self->anm2->path = path;
imgui_file_save(self);
}
static inline void imgui_file_save_as(Imgui* self)
{
dialog_anm2_save(self->dialog);
}
static inline void imgui_quit(Imgui* self)
{
if (self->saveAnm2 != *self->anm2)
self->isTryQuit = true;
else
self->isQuit = true;
}
static inline void imgui_explore(Imgui* self)
{
std::filesystem::path filePath = self->anm2->path;
std::filesystem::path parentPath = filePath.parent_path();
dialog_explorer_open(parentPath.string());
}
static inline void imgui_tool_pan_set(Imgui* self)
{
self->settings->tool = TOOL_PAN;
}
static inline void imgui_tool_move_set(Imgui* self)
{
self->settings->tool = TOOL_MOVE;
}
static inline void imgui_tool_rotate_set(Imgui* self)
{
self->settings->tool = TOOL_ROTATE;
}
static inline void imgui_tool_scale_set(Imgui* self)
{
self->settings->tool = TOOL_SCALE;
}
static inline void imgui_tool_crop_set(Imgui* self)
{
self->settings->tool = TOOL_CROP;
}
static inline void imgui_tool_draw_set(Imgui* self)
{
self->settings->tool = TOOL_DRAW;
}
static inline void imgui_tool_erase_set(Imgui* self)
{
self->settings->tool = TOOL_ERASE;
}
static inline void imgui_tool_color_picker_set(Imgui* self)
{
self->settings->tool = TOOL_COLOR_PICKER;
}
static inline void imgui_undo(Imgui* self)
{
if (self->snapshots->undoStack.top == 0) return;
snapshots_undo(self->snapshots);
imgui_log_push(self, std::format(IMGUI_LOG_UNDO_FORMAT, self->snapshots->action));
}
static inline void imgui_redo(Imgui* self)
{
if (self->snapshots->redoStack.top == 0) return;
std::string action = self->snapshots->action;
snapshots_redo(self->snapshots);
imgui_log_push(self, std::format(IMGUI_LOG_REDO_FORMAT, action));
}
static inline void imgui_cut(Imgui* self)
{
clipboard_cut(self->clipboard);
}
static inline void imgui_copy(Imgui* self)
{
clipboard_copy(self->clipboard);
}
static inline void imgui_paste(Imgui* self)
{
if (!clipboard_paste(self->clipboard))
{
switch (self->clipboard->type)
{
case CLIPBOARD_FRAME: imgui_log_push(self, IMGUI_LOG_FRAME_PASTE_ERROR); break;
case CLIPBOARD_ANIMATION: imgui_log_push(self, IMGUI_LOG_ANIMATION_PASTE_ERROR); break;
default: break;
}
}
}
static inline void imgui_onionskin_toggle(Imgui* self)
{
self->settings->onionskinIsEnabled = !self->settings->onionskinIsEnabled;
}
static const std::unordered_map<std::string, ImGuiKey> IMGUI_KEY_MAP =
{
{ "A", ImGuiKey_A },
{ "B", ImGuiKey_B },
{ "C", ImGuiKey_C },
{ "D", ImGuiKey_D },
{ "E", ImGuiKey_E },
{ "F", ImGuiKey_F },
{ "G", ImGuiKey_G },
{ "H", ImGuiKey_H },
{ "I", ImGuiKey_I },
{ "J", ImGuiKey_J },
{ "K", ImGuiKey_K },
{ "L", ImGuiKey_L },
{ "M", ImGuiKey_M },
{ "N", ImGuiKey_N },
{ "O", ImGuiKey_O },
{ "P", ImGuiKey_P },
{ "Q", ImGuiKey_Q },
{ "R", ImGuiKey_R },
{ "S", ImGuiKey_S },
{ "T", ImGuiKey_T },
{ "U", ImGuiKey_U },
{ "V", ImGuiKey_V },
{ "W", ImGuiKey_W },
{ "X", ImGuiKey_X },
{ "Y", ImGuiKey_Y },
{ "Z", ImGuiKey_Z },
{ "0", ImGuiKey_0 },
{ "1", ImGuiKey_1 },
{ "2", ImGuiKey_2 },
{ "3", ImGuiKey_3 },
{ "4", ImGuiKey_4 },
{ "5", ImGuiKey_5 },
{ "6", ImGuiKey_6 },
{ "7", ImGuiKey_7 },
{ "8", ImGuiKey_8 },
{ "9", ImGuiKey_9 },
{ "Num0", ImGuiKey_Keypad0 },
{ "Num1", ImGuiKey_Keypad1 },
{ "Num2", ImGuiKey_Keypad2 },
{ "Num3", ImGuiKey_Keypad3 },
{ "Num4", ImGuiKey_Keypad4 },
{ "Num5", ImGuiKey_Keypad5 },
{ "Num6", ImGuiKey_Keypad6 },
{ "Num7", ImGuiKey_Keypad7 },
{ "Num8", ImGuiKey_Keypad8 },
{ "Num9", ImGuiKey_Keypad9 },
{ "NumAdd", ImGuiKey_KeypadAdd },
{ "NumSubtract", ImGuiKey_KeypadSubtract },
{ "NumMultiply", ImGuiKey_KeypadMultiply },
{ "NumDivide", ImGuiKey_KeypadDivide },
{ "NumEnter", ImGuiKey_KeypadEnter },
{ "NumDecimal", ImGuiKey_KeypadDecimal },
{ "F1", ImGuiKey_F1 },
{ "F2", ImGuiKey_F2 },
{ "F3", ImGuiKey_F3 },
{ "F4", ImGuiKey_F4 },
{ "F5", ImGuiKey_F5 },
{ "F6", ImGuiKey_F6 },
{ "F7", ImGuiKey_F7 },
{ "F8", ImGuiKey_F8 },
{ "F9", ImGuiKey_F9 },
{ "F10", ImGuiKey_F10 },
{ "F11", ImGuiKey_F11 },
{ "F12", ImGuiKey_F12 },
{ "Up", ImGuiKey_UpArrow },
{ "Down", ImGuiKey_DownArrow },
{ "Left", ImGuiKey_LeftArrow },
{ "Right", ImGuiKey_RightArrow },
{ "Space", ImGuiKey_Space },
{ "Enter", ImGuiKey_Enter },
{ "Escape", ImGuiKey_Escape },
{ "Tab", ImGuiKey_Tab },
{ "Backspace", ImGuiKey_Backspace },
{ "Delete", ImGuiKey_Delete },
{ "Insert", ImGuiKey_Insert },
{ "Home", ImGuiKey_Home },
{ "End", ImGuiKey_End },
{ "PageUp", ImGuiKey_PageUp },
{ "PageDown", ImGuiKey_PageDown },
{ "Minus", ImGuiKey_Minus },
{ "Equal", ImGuiKey_Equal },
{ "LeftBracket", ImGuiKey_LeftBracket },
{ "RightBracket", ImGuiKey_RightBracket },
{ "Semicolon", ImGuiKey_Semicolon },
{ "Apostrophe", ImGuiKey_Apostrophe },
{ "Comma", ImGuiKey_Comma },
{ "Period", ImGuiKey_Period },
{ "Slash", ImGuiKey_Slash },
{ "Backslash", ImGuiKey_Backslash },
{ "GraveAccent", ImGuiKey_GraveAccent },
{ "MouseLeft", ImGuiKey_MouseLeft },
{ "MouseRight", ImGuiKey_MouseRight },
{ "MouseMiddle", ImGuiKey_MouseMiddle },
{ "MouseX1", ImGuiKey_MouseX1 },
{ "MouseX2", ImGuiKey_MouseX2 }
};
static std::unordered_map<std::string, ImGuiKey> IMGUI_MOD_MAP =
{
{ "Ctrl", ImGuiMod_Ctrl },
{ "Shift", ImGuiMod_Shift },
{ "Alt", ImGuiMod_Alt },
{ "Super", ImGuiMod_Super },
};
static inline ImGuiKey imgui_key_from_char_get(char c)
{
if (c >= 'a' && c <= 'z') c -= 'a' - 'A';
if (c >= 'A' && c <= 'Z') return (ImGuiKey)(ImGuiKey_A + (c - 'A'));
return ImGuiKey_None;
}
static inline std::string imgui_string_from_chord_get(ImGuiKeyChord chord)
{
std::string result;
if (chord & ImGuiMod_Ctrl) result += "Ctrl+";
if (chord & ImGuiMod_Shift) result += "Shift+";
if (chord & ImGuiMod_Alt) result += "Alt+";
if (chord & ImGuiMod_Super) result += "Super+";
ImGuiKey key = (ImGuiKey)(chord & ~ImGuiMod_Mask_);
if (key != ImGuiKey_None)
{
const char* name = ImGui::GetKeyName(key);
if (name && *name)
result += name;
else
result += "Unknown";
}
if (!result.empty() && result.back() == '+')
result.pop_back();
return result;
}
static inline ImGuiKeyChord imgui_chord_from_string_get(const std::string& str)
{
ImGuiKeyChord chord = 0;
ImGuiKey baseKey = ImGuiKey_None;
std::stringstream ss(str);
std::string token;
while (std::getline(ss, token, '+'))
{
// trim
token.erase(0, token.find_first_not_of(" \t\r\n"));
token.erase(token.find_last_not_of(" \t\r\n") + 1);
if (token.empty())
continue;
if (auto it = IMGUI_MOD_MAP.find(token); it != IMGUI_MOD_MAP.end()) {
chord |= it->second;
}
else if (baseKey == ImGuiKey_None) {
if (auto it2 = IMGUI_KEY_MAP.find(token); it2 != IMGUI_KEY_MAP.end())
baseKey = it2->second;
}
}
if (baseKey != ImGuiKey_None)
chord |= baseKey;
return chord;
}
static inline void imgui_keyboard_nav_enable(void) { ImGui::GetIO().ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; }
static inline void imgui_keyboard_nav_disable(void) { ImGui::GetIO().ConfigFlags &= ~ImGuiConfigFlags_NavEnableKeyboard; }
static inline void imgui_contextual_actions_enable(Imgui* self) { self->isContextualActionsEnabled = true; }
static inline void imgui_contextual_actions_disable(Imgui* self){ self->isContextualActionsEnabled = false; }
static inline bool imgui_is_popup_open(const std::string& label) { return ImGui::IsPopupOpen(label.c_str()); }
static inline bool imgui_is_any_popup_open(void)
{
return ImGui::IsPopupOpen(nullptr, ImGuiPopupFlags_AnyPopupId);
}
static inline void imgui_open_popup(const std::string& label) { ImGui::OpenPopup(label.c_str()); }
static inline void imgui_pending_popup_process(Imgui* self)
{
if (self->pendingPopup.empty()) return;
switch (self->pendingPopupType)
{
case IMGUI_POPUP_CENTER_WINDOW:
ImGui::SetNextWindowPos(ImGui::GetMainViewport()->GetCenter(), ImGuiCond_Appearing, ImVec2(0.5f, 0.5f));
break;
case IMGUI_POPUP_BY_ITEM:
default:
ImGui::SetNextWindowPos(self->pendingPopupPosition);
break;
}
imgui_open_popup(self->pendingPopup.c_str());
self->pendingPopup.clear();
self->pendingPopupType = IMGUI_POPUP_NONE;
self->pendingPopupPosition = ImVec2();
}
static inline bool imgui_begin_popup(const std::string& label, Imgui* imgui, ImVec2 size = ImVec2())
{
imgui_pending_popup_process(imgui);
if (size != ImVec2()) ImGui::SetNextWindowSizeConstraints(size, ImVec2(FLT_MAX, FLT_MAX));
bool isActivated = ImGui::BeginPopup(label.c_str(), IMGUI_POPUP_FLAGS);
return isActivated;
}
static inline bool imgui_begin_popup_modal(const std::string& label, Imgui* imgui, ImVec2 size = ImVec2())
{
imgui_pending_popup_process(imgui);
if (size != ImVec2()) ImGui::SetNextWindowSizeConstraints(size, ImVec2(FLT_MAX, FLT_MAX));
bool isActivated = ImGui::BeginPopupModal(label.c_str(), nullptr, IMGUI_POPUP_MODAL_FLAGS);
if (isActivated) imgui_contextual_actions_disable(imgui);
return isActivated;
}
static inline void imgui_close_current_popup(Imgui* imgui)
{
imgui_contextual_actions_enable(imgui);
ImGui::CloseCurrentPopup();
}
static inline void imgui_end_popup(Imgui* imgui)
{
ImGui::EndPopup();
imgui_pending_popup_process(imgui);
}
enum ImguiItemType
{
IMGUI_ITEM,
IMGUI_TEXT,
IMGUI_WINDOW,
IMGUI_DOCKSPACE,
IMGUI_CHILD,
IMGUI_TABLE,
IMGUI_CONFIRM_POPUP,
IMGUI_SELECTABLE,
IMGUI_BUTTON,
IMGUI_RADIO_BUTTON,
IMGUI_COLOR_BUTTON,
IMGUI_CHECKBOX,
IMGUI_INPUT_INT,
IMGUI_INPUT_TEXT,
IMGUI_INPUT_FLOAT,
IMGUI_SLIDER_FLOAT,
IMGUI_DRAG_FLOAT,
IMGUI_COLOR_EDIT,
IMGUI_COMBO,
IMGUI_ATLAS_BUTTON
};
struct ImguiItemOverride
{
bool isDisabled{};
bool isSelected{};
std::string label{};
ImVec2 size{};
s32 id{};
s32 max{};
AtlasType atlas = ATLAS_NONE;
bool isMnemonicDisabled{};
s32 value{};
s32 rowCount{};
};
struct ImguiItem;
static std::vector<ImguiItem*>& imgui_item_registry(void)
{
static std::vector<ImguiItem*> registry;
return registry;
}
static ImGuiKeyChord* imgui_hotkey_chord_registry(void)
{
static ImGuiKeyChord registry[HOTKEY_COUNT];
return registry;
}
typedef void(*ImguiFunction)(Imgui*);
// Item
struct ImguiItem
{
std::string label{};
std::string tooltip{};
std::string& text = tooltip;
std::string snapshotAction{};
std::string popup{};
std::string dragDrop{};
std::string focusWindow{};
std::vector<std::string> items{};
AtlasType atlas = ATLAS_NONE;
ImGuiKeyChord chord = IMGUI_CHORD_NONE;
HotkeyType hotkey = HOTKEY_NONE;
ImGuiKey mnemonicKey = ImGuiKey_None;
s32 mnemonicIndex = INDEX_NONE;
ImVec2 size{};
ImVec2 popupSize{};
ImguiColorSet color{};
ImguiFunction function = nullptr;
ImguiPopupType popupType = IMGUI_POPUP_CENTER_WINDOW;
bool isDisabled = false;
bool isMnemonicDisabled = false;
bool isEmptyFormat = false;
bool isSelected = false;
bool isUseItemActivated = false;
bool isSizeToText = false;
bool isHotkeyInLabel = false;
bool isSameLine = false;
bool isSeparator = false;
s32 id = 0;
s32 idOffset{};
f32 speed = 0.25f;
s32 step = 1;
s32 stepFast = 10;
s32 min{};
s32 max{};
s32 value{};
vec2 atlasOffset{};
s32 border{};
s32 flags{};
s32 windowFlags{};
s32 rowCount = 0;
bool is_border() const { return border != 0; }
bool is_row() const { return rowCount != 0; }
bool is_hotkey() const { return hotkey != HOTKEY_NONE; }
bool is_chord() const { return chord != IMGUI_CHORD_NONE || is_hotkey(); }
bool is_drag_drop() const { return !dragDrop.empty(); }
bool is_focus_window() const { return !focusWindow.empty(); }
bool is_popup() const { return !popup.empty(); }
bool is_function() const { return function; }
bool is_size() const { return size != ImVec2(); }
bool is_popup_size() const { return popupSize != ImVec2(); }
bool is_tooltip() const { return !tooltip.empty(); }
bool is_undoable() const { return !snapshotAction.empty(); }
bool is_mnemonic() const { return mnemonicKey != ImGuiKey_None; }
bool is_range() const { return min != 0 || max != 0; }
const char* drag_drop_get() const { return dragDrop.c_str(); }
const char* text_get() const { return text.c_str(); }
void construct()
{
static s32 idNew = 0;
id = idNew++;
imgui_item_registry().push_back(this);
std::string labelNew{};
for (s32 i = 0; i < (s32)label.size(); i++)
{
if (label[i] == '&')
{
if (label[i + 1] == '&')
{
labelNew += '&';
i++;
}
else if (label[i + 1] != '\0')
{
mnemonicKey = imgui_key_from_char_get(label[i + 1]);
mnemonicIndex = (s32)labelNew.size();
labelNew += label[i + 1];
i++;
}
}
else
labelNew += label[i];
}
label = labelNew;
}
ImguiItem copy(const ImguiItemOverride& override) const
{
ImguiItem out = *this;
if (override.isDisabled) out.isDisabled = override.isDisabled;
if(override.isSelected) out.isSelected = override.isSelected;
if (is_popup() && imgui_is_popup_open(popup)) out.isSelected = true;
if (id != ID_NONE) out.id = id + idOffset + override.id;
if (!override.label.empty()) out.label = override.label;
if (override.size != ImVec2{}) out.size = override.size;
if (override.max != 0) out.max = override.max;
if (override.value != 0) out.value = override.value;
if (override.rowCount != 0) out.rowCount = override.rowCount;
if (override.atlas != ATLAS_NONE) out.atlas = override.atlas;
if (override.isMnemonicDisabled) out.isMnemonicDisabled = override.isMnemonicDisabled;
return out;
}
ImGuiKeyChord chord_get() const
{
if (is_hotkey()) return imgui_hotkey_chord_registry()[hotkey];
return chord;
}
std::string label_get() const
{
std::string newLabel = label;
if (isHotkeyInLabel)
newLabel += std::format(IMGUI_LABEL_HOTKEY_FORMAT, imgui_string_from_chord_get(chord_get()));
return newLabel;
}
std::string tooltip_get() const
{
std::string newTooltip = tooltip;
if (is_chord())
newTooltip += std::format(IMGUI_TOOLTIP_HOTKEY_FORMAT, imgui_string_from_chord_get(chord_get()));
return newTooltip;
}
};
#define IMGUI_ITEM(NAME, ...) const inline ImguiItem NAME = []{ ImguiItem self; __VA_ARGS__; self.construct(); return self; }()
IMGUI_ITEM(IMGUI_WINDOW_MAIN,
self.label = "## Window",
self.flags = ImGuiWindowFlags_NoTitleBar |
ImGuiWindowFlags_NoCollapse |
ImGuiWindowFlags_NoResize |
ImGuiWindowFlags_NoMove |
ImGuiWindowFlags_NoBringToFrontOnFocus |
ImGuiWindowFlags_NoNavFocus
);
IMGUI_ITEM(IMGUI_DOCKSPACE_MAIN,
self.label = "## Dockspace",
self.flags = ImGuiDockNodeFlags_PassthruCentralNode
);
IMGUI_ITEM(IMGUI_FOOTER_CHILD,
self.label = "## Footer Child",
self.size = {0, 36},
self.flags = true
);
IMGUI_ITEM(IMGUI_TASKBAR,
self.label = "Taskbar",
self.size = {0, 32},
self.flags = ImGuiWindowFlags_NoTitleBar |
ImGuiWindowFlags_NoResize |
ImGuiWindowFlags_NoMove |
ImGuiWindowFlags_NoScrollbar |
ImGuiWindowFlags_NoScrollWithMouse |
ImGuiWindowFlags_NoSavedSettings
);
IMGUI_ITEM(IMGUI_FILE,
self.label = "&File",
self.tooltip = "Opens the file menu, for reading/writing anm2 files.",
self.popup = "## File Popup",
self.popupType = IMGUI_POPUP_BY_ITEM,
self.isSizeToText = true,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_NEW,
self.label = "&New ",
self.tooltip = "Load a blank .anm2 file to edit.",
self.function = imgui_file_new,
self.hotkey = HOTKEY_NEW,
self.isSizeToText = true,
self.isHotkeyInLabel = true
);
IMGUI_ITEM(IMGUI_OPEN,
self.label = "&Open ",
self.tooltip = "Open an existing .anm2 file to edit.",
self.function = imgui_file_open,
self.hotkey = HOTKEY_OPEN,
self.isSizeToText = true,
self.isHotkeyInLabel = true
);
IMGUI_ITEM(IMGUI_SAVE,
self.label = "&Save ",
self.tooltip = "Saves the current .anm2 file to its path.\nIf no path exists, one can be chosen.",
self.function = imgui_file_save,
self.hotkey = HOTKEY_SAVE,
self.isSizeToText = true,
self.isHotkeyInLabel = true
);
IMGUI_ITEM(IMGUI_SAVE_AS,
self.label = "S&ave As ",
self.tooltip = "Saves the current .anm2 file to a chosen path.",
self.function = imgui_file_save_as,
self.hotkey = HOTKEY_SAVE_AS,
self.isSizeToText = true,
self.isHotkeyInLabel = true
);
IMGUI_ITEM(IMGUI_EXPLORE_ANM2_LOCATION,
self.label = "E&xplore Anm2 Location",
self.tooltip = "Open the system's file explorer in the anm2's path.",
self.function = imgui_explore,
self.isSizeToText = true,
self.isSeparator = true
);
IMGUI_ITEM(IMGUI_EXIT,
self.label = "&Exit ",
self.tooltip = "Exits the program.",
self.function = imgui_quit,
self.hotkey = HOTKEY_EXIT,
self.isSizeToText = true,
self.isHotkeyInLabel = true
);
IMGUI_ITEM(IMGUI_EXIT_CONFIRMATION,
self.label = "Exit Confirmation",
self.text = "Unsaved changes will be lost!\nAre you sure you want to exit?"
);
IMGUI_ITEM(IMGUI_OPEN_CONFIRMATION,
self.label = "Open Confirmation",
self.text = "Unsaved changes will be lost!\nAre you sure you open a new file?"
);
IMGUI_ITEM(IMGUI_NO_ANM2_PATH_CONFIRMATION,
self.label = "No Anm2 Path",
self.text = "You will need to load or make a new .anm2 file first!\n"
);
IMGUI_ITEM(IMGUI_WIZARD,
self.label = "&Wizard",
self.tooltip = "Opens the wizard menu, for neat functions related to the .anm2.",
self.popup = "## Wizard Popup",
self.popupType = IMGUI_POPUP_BY_ITEM,
self.isSizeToText = true,
self.isSameLine = true
);
#define IMGUI_GENERATE_ANIMATION_FROM_GRID_PADDING 40
IMGUI_ITEM(IMGUI_GENERATE_ANIMATION_FROM_GRID,
self.label = "&Generate Animation from Grid",
self.tooltip = "Generate a new animation from grid values.",
self.popup = "Generate Animation from Grid",
self.popupType = IMGUI_POPUP_CENTER_WINDOW,
self.popupSize =
{
(GENERATE_PREVIEW_SIZE.x * 2) + IMGUI_GENERATE_ANIMATION_FROM_GRID_PADDING,
GENERATE_PREVIEW_SIZE.y + (IMGUI_FOOTER_CHILD.size.y * 2) + (IMGUI_GENERATE_ANIMATION_FROM_GRID_PADDING / 2)
}
);
IMGUI_ITEM(IMGUI_GENERATE_ANIMATION_FROM_GRID_OPTIONS_CHILD,
self.label = "## Generate Animation From Grid Options Child",
self.size =
{
IMGUI_GENERATE_ANIMATION_FROM_GRID.popupSize.x / 2,
IMGUI_GENERATE_ANIMATION_FROM_GRID.popupSize.y - IMGUI_FOOTER_CHILD.size.y
},
self.flags = true
);
IMGUI_ITEM(IMGUI_GENERATE_ANIMATION_FROM_GRID_START_POSITION,
self.label = "Start Position",
self.tooltip = "Set the starting position on the layer's spritesheet for the generated animation."
);
IMGUI_ITEM(IMGUI_GENERATE_ANIMATION_FROM_GRID_SIZE,
self.label = "Size",
self.tooltip = "Set the size of each frame in the generated animation."
);
IMGUI_ITEM(IMGUI_GENERATE_ANIMATION_FROM_GRID_PIVOT,
self.label = "Pivot",
self.tooltip = "Set the pivot of each frame in the generated animation."
);
IMGUI_ITEM(IMGUI_GENERATE_ANIMATION_FROM_GRID_ROWS,
self.label = "Rows",
self.tooltip = "Set how many rows will be used in the generated animation.",
self.min = 1,
self.max = 1000
);
IMGUI_ITEM(IMGUI_GENERATE_ANIMATION_FROM_GRID_COLUMNS,
self.label = "Columns",
self.tooltip = "Set how many columns will be used in the generated animation.",
self.min = 1,
self.max = 1000
);
IMGUI_ITEM(IMGUI_GENERATE_ANIMATION_FROM_GRID_COUNT,
self.label = "Count",
self.tooltip = "Set how many frames will be made for the generated animation.",
self.value = ANM2_FRAME_NUM_MIN
);
IMGUI_ITEM(IMGUI_GENERATE_ANIMATION_FROM_GRID_DELAY,
self.label = "Delay",
self.tooltip = "Set the delay of each frame in the generated animation.",
self.max = 1000
);
IMGUI_ITEM(IMGUI_GENERATE_ANIMATION_FROM_GRID_PREVIEW_CHILD,
self.label = "## Generate Animation From Grid Preview Child",
self.size =
{
IMGUI_GENERATE_ANIMATION_FROM_GRID.popupSize.x / 2,
IMGUI_GENERATE_ANIMATION_FROM_GRID.popupSize.y - IMGUI_FOOTER_CHILD.size.y
},
self.flags = true
);
IMGUI_ITEM(IMGUI_GENERATE_ANIMATION_FROM_GRID_SLIDER_CHILD,
self.label = "## Generate Animation From Grid Slider Child",
self.size =
{
(IMGUI_GENERATE_ANIMATION_FROM_GRID.popupSize.x / 2) - (IMGUI_GENERATE_ANIMATION_FROM_GRID_PADDING / 2),
IMGUI_FOOTER_CHILD.size.y
},
self.flags = true
);
IMGUI_ITEM(IMGUI_GENERATE_ANIMATION_FROM_GRID_SLIDER,
self.label = "## Generate Animation From Grid Slider",
self.tooltip = "Change the time of the generated animation preview.",
self.min = GENERATE_PREVIEW_TIME_MIN,
self.max = GENERATE_PREVIEW_TIME_MAX,
self.value = GENERATE_PREVIEW_TIME_MIN,
self.rowCount = 1,
self.isEmptyFormat = true,
self.flags = ImGuiSliderFlags_NoInput
);
IMGUI_ITEM(IMGUI_GENERATE_ANIMATION_FROM_GRID_GENERATE,
self.label = "Generate",
self.tooltip = "Generate an animation with the used settings.",
self.snapshotAction = "Generate Animation from Grid",
self.rowCount = IMGUI_CONFIRM_POPUP_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_CHANGE_ALL_FRAME_PROPERTIES,
self.label = "&Change All Frame Properties",
self.tooltip = "Change all frame properties in the selected animation item (or selected frame).",
self.popup = "Change All Frame Properties",
self.popupType = IMGUI_POPUP_CENTER_WINDOW,
self.popupSize = {500, 405}
);
IMGUI_ITEM(IMGUI_CHANGE_ALL_FRAME_PROPERTIES_CHILD,
self.label = "## Change All Frame Properties Child",
self.size =
{
IMGUI_CHANGE_ALL_FRAME_PROPERTIES.popupSize.x,
275
},
self.flags = true
);
IMGUI_ITEM(IMGUI_CHANGE_ALL_FRAME_PROPERTIES_SETTINGS_CHILD,
self.label = "## Change All Frame Properties Settings Child",
self.size =
{
IMGUI_CHANGE_ALL_FRAME_PROPERTIES.popupSize.x,
55
},
self.flags = true
);
IMGUI_ITEM(IMGUI_CHANGE_ALL_FRAME_PROPERTIES_SETTINGS, self.label = "Settings");
IMGUI_ITEM(IMGUI_CHANGE_ALL_FRAME_PROPERTIES_FROM_SELECTED_FRAME,
self.label = "From Selected Frames",
self.tooltip = "The set frame properties will start from the selected frame.",
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_CHANGE_ALL_FRAME_PROPERTIES_NUMBER_FRAMES,
self.label = "# of Frames",
self.tooltip = "Set the amount of frames that the set frame properties will apply to.",
self.size = {200, 0},
self.value = ANM2_FRAME_NUM_MIN,
self.max = 1000
);
#define IMGUI_CHANGE_ALL_FRAME_PROPERTIES_OPTIONS_ROW_COUNT 4
IMGUI_ITEM(IMGUI_CHANGE_ALL_FRAME_PROPERTIES_ADD,
self.label = "Add",
self.tooltip = "The specified values will be added to all specified frames.",
self.snapshotAction = "Add Frame Properties",
self.rowCount = IMGUI_CHANGE_ALL_FRAME_PROPERTIES_OPTIONS_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_CHANGE_ALL_FRAME_PROPERTIES_SUBTRACT,
self.label = "Subtract",
self.tooltip = "The specified values will be subtracted from all selected frames.",
self.snapshotAction = "Subtract Frame Properties",
self.rowCount = IMGUI_CHANGE_ALL_FRAME_PROPERTIES_OPTIONS_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_CHANGE_ALL_FRAME_PROPERTIES_SET,
self.label = "Set",
self.tooltip = "The specified values will be set to the specified value in selected frames.",
self.snapshotAction = "Set Frame Properties",
self.rowCount = IMGUI_CHANGE_ALL_FRAME_PROPERTIES_OPTIONS_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_CHANGE_ALL_FRAME_PROPERTIES_CANCEL,
self.label = "Cancel",
self.tooltip = "Cancel changing all frame properties.",
self.rowCount = IMGUI_CHANGE_ALL_FRAME_PROPERTIES_OPTIONS_ROW_COUNT
);
IMGUI_ITEM(IMGUI_SCALE_ANM2,
self.label = "S&cale Anm2",
self.tooltip = "Scale up all size and position-related frame properties in the anm2.",
self.popup = "Scale Anm2",
self.popupType = IMGUI_POPUP_CENTER_WINDOW,
self.popupSize = {260, 75},
self.isSizeToText = true,
self.isSeparator = true
);
IMGUI_ITEM(IMGUI_SCALE_ANM2_OPTIONS_CHILD,
self.label = "## Scale Anm2 Options Child",
self.size = {IMGUI_SCALE_ANM2.popupSize.x, IMGUI_SCALE_ANM2.popupSize.y - IMGUI_FOOTER_CHILD.size.y},
self.flags = true
);
IMGUI_ITEM(IMGUI_SCALE_ANM2_VALUE,
self.label = "Value",
self.tooltip = "The size and position-related frame properties in the anm2 will be scaled by this value.",
self.value = 1,
self.step = 0.25,
self.stepFast = 1
);
IMGUI_ITEM(IMGUI_SCALE_ANM2_SCALE,
self.label = "Scale",
self.tooltip = "Scale the anm2 with the value specified.",
self.snapshotAction = "Scale Anm2",
self.rowCount = IMGUI_CONFIRM_POPUP_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_RENDER_ANIMATION,
self.label = "&Render Animation",
self.tooltip = "Renders the current animation preview; output options can be customized.",
self.popup = "Render Animation",
self.popupSize = {500, 170},
self.popupType = IMGUI_POPUP_CENTER_WINDOW
);
IMGUI_ITEM(IMGUI_RENDER_ANIMATION_CHILD,
self.label = "## Render Animation Child",
self.size = {IMGUI_RENDER_ANIMATION.popupSize.x, IMGUI_RENDER_ANIMATION.popupSize.y - IMGUI_FOOTER_CHILD.size.y},
self.flags = true
);
IMGUI_ITEM(IMGUI_RENDER_ANIMATION_FOOTER_CHILD,
self.label = "## Render Animation Footer Child",
self.size = {IMGUI_RENDER_ANIMATION.popupSize.x, IMGUI_FOOTER_CHILD.size.y},
self.flags = true
);
IMGUI_ITEM(IMGUI_RENDER_ANIMATION_LOCATION_BROWSE,
self.label = "## Location Browse",
self.tooltip = "Open file explorer to pick rendered animation location.",
self.atlas = ATLAS_FOLDER,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_RENDER_ANIMATION_LOCATION,
self.label = "Location",
self.tooltip = "Select the location of the rendered animation.\nFor PNG images, this should be a directory, otherwise, a filepath.",
self.max = 1024
);
IMGUI_ITEM(IMGUI_RENDER_ANIMATION_FFMPEG_BROWSE,
self.label = "## FFMpeg Browse",
self.tooltip = "Open file explorer to pick the path of FFmpeg",
self.atlas = ATLAS_FOLDER,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_RENDER_ANIMATION_FFMPEG_PATH,
self.label = "FFmpeg Path",
self.tooltip = "Sets the path FFmpeg currently resides in.\nFFmpeg is required for rendering animations.\nDownload it from https://ffmpeg.org/, your package manager, or wherever else.",
self.max = 1024
);
IMGUI_ITEM(IMGUI_RENDER_ANIMATION_OUTPUT,
self.label = "Output",
self.tooltip = "Select the rendered animation output.\nIt can either be one animated image or a sequence of frames.",
self.items = {std::begin(RENDER_TYPE_STRINGS), std::end(RENDER_TYPE_STRINGS)},
self.value = RENDER_PNG
);
IMGUI_ITEM(IMGUI_RENDER_ANIMATION_FORMAT,
self.label = "Format",
self.tooltip = "(PNG images only).\nSet the format of each output frame; i.e., its filename.\nThe format will only take one argument; that being the frame's index.\nFor example, a format like \"{}.png\" will export a frame of index 0 as \"0.png\".",
self.max = UCHAR_MAX
);
IMGUI_ITEM(IMGUI_RENDER_ANIMATION_IS_USE_ANIMATION_BOUNDS,
self.label = "Use Animation Bounds",
self.tooltip = "Instead of using the animation preview's bounds, the rendered animation will use the animation's bounds.\nNOTE: If you're looking to make a transparent animation, set the preview background to be transparent\nand toggle off other drawn things.",
self.value = SETTINGS_RENDER_IS_USE_ANIMATION_BOUNDS_DEFAULT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_RENDER_ANIMATION_SCALE,
self.label = "Scale",
self.tooltip = "Change the scale the animation will be rendered at.",
self.value = SETTINGS_RENDER_SCALE_DEFAULT,
self.size = {125, 0}
);
IMGUI_ITEM(IMGUI_RENDER_ANIMATION_CONFIRM,
self.label = "Render",
self.tooltip = "Render the animation, with the used settings.",
self.popup = "Rendering Animation...",
self.popupType = IMGUI_POPUP_CENTER_WINDOW,
self.popupSize = {300, 60},
self.isSameLine = true,
self.rowCount = IMGUI_CONFIRM_POPUP_ROW_COUNT
);
IMGUI_ITEM(IMGUI_RENDERING_ANIMATION_CHILD,
self.label = "##Rendering Child",
self.size = {400.0f, 65.0f},
self.flags = true
);
IMGUI_ITEM(IMGUI_RENDERING_ANIMATION_INFO, self.label = "Recording frames. Once done, the program may halt\nas FFmpeg renders the animation. Please be patient!");
IMGUI_ITEM(IMGUI_RENDERING_ANIMATION_CANCEL,
self.label = "Cancel",
self.tooltip = "Cancel rendering the animation.",
self.rowCount = 1
);
IMGUI_ITEM(IMGUI_PLAYBACK,
self.label = "&Playback",
self.tooltip = "Opens the playback menu, for configuring playback settings.",
self.popup = "## Playback Popup",
self.popupType = IMGUI_POPUP_BY_ITEM,
self.isSizeToText = true,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_ALWAYS_LOOP,
self.label = "&Always Loop",
self.tooltip = "Sets the animation playback to always loop, regardless of the animation's loop setting.",
self.isSizeToText = true
);
IMGUI_ITEM(IMGUI_CLAMP_PLAYHEAD,
self.label = "&Clamp Playhead",
self.tooltip = "The playhead (draggable icon on timeline) won't be able to exceed the animation length.",
self.isSizeToText = true
);
IMGUI_ITEM(IMGUI_SETTINGS,
self.label = "&Settings",
self.tooltip = "Opens the setting menu, for configuring general program settings.",
self.popup = "## Settings Popup",
self.popupType = IMGUI_POPUP_BY_ITEM,
self.isSizeToText = true
);
IMGUI_ITEM(IMGUI_VSYNC,
self.label = "&Vsync",
self.tooltip = "Toggle vertical sync; synchronizes program framerate with your monitor's refresh rate.",
self.isSizeToText = true,
self.isSeparator = true
);
IMGUI_ITEM(IMGUI_HOTKEYS,
self.label = "&Hotkeys",
self.tooltip = "Change the program's hotkeys.",
self.popup = "Hotkeys",
self.popupSize = {500, 405},
self.isSizeToText = true,
self.isSeparator = true
);
IMGUI_ITEM(IMGUI_HOTKEYS_CHILD,
self.label = "## Hotkeys Child",
self.size = {IMGUI_HOTKEYS.popupSize.x, IMGUI_HOTKEYS.popupSize.y - 35},
self.flags = true
);
#define IMGUI_HOTKEYS_FUNCTION "Function"
#define IMGUI_HOTKEYS_HOTKEY "Hotkey"
IMGUI_ITEM(IMGUI_HOTKEYS_TABLE,
self.label = "## Hotkeys Table",
self.value = 2,
self.flags = ImGuiTableFlags_Borders
);
IMGUI_ITEM(IMGUI_HOTKEYS_OPTIONS_CHILD,
self.label = "## Merge Options Child",
self.size = {IMGUI_HOTKEYS.popupSize.x, 35},
self.flags = true
);
IMGUI_ITEM(IMGUI_HOTKEYS_CONFIRM,
self.label = "Confirm",
self.tooltip = "Use these hotkeys.",
self.rowCount = 1
);
IMGUI_ITEM(IMGUI_DEFAULT_SETTINGS,
self.label = "&Reset to Default Settings",
self.tooltip = "Reset the program's settings to their default state.",
self.isSizeToText = true
);
IMGUI_ITEM(IMGUI_LAYERS,
self.label = "Layers",
self.flags = ImGuiWindowFlags_NoScrollbar |
ImGuiWindowFlags_NoScrollWithMouse
);
IMGUI_ITEM(IMGUI_LAYERS_CHILD, self.label = "## Layers Child", self.flags = true);
IMGUI_ITEM(IMGUI_LAYER,
self.label = "## Layer Item",
self.dragDrop = "## Layer Drag Drop",
self.atlas = ATLAS_LAYER,
self.idOffset = 3000
);
IMGUI_ITEM(IMGUI_LAYER_SPRITESHEET_ID,
self.label = "## Spritesheet ID",
self.tooltip = "Change the spritesheet ID this layer uses.",
self.atlas = ATLAS_SPRITESHEET,
self.size = {50, 0}
);
#define IMGUI_LAYERS_OPTIONS_ROW_COUNT 2
IMGUI_ITEM(IMGUI_LAYER_ADD,
self.label = "Add",
self.tooltip = "Adds a new layer.",
self.snapshotAction = "Add Layer",
self.rowCount = IMGUI_LAYERS_OPTIONS_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_LAYER_REMOVE,
self.label = "Remove",
self.tooltip = "Removes the selected layer.\nThis will remove all layer animations that use this layer from all animations.",
self.snapshotAction = "Remove Layer",
self.chord = ImGuiKey_Delete,
self.focusWindow = IMGUI_LAYERS.label,
self.rowCount = IMGUI_LAYERS_OPTIONS_ROW_COUNT
);
IMGUI_ITEM(IMGUI_NULLS,
self.label = "Nulls",
self.flags = ImGuiWindowFlags_NoScrollbar |
ImGuiWindowFlags_NoScrollWithMouse
);
IMGUI_ITEM(IMGUI_NULLS_CHILD, self.label = "## Nulls Child", self.flags = true);
IMGUI_ITEM(IMGUI_NULL,
self.label = "## Null Item",
self.dragDrop = "## Null Drag Drop",
self.atlas = ATLAS_NULL,
self.idOffset = 4000
);
#define IMGUI_NULLS_OPTIONS_ROW_COUNT 2
IMGUI_ITEM(IMGUI_NULL_ADD,
self.label = "Add",
self.tooltip = "Adds a null layer.",
self.snapshotAction = "Add Null",
self.rowCount = IMGUI_NULLS_OPTIONS_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_NULL_REMOVE,
self.label = "Remove",
self.tooltip = "Removes the selected null.\nThis will remove all null animations that use this null from all animations.",
self.snapshotAction = "Remove Null",
self.chord = ImGuiKey_Delete,
self.focusWindow = IMGUI_NULLS.label,
self.rowCount = IMGUI_NULLS_OPTIONS_ROW_COUNT
);
IMGUI_ITEM(IMGUI_ANIMATIONS,
self.label = "Animations",
self.flags = ImGuiWindowFlags_NoScrollbar |
ImGuiWindowFlags_NoScrollWithMouse
);
IMGUI_ITEM(IMGUI_ANIMATIONS_CHILD, self.label = "## Animations Child", self.flags = true);
IMGUI_ITEM(IMGUI_ANIMATION,
self.label = "## Animation Item",
self.dragDrop = "## Animation Drag Drop",
self.atlas = ATLAS_ANIMATION,
self.idOffset = 2000
);
#define IMGUI_ANIMATIONS_OPTIONS_ROW_COUNT 5
IMGUI_ITEM(IMGUI_ANIMATION_ADD,
self.label = "Add",
self.tooltip = "Adds a new animation.",
self.snapshotAction = "Add Animation",
self.rowCount = IMGUI_ANIMATIONS_OPTIONS_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_ANIMATION_DUPLICATE,
self.label = "Duplicate",
self.tooltip = "Duplicates the selected animation, placing it after.",
self.snapshotAction = "Duplicate Animation",
self.rowCount = IMGUI_ANIMATIONS_OPTIONS_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_ANIMATION_MERGE,
self.label = "Merge",
self.tooltip = "Open the animation merge popup, to merge animations together.",
self.popup = "Merge Animations",
self.popupSize = {300, 400},
self.rowCount = IMGUI_ANIMATIONS_OPTIONS_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_MERGE_ANIMATIONS_CHILD,
self.label = "## Merge Animations",
self.size = {IMGUI_ANIMATION_MERGE.popupSize.x, 250},
self.flags = true
);
IMGUI_ITEM(IMGUI_MERGE_ON_CONFLICT_CHILD,
self.label = "## Merge On Conflict Child",
self.size = {IMGUI_ANIMATION_MERGE.popupSize.x, 75},
self.flags = true
);
IMGUI_ITEM(IMGUI_MERGE_ON_CONFLICT, self.label = "On Conflict");
IMGUI_ITEM(IMGUI_MERGE_APPEND_FRAMES,
self.label = "Append Frames ",
self.tooltip = "On frame conflict, the merged animation will have the selected animations' frames appended.",
self.value = ANM2_MERGE_APPEND,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_MERGE_REPLACE_FRAMES,
self.label = "Replace Frames",
self.tooltip = "On frame conflict, the merged animation will have the latest selected animations' frames.",
self.value = ANM2_MERGE_REPLACE
);
IMGUI_ITEM(IMGUI_MERGE_PREPEND_FRAMES,
self.label = "Prepend Frames",
self.tooltip = "On frame conflict, the merged animation will have the selected animations' frames prepended.",
self.value = ANM2_MERGE_PREPEND,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_MERGE_IGNORE,
self.label = "Ignore ",
self.tooltip = "On frame conflict, the merged animation will ignore the other selected animations' frames.",
self.value = ANM2_MERGE_IGNORE
);
IMGUI_ITEM(IMGUI_MERGE_OPTIONS_CHILD,
self.label = "## Merge Options Child",
self.size = {IMGUI_ANIMATION_MERGE.popupSize.x, 35},
self.flags = true
);
IMGUI_ITEM(IMGUI_MERGE_DELETE_ANIMATIONS_AFTER,
self.label = "Delete Animations After Merging",
self.tooltip = "After merging, the selected animations (besides the original) will be deleted."
);
IMGUI_ITEM(IMGUI_MERGE_CONFIRM,
self.label = "Merge",
self.tooltip = "Merge the selected animations with the options set.",
self.snapshotAction = "Merge Animations",
self.rowCount = IMGUI_CONFIRM_POPUP_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_ANIMATION_REMOVE,
self.label = "Remove",
self.tooltip = "Remove the selected animation.",
self.snapshotAction = "Remove Animation",
self.rowCount = IMGUI_ANIMATIONS_OPTIONS_ROW_COUNT,
self.chord = ImGuiKey_Delete,
self.focusWindow = IMGUI_ANIMATIONS.label,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_ANIMATION_DEFAULT,
self.label = "Default",
self.tooltip = "Set the selected animation as the default one.",
self.snapshotAction = "Default Animation",
self.rowCount = IMGUI_ANIMATIONS_OPTIONS_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_EVENTS,
self.label = "Events",
self.flags = ImGuiWindowFlags_NoScrollbar |
ImGuiWindowFlags_NoScrollWithMouse
);
IMGUI_ITEM(IMGUI_EVENTS_CHILD, self.label = "## Events Child", self.flags = true);
IMGUI_ITEM(IMGUI_EVENT,
self.label = "## Event",
self.atlas = ATLAS_EVENT,
self.idOffset = 1000
);
#define IMGUI_EVENTS_OPTIONS_ROW_COUNT 2
IMGUI_ITEM(IMGUI_EVENTS_ADD,
self.label = "Add",
self.tooltip = "Adds a new event.",
self.snapshotAction = "Add Event",
self.rowCount = IMGUI_EVENTS_OPTIONS_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_EVENTS_REMOVE_UNUSED,
self.label = "Remove Unused",
self.tooltip = "Removes all unused events (i.e., not being used in any triggers in any animation).",
self.snapshotAction = "Remove Unused Events",
self.rowCount = IMGUI_EVENTS_OPTIONS_ROW_COUNT
);
IMGUI_ITEM(IMGUI_SPRITESHEETS,
self.label = "Spritesheets",
self.flags = ImGuiWindowFlags_NoScrollbar |
ImGuiWindowFlags_NoScrollWithMouse
);
IMGUI_ITEM(IMGUI_SPRITESHEETS_CHILD, self.label = "## Spritesheets Child", self.flags = true);
IMGUI_ITEM(IMGUI_SPRITESHEET_CHILD,
self.label = "## Spritesheet Child",
self.rowCount = 1,
self.size = {0, IMGUI_SPRITESHEET_PREVIEW_SIZE.y + 40},
self.flags = true
);
IMGUI_ITEM(IMGUI_SPRITESHEET_SELECTED, self.label = "## Spritesheet Selected", self.isSameLine = true);
IMGUI_ITEM(IMGUI_SPRITESHEET,
self.label = "## Spritesheet",
self.dragDrop = "## Spritesheet Drag Drop",
self.atlas = ATLAS_SPRITESHEET,
self.isSizeToText = true
);
IMGUI_ITEM(IMGUI_SPRITESHEETS_FOOTER_CHILD,
self.label = "## Spritesheets Footer Child",
self.size = {0, 60},
self.flags = true
);
#define IMGUI_SPRITESHEETS_OPTIONS_FIRST_ROW_COUNT 4
#define IMGUI_SPRITESHEETS_OPTIONS_SECOND_ROW_COUNT 3
IMGUI_ITEM(IMGUI_SPRITESHEET_ADD,
self.label = "Add",
self.tooltip = "Select a .png image to add as a spritesheet.",
self.rowCount = IMGUI_SPRITESHEETS_OPTIONS_FIRST_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_SPRITESHEETS_RELOAD,
self.label = "Reload",
self.tooltip = "Reload the selected spritesheet(s).",
self.snapshotAction = "Reload Spritesheet(s)",
self.rowCount = IMGUI_SPRITESHEETS_OPTIONS_FIRST_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_SPRITESHEETS_REPLACE,
self.label = "Replace",
self.tooltip = "Replace the highlighted spritesheet with another.",
self.rowCount = IMGUI_SPRITESHEETS_OPTIONS_FIRST_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_SPRITESHEETS_REMOVE_UNUSED,
self.label = "Remove Unused",
self.tooltip = "Remove all unused spritesheets in the anm2 (i.e., no layer in any animation uses the spritesheet).",
self.rowCount = IMGUI_SPRITESHEETS_OPTIONS_FIRST_ROW_COUNT
);
IMGUI_ITEM(IMGUI_SPRITESHEETS_SELECT_ALL,
self.label = "Select All",
self.tooltip = "Select all spritesheets.",
self.rowCount = IMGUI_SPRITESHEETS_OPTIONS_SECOND_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_SPRITESHEETS_SELECT_NONE,
self.label = "Select None",
self.tooltip = "Unselect all spritesheets.",
self.rowCount = IMGUI_SPRITESHEETS_OPTIONS_SECOND_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_SPRITESHEET_SAVE,
self.label = "Save",
self.tooltip = "Save the selected spritesheets to their original locations.",
self.rowCount = IMGUI_SPRITESHEETS_OPTIONS_SECOND_ROW_COUNT
);
const ImVec2 IMGUI_CANVAS_CHILD_SIZE = {230, 85};
IMGUI_ITEM(IMGUI_CANVAS_GRID_CHILD,
self.label = "## Canvas Grid Child",
self.size = IMGUI_CANVAS_CHILD_SIZE,
self.flags = true,
self.windowFlags = ImGuiWindowFlags_NoScrollbar |
ImGuiWindowFlags_NoScrollWithMouse
);
IMGUI_ITEM(IMGUI_CANVAS_GRID,
self.label = "Grid",
self.tooltip = "Toggles the visiblity of the canvas' grid."
);
IMGUI_ITEM(IMGUI_CANVAS_GRID_SNAP,
self.label = "Snap",
self.tooltip = "Using the crop tool will snap the points to the nearest grid point."
);
IMGUI_ITEM(IMGUI_CANVAS_GRID_COLOR,
self.label = "Color",
self.tooltip = "Change the color of the canvas' grid.",
self.flags = ImGuiColorEditFlags_NoInputs
);
IMGUI_ITEM(IMGUI_CANVAS_GRID_SIZE,
self.label = "Size",
self.tooltip = "Change the size of the canvas' grid.",
self.min = CANVAS_GRID_MIN,
self.max = CANVAS_GRID_MAX,
self.value = CANVAS_GRID_DEFAULT
);
IMGUI_ITEM(IMGUI_CANVAS_GRID_OFFSET,
self.label = "Offset",
self.tooltip = "Change the offset of the canvas' grid, in pixels."
);
IMGUI_ITEM(IMGUI_CANVAS_VIEW_CHILD,
self.label = "## View Child",
self.size = IMGUI_CANVAS_CHILD_SIZE,
self.flags = true,
self.windowFlags = ImGuiWindowFlags_NoScrollbar |
ImGuiWindowFlags_NoScrollWithMouse
);
IMGUI_ITEM(IMGUI_CANVAS_ZOOM,
self.label = "Zoom",
self.tooltip = "Change the zoom of the canvas.",
self.min = CANVAS_ZOOM_MIN,
self.max = CANVAS_ZOOM_MAX,
self.speed = 1.0f,
self.value = CANVAS_ZOOM_DEFAULT
);
IMGUI_ITEM(IMGUI_CANVAS_VISUAL_CHILD,
self.label = "## Animation Preview Visual Child",
self.size = IMGUI_CANVAS_CHILD_SIZE,
self.flags = true,
self.windowFlags = ImGuiWindowFlags_NoScrollbar |
ImGuiWindowFlags_NoScrollWithMouse
);
IMGUI_ITEM(IMGUI_CANVAS_BACKGROUND_COLOR,
self.label = "Background Color",
self.tooltip = "Change the background color of the canvas.",
self.flags = ImGuiColorEditFlags_NoInputs
);
IMGUI_ITEM(IMGUI_CANVAS_ANIMATION_OVERLAY,
self.label = "Overlay",
self.tooltip = "Choose an animation to overlay over the previewed animation, for reference."
);
IMGUI_ITEM(IMGUI_CANVAS_ANIMATION_OVERLAY_TRANSPARENCY,
self.label = "Alpha",
self.tooltip = "Set the transparency of the animation overlay.",
self.value = SETTINGS_PREVIEW_OVERLAY_TRANSPARENCY_DEFAULT,
self.max = UCHAR_MAX
);
IMGUI_ITEM(IMGUI_CANVAS_HELPER_CHILD,
self.label = "## Animation Preview Helper Child",
self.size = IMGUI_CANVAS_CHILD_SIZE,
self.flags = true,
self.windowFlags = ImGuiWindowFlags_NoScrollbar |
ImGuiWindowFlags_NoScrollWithMouse
);
IMGUI_ITEM(IMGUI_CANVAS_AXES,
self.label = "Axes",
self.tooltip = "Toggle the display of the X/Y axes."
);
IMGUI_ITEM(IMGUI_CANVAS_AXES_COLOR,
self.label = "Color",
self.tooltip = "Change the color of the axes.",
self.flags = ImGuiColorEditFlags_NoInputs
);
IMGUI_ITEM(IMGUI_CANVAS_ROOT_TRANSFORM,
self.label = "Root Transform",
self.tooltip = "Toggles the root frames's attributes transforming the other items in an animation.",
self.value = SETTINGS_PREVIEW_IS_ROOT_TRANSFORM_DEFAULT
);
IMGUI_ITEM(IMGUI_CANVAS_TRIGGERS,
self.label = "Triggers",
self.tooltip = "Toggles activated triggers drawing their event name.",
self.value = SETTINGS_PREVIEW_IS_TRIGGERS_DEFAULT
);
IMGUI_ITEM(IMGUI_CANVAS_PIVOTS,
self.label = "Pivots",
self.tooltip = "Toggles drawing each layer's pivot.",
self.value = SETTINGS_PREVIEW_IS_PIVOTS_DEFAULT
);
IMGUI_ITEM(IMGUI_CANVAS_ICONS,
self.label = "Icons",
self.tooltip = "Toggles drawing the the colored root/null icons.",
self.value = SETTINGS_PREVIEW_IS_ICONS_DEFAULT
);
IMGUI_ITEM(IMGUI_CANVAS_ALT_ICONS,
self.label = "Alt Icons",
self.tooltip = "Toggles the use of alternate icons for the targets (the colored root/null icons).",
self.value = SETTINGS_PREVIEW_IS_ALT_ICONS_DEFAULT
);
IMGUI_ITEM(IMGUI_CANVAS_BORDER,
self.label = "Border",
self.tooltip = "Toggles the appearance of a border around the items.",
self.value = SETTINGS_PREVIEW_IS_BORDER_DEFAULT
);
IMGUI_ITEM(IMGUI_ANIMATION_PREVIEW,
self.label = "Animation Preview",
self.flags = ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoScrollWithMouse
);
#define IMGUI_ANIMATION_PREVIEW_VIEW_ROW_COUNT 2
IMGUI_ITEM(IMGUI_ANIMATION_PREVIEW_CENTER_VIEW,
self.label = "Center View",
self.tooltip = "Centers the current view on the animation preview.",
self.hotkey = HOTKEY_CENTER_VIEW,
self.focusWindow = IMGUI_ANIMATION_PREVIEW.label,
self.rowCount = IMGUI_ANIMATION_PREVIEW_VIEW_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_ANIMATION_PREVIEW_FIT,
self.label = "Fit",
self.tooltip = "Adjust the view/pan based on the size of the animation, to fit the canvas' size.",
self.hotkey = HOTKEY_FIT,
self.focusWindow = IMGUI_ANIMATION_PREVIEW.label,
self.rowCount = IMGUI_ANIMATION_PREVIEW_VIEW_ROW_COUNT
);
IMGUI_ITEM(IMGUI_SPRITESHEET_EDITOR,
self.label = "Spritesheet Editor",
self.flags = ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoScrollWithMouse
);
#define IMGUI_SPRITESHEET_EDITOR_VIEW_ROW_COUNT 2
IMGUI_ITEM(IMGUI_SPRITESHEET_EDITOR_CENTER_VIEW,
self.label = "Center View",
self.tooltip = "Centers the current view on the spritesheet editor.",
self.hotkey = HOTKEY_CENTER_VIEW,
self.focusWindow = IMGUI_SPRITESHEET_EDITOR.label,
self.rowCount = IMGUI_SPRITESHEET_EDITOR_VIEW_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_SPRITESHEET_EDITOR_FIT,
self.label = "Fit",
self.tooltip = "Adjust the view/pan based on the size of the spritesheet, to fit the canvas' size.",
self.hotkey = HOTKEY_FIT,
self.focusWindow = IMGUI_SPRITESHEET_EDITOR.label,
self.rowCount = IMGUI_SPRITESHEET_EDITOR_VIEW_ROW_COUNT
);
IMGUI_ITEM(IMGUI_FRAME_PROPERTIES, self.label = "Frame Properties");
IMGUI_ITEM(IMGUI_FRAME_PROPERTIES_POSITION,
self.label = "Position",
self.tooltip = "Change the position of the selected frame.",
self.snapshotAction = "Frame Position",
self.isUseItemActivated = true
);
IMGUI_ITEM(IMGUI_FRAME_PROPERTIES_CROP,
self.label = "Crop",
self.tooltip = "Change the crop position of the selected frame.",
self.snapshotAction = "Frame Crop",
self.isUseItemActivated = true
);
IMGUI_ITEM(IMGUI_FRAME_PROPERTIES_SIZE,
self.label = "Size",
self.tooltip = "Change the size of the crop of the selected frame.",
self.snapshotAction = "Frame Size",
self.isUseItemActivated = true
);
IMGUI_ITEM(IMGUI_FRAME_PROPERTIES_PIVOT,
self.label = "Pivot",
self.tooltip = "Change the pivot of the selected frame.",
self.snapshotAction = "Frame Pivot",
self.isUseItemActivated = true
);
IMGUI_ITEM(IMGUI_FRAME_PROPERTIES_SCALE,
self.label = "Scale",
self.tooltip = "Change the scale of the selected frame.",
self.snapshotAction = "Frame Scale",
self.isUseItemActivated = true
);
IMGUI_ITEM(IMGUI_FRAME_PROPERTIES_ROTATION,
self.label = "Rotation",
self.tooltip = "Change the rotation of the selected frame.",
self.snapshotAction = "Frame Rotation",
self.isUseItemActivated = true
);
IMGUI_ITEM(IMGUI_FRAME_PROPERTIES_DELAY,
self.label = "Duration",
self.tooltip = "Change the duration of the selected frame.",
self.snapshotAction = "Frame Duration",
self.isUseItemActivated = true,
self.min = ANM2_FRAME_NUM_MIN,
self.max = ANM2_FRAME_NUM_MAX,
self.value = ANM2_FRAME_NUM_MIN
);
IMGUI_ITEM(IMGUI_FRAME_PROPERTIES_TINT,
self.label = "Tint",
self.tooltip = "Change the tint of the selected frame.",
self.snapshotAction = "Frame Tint",
self.isUseItemActivated = true,
self.value = 1
);
IMGUI_ITEM(IMGUI_FRAME_PROPERTIES_COLOR_OFFSET,
self.label = "Color Offset",
self.tooltip = "Change the color offset of the selected frame.",
self.snapshotAction = "Frame Color Offset",
self.isUseItemActivated = true,
self.value = 0
);
#define IMGUI_FRAME_PROPERTIES_FLIP_ROW_COUNT 2
IMGUI_ITEM(IMGUI_FRAME_PROPERTIES_FLIP_X,
self.label = "Flip X",
self.tooltip = "Change the sign of the X scale, to cheat flipping the layer horizontally.\n(Anm2 doesn't support flipping directly.)",
self.snapshotAction = "Frame Flip X",
self.rowCount = IMGUI_FRAME_PROPERTIES_FLIP_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_FRAME_PROPERTIES_FLIP_Y,
self.label = "Flip Y",
self.tooltip = "Change the sign of the Y scale, to cheat flipping the layer vertically.\n(Anm2 doesn't support flipping directly.)",
self.snapshotAction = "Frame Flip Y",
self.rowCount = IMGUI_FRAME_PROPERTIES_FLIP_ROW_COUNT
);
IMGUI_ITEM(IMGUI_FRAME_PROPERTIES_VISIBLE,
self.label = "Visible",
self.tooltip = "Toggles the visibility of the selected frame.",
self.snapshotAction = "Frame Visibility",
self.isSameLine = true,
self.value = true
);
IMGUI_ITEM(IMGUI_FRAME_PROPERTIES_INTERPOLATED,
self.label = "Interpolation",
self.tooltip = "Toggles the interpolation of the selected frame.",
self.snapshotAction = "Frame Interpolation",
self.isSameLine = true,
self.value = true
);
IMGUI_ITEM(IMGUI_FRAME_PROPERTIES_ROUND,
self.label = "Round",
self.tooltip = "Values will be rounded to the nearest integer.",
self.value = SETTINGS_PROPERTIES_IS_ROUND_DEFAULT
);
IMGUI_ITEM(IMGUI_FRAME_PROPERTIES_EVENT,
self.label = "Event",
self.tooltip = "Change the event the trigger uses.",
self.snapshotAction = "Trigger Event"
);
IMGUI_ITEM(IMGUI_FRAME_PROPERTIES_AT_FRAME,
self.label = "At Frame",
self.tooltip = "Change the frame where the trigger occurs.",
self.snapshotAction = "Trigger At Frame"
);
IMGUI_ITEM(IMGUI_TOOLS, self.label = "Tools");
IMGUI_ITEM(IMGUI_TOOL_PAN,
self.label = "## Pan",
self.tooltip = "Use the pan tool.\nWill shift the view as the cursor is dragged.\nYou can also use the middle mouse button to pan at any time.",
self.function = imgui_tool_pan_set,
self.hotkey = HOTKEY_PAN,
self.atlas = ATLAS_PAN
);
IMGUI_ITEM(IMGUI_TOOL_MOVE,
self.label = "## Move",
self.tooltip = "Use the move tool.\nWhen in animation preview, will move the position of the frame.\nWhen in spritesheet editor, will move the pivot instead.\nUse mouse or directional keys to change the value.",
self.function = imgui_tool_move_set,
self.hotkey = HOTKEY_MOVE,
self.atlas = ATLAS_MOVE
);
IMGUI_ITEM(IMGUI_TOOL_ROTATE,
self.label = "## Rotate",
self.tooltip = "Use the rotate tool.\nWill rotate the selected item as the cursor is dragged, or directional keys are pressed.\n(Animation Preview only.)",
self.function = imgui_tool_rotate_set,
self.hotkey = HOTKEY_ROTATE,
self.atlas = ATLAS_ROTATE
);
IMGUI_ITEM(IMGUI_TOOL_SCALE,
self.label = "## Scale",
self.tooltip = "Use the scale tool.\nWill scale the selected item as the cursor is dragged, or directional keys are pressed.\n(Animation Preview only.)",
self.function = imgui_tool_scale_set,
self.hotkey = HOTKEY_SCALE,
self.atlas = ATLAS_SCALE
);
IMGUI_ITEM(IMGUI_TOOL_CROP,
self.label = "## Crop",
self.tooltip = "Use the crop tool.\nWill produce a crop rectangle based on how the cursor is dragged.\nAlternatively, you can use the arrow keys and Ctrl/Shift to move the size/position, respectively.\n(Spritesheet Editor only.)",
self.function = imgui_tool_crop_set,
self.hotkey = HOTKEY_CROP,
self.atlas = ATLAS_CROP
);
IMGUI_ITEM(IMGUI_TOOL_DRAW,
self.label = "## Draw",
self.tooltip = "Draws pixels onto the selected spritesheet, with the current color.\n(Spritesheet Editor only.)",
self.function = imgui_tool_draw_set,
self.hotkey = HOTKEY_DRAW,
self.atlas = ATLAS_DRAW
);
IMGUI_ITEM(IMGUI_TOOL_ERASE,
self.label = "## Erase",
self.tooltip = "Erases pixels from the selected spritesheet.\n(Spritesheet Editor only.)",
self.function = imgui_tool_erase_set,
self.hotkey = HOTKEY_ERASE,
self.atlas = ATLAS_ERASE
);
IMGUI_ITEM(IMGUI_TOOL_COLOR_PICKER,
self.label = "## Color Picker",
self.tooltip = "Selects a color from the canvas, to be used for drawing.\n(Spritesheet Editor only).",
self.function = imgui_tool_color_picker_set,
self.hotkey = HOTKEY_COLOR_PICKER,
self.atlas = ATLAS_COLOR_PICKER
);
IMGUI_ITEM(IMGUI_TOOL_UNDO,
self.label = "## Undo",
self.tooltip = "Undo the last action.",
self.function = imgui_undo,
self.hotkey = HOTKEY_UNDO,
self.atlas = ATLAS_UNDO
);
IMGUI_ITEM(IMGUI_TOOL_REDO,
self.label = "## Redo",
self.tooltip = "Redo the last action.",
self.function = imgui_redo,
self.hotkey = HOTKEY_REDO,
self.atlas = ATLAS_REDO
);
IMGUI_ITEM(IMGUI_TOOL_COLOR,
self.label = "## Color",
self.tooltip = "Set the color, to be used by the draw tool.",
self.flags = ImGuiColorEditFlags_NoInputs
);
const inline ImguiItem* IMGUI_TOOL_ITEMS[TOOL_COUNT] =
{
&IMGUI_TOOL_PAN,
&IMGUI_TOOL_MOVE,
&IMGUI_TOOL_ROTATE,
&IMGUI_TOOL_SCALE,
&IMGUI_TOOL_CROP,
&IMGUI_TOOL_DRAW,
&IMGUI_TOOL_ERASE,
&IMGUI_TOOL_COLOR_PICKER,
&IMGUI_TOOL_UNDO,
&IMGUI_TOOL_REDO,
&IMGUI_TOOL_COLOR
};
IMGUI_ITEM(IMGUI_COLOR_PICKER_BUTTON, self.label = "## Color Picker Button");
IMGUI_ITEM(IMGUI_TIMELINE,
self.label = "Timeline",
self.flags = ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoScrollWithMouse
);
IMGUI_ITEM(IMGUI_TIMELINE_CHILD,
self.label = "## Timeline Child",
self.flags = true
);
IMGUI_ITEM(IMGUI_TIMELINE_HEADER_CHILD,
self.label = "## Timeline Header Child",
self.size = {0, IMGUI_TIMELINE_FRAME_SIZE.y},
self.windowFlags = ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoScrollWithMouse
);
IMGUI_ITEM(IMGUI_PLAYHEAD,
self.label = "## Playhead",
self.flags = ImGuiWindowFlags_NoTitleBar |
ImGuiWindowFlags_NoResize |
ImGuiWindowFlags_NoMove |
ImGuiWindowFlags_NoBackground |
ImGuiWindowFlags_NoInputs
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEMS_CHILD,
self.label = "## Timeline Items",
self.size = {IMGUI_TIMELINE_ITEM_SIZE.x, 0},
self.windowFlags = ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoScrollWithMouse
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_CHILD,
self.label = "## Timeline Item Child",
self.size = IMGUI_TIMELINE_ITEM_SIZE,
self.flags = true,
self.windowFlags = ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoScrollWithMouse
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_ROOT_CHILD,
self.label = "## Root Item Child",
self.color = {{0.045f, 0.08f, 0.11f, 1.0f}},
self.size = IMGUI_TIMELINE_ITEM_SIZE,
self.flags = true,
self.windowFlags = ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoScrollWithMouse
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_LAYER_CHILD,
self.label = "## Layer Item Child",
self.color = {{0.0875f, 0.05f, 0.015f, 1.0f}},
self.size = IMGUI_TIMELINE_ITEM_SIZE,
self.flags = true,
self.windowFlags = ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoScrollWithMouse
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_NULL_CHILD,
self.label = "## Null Item Child",
self.color = {{0.055f, 0.10f, 0.055f, 1.0f}},
self.size = IMGUI_TIMELINE_ITEM_SIZE,
self.flags = true,
self.windowFlags = ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoScrollWithMouse
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_TRIGGERS_CHILD,
self.label = "## Triggers Item Child",
self.color = {{0.10f, 0.0375f, 0.07f, 1.0f}},
self.size = IMGUI_TIMELINE_ITEM_SIZE,
self.flags = true,
self.windowFlags = ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoScrollWithMouse
);
const inline ImguiItem* IMGUI_TIMELINE_ITEM_CHILDS[ANM2_COUNT]
{
&IMGUI_TIMELINE_ITEM_CHILD,
&IMGUI_TIMELINE_ITEM_ROOT_CHILD,
&IMGUI_TIMELINE_ITEM_LAYER_CHILD,
&IMGUI_TIMELINE_ITEM_NULL_CHILD,
&IMGUI_TIMELINE_ITEM_TRIGGERS_CHILD
};
#define IMGUI_POPUP_ITEM_PROPERTIES "Item Properties"
#define IMGUI_POPUP_ITEM_PROPERTIES_TYPE IMGUI_POPUP_CENTER_WINDOW
const ImVec2 IMGUI_POPUP_ITEM_PROPERTIES_SIZE = {300, 350};
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_PROPERTIES_TYPE_CHILD,
self.label = "## Item Properties Type Child",
self.size = {IMGUI_POPUP_ITEM_PROPERTIES_SIZE.x, 35},
self.flags = true
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_PROPERTIES_LAYER,
self.label = "Layer",
self.tooltip = "The item will be a layer item.\nA layer item is a primary graphical item, using a spritesheet.",
self.isSizeToText = true,
self.value = ANM2_LAYER,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_PROPERTIES_NULL,
self.label = "Null",
self.tooltip = "The item will be a null item.\nA null item is an invisible item, often accessed by a game engine.",
self.isSizeToText = true,
self.value = ANM2_NULL
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_PROPERTIES_ITEMS_CHILD,
self.label = "## Item Properties Items",
self.size = {IMGUI_POPUP_ITEM_PROPERTIES_SIZE.x, 250},
self.flags = true
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_PROPERTIES_OPTIONS_CHILD,
self.label = "## Item Properties Options Child",
self.size = {IMGUI_POPUP_ITEM_PROPERTIES_SIZE.x, 35},
self.flags = true
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_PROPERTIES_CONFIRM,
self.label = "Confirm",
self.tooltip = "Set the timeline item's properties.",
self.snapshotAction = "Timeline Item Change",
self.rowCount = IMGUI_CONFIRM_POPUP_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_SELECTABLE,
self.label = "## Selectable",
self.size = IMGUI_TIMELINE_ITEM_SELECTABLE_SIZE
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_ROOT_SELECTABLE,
self.label = "Root",
self.tooltip = "The root item of an animation.\nChanging its properties will transform the rest of the animation.",
self.atlas = ATLAS_ROOT,
self.size = IMGUI_TIMELINE_ITEM_SELECTABLE_SIZE
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_LAYER_SELECTABLE,
self.label = "## Layer Selectable",
self.tooltip = "A layer item.\nA graphical item within the animation.",
self.dragDrop = "## Layer Drag Drop",
self.popup = IMGUI_POPUP_ITEM_PROPERTIES,
self.popupType = IMGUI_POPUP_ITEM_PROPERTIES_TYPE,
self.atlas = ATLAS_LAYER,
self.size = IMGUI_TIMELINE_ITEM_SELECTABLE_SIZE
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_NULL_SELECTABLE,
self.label = "## Null Selectable",
self.tooltip = "A null item.\nAn invisible item within the animation that is accessible via a game engine.",
self.dragDrop = "## Null Drag Drop",
self.popup = IMGUI_POPUP_ITEM_PROPERTIES,
self.popupType = IMGUI_POPUP_ITEM_PROPERTIES_TYPE,
self.atlas = ATLAS_NULL,
self.size = IMGUI_TIMELINE_ITEM_SELECTABLE_SIZE
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_TRIGGERS_SELECTABLE,
self.label = "Triggers",
self.tooltip = "The animation's triggers.\nWill fire based on an event.",
self.atlas = ATLAS_TRIGGERS,
self.size = IMGUI_TIMELINE_ITEM_SELECTABLE_SIZE
);
const inline ImguiItem* IMGUI_TIMELINE_ITEM_SELECTABLES[ANM2_COUNT]
{
&IMGUI_TIMELINE_ITEM_SELECTABLE,
&IMGUI_TIMELINE_ITEM_ROOT_SELECTABLE,
&IMGUI_TIMELINE_ITEM_LAYER_SELECTABLE,
&IMGUI_TIMELINE_ITEM_NULL_SELECTABLE,
&IMGUI_TIMELINE_ITEM_TRIGGERS_SELECTABLE
};
IMGUI_ITEM(IMGUI_TIMELINE_SHOW_UNUSED,
self.label = "## Show Unused",
self.tooltip = "Layers/nulls without any frames will be hidden.",
self.snapshotAction = "Hide Unused",
self.atlas = ATLAS_SHOW_UNUSED
);
IMGUI_ITEM(IMGUI_TIMELINE_HIDE_UNUSED,
self.label = "## Hide Unused",
self.tooltip = "Layers/nulls without any frames will be shown.",
self.snapshotAction = "Show Unused",
self.atlas = ATLAS_HIDE_UNUSED
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_VISIBLE,
self.label = "## Visible",
self.tooltip = "The item is visible.\nPress to set to invisible.",
self.snapshotAction = "Item Invisible",
self.atlas = ATLAS_VISIBLE
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_INVISIBLE,
self.label = "## Invisible",
self.tooltip = "The item is invisible.\nPress to set to visible.",
self.snapshotAction = "Item Visible",
self.atlas = ATLAS_INVISIBLE
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_SHOW_RECT,
self.label = "## Show Rect",
self.tooltip = "The rect is shown.\nPress to hide rect.",
self.snapshotAction = "Hide Rect",
self.atlas = ATLAS_SHOW_RECT
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_HIDE_RECT,
self.label = "## Hide Rect",
self.tooltip = "The rect is hidden.\nPress to show rect.",
self.snapshotAction = "Show Rect",
self.atlas = ATLAS_HIDE_RECT
);
IMGUI_ITEM(IMGUI_TIMELINE_FRAMES_CHILD,
self.label = "## Timeline Frames Child",
self.windowFlags = ImGuiWindowFlags_NoScrollWithMouse | ImGuiWindowFlags_HorizontalScrollbar
);
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_FRAMES_CHILD,
self.label = "## Timeline Item Frames Child",
self.size = {0, IMGUI_TIMELINE_FRAME_SIZE.y}
);
IMGUI_ITEM(IMGUI_TIMELINE_FRAME, self.label = "## Frame");
#define IMGUI_TIMELINE_FRAME_BORDER 5
static const vec4 IMGUI_FRAME_BORDER_COLOR = {1.0f, 1.0f, 1.0f, 0.25f};
IMGUI_ITEM(IMGUI_TIMELINE_ROOT_FRAME,
self.label = "## Root Frame",
self.snapshotAction = "Root Frame",
self.color = {{0.14f, 0.27f, 0.39f, 1.0f}, {0.28f, 0.54f, 0.78f, 1.0f}, {0.36f, 0.70f, 0.95f, 1.0f}, IMGUI_FRAME_BORDER_COLOR},
self.size = IMGUI_TIMELINE_FRAME_SIZE,
self.atlasOffset = IMGUI_TIMELINE_FRAME_ATLAS_OFFSET,
self.border = IMGUI_FRAME_BORDER
);
IMGUI_ITEM(IMGUI_TIMELINE_LAYER_FRAME,
self.label = "## Layer Frame",
self.dragDrop = "## Layer Frame Drag Drop",
self.snapshotAction = "Layer Frame",
self.color = {{0.45f, 0.18f, 0.07f, 1.0f}, {0.78f, 0.32f, 0.12f, 1.0f}, {0.95f, 0.40f, 0.15f, 1.0f}, IMGUI_FRAME_BORDER_COLOR},
self.size = IMGUI_TIMELINE_FRAME_SIZE,
self.atlasOffset = IMGUI_TIMELINE_FRAME_ATLAS_OFFSET,
self.border = IMGUI_FRAME_BORDER
);
IMGUI_ITEM(IMGUI_TIMELINE_NULL_FRAME,
self.label = "## Null Frame",
self.dragDrop = "## Null Frame Drag Drop",
self.snapshotAction = "Null Frame",
self.color = {{0.17f, 0.33f, 0.17f, 1.0f}, {0.34f, 0.68f, 0.34f, 1.0f}, {0.44f, 0.88f, 0.44f, 1.0f}, IMGUI_FRAME_BORDER_COLOR},
self.size = IMGUI_TIMELINE_FRAME_SIZE,
self.atlasOffset = IMGUI_TIMELINE_FRAME_ATLAS_OFFSET,
self.border = IMGUI_FRAME_BORDER
);
IMGUI_ITEM(IMGUI_TIMELINE_TRIGGERS_FRAME,
self.label = "## Triggers Frame",
self.snapshotAction = "Trigger",
self.color = {{0.36f, 0.14f, 0.24f, 1.0f}, {0.72f, 0.28f, 0.48f, 1.0f}, {0.92f, 0.36f, 0.60f, 1.0f}, IMGUI_FRAME_BORDER_COLOR},
self.size = IMGUI_TIMELINE_FRAME_SIZE,
self.atlasOffset = IMGUI_TIMELINE_FRAME_ATLAS_OFFSET,
self.border = IMGUI_FRAME_BORDER
);
const inline ImguiItem* IMGUI_TIMELINE_FRAMES[ANM2_COUNT]
{
&IMGUI_TIMELINE_FRAME,
&IMGUI_TIMELINE_ROOT_FRAME,
&IMGUI_TIMELINE_LAYER_FRAME,
&IMGUI_TIMELINE_NULL_FRAME,
&IMGUI_TIMELINE_TRIGGERS_FRAME
};
IMGUI_ITEM(IMGUI_TIMELINE_ITEM_FOOTER_CHILD,
self.label = "## Item Footer Child",
self.size = {IMGUI_TIMELINE_ITEM_CHILD.size.x, IMGUI_FOOTER_CHILD.size.y},
self.flags = true,
self.windowFlags = ImGuiWindowFlags_NoScrollbar |
ImGuiWindowFlags_NoScrollWithMouse
);
IMGUI_ITEM(IMGUI_TIMELINE_OPTIONS_FOOTER_CHILD,
self.label = "## Options Footer Child",
self.size = {0, IMGUI_FOOTER_CHILD.size.y},
self.flags = true,
self.windowFlags = ImGuiWindowFlags_NoScrollbar |
ImGuiWindowFlags_NoScrollWithMouse
);
#define IMGUI_TIMELINE_FOOTER_ITEM_CHILD_ITEM_COUNT 2
IMGUI_ITEM(IMGUI_TIMELINE_ADD_ITEM,
self.label = "Add",
self.tooltip = "Adds an item (layer or null) to the animation.\nMake sure to add a Layer/Null first in the Layers or Nulls windows.",
self.popup = "Add Item",
self.popupType = IMGUI_POPUP_ITEM_PROPERTIES_TYPE,
self.popupSize = {300, 350},
self.rowCount = IMGUI_TIMELINE_FOOTER_ITEM_CHILD_ITEM_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_TIMELINE_REMOVE_ITEM,
self.label = "Remove",
self.tooltip = "Removes the selected item (layer or null) from the animation.",
self.snapshotAction = "Remove Item",
self.chord = ImGuiKey_Delete,
self.focusWindow = IMGUI_TIMELINE_ITEMS_CHILD.label,
self.rowCount = IMGUI_TIMELINE_FOOTER_ITEM_CHILD_ITEM_COUNT
);
#define IMGUI_TIMELINE_OPTIONS_ROW_COUNT 10
IMGUI_ITEM(IMGUI_PLAY,
self.label = "|> Play",
self.tooltip = "Play the current animation, if paused.",
self.focusWindow = IMGUI_TIMELINE.label,
self.hotkey = HOTKEY_PLAY_PAUSE,
self.rowCount = IMGUI_TIMELINE_OPTIONS_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_PAUSE,
self.label = "|| Pause",
self.tooltip = "Pause the current animation, if playing.",
self.focusWindow = IMGUI_TIMELINE.label,
self.hotkey = HOTKEY_PLAY_PAUSE,
self.rowCount = IMGUI_TIMELINE_OPTIONS_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_ADD_FRAME,
self.label = "+ Insert Frame",
self.tooltip = "Inserts a frame in the selected animation item, based on the preview time.",
self.snapshotAction = "Insert Frame",
self.rowCount = IMGUI_TIMELINE_OPTIONS_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_REMOVE_FRAME,
self.label = "- Delete Frame",
self.tooltip = "Removes the selected frame from the selected animation item.",
self.snapshotAction = "Delete Frame",
self.focusWindow = IMGUI_TIMELINE.label,
self.chord = ImGuiKey_Delete,
self.rowCount = IMGUI_TIMELINE_OPTIONS_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_BAKE,
self.label = "Bake",
self.tooltip = "Opens the bake popup menu, if a frame is selected.\nBaking a frame takes the currently interpolated values at the time between it and the next frame and separates them based on the interval.",
self.popup = "Bake Frames",
self.rowCount = IMGUI_TIMELINE_OPTIONS_ROW_COUNT,
self.popupSize = {260, 145},
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_BAKE_CHILD,
self.label = "## Bake Child",
self.flags = true
);
IMGUI_ITEM(IMGUI_BAKE_INTERVAL,
self.label = "Interval",
self.tooltip = "Sets the delay of the baked frames the selected frame will be separated out into.",
self.min = ANM2_FRAME_DELAY_MIN,
self.value = ANM2_FRAME_DELAY_MIN
);
IMGUI_ITEM(IMGUI_BAKE_ROUND_SCALE,
self.label = "Round Scale",
self.tooltip = "The scale of the baked frames will be rounded to the nearest integer.",
self.value = true
);
IMGUI_ITEM(IMGUI_BAKE_ROUND_ROTATION,
self.label = "Round Rotation",
self.tooltip = "The rotation of the baked frames will be rounded to the nearest integer.",
self.value = true,
self.isSeparator = true
);
IMGUI_ITEM(IMGUI_BAKE_CONFIRM,
self.label = "Bake",
self.tooltip = "Bake the selected frame with the options selected.",
self.snapshotAction = "Bake Frames",
self.rowCount = IMGUI_CONFIRM_POPUP_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_FIT_ANIMATION_LENGTH,
self.label = "Fit Animation Length",
self.tooltip = "Sets the animation's length to the latest frame.",
self.snapshotAction = "Fit Animation Length",
self.rowCount = IMGUI_TIMELINE_OPTIONS_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_ANIMATION_LENGTH,
self.label = "Length",
self.tooltip = "Sets the animation length.\n(Will not change frames.)",
self.snapshotAction = "Set Animation Length",
self.rowCount = IMGUI_TIMELINE_OPTIONS_ROW_COUNT,
self.min = ANM2_FRAME_NUM_MIN,
self.max = ANM2_FRAME_NUM_MAX,
self.value = ANM2_FRAME_NUM_MIN,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_FPS,
self.label = "FPS",
self.tooltip = "Sets the animation's frames per second (its speed).",
self.snapshotAction = "Set FPS",
self.rowCount = IMGUI_TIMELINE_OPTIONS_ROW_COUNT,
self.min = ANM2_FPS_MIN,
self.max = ANM2_FPS_MAX,
self.value = ANM2_FPS_DEFAULT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_LOOP,
self.label = "Loop",
self.tooltip = "Toggles the animation looping.",
self.snapshotAction = "Set Loop",
self.rowCount = IMGUI_TIMELINE_OPTIONS_ROW_COUNT,
self.value = true,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_CREATED_BY,
self.label = "Author",
self.tooltip = "Sets the author of the animation.",
self.rowCount = IMGUI_TIMELINE_OPTIONS_ROW_COUNT,
self.max = UCHAR_MAX
);
#define IMGUI_ONIONSKIN_ROW_COUNT 3
IMGUI_ITEM(IMGUI_ONIONSKIN, self.label = "Onionskin");
IMGUI_ITEM(IMGUI_ONIONSKIN_ENABLED,
self.label = "Enabled",
self.tooltip = "Toggle onionskin (previews of frames before/after the current one.)",
self.function = imgui_onionskin_toggle,
self.hotkey = HOTKEY_ONIONSKIN,
self.isSeparator = true
);
IMGUI_ITEM(IMGUI_ONIONSKIN_BEFORE, self.label = "-- Before -- ");
IMGUI_ITEM(IMGUI_ONIONSKIN_AFTER, self.label = "-- After -- ");
IMGUI_ITEM(IMGUI_ONIONSKIN_COUNT,
self.label = "Count",
self.tooltip = "Set the number of previewed frames appearing.",
self.min = 0,
self.max = 100,
self.value = SETTINGS_ONIONSKIN_BEFORE_COUNT_DEFAULT,
self.rowCount = IMGUI_ONIONSKIN_ROW_COUNT,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_ONIONSKIN_COLOR_OFFSET,
self.label = "Color Offset",
self.tooltip = "Set the color offset of the previewed frames.",
self.flags = ImGuiColorEditFlags_NoInputs,
self.rowCount = IMGUI_ONIONSKIN_ROW_COUNT
);
IMGUI_ITEM(IMGUI_ONIONSKIN_DRAW_ORDER,
self.label = "Draw Order",
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_ONIONSKIN_BELOW,
self.label = "Below",
self.tooltip = "The onionskin frames will draw below the base frame.",
self.value = ONIONSKIN_BELOW,
self.isSameLine = true
);
IMGUI_ITEM(IMGUI_ONIONSKIN_ABOVE,
self.label = "Above",
self.tooltip = "The onionskin frames will draw above the base frame.",
self.value = ONIONSKIN_ABOVE
);
IMGUI_ITEM(IMGUI_CONTEXT_MENU, self.label = "## Context Menu");
IMGUI_ITEM(IMGUI_CUT,
self.label = "Cut",
self.tooltip = "Cuts the currently selected contextual element; removing it and putting it to the clipboard.",
self.snapshotAction = "Cut",
self.function = imgui_cut,
self.hotkey = HOTKEY_CUT,
self.isSizeToText = true
);
IMGUI_ITEM(IMGUI_COPY,
self.label = "Copy",
self.tooltip = "Copies the currently selected contextual element to the clipboard.",
self.snapshotAction = "Copy",
self.function = imgui_copy,
self.hotkey = HOTKEY_COPY,
self.isSizeToText = true
);
IMGUI_ITEM(IMGUI_PASTE,
self.label = "Paste",
self.tooltip = "Pastes the currently selection contextual element from the clipboard.",
self.snapshotAction = "Paste",
self.function = imgui_paste,
self.hotkey = HOTKEY_PASTE,
self.isSizeToText = true
);
IMGUI_ITEM(IMGUI_CHANGE_INPUT_TEXT,
self.label = "## Input Text",
self.tooltip = "Rename the selected item.",
self.snapshotAction = "Rename Item",
self.flags = ImGuiInputTextFlags_AutoSelectAll | ImGuiInputTextFlags_EnterReturnsTrue,
self.max = UCHAR_MAX
);
IMGUI_ITEM(IMGUI_CHANGE_INPUT_INT,
self.label = "## Input Int",
self.tooltip = "Change the selected item's value.",
self.snapshotAction = "Change Value",
self.step = 0
);
#define IMGUI_CONFIRM_POPUP_ROW_COUNT 2
IMGUI_ITEM(IMGUI_POPUP_OK,
self.label = "OK",
self.tooltip = "Confirm the action.",
self.rowCount = IMGUI_CONFIRM_POPUP_ROW_COUNT
);
IMGUI_ITEM(IMGUI_POPUP_CANCEL,
self.label = "Cancel",
self.tooltip = "Cancel the action.",
self.rowCount = IMGUI_CONFIRM_POPUP_ROW_COUNT
);
IMGUI_ITEM(IMGUI_LOG_WINDOW,
self.label = "## Log Window",
self.flags = ImGuiWindowFlags_NoTitleBar |
ImGuiWindowFlags_NoResize |
ImGuiWindowFlags_NoMove |
ImGuiWindowFlags_NoScrollbar |
ImGuiWindowFlags_NoSavedSettings |
ImGuiWindowFlags_AlwaysAutoResize |
ImGuiWindowFlags_NoFocusOnAppearing |
ImGuiWindowFlags_NoNav |
ImGuiWindowFlags_NoInputs
);
void imgui_init
(
Imgui* self,
Dialog* dialog,
Resources* resources,
Anm2* anm2,
Anm2Reference* reference,
Editor* editor,
Preview* preview,
GeneratePreview* generatePreview,
Settings* settings,
Snapshots* snapshots,
Clipboard* clipboard,
SDL_Window* window,
SDL_GLContext* glContext
);
void imgui_update(Imgui* self);
void imgui_draw();
void imgui_free();