mirror of
https://github.com/isledecomp/isle-portable.git
synced 2026-01-11 10:31:16 +00:00
Support for international versions of isle (#327)
* German * Add HistoryBook international support * Fixes * Fixes * Fixes * Fixes * Fixes * Add Danish support * Add Spanish support
This commit is contained in:
parent
c1543954d0
commit
6cdbfa86ac
@ -46,6 +46,9 @@ class HistoryBook : public LegoWorld {
|
||||
MxStillPresenter* m_name[20][7]; // 0x164
|
||||
|
||||
MxStillPresenter* m_scores[20]; // 0x394
|
||||
|
||||
MxStillPresenter* m_intAlphabet[sizeOfArray(LegoGameState::g_intCharacters)];
|
||||
MxU32 m_intAlphabetOffset;
|
||||
};
|
||||
|
||||
#endif // HISTORYBOOK_H
|
||||
|
||||
@ -23,6 +23,12 @@ struct ColorStringStruct {
|
||||
const char* m_colorName; // 0x04
|
||||
};
|
||||
|
||||
struct InternationalCharacter {
|
||||
unsigned char m_character;
|
||||
const char* m_bitmap;
|
||||
MxU32 m_buttonId;
|
||||
};
|
||||
|
||||
// VTABLE: LEGO1 0x100d74a8
|
||||
// SIZE 0x30
|
||||
class LegoBackgroundColor : public MxVariable {
|
||||
@ -256,6 +262,8 @@ class LegoGameState {
|
||||
Area m_currentArea; // 0x424
|
||||
Area m_previousArea; // 0x428
|
||||
Area m_unk0x42c; // 0x42c
|
||||
|
||||
static const InternationalCharacter g_intCharacters[8];
|
||||
};
|
||||
|
||||
MxBool ROIColorOverride(const char* p_input, char* p_output, MxU32 p_copyLen);
|
||||
|
||||
@ -64,6 +64,8 @@ class RegistrationBook : public LegoWorld {
|
||||
LPDIRECTDRAWSURFACE m_checkboxHilite; // 0x2c4
|
||||
LPDIRECTDRAWSURFACE m_checkboxSurface; // 0x2c8
|
||||
LPDIRECTDRAWSURFACE m_checkboxNormal; // 0x2cc
|
||||
MxStillPresenter* m_intAlphabet[sizeOfArray(LegoGameState::g_intCharacters)];
|
||||
MxU32 m_intAlphabetOffset;
|
||||
|
||||
MxLong HandleEndAction(MxEndActionNotificationParam& p_param);
|
||||
MxLong HandleKeyPress(SDL_Keycode p_key);
|
||||
|
||||
@ -143,6 +143,17 @@ const char* g_strEnable = "enable";
|
||||
// STRING: LEGO1 0x100f3bf4
|
||||
const char* g_strDisable = "disable";
|
||||
|
||||
const InternationalCharacter LegoGameState::g_intCharacters[8] = {
|
||||
{0xe4, "Aum_Bitmap", 29},
|
||||
{0xf6, "Oum_Bitmap", 30},
|
||||
{0xdf, "Beta_Bitmap", 31},
|
||||
{0xfc, "Uum_Bitmap", 32},
|
||||
{0xe5, "Ao_Bitmap", 29},
|
||||
{0xe6, "Ae_Bitmap", 30},
|
||||
{0xf8, "Oz_Bitmap", 31},
|
||||
{0xf1, "Ene_Bitmap", 29}
|
||||
};
|
||||
|
||||
// FUNCTION: LEGO1 0x10039550
|
||||
LegoGameState::LegoGameState()
|
||||
{
|
||||
|
||||
@ -10,12 +10,15 @@
|
||||
#include "mxstillpresenter.h"
|
||||
#include "mxtransitionmanager.h"
|
||||
|
||||
#include <SDL3/SDL_log.h>
|
||||
|
||||
DECOMP_SIZE_ASSERT(HistoryBook, 0x3e4)
|
||||
|
||||
// FUNCTION: LEGO1 0x100822f0
|
||||
HistoryBook::HistoryBook()
|
||||
{
|
||||
memset(m_alphabet, 0, sizeof(m_alphabet));
|
||||
memset(m_intAlphabet, 0, sizeof(m_intAlphabet));
|
||||
memset(m_name, 0, sizeof(m_name));
|
||||
memset(m_scores, 0, sizeof(m_scores));
|
||||
NotificationManager()->Register(this);
|
||||
@ -112,6 +115,20 @@ void HistoryBook::ReadyWorld()
|
||||
}
|
||||
}
|
||||
|
||||
for (i = 0; i < sizeOfArray(m_intAlphabet); i++) {
|
||||
m_intAlphabet[i] = (MxStillPresenter*) Find("MxStillPresenter", LegoGameState::g_intCharacters[i].m_bitmap);
|
||||
}
|
||||
|
||||
m_intAlphabetOffset = 0;
|
||||
for (i = 0; i < sizeOfArray(m_intAlphabet); i++) {
|
||||
if (!m_intAlphabet[i]) {
|
||||
m_intAlphabetOffset++;
|
||||
}
|
||||
else {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
MxStillPresenter* scoreboxMaster = (MxStillPresenter*) Find("MxStillPresenter", "ScoreBox");
|
||||
MxU8 scoreColors[3] =
|
||||
{0x76, 0x4c, 0x38}; // yellow - #FFB900, blue - #00548C, red - #CB1220, background - #CECECE, border - #74818B
|
||||
@ -167,7 +184,24 @@ void HistoryBook::ReadyWorld()
|
||||
for (MxS16 j = 0; j < (MxS16) sizeOfArray(m_name[0]) && score->m_name.m_letters[j] != -1; j++, scoreX += 0x17)
|
||||
#endif
|
||||
{
|
||||
m_name[i][j] = m_alphabet[score->m_name.m_letters[j]]->Clone();
|
||||
MxStillPresenter** intoAlphabet = [this,
|
||||
index = score->m_name.m_letters[j]]() mutable -> MxStillPresenter** {
|
||||
if (index < sizeOfArray(m_alphabet)) {
|
||||
return &m_alphabet[index];
|
||||
}
|
||||
|
||||
index -= sizeOfArray(m_alphabet);
|
||||
index += m_intAlphabetOffset;
|
||||
|
||||
if (index >= sizeOfArray(m_intAlphabet) || !m_intAlphabet[index]) {
|
||||
SDL_Log("Warning: international character not present in current game. Falling back to X");
|
||||
return &m_alphabet[SDLK_X - SDLK_A];
|
||||
}
|
||||
|
||||
return &m_intAlphabet[index];
|
||||
}();
|
||||
|
||||
m_name[i][j] = (*intoAlphabet)->Clone();
|
||||
|
||||
assert(m_name[i][j]);
|
||||
m_name[i][j]->Enable(TRUE);
|
||||
|
||||
@ -29,6 +29,8 @@
|
||||
#include "regbook_actions.h"
|
||||
#include "scripts.h"
|
||||
|
||||
#include <SDL3/SDL_log.h>
|
||||
|
||||
DECOMP_SIZE_ASSERT(RegistrationBook, 0x2d0)
|
||||
|
||||
// GLOBAL: LEGO1 0x100d9924
|
||||
@ -45,6 +47,7 @@ MxBool g_nextCheckbox = FALSE;
|
||||
RegistrationBook::RegistrationBook() : m_registerDialogueTimer(0x80000000), m_unk0xfc(1)
|
||||
{
|
||||
memset(m_alphabet, 0, sizeof(m_alphabet));
|
||||
memset(m_intAlphabet, 0, sizeof(m_intAlphabet));
|
||||
memset(m_name, 0, sizeof(m_name));
|
||||
m_unk0x280.m_cursorPos = 0;
|
||||
|
||||
@ -175,19 +178,31 @@ MxLong RegistrationBook::HandleKeyPress(SDL_Keycode p_key)
|
||||
// keycode is case-insensitive
|
||||
SDL_Keycode key = p_key;
|
||||
|
||||
if ((key < SDLK_A || key > SDLK_Z) && key != SDLK_BACKSPACE) {
|
||||
MxStillPresenter** intoAlphabet = [this, key]() -> MxStillPresenter** {
|
||||
if (key >= SDLK_A && key <= SDLK_Z) {
|
||||
return &m_alphabet[key - SDLK_A];
|
||||
}
|
||||
|
||||
for (int i = 0; i < sizeOfArray(m_intAlphabet); i++) {
|
||||
if (m_intAlphabet[i] && LegoGameState::g_intCharacters[i].m_character == key) {
|
||||
return &m_intAlphabet[i];
|
||||
}
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}();
|
||||
|
||||
if (!intoAlphabet && key != SDLK_BACKSPACE) {
|
||||
if (key == SDLK_SPACE) {
|
||||
DeleteObjects(&m_atomId, RegbookScript::c_iic006in_RunAnim, RegbookScript::c_iic008in_PlayWav);
|
||||
BackgroundAudioManager()->RaiseVolume();
|
||||
}
|
||||
}
|
||||
else if (key != SDLK_BACKSPACE && m_unk0x280.m_cursorPos < 7) {
|
||||
m_name[0][m_unk0x280.m_cursorPos] = m_alphabet[key - SDLK_A]->Clone();
|
||||
m_name[0][m_unk0x280.m_cursorPos] = (*intoAlphabet)->Clone();
|
||||
|
||||
if (m_name[0][m_unk0x280.m_cursorPos] != NULL) {
|
||||
m_alphabet[key - SDLK_A]->GetAction()->SetUnknown24(
|
||||
m_alphabet[key - SDLK_A]->GetAction()->GetUnknown24() + 1
|
||||
);
|
||||
(*intoAlphabet)->GetAction()->SetUnknown24((*intoAlphabet)->GetAction()->GetUnknown24() + 1);
|
||||
m_name[0][m_unk0x280.m_cursorPos]->Enable(TRUE);
|
||||
m_name[0][m_unk0x280.m_cursorPos]->SetTickleState(MxPresenter::e_repeating);
|
||||
m_name[0][m_unk0x280.m_cursorPos]->SetPosition(m_unk0x280.m_cursorPos * 23 + 343, 121);
|
||||
@ -196,7 +211,10 @@ MxLong RegistrationBook::HandleKeyPress(SDL_Keycode p_key)
|
||||
m_checkmark[0]->Enable(TRUE);
|
||||
}
|
||||
|
||||
m_unk0x280.m_letters[m_unk0x280.m_cursorPos] = key - SDLK_A;
|
||||
m_unk0x280.m_letters[m_unk0x280.m_cursorPos] =
|
||||
key >= SDLK_A && key <= SDLK_Z
|
||||
? key - SDLK_A
|
||||
: (intoAlphabet - m_intAlphabet) + sizeOfArray(m_alphabet) - m_intAlphabetOffset;
|
||||
m_unk0x280.m_cursorPos++;
|
||||
}
|
||||
}
|
||||
@ -224,13 +242,22 @@ MxLong RegistrationBook::HandleKeyPress(SDL_Keycode p_key)
|
||||
MxLong RegistrationBook::HandleControl(LegoControlManagerNotificationParam& p_param)
|
||||
{
|
||||
MxS16 buttonId = p_param.m_unk0x28;
|
||||
const InternationalCharacter* intChar = NULL;
|
||||
|
||||
if (buttonId >= 1 && buttonId <= 28) {
|
||||
for (int i = 0; i < sizeOfArray(m_intAlphabet); i++) {
|
||||
if (m_intAlphabet[i] && LegoGameState::g_intCharacters[i].m_buttonId == buttonId) {
|
||||
intChar = &LegoGameState::g_intCharacters[i];
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if ((buttonId >= 1 && buttonId <= 28) || intChar) {
|
||||
if (p_param.m_clickedObjectId == RegbookScript::c_Alphabet_Ctl) {
|
||||
// buttonId:
|
||||
// - [1, 26]: alphabet
|
||||
// - 27: backspace
|
||||
// - 28: go back to information center
|
||||
// - 29+: international alphabet
|
||||
if (buttonId == 28) {
|
||||
DeleteObjects(&m_atomId, RegbookScript::c_iic006in_RunAnim, RegbookScript::c_iic008in_PlayWav);
|
||||
|
||||
@ -244,11 +271,19 @@ MxLong RegistrationBook::HandleControl(LegoControlManagerNotificationParam& p_pa
|
||||
TransitionManager()->StartTransition(MxTransitionManager::e_mosaic, 50, FALSE, FALSE);
|
||||
}
|
||||
else {
|
||||
if (buttonId > 28) {
|
||||
if (buttonId > 28 && !intChar) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
HandleKeyPress(buttonId < 27 ? SDLK_A + buttonId - 1 : SDLK_BACKSPACE);
|
||||
if (buttonId < 27) {
|
||||
HandleKeyPress(SDLK_A + buttonId - 1);
|
||||
}
|
||||
else if (intChar) {
|
||||
HandleKeyPress((SDL_Keycode) intChar->m_character);
|
||||
}
|
||||
else {
|
||||
HandleKeyPress(SDLK_BACKSPACE);
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
@ -422,6 +457,20 @@ void RegistrationBook::ReadyWorld()
|
||||
}
|
||||
}
|
||||
|
||||
for (i = 0; i < sizeOfArray(m_intAlphabet); i++) {
|
||||
m_intAlphabet[i] = (MxStillPresenter*) Find("MxStillPresenter", LegoGameState::g_intCharacters[i].m_bitmap);
|
||||
}
|
||||
|
||||
m_intAlphabetOffset = 0;
|
||||
for (i = 0; i < sizeOfArray(m_intAlphabet); i++) {
|
||||
if (!m_intAlphabet[i]) {
|
||||
m_intAlphabetOffset++;
|
||||
}
|
||||
else {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// Now we have to do the checkmarks
|
||||
char checkmarkBuffer[] = "Check0_Ctl";
|
||||
for (i = 0; i < 10; i++) {
|
||||
@ -443,8 +492,25 @@ void RegistrationBook::ReadyWorld()
|
||||
m_checkmark[i]->Enable(TRUE);
|
||||
}
|
||||
|
||||
MxStillPresenter** intoAlphabet =
|
||||
[this, index = players[i - 1].m_letters[j]]() mutable -> MxStillPresenter** {
|
||||
if (index < sizeOfArray(m_alphabet)) {
|
||||
return &m_alphabet[index];
|
||||
}
|
||||
|
||||
index -= sizeOfArray(m_alphabet);
|
||||
index += m_intAlphabetOffset;
|
||||
|
||||
if (index >= sizeOfArray(m_intAlphabet) || !m_intAlphabet[index]) {
|
||||
SDL_Log("Warning: international character not present in current game. Falling back to X");
|
||||
return &m_alphabet[SDLK_X - SDLK_A];
|
||||
}
|
||||
|
||||
return &m_intAlphabet[index];
|
||||
}();
|
||||
|
||||
// Start building the player names using a two-dimensional array
|
||||
m_name[i][j] = m_alphabet[players[i - 1].m_letters[j]]->Clone();
|
||||
m_name[i][j] = (*intoAlphabet)->Clone();
|
||||
|
||||
assert(m_name[i][j]);
|
||||
// Enable the presenter to actually show the letter in the grid
|
||||
|
||||
Loading…
Reference in New Issue
Block a user