Enhance message parsing and editor functionality; add expanded message settings UI, improve message data handling, and remove import/export features for cleaner code structure.
This commit is contained in:
@@ -276,6 +276,7 @@ std::vector<std::string> ParseMessageData(
|
|||||||
|
|
||||||
for (auto &message : message_data) {
|
for (auto &message : message_data) {
|
||||||
std::string parsed_message = "";
|
std::string parsed_message = "";
|
||||||
|
int pos = 0;
|
||||||
for (const uint8_t &byte : message.Data) {
|
for (const uint8_t &byte : message.Data) {
|
||||||
if (CharEncoder.contains(byte)) {
|
if (CharEncoder.contains(byte)) {
|
||||||
parsed_message.push_back(CharEncoder.at(byte));
|
parsed_message.push_back(CharEncoder.at(byte));
|
||||||
@@ -296,10 +297,19 @@ std::vector<std::string> ParseMessageData(
|
|||||||
text_element->ID == kLine2 || text_element->ID == kLine3) {
|
text_element->ID == kLine2 || text_element->ID == kLine3) {
|
||||||
parsed_message.append("\n");
|
parsed_message.append("\n");
|
||||||
}
|
}
|
||||||
parsed_message.append(text_element->GenericToken);
|
// If there is a param, add it to the message using GetParamToken.
|
||||||
|
if (text_element->HasArgument) {
|
||||||
|
// The next byte is the param.
|
||||||
|
parsed_message.append(
|
||||||
|
text_element->GetParamToken(message.Data[pos + 1]));
|
||||||
|
pos++;
|
||||||
|
} else {
|
||||||
|
parsed_message.append(text_element->GetParamToken());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
pos++;
|
||||||
}
|
}
|
||||||
parsed_messages.push_back(parsed_message);
|
parsed_messages.push_back(parsed_message);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,13 +1,11 @@
|
|||||||
#include "message_editor.h"
|
#include "message_editor.h"
|
||||||
|
|
||||||
#include <string>
|
#include <string>
|
||||||
#include <unordered_map>
|
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
#include "absl/status/status.h"
|
#include "absl/status/status.h"
|
||||||
#include "absl/strings/str_cat.h"
|
#include "absl/strings/str_cat.h"
|
||||||
#include "absl/strings/str_format.h"
|
#include "absl/strings/str_format.h"
|
||||||
#include "absl/strings/str_replace.h"
|
|
||||||
#include "app/core/platform/renderer.h"
|
#include "app/core/platform/renderer.h"
|
||||||
#include "app/gfx/bitmap.h"
|
#include "app/gfx/bitmap.h"
|
||||||
#include "app/gfx/snes_palette.h"
|
#include "app/gfx/snes_palette.h"
|
||||||
@@ -17,6 +15,7 @@
|
|||||||
#include "app/rom.h"
|
#include "app/rom.h"
|
||||||
#include "imgui.h"
|
#include "imgui.h"
|
||||||
#include "imgui/misc/cpp/imgui_stdlib.h"
|
#include "imgui/misc/cpp/imgui_stdlib.h"
|
||||||
|
#include "imgui_memory_editor.h"
|
||||||
#include "util/hex.h"
|
#include "util/hex.h"
|
||||||
|
|
||||||
namespace yaze {
|
namespace yaze {
|
||||||
@@ -30,6 +29,8 @@ using ImGui::Button;
|
|||||||
using ImGui::EndChild;
|
using ImGui::EndChild;
|
||||||
using ImGui::EndTable;
|
using ImGui::EndTable;
|
||||||
using ImGui::InputTextMultiline;
|
using ImGui::InputTextMultiline;
|
||||||
|
using ImGui::PopID;
|
||||||
|
using ImGui::PushID;
|
||||||
using ImGui::SameLine;
|
using ImGui::SameLine;
|
||||||
using ImGui::Separator;
|
using ImGui::Separator;
|
||||||
using ImGui::TableHeadersRow;
|
using ImGui::TableHeadersRow;
|
||||||
@@ -90,6 +91,7 @@ absl::Status MessageEditor::Update() {
|
|||||||
if (rom()->is_loaded() && !data_loaded_) {
|
if (rom()->is_loaded() && !data_loaded_) {
|
||||||
Initialize();
|
Initialize();
|
||||||
current_message_ = list_of_texts_[1];
|
current_message_ = list_of_texts_[1];
|
||||||
|
message_text_box_.text = parsed_messages_[current_message_.ID];
|
||||||
data_loaded_ = true;
|
data_loaded_ = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -112,8 +114,8 @@ absl::Status MessageEditor::Update() {
|
|||||||
DrawSpecialCharacters();
|
DrawSpecialCharacters();
|
||||||
|
|
||||||
TableNextColumn();
|
TableNextColumn();
|
||||||
|
DrawExpandedMessageSettings();
|
||||||
DrawDictionary();
|
DrawDictionary();
|
||||||
DrawImportExport();
|
|
||||||
|
|
||||||
EndTable();
|
EndTable();
|
||||||
}
|
}
|
||||||
@@ -132,10 +134,11 @@ void MessageEditor::DrawMessageList() {
|
|||||||
TableHeadersRow();
|
TableHeadersRow();
|
||||||
for (const auto& message : list_of_texts_) {
|
for (const auto& message : list_of_texts_) {
|
||||||
TableNextColumn();
|
TableNextColumn();
|
||||||
|
PushID(message.ID);
|
||||||
if (Button(util::HexWord(message.ID).c_str())) {
|
if (Button(util::HexWord(message.ID).c_str())) {
|
||||||
current_message_ = message;
|
current_message_ = message;
|
||||||
DrawMessagePreview();
|
|
||||||
}
|
}
|
||||||
|
PopID();
|
||||||
TableNextColumn();
|
TableNextColumn();
|
||||||
TextWrapped("%s", parsed_messages_[message.ID].c_str());
|
TextWrapped("%s", parsed_messages_[message.ID].c_str());
|
||||||
TableNextColumn();
|
TableNextColumn();
|
||||||
@@ -154,34 +157,34 @@ void MessageEditor::DrawCurrentMessage() {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
Button(absl::StrCat("Message ", current_message_.ID).c_str());
|
Button(absl::StrCat("Message ", current_message_.ID).c_str());
|
||||||
if (InputTextMultiline("##MessageEditor",
|
if (InputTextMultiline("##MessageEditor", &message_text_box_.text,
|
||||||
&parsed_messages_[current_message_.ID],
|
|
||||||
ImVec2(ImGui::GetContentRegionAvail().x, 0))) {
|
ImVec2(ImGui::GetContentRegionAvail().x, 0))) {
|
||||||
current_message_.Data = ParseMessageToData(message_text_box_.text);
|
current_message_.Data = ParseMessageToData(message_text_box_.text);
|
||||||
DrawMessagePreview();
|
DrawMessagePreview();
|
||||||
}
|
}
|
||||||
Separator();
|
Separator();
|
||||||
|
|
||||||
|
static bool show_message_data = false;
|
||||||
|
if (ImGui::Button("View Message Data")) {
|
||||||
|
show_message_data = true;
|
||||||
|
}
|
||||||
|
if (show_message_data) {
|
||||||
|
MemoryEditor mem_edit;
|
||||||
|
mem_edit.DrawWindow("Message Data", current_message_.Data.data(),
|
||||||
|
current_message_.Data.size());
|
||||||
|
}
|
||||||
|
|
||||||
Text("Font Graphics");
|
Text("Font Graphics");
|
||||||
gui::BeginPadding(1);
|
gui::BeginCanvas(font_gfx_canvas_, ImVec2(0, 130));
|
||||||
BeginChild("MessageEditorCanvas", ImVec2(0, 130));
|
|
||||||
font_gfx_canvas_.DrawBackground();
|
|
||||||
font_gfx_canvas_.DrawContextMenu();
|
|
||||||
font_gfx_canvas_.DrawBitmap(font_gfx_bitmap_, 0, 0);
|
font_gfx_canvas_.DrawBitmap(font_gfx_bitmap_, 0, 0);
|
||||||
font_gfx_canvas_.DrawGrid();
|
gui::EndCanvas(font_gfx_canvas_);
|
||||||
font_gfx_canvas_.DrawOverlay();
|
|
||||||
EndChild();
|
|
||||||
gui::EndPadding();
|
|
||||||
Separator();
|
Separator();
|
||||||
|
|
||||||
|
ImGui::BeginChild("##MessagePreview", ImVec2(0, 0), true, 1);
|
||||||
Text("Message Preview");
|
Text("Message Preview");
|
||||||
if (Button("Create Preview")) {
|
if (Button("Create Preview")) {
|
||||||
DrawMessagePreview();
|
DrawMessagePreview();
|
||||||
}
|
}
|
||||||
if (Button("Refresh Bitmap")) {
|
|
||||||
Renderer::GetInstance().UpdateBitmap(¤t_font_gfx16_bitmap_);
|
|
||||||
}
|
|
||||||
ImGui::SameLine();
|
|
||||||
if (Button("View Palette")) {
|
if (Button("View Palette")) {
|
||||||
ImGui::OpenPopup("Palette");
|
ImGui::OpenPopup("Palette");
|
||||||
}
|
}
|
||||||
@@ -199,6 +202,7 @@ void MessageEditor::DrawCurrentMessage() {
|
|||||||
current_font_gfx16_canvas_.DrawGrid();
|
current_font_gfx16_canvas_.DrawGrid();
|
||||||
current_font_gfx16_canvas_.DrawOverlay();
|
current_font_gfx16_canvas_.DrawOverlay();
|
||||||
EndChild();
|
EndChild();
|
||||||
|
ImGui::EndChild();
|
||||||
}
|
}
|
||||||
|
|
||||||
void MessageEditor::DrawTextCommands() {
|
void MessageEditor::DrawTextCommands() {
|
||||||
@@ -217,24 +221,40 @@ void MessageEditor::DrawTextCommands() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void MessageEditor::DrawSpecialCharacters() {
|
void MessageEditor::DrawSpecialCharacters() {
|
||||||
ImGui::BeginChild("##SpecialChars",
|
ImGui::BeginChild("##SpecialChars", ImVec2(0, 0), true,
|
||||||
ImVec2(0, ImGui::GetWindowContentRegionMax().y / 2), true,
|
|
||||||
ImGuiWindowFlags_AlwaysVerticalScrollbar);
|
ImGuiWindowFlags_AlwaysVerticalScrollbar);
|
||||||
for (const auto& text_element : SpecialChars) {
|
for (const auto& text_element : SpecialChars) {
|
||||||
if (Button(text_element.GenericToken.c_str())) {
|
if (Button(text_element.GenericToken.c_str())) {
|
||||||
message_text_box_.text.append(text_element.GenericToken);
|
message_text_box_.text.append(text_element.GenericToken);
|
||||||
}
|
}
|
||||||
|
SameLine();
|
||||||
|
TextWrapped("%s", text_element.Description.c_str());
|
||||||
Separator();
|
Separator();
|
||||||
}
|
}
|
||||||
EndChild();
|
EndChild();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void MessageEditor::DrawExpandedMessageSettings() {
|
||||||
|
ImGui::BeginChild("##ExpandedMessageSettings",
|
||||||
|
ImVec2(0, ImGui::GetWindowContentRegionMax().y / 2), true,
|
||||||
|
ImGuiWindowFlags_AlwaysVerticalScrollbar);
|
||||||
|
// Input for the address of the expanded messages
|
||||||
|
ImGui::InputText("Address", &expanded_message_address_,
|
||||||
|
ImGuiInputTextFlags_CharsHexadecimal);
|
||||||
|
|
||||||
|
if (ImGui::Button("Load Expanded Message")) {
|
||||||
|
// Load the expanded message from the address.
|
||||||
|
// TODO: Implement this.
|
||||||
|
}
|
||||||
|
EndChild();
|
||||||
|
}
|
||||||
|
|
||||||
void MessageEditor::DrawDictionary() {
|
void MessageEditor::DrawDictionary() {
|
||||||
if (all_dictionaries_.empty()) {
|
if (all_dictionaries_.empty()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (ImGui::BeginChild("##DictionaryChild",
|
if (ImGui::BeginChild("##DictionaryChild",
|
||||||
ImVec2(200, ImGui::GetWindowContentRegionMax().y / 2),
|
ImVec2(0, ImGui::GetWindowContentRegionMax().y / 2),
|
||||||
true, ImGuiWindowFlags_AlwaysVerticalScrollbar)) {
|
true, ImGuiWindowFlags_AlwaysVerticalScrollbar)) {
|
||||||
if (BeginTable("##Dictionary", 2, kMessageTableFlags)) {
|
if (BeginTable("##Dictionary", 2, kMessageTableFlags)) {
|
||||||
TableSetupColumn("ID");
|
TableSetupColumn("ID");
|
||||||
@@ -252,30 +272,6 @@ void MessageEditor::DrawDictionary() {
|
|||||||
EndChild();
|
EndChild();
|
||||||
}
|
}
|
||||||
|
|
||||||
void MessageEditor::DrawImportExport() {
|
|
||||||
ImGui::Text("Import Messages");
|
|
||||||
ImGui::Separator();
|
|
||||||
|
|
||||||
static char import_path[256] = "";
|
|
||||||
ImGui::InputText("Import File", import_path, sizeof(import_path));
|
|
||||||
|
|
||||||
if (ImGui::Button("Import")) {
|
|
||||||
status_ = ImportMessagesFromFile(import_path);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Export section
|
|
||||||
ImGui::Spacing();
|
|
||||||
ImGui::Text("Export Messages");
|
|
||||||
ImGui::Separator();
|
|
||||||
|
|
||||||
static char export_path[256] = "";
|
|
||||||
ImGui::InputText("Export File", export_path, sizeof(export_path));
|
|
||||||
|
|
||||||
if (ImGui::Button("Export")) {
|
|
||||||
status_ = ExportMessagesToFile(export_path);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void MessageEditor::DrawTileToPreview(int x, int y, int srcx, int srcy, int pal,
|
void MessageEditor::DrawTileToPreview(int x, int y, int srcx, int srcy, int pal,
|
||||||
int sizex, int sizey) {
|
int sizex, int sizey) {
|
||||||
const int num_x_tiles = 16;
|
const int num_x_tiles = 16;
|
||||||
@@ -387,8 +383,7 @@ void MessageEditor::DrawMessagePreview() {
|
|||||||
DrawCharacterToPreview(current_message_.Data);
|
DrawCharacterToPreview(current_message_.Data);
|
||||||
shown_lines_ = 0;
|
shown_lines_ = 0;
|
||||||
|
|
||||||
Renderer::GetInstance().UpdateBitmap(&font_gfx_bitmap_);
|
Renderer::GetInstance().UpdateBitmap(¤t_font_gfx16_bitmap_);
|
||||||
Renderer::GetInstance().RenderBitmap(¤t_font_gfx16_bitmap_);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
absl::Status MessageEditor::Save() {
|
absl::Status MessageEditor::Save() {
|
||||||
@@ -540,74 +535,5 @@ absl::Status MessageEditor::Find() {
|
|||||||
return absl::OkStatus();
|
return absl::OkStatus();
|
||||||
}
|
}
|
||||||
|
|
||||||
absl::Status MessageEditor::ImportMessagesFromFile(const std::string& path) {
|
|
||||||
// Open the file
|
|
||||||
std::ifstream file(path);
|
|
||||||
if (!file.is_open()) {
|
|
||||||
return absl::NotFoundError("Failed to open file");
|
|
||||||
}
|
|
||||||
|
|
||||||
// Read the file line by line
|
|
||||||
std::string line;
|
|
||||||
int line_number = 0;
|
|
||||||
|
|
||||||
while (std::getline(file, line)) {
|
|
||||||
line_number++;
|
|
||||||
|
|
||||||
// Skip empty lines and comments
|
|
||||||
if (line.empty() || line[0] == '#') {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Parse the line
|
|
||||||
// Format: ID=content
|
|
||||||
size_t equal_pos = line.find('=');
|
|
||||||
if (equal_pos == std::string::npos) {
|
|
||||||
return absl::InvalidArgumentError(
|
|
||||||
absl::StrFormat("Invalid format at line %d", line_number));
|
|
||||||
}
|
|
||||||
|
|
||||||
std::string id_str = line.substr(0, equal_pos);
|
|
||||||
std::string content = line.substr(equal_pos + 1);
|
|
||||||
|
|
||||||
// Parse the ID
|
|
||||||
int id;
|
|
||||||
if (!absl::SimpleAtoi(id_str, &id)) {
|
|
||||||
return absl::InvalidArgumentError(
|
|
||||||
absl::StrFormat("Invalid ID at line %d", line_number));
|
|
||||||
}
|
|
||||||
|
|
||||||
// Update a regular message
|
|
||||||
for (auto& message : list_of_texts_) {
|
|
||||||
if (message.ID == id) {
|
|
||||||
message.ContentsParsed = content;
|
|
||||||
message.DataParsed = ParseMessageToData(content);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return absl::OkStatus();
|
|
||||||
}
|
|
||||||
|
|
||||||
absl::Status MessageEditor::ExportMessagesToFile(const std::string& path) {
|
|
||||||
// Open the file
|
|
||||||
std::ofstream file(path);
|
|
||||||
if (!file.is_open()) {
|
|
||||||
return absl::NotFoundError("Failed to open file");
|
|
||||||
}
|
|
||||||
|
|
||||||
// Write a header
|
|
||||||
file << "# Message Export\n";
|
|
||||||
file << "# Format: ID=content\n\n";
|
|
||||||
|
|
||||||
// Write regular messages
|
|
||||||
for (const auto& message : list_of_texts_) {
|
|
||||||
file << absl::StrFormat("%d=%s\n", message.ID, message.ContentsParsed);
|
|
||||||
}
|
|
||||||
|
|
||||||
return absl::OkStatus();
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace editor
|
} // namespace editor
|
||||||
} // namespace yaze
|
} // namespace yaze
|
||||||
|
|||||||
@@ -38,13 +38,6 @@ class MessageEditor : public Editor {
|
|||||||
void Initialize() override;
|
void Initialize() override;
|
||||||
absl::Status Load() override;
|
absl::Status Load() override;
|
||||||
absl::Status Update() override;
|
absl::Status Update() override;
|
||||||
void DrawMessageList();
|
|
||||||
void DrawCurrentMessage();
|
|
||||||
void DrawTextCommands();
|
|
||||||
void DrawSpecialCharacters();
|
|
||||||
void DrawDictionary();
|
|
||||||
void DrawImportExport();
|
|
||||||
void DrawMessageSettings();
|
|
||||||
|
|
||||||
absl::Status Cut() override;
|
absl::Status Cut() override;
|
||||||
absl::Status Copy() override;
|
absl::Status Copy() override;
|
||||||
@@ -56,6 +49,13 @@ class MessageEditor : public Editor {
|
|||||||
void Delete();
|
void Delete();
|
||||||
void SelectAll();
|
void SelectAll();
|
||||||
|
|
||||||
|
void DrawMessageList();
|
||||||
|
void DrawCurrentMessage();
|
||||||
|
void DrawTextCommands();
|
||||||
|
void DrawSpecialCharacters();
|
||||||
|
void DrawExpandedMessageSettings();
|
||||||
|
void DrawDictionary();
|
||||||
|
|
||||||
void DrawTileToPreview(int x, int y, int srcx, int srcy, int pal,
|
void DrawTileToPreview(int x, int y, int srcx, int srcy, int pal,
|
||||||
int sizex = 1, int sizey = 1);
|
int sizex = 1, int sizey = 1);
|
||||||
void DrawCharacterToPreview(char c);
|
void DrawCharacterToPreview(char c);
|
||||||
@@ -65,15 +65,6 @@ class MessageEditor : public Editor {
|
|||||||
void DrawMessagePreview();
|
void DrawMessagePreview();
|
||||||
std::string DisplayTextOverflowError(int pos, bool bank);
|
std::string DisplayTextOverflowError(int pos, bool bank);
|
||||||
|
|
||||||
absl::Status ImportMessagesFromFile(const std::string& filename);
|
|
||||||
absl::Status ExportMessagesToFile(const std::string& filename);
|
|
||||||
|
|
||||||
void SetMessageFont(int font_index);
|
|
||||||
void SetMessageColor(int color_index);
|
|
||||||
void SetMessageSpeed(int speed);
|
|
||||||
void SetMessageWindow(int window_type);
|
|
||||||
void SetMessagePosition(int x, int y);
|
|
||||||
|
|
||||||
void set_rom(Rom* rom) { rom_ = rom; }
|
void set_rom(Rom* rom) { rom_ = rom; }
|
||||||
Rom* rom() const { return rom_; }
|
Rom* rom() const { return rom_; }
|
||||||
|
|
||||||
@@ -89,9 +80,8 @@ class MessageEditor : public Editor {
|
|||||||
int text_position_ = 0;
|
int text_position_ = 0;
|
||||||
int shown_lines_ = 0;
|
int shown_lines_ = 0;
|
||||||
|
|
||||||
|
std::string expanded_message_address_ = "";
|
||||||
std::string search_text_ = "";
|
std::string search_text_ = "";
|
||||||
std::string import_filename_ = "";
|
|
||||||
std::string export_filename_ = "";
|
|
||||||
|
|
||||||
std::array<uint8_t, kWidthArraySize> width_array = {0};
|
std::array<uint8_t, kWidthArraySize> width_array = {0};
|
||||||
std::vector<uint8_t> font_gfx16_data_;
|
std::vector<uint8_t> font_gfx16_data_;
|
||||||
|
|||||||
Reference in New Issue
Block a user