diff options
author | 2016-02-21 04:59:39 +0100 | |
---|---|---|
committer | 2016-02-21 04:59:39 +0100 | |
commit | 526d56d3597c9394713596e52fb6e9030ca5b107 (patch) | |
tree | 3f1808ef16106ba98c145c71753d80ae8dd2c18b | |
parent | c13089a065523ee1a302b95bcf111ac8264e8444 (diff) |
Added option in the "Customize UI" menu for selecting the language. (nw)
-rw-r--r-- | scripts/src/emu.lua | 2 | ||||
-rw-r--r-- | src/emu/clifront.cpp | 8 | ||||
-rw-r--r-- | src/emu/clifront.h | 2 | ||||
-rw-r--r-- | src/emu/language.cpp | 74 | ||||
-rw-r--r-- | src/emu/language.h | 21 | ||||
-rw-r--r-- | src/emu/ui/custui.cpp | 76 | ||||
-rw-r--r-- | src/emu/ui/custui.h | 5 |
7 files changed, 165 insertions, 23 deletions
diff --git a/scripts/src/emu.lua b/scripts/src/emu.lua index e0358285114..9413b092af7 100644 --- a/scripts/src/emu.lua +++ b/scripts/src/emu.lua @@ -149,6 +149,8 @@ files { MAME_DIR .. "src/emu/inpttype.h", MAME_DIR .. "src/emu/luaengine.cpp", MAME_DIR .. "src/emu/luaengine.h", + MAME_DIR .. "src/emu/language.cpp", + MAME_DIR .. "src/emu/language.h", MAME_DIR .. "src/emu/mame.cpp", MAME_DIR .. "src/emu/mame.h", MAME_DIR .. "src/emu/machine.cpp", diff --git a/src/emu/clifront.cpp b/src/emu/clifront.cpp index 2875178b7fe..bda542693fa 100644 --- a/src/emu/clifront.cpp +++ b/src/emu/clifront.cpp @@ -28,6 +28,7 @@ #include "softlist.h" #include "ui/moptions.h" +#include "language.h" #include <new> #include <ctype.h> @@ -88,7 +89,7 @@ cli_frontend::~cli_frontend() // nuke any device options since they will leak memory m_options.remove_device_options(); } - +/* const UINT32 MO_MAGIC = 0x950412de; const UINT32 MO_MAGIC_REVERSED = 0xde120495; @@ -151,7 +152,7 @@ void cli_frontend::load_translation() global_free_array(buffer); } } - +*/ //------------------------------------------------- // execute - execute a game via the standard // command line interface @@ -171,7 +172,8 @@ int cli_frontend::execute(int argc, char **argv) m_options.parse_standard_inis(option_errors); - load_translation(); + //load_translation(); + load_translation(m_options); manager->start_luaengine(); diff --git a/src/emu/clifront.h b/src/emu/clifront.h index c1529ac45a1..dfdc79a7638 100644 --- a/src/emu/clifront.h +++ b/src/emu/clifront.h @@ -32,7 +32,7 @@ public: cli_frontend(cli_options &options, osd_interface &osd); ~cli_frontend(); - void load_translation(); +// void load_translation(); // execute based on the incoming argc/argv int execute(int argc, char **argv); diff --git a/src/emu/language.cpp b/src/emu/language.cpp new file mode 100644 index 00000000000..8d489f63009 --- /dev/null +++ b/src/emu/language.cpp @@ -0,0 +1,74 @@ +// license:BSD-3-Clause +// copyright-holders:Miodrag Milanovic +/*************************************************************************** + + language.cpp + + Multi-language support. + +***************************************************************************/ + +#include "language.h" + +static std::unordered_map<std::string, std::string> g_translation; + +const char *lang_translate(const char *word) +{ + if (g_translation.find(word) == g_translation.end()) + { + return word; + } + return g_translation[word].c_str(); +} + +const UINT32 MO_MAGIC = 0x950412de; +const UINT32 MO_MAGIC_REVERSED = 0xde120495; + +inline UINT32 endianchange(UINT32 value) { + UINT32 b0 = (value >> 0) & 0xff; + UINT32 b1 = (value >> 8) & 0xff; + UINT32 b2 = (value >> 16) & 0xff; + UINT32 b3 = (value >> 24) & 0xff; + + return (b0 << 24) | (b1 << 16) | (b2 << 8) | b3; +} + +void load_translation(emu_options &m_options) +{ + g_translation.clear(); + emu_file file(m_options.language_path(), OPEN_FLAG_READ); + if (file.open(m_options.language(), PATH_SEPARATOR "strings.mo") == FILERR_NONE) + { + UINT64 size = file.size(); + UINT32 *buffer = global_alloc_array(UINT32, size / 4 + 1); + file.read(buffer, size); + file.close(); + + if (buffer[0] != MO_MAGIC && buffer[0] != MO_MAGIC_REVERSED) + { + global_free_array(buffer); + return; + } + if (buffer[0] == MO_MAGIC_REVERSED) + { + for (auto i = 0; i < (size / 4) + 1; ++i) + { + buffer[i] = endianchange(buffer[i]); + } + } + + UINT32 number_of_strings = buffer[2]; + UINT32 original_table_offset = buffer[3] >> 2; + UINT32 translation_table_offset = buffer[4] >> 2; + + const char *data = reinterpret_cast<const char*>(buffer); + + for (auto i = 1; i < number_of_strings; ++i) + { + std::string original = (const char *)data + buffer[original_table_offset + 2 * i + 1]; + std::string translation = (const char *)data + buffer[translation_table_offset + 2 * i + 1]; + g_translation.insert(std::pair<std::string, std::string>(original, translation)); + } + global_free_array(buffer); + } +}
\ No newline at end of file diff --git a/src/emu/language.h b/src/emu/language.h new file mode 100644 index 00000000000..5a885d1b05f --- /dev/null +++ b/src/emu/language.h @@ -0,0 +1,21 @@ +// license:BSD-3-Clause +// copyright-holders:Miodrag Milanovic +/*************************************************************************** + + language.h + + Multi-language support. + +***************************************************************************/ +#pragma once + +#ifndef __LANGUAGE_H__ +#define __LANGUAGE_H__ + +#include "emu.h" + +void load_translation(emu_options &option); +const char *lang_translate(const char *word); + +#endif /*__LANGUAGE_H__*/ + diff --git a/src/emu/ui/custui.cpp b/src/emu/ui/custui.cpp index 355f486918a..a6987673aa9 100644 --- a/src/emu/ui/custui.cpp +++ b/src/emu/ui/custui.cpp @@ -15,6 +15,7 @@ #include "ui/custui.h" #include "ui/utils.h" #include <algorithm> +#include "language.h" const char *ui_menu_custom_ui::hide_status[] = { "Show All", "Hide Filters", "Hide Info/Image", "Hide Both" }; @@ -24,6 +25,17 @@ const char *ui_menu_custom_ui::hide_status[] = { "Show All", "Hide Filters", "Hi ui_menu_custom_ui::ui_menu_custom_ui(running_machine &machine, render_container *container) : ui_menu(machine, container) { + // load languages + file_enumerator path(machine.options().language_path()); + const char *lang = machine.options().language(); + const osd_directory_entry *dirent; + for (int x = 0; (dirent = path.next()) != nullptr; ++x) + if (dirent->type == ENTTYPE_DIR && strcmp(dirent->name, ".") != 0 && strcmp(dirent->name, "..") != 0) + { + m_lang.push_back(dirent->name); + if (strcmp(dirent->name, lang) == 0) + m_currlang = x; + } } //------------------------------------------------- @@ -34,6 +46,11 @@ ui_menu_custom_ui::~ui_menu_custom_ui() { std::string error_string; machine().ui().options().set_value(OPTION_HIDE_PANELS, ui_globals::panels_status, OPTION_PRIORITY_CMDLINE, error_string); + if (!m_lang.empty()) + { + machine().options().set_value(OPTION_LANGUAGE, m_lang[m_currlang].c_str(), OPTION_PRIORITY_CMDLINE, error_string); + load_translation(machine().options()); + } ui_globals::reset = true; } @@ -50,25 +67,24 @@ void ui_menu_custom_ui::handle() if (m_event != nullptr && m_event->itemref != nullptr) { - if (m_event->iptkey == IPT_UI_LEFT || m_event->iptkey == IPT_UI_RIGHT) - { - changed = true; - (m_event->iptkey == IPT_UI_RIGHT) ? ui_globals::panels_status++ : ui_globals::panels_status--; - } - - - else if (m_event->iptkey == IPT_UI_SELECT) + switch ((FPTR)m_event->itemref) { - switch ((FPTR)m_event->itemref) - { - case FONT_MENU: + case FONT_MENU: + if (m_event->iptkey == IPT_UI_SELECT) ui_menu::stack_push(global_alloc_clear<ui_menu_font_ui>(machine(), container)); - break; - - case COLORS_MENU: + break; + case COLORS_MENU: + if (m_event->iptkey == IPT_UI_SELECT) ui_menu::stack_push(global_alloc_clear<ui_menu_colors_ui>(machine(), container)); - break; - case HIDE_MENU: + break; + case HIDE_MENU: + { + if (m_event->iptkey == IPT_UI_LEFT || m_event->iptkey == IPT_UI_RIGHT) + { + changed = true; + (m_event->iptkey == IPT_UI_RIGHT) ? ui_globals::panels_status++ : ui_globals::panels_status--; + } + else if (m_event->iptkey == IPT_UI_SELECT) { int total = ARRAY_LENGTH(hide_status); std::vector<std::string> s_sel(total); @@ -78,6 +94,23 @@ void ui_menu_custom_ui::handle() ui_menu::stack_push(global_alloc_clear<ui_menu_selector>(machine(), container, s_sel, ui_globals::panels_status)); } } + case LANGUAGE_MENU: + { + if (m_event->iptkey == IPT_UI_LEFT || m_event->iptkey == IPT_UI_RIGHT) + { + changed = true; + (m_event->iptkey == IPT_UI_RIGHT) ? m_currlang++ : m_currlang--; + } + else if (m_event->iptkey == IPT_UI_SELECT) + { + int total = m_lang.size(); + std::vector<std::string> s_sel(total); + for (int index = 0; index < total; ++index) + s_sel[index] = m_lang[index]; + + ui_menu::stack_push(global_alloc_clear<ui_menu_selector>(machine(), container, s_sel, m_currlang)); + } + } } } @@ -91,11 +124,18 @@ void ui_menu_custom_ui::handle() void ui_menu_custom_ui::populate() { + UINT32 arrow_flags; item_append("Fonts", nullptr, 0, (void *)(FPTR)FONT_MENU); item_append("Colors", nullptr, 0, (void *)(FPTR)COLORS_MENU); - UINT32 arrow_flags = get_arrow_flags(0, (int)HIDE_BOTH, ui_globals::panels_status); - item_append("Filters and Info/Image", hide_status[ui_globals::panels_status], arrow_flags, (void *)(FPTR)HIDE_MENU); + if (!m_lang.empty()) + { + arrow_flags = get_arrow_flags(0, m_lang.size() - 1, m_currlang); + item_append("Language", m_lang[m_currlang].c_str(), arrow_flags, (void *)(FPTR)LANGUAGE_MENU); + } + + arrow_flags = get_arrow_flags(0, (int)HIDE_BOTH, ui_globals::panels_status); + item_append("Show side panels", hide_status[ui_globals::panels_status], arrow_flags, (void *)(FPTR)HIDE_MENU); item_append(MENU_SEPARATOR_ITEM, nullptr, 0, nullptr); customtop = machine().ui().get_line_height() + 3.0f * UI_BOX_TB_BORDER; diff --git a/src/emu/ui/custui.h b/src/emu/ui/custui.h index 79f45cc3a6e..0a2caf8de8c 100644 --- a/src/emu/ui/custui.h +++ b/src/emu/ui/custui.h @@ -34,11 +34,14 @@ public: private: enum { - FONT_MENU = 1, + LANGUAGE_MENU = 1, + FONT_MENU, COLORS_MENU, HIDE_MENU }; static const char *hide_status[]; + std::vector<std::string> m_lang; + UINT16 m_currlang; }; //------------------------------------------------- |