Merge branch 'rando-next' of github.com:HarbourMasters/Shipwright into color-coded-keys

This commit is contained in:
Christopher Leggett 2022-08-24 13:03:44 -04:00
commit ecd0e3e8bb
No known key found for this signature in database
GPG key ID: 7093AE5FF7037D79
12 changed files with 874 additions and 1581 deletions

View file

@ -461,6 +461,7 @@ namespace SohImGui {
io->ConfigFlags |= ImGuiConfigFlags_DockingEnable; io->ConfigFlags |= ImGuiConfigFlags_DockingEnable;
io->Fonts->AddFontDefault(); io->Fonts->AddFontDefault();
statsWindowOpen = CVar_GetS32("gStatsEnabled", 0); statsWindowOpen = CVar_GetS32("gStatsEnabled", 0);
CVar_RegisterS32("gRandomizeRupeeNames", 1);
CVar_RegisterS32("gRandoRelevantNavi", 1); CVar_RegisterS32("gRandoRelevantNavi", 1);
#ifdef __SWITCH__ #ifdef __SWITCH__
Ship::Switch::SetupFont(io->Fonts); Ship::Switch::SetupFont(io->Fonts);
@ -2000,16 +2001,18 @@ namespace SohImGui {
if (ImGui::BeginMenu("Rando Enhancements")) if (ImGui::BeginMenu("Rando Enhancements"))
{ {
PaddedEnhancementCheckbox("Quest Item Fanfares", "gRandoQuestItemFanfares"); EnhancementCheckbox("Quest Item Fanfares", "gRandoQuestItemFanfares");
Tooltip( Tooltip(
"Play unique fanfares when obtaining quest items\n" "Play unique fanfares when obtaining quest items "
"(medallions/stones/songs). Note that these fanfares\n" "(medallions/stones/songs). Note that these fanfares are longer than usual."
"are longer than usual."
); );
PaddedEnhancementCheckbox("Rando-Relevant Navi Hints", "gRandoRelevantNavi"); PaddedEnhancementCheckbox("Random Rupee Names", "gRandomizeRupeeNames", true, false);
Tooltip( Tooltip(
"Replace Navi's overworld quest hints with rando-\n" "When obtaining rupees, randomize what the rupee is called in the textbox."
"related gameplay hints.\n" );
PaddedEnhancementCheckbox("Rando-Relevant Navi Hints", "gRandoRelevantNavi", true, false);
Tooltip(
"Replace Navi's overworld quest hints with rando-related gameplay hints."
); );
PaddedEnhancementCheckbox("Key Colors Match Dungeon", "gRandoMatchKeyColors", true, false); PaddedEnhancementCheckbox("Key Colors Match Dungeon", "gRandoMatchKeyColors", true, false);
Tooltip( Tooltip(

View file

@ -110,6 +110,9 @@ set(Header_Files__include
"include/ichain.h" "include/ichain.h"
"include/macro.inc" "include/macro.inc"
"include/macros.h" "include/macros.h"
"include/message_data_fmt.h"
"include/message_data_static.h"
"include/message_data_textbox_types.h"
#"include/math_n64.h" #"include/math_n64.h"
"include/regs.h" "include/regs.h"
"include/segment_symbols.h" "include/segment_symbols.h"

View file

@ -3,32 +3,12 @@
#include "global.h" #include "global.h"
#include "message_data_fmt.h" #include "message_data_fmt.h"
#include "message_data_textbox_types.h"
#ifdef __cplusplus #ifdef __cplusplus
extern "C" { extern "C" {
#endif #endif
typedef enum {
/* 0 */ TEXTBOX_TYPE_BLACK,
/* 1 */ TEXTBOX_TYPE_WOODEN,
/* 2 */ TEXTBOX_TYPE_BLUE,
/* 3 */ TEXTBOX_TYPE_OCARINA,
/* 4 */ TEXTBOX_TYPE_NONE_BOTTOM,
/* 5 */ TEXTBOX_TYPE_NONE_NO_SHADOW,
/* 11 */ TEXTBOX_TYPE_CREDITS = 11
} TextBoxType;
typedef enum {
/* 0 */ TEXTBOX_BG_CROSS
} TextBoxBackground;
typedef enum {
/* 0 */ TEXTBOX_POS_VARIABLE,
/* 1 */ TEXTBOX_POS_TOP,
/* 2 */ TEXTBOX_POS_MIDDLE,
/* 3 */ TEXTBOX_POS_BOTTOM
} TextBoxPosition;
typedef struct { typedef struct {
u16 textId; u16 textId;
u8 typePos; u8 typePos;

View file

@ -0,0 +1,25 @@
#ifndef MESSAGE_DATA_TEXTBOX_TYPES_H
#define MESSAGE_DATA_TEXTBOX_TYPES_H
typedef enum {
/* 0 */ TEXTBOX_TYPE_BLACK,
/* 1 */ TEXTBOX_TYPE_WOODEN,
/* 2 */ TEXTBOX_TYPE_BLUE,
/* 3 */ TEXTBOX_TYPE_OCARINA,
/* 4 */ TEXTBOX_TYPE_NONE_BOTTOM,
/* 5 */ TEXTBOX_TYPE_NONE_NO_SHADOW,
/* 11 */ TEXTBOX_TYPE_CREDITS = 11
} TextBoxType;
typedef enum {
/* 0 */ TEXTBOX_BG_CROSS
} TextBoxBackground;
typedef enum {
/* 0 */ TEXTBOX_POS_VARIABLE,
/* 1 */ TEXTBOX_POS_TOP,
/* 2 */ TEXTBOX_POS_MIDDLE,
/* 3 */ TEXTBOX_POS_BOTTOM
} TextBoxPosition;
#endif

View file

@ -2,6 +2,7 @@
#include <string> #include <string>
#include <unordered_map> #include <unordered_map>
#include "../../../include/z64item.h" #include "../../../include/z64item.h"
#include "../../../include/message_data_textbox_types.h"
#undef MESSAGE_END #undef MESSAGE_END
@ -14,31 +15,6 @@
#define QM_YELLOW 0x46 #define QM_YELLOW 0x46
#define QM_BLACK 0x47 #define QM_BLACK 0x47
#ifndef MESSAGE_DATA_STATIC_H
typedef enum {
/* 0 */ TEXTBOX_TYPE_BLACK,
/* 1 */ TEXTBOX_TYPE_WOODEN,
/* 2 */ TEXTBOX_TYPE_BLUE,
/* 3 */ TEXTBOX_TYPE_OCARINA,
/* 4 */ TEXTBOX_TYPE_NONE_BOTTOM,
/* 5 */ TEXTBOX_TYPE_NONE_NO_SHADOW,
/* 11 */ TEXTBOX_TYPE_CREDITS = 11
} TextBoxType;
typedef enum {
/* 0 */ TEXTBOX_BG_CROSS
} TextBoxBackground;
typedef enum {
/* 0 */ TEXTBOX_POS_VARIABLE,
/* 1 */ TEXTBOX_POS_TOP,
/* 2 */ TEXTBOX_POS_MIDDLE,
/* 3 */ TEXTBOX_POS_BOTTOM
} TextBoxPosition;
#endif
typedef struct { typedef struct {
TextBoxType textBoxType; TextBoxType textBoxType;
TextBoxPosition textBoxPos; TextBoxPosition textBoxPos;

View file

@ -11,7 +11,11 @@ typedef enum {
TEXT_ALTAR_CHILD = 0x7040, TEXT_ALTAR_CHILD = 0x7040,
TEXT_ALTAR_ADULT = 0x7088, TEXT_ALTAR_ADULT = 0x7088,
TEXT_GANONDORF = 0x70CC, TEXT_GANONDORF = 0x70CC,
TEXT_GANONDORF_NOHINT = 0x70CD TEXT_GANONDORF_NOHINT = 0x70CD,
TEXT_BLUE_RUPEE = 0xCC,
TEXT_RED_RUPEE = 0xF0,
TEXT_PURPLE_RUPEE = 0xF1,
TEXT_HUGE_RUPEE = 0xF2
} TextIDs; } TextIDs;
#ifdef __cplusplus #ifdef __cplusplus

View file

@ -14,7 +14,6 @@
#include "3drando/rando_main.hpp" #include "3drando/rando_main.hpp"
#include <soh/Enhancements/debugger/ImGuiHelpers.h> #include <soh/Enhancements/debugger/ImGuiHelpers.h>
#include "Lib/ImGui/imgui_internal.h" #include "Lib/ImGui/imgui_internal.h"
#include <soh/Enhancements/custom-message/CustomMessageManager.h>
#include <soh/Enhancements/custom-message/CustomMessageTypes.h> #include <soh/Enhancements/custom-message/CustomMessageTypes.h>
#include <soh/Enhancements/item-tables/ItemTableManager.h> #include <soh/Enhancements/item-tables/ItemTableManager.h>
#include <stdexcept> #include <stdexcept>
@ -34,8 +33,30 @@ u8 generated;
const std::string Randomizer::getItemMessageTableID = "Randomizer"; const std::string Randomizer::getItemMessageTableID = "Randomizer";
const std::string Randomizer::hintMessageTableID = "RandomizerHints"; const std::string Randomizer::hintMessageTableID = "RandomizerHints";
const std::string Randomizer::scrubMessageTableID = "RandomizerScrubs"; const std::string Randomizer::scrubMessageTableID = "RandomizerScrubs";
const std::string Randomizer::rupeeMessageTableID = "RandomizerRupees";
const std::string Randomizer::NaviRandoMessageTableID = "RandomizerNavi"; const std::string Randomizer::NaviRandoMessageTableID = "RandomizerNavi";
static const char* englishRupeeNames[44] = {
"Rupees", "Bitcoin", "Bananas", "Cornflakes", "Gummybears", "Floopies", "Dollars", "Lemmings",
"Emeralds", "Bucks", "Rubles", "Diamonds", "Moons", "Stars", "Mana", "Doll Hairs",
"Dogecoin", "Mushrooms", "Experience", "Friends", "Coins", "Rings", "Gil", "Pokédollars",
"Bells", "Orbs", "Bottle Caps", "Simoleons", "Pokémon", "Toys", "Smackaroos", "Zorkmids",
"Zenny", "Bones", "Souls", "Studs", "Munny", "Rubies", "Gald", "Gold",
"Shillings", "Pounds", "Glimmer", "Potch"
};
static const char* germanRupeeNames[1] = {
"Rubine"
};
static const char* frenchRupeeNames[36] = {
"Rubis", "Bitcoin", "Bananes", "Euros", "Dollars", "Émeraudes", "Joyaux", "Diamants",
"Balles", "Pokémon", "Pièces", "Lunes", "Étoiles", "Dogecoin", "Anneaux", "Radis",
"Pokédollars", "Zennies", "Pépètes", "Mailles", "Éthers", "Clochettes", "Capsules", "Gils",
"Champignons", "Blés", "Halos", "Munnies", "Orens", "Florens", "Crédits", "Galds",
"Bling", "Orbes", "Baguettes", "Croissants"
};
Randomizer::Randomizer() { Randomizer::Randomizer() {
Sprite bowSprite = { dgFairyBowIconTex, 32, 32, G_IM_FMT_RGBA, G_IM_SIZ_32b, 0 }; Sprite bowSprite = { dgFairyBowIconTex, 32, 32, G_IM_FMT_RGBA, G_IM_SIZ_32b, 0 };
gSeedTextures[0] = bowSprite; gSeedTextures[0] = bowSprite;
@ -3716,6 +3737,69 @@ void CreateScrubMessages() {
} }
} }
void CreateRupeeMessages() {
CustomMessageManager* customMessageManager = CustomMessageManager::Instance;
customMessageManager->AddCustomMessageTable(Randomizer::rupeeMessageTableID);
const std::vector<u8> rupees = { TEXT_BLUE_RUPEE, TEXT_RED_RUPEE, TEXT_PURPLE_RUPEE, TEXT_HUGE_RUPEE };
std::string rupeeText = " ";
for (u8 rupee : rupees) {
switch (rupee) {
case TEXT_BLUE_RUPEE:
rupeeText = "\x05\x03 5 #RUPEE#\x05\x00";
break;
case TEXT_RED_RUPEE:
rupeeText = "\x05\x01 20 #RUPEE#\x05\x00";
break;
case TEXT_PURPLE_RUPEE:
rupeeText = "\x05\x05 50 #RUPEE#\x05\x00";
break;
case TEXT_HUGE_RUPEE:
rupeeText = "\x05\x06 200 #RUPEE#\x05\x00";
break;
}
customMessageManager->CreateMessage(Randomizer::rupeeMessageTableID, rupee,
{ TEXTBOX_TYPE_BLACK, TEXTBOX_POS_BOTTOM,
"You found" + rupeeText + " !",
"Du hast" + rupeeText + " gefunden!",
"Vous obtenez" + rupeeText + " !"
});
}
}
std::string Randomizer::RandomizeRupeeName(std::string message, int language) {
int randomIndex;
std::string replaceWith;
switch (language) {
case LANGUAGE_ENG:
randomIndex = rand() % (sizeof(englishRupeeNames) / sizeof(englishRupeeNames[0]));
replaceWith = englishRupeeNames[randomIndex];
break;
case LANGUAGE_GER:
randomIndex = rand() % (sizeof(germanRupeeNames) / sizeof(germanRupeeNames[0]));
replaceWith = germanRupeeNames[randomIndex];
break;
case LANGUAGE_FRA:
randomIndex = rand() % (sizeof(frenchRupeeNames) / sizeof(frenchRupeeNames[0]));
replaceWith = frenchRupeeNames[randomIndex];
break;
}
std::string replaceString = "#RUPEE#";
size_t pos = message.find(replaceString);
size_t len = replaceString.length();
message.replace(pos, len, replaceWith);
CustomMessageManager::Instance->FormatCustomMessage(message);
return message;
}
CustomMessageEntry Randomizer::GetRupeeMessage(u16 rupeeTextId) {
CustomMessageEntry messageEntry =
CustomMessageManager::Instance->RetrieveMessage(Randomizer::rupeeMessageTableID, rupeeTextId);
messageEntry.english = Randomizer::RandomizeRupeeName(messageEntry.english, LANGUAGE_ENG);
messageEntry.german = Randomizer::RandomizeRupeeName(messageEntry.german, LANGUAGE_GER);
messageEntry.french = Randomizer::RandomizeRupeeName(messageEntry.french, LANGUAGE_FRA);
return messageEntry;
}
CustomMessageMinimal NaviMessages[NUM_NAVI_MESSAGES] = { CustomMessageMinimal NaviMessages[NUM_NAVI_MESSAGES] = {
{ "%cMissing a small key in a dungeon?&Maybe the %rboss %chas it!", { "%cMissing a small key in a dungeon?&Maybe the %rboss %chas it!",
@ -3864,6 +3948,7 @@ void Randomizer::CreateCustomMessages() {
}; };
CreateGetItemMessages(getItemMessages); CreateGetItemMessages(getItemMessages);
CreateScrubMessages(); CreateScrubMessages();
CreateRupeeMessages();
CreateNaviRandoMessages(); CreateNaviRandoMessages();
} }

View file

@ -6,6 +6,7 @@
#include "../../../include/z64item.h" #include "../../../include/z64item.h"
#include <memory> #include <memory>
#include <soh/Enhancements/randomizer/randomizerTypes.h> #include <soh/Enhancements/randomizer/randomizerTypes.h>
#include <soh/Enhancements/custom-message/CustomMessageManager.h>
#define NUM_NAVI_MESSAGES 15 #define NUM_NAVI_MESSAGES 15
@ -33,6 +34,7 @@ class Randomizer {
static const std::string getItemMessageTableID; static const std::string getItemMessageTableID;
static const std::string hintMessageTableID; static const std::string hintMessageTableID;
static const std::string scrubMessageTableID; static const std::string scrubMessageTableID;
static const std::string rupeeMessageTableID;
static const std::string NaviRandoMessageTableID; static const std::string NaviRandoMessageTableID;
static Sprite* GetSeedTexture(uint8_t index); static Sprite* GetSeedTexture(uint8_t index);
@ -51,6 +53,8 @@ class Randomizer {
s16 GetRandomizedItemIdFromKnownCheck(RandomizerCheck randomizerCheck, GetItemID ogId); s16 GetRandomizedItemIdFromKnownCheck(RandomizerCheck randomizerCheck, GetItemID ogId);
s16 GetRandomizedItemId(GetItemID ogId, s16 actorId, s16 actorParams, s16 sceneNum); s16 GetRandomizedItemId(GetItemID ogId, s16 actorId, s16 actorParams, s16 sceneNum);
static void CreateCustomMessages(); static void CreateCustomMessages();
static std::string RandomizeRupeeName(std::string message, int language);
static CustomMessageEntry GetRupeeMessage(u16 rupeeTextId);
bool CheckContainsVanillaItem(RandomizerCheck randoCheck); bool CheckContainsVanillaItem(RandomizerCheck randoCheck);
}; };

File diff suppressed because it is too large Load diff

View file

@ -1,5 +1,26 @@
#pragma once #pragma once
#include <string>
#include <vector>
void InitItemTracker(); void InitItemTracker();
void DrawItemTracker(bool& open); void DrawItemTracker(bool& open);
void DrawItemAmmo(int itemId); void DrawItemAmmo(int itemId);
typedef struct ItemTrackerItem {
uint32_t id;
std::string name;
std::string nameFaded;
uint32_t data;
void (*drawFunc)(ItemTrackerItem);
} ItemTrackerItem;
#define ITEM_TRACKER_ITEM(id, data, drawFunc) \
{ \
id, #id, #id "_Faded", data, drawFunc \
}
typedef struct ItemTrackerDungeon {
uint32_t id;
std::vector<uint32_t> items;
} ItemTrackerDungeon;

View file

@ -33,6 +33,7 @@
#include "Enhancements/cosmetics/CosmeticsEditor.h" #include "Enhancements/cosmetics/CosmeticsEditor.h"
#include "Enhancements/debugconsole.h" #include "Enhancements/debugconsole.h"
#include "Enhancements/debugger/debugger.h" #include "Enhancements/debugger/debugger.h"
#include <soh/Enhancements/randomizer/randomizer.h>
#include <soh/Enhancements/randomizer/randomizer_item_tracker.h> #include <soh/Enhancements/randomizer/randomizer_item_tracker.h>
#include "Enhancements/n64_weird_frame_data.inc" #include "Enhancements/n64_weird_frame_data.inc"
#include "soh/frame_interpolation.h" #include "soh/frame_interpolation.h"
@ -1719,6 +1720,10 @@ extern "C" int CustomMessage_RetrieveIfExists(GlobalContext* globalCtx) {
} }
} else if (textId == TEXT_SCRUB_POH || textId == TEXT_SCRUB_STICK_UPGRADE || textId == TEXT_SCRUB_NUT_UPGRADE) { } else if (textId == TEXT_SCRUB_POH || textId == TEXT_SCRUB_STICK_UPGRADE || textId == TEXT_SCRUB_NUT_UPGRADE) {
messageEntry = Randomizer_GetScrubMessage(textId); messageEntry = Randomizer_GetScrubMessage(textId);
} else if (CVar_GetS32("gRandomizeRupeeNames", 0) &&
(textId == TEXT_BLUE_RUPEE || textId == TEXT_RED_RUPEE || textId == TEXT_PURPLE_RUPEE ||
textId == TEXT_HUGE_RUPEE)) {
messageEntry = Randomizer::GetRupeeMessage(textId);
// In rando, replace Navi's general overworld hints with rando-related gameplay tips // In rando, replace Navi's general overworld hints with rando-related gameplay tips
} else if (CVar_GetS32("gRandoRelevantNavi", 1) && textId >= 0x0140 && textId <= 0x015F) { } else if (CVar_GetS32("gRandoRelevantNavi", 1) && textId >= 0x0140 && textId <= 0x015F) {
messageEntry = Randomizer_GetNaviMessage(); messageEntry = Randomizer_GetNaviMessage();
@ -1751,7 +1756,6 @@ extern "C" int CustomMessage_RetrieveIfExists(GlobalContext* globalCtx) {
case LANGUAGE_GER: case LANGUAGE_GER:
return msgCtx->msgLength = font->msgLength = return msgCtx->msgLength = font->msgLength =
CopyStringToCharBuffer(messageEntry.german, buffer, maxBufferSize); CopyStringToCharBuffer(messageEntry.german, buffer, maxBufferSize);
case LANGUAGE_ENG: case LANGUAGE_ENG:
default: default:
return msgCtx->msgLength = font->msgLength = return msgCtx->msgLength = font->msgLength =

View file

@ -6165,7 +6165,7 @@ s32 func_8083E5A8(Player* this, GlobalContext* globalCtx) {
} }
} else if (CHECK_BTN_ALL(sControlInput->press.button, BTN_A) && !(this->stateFlags1 & PLAYER_STATE1_11) && } else if (CHECK_BTN_ALL(sControlInput->press.button, BTN_A) && !(this->stateFlags1 & PLAYER_STATE1_11) &&
!(this->stateFlags2 & PLAYER_STATE2_10)) { !(this->stateFlags2 & PLAYER_STATE2_10)) {
if (this->getItemId != GI_NONE || this->getItemEntry.objectId != OBJECT_INVALID) { if (this->getItemId != GI_NONE && this->getItemEntry.objectId != OBJECT_INVALID) {
GetItemEntry giEntry; GetItemEntry giEntry;
if (this->getItemEntry.objectId == OBJECT_INVALID) { if (this->getItemEntry.objectId == OBJECT_INVALID) {
giEntry = ItemTable_Retrieve(-this->getItemId); giEntry = ItemTable_Retrieve(-this->getItemId);
@ -9687,8 +9687,8 @@ void func_808473D4(GlobalContext* globalCtx, Player* this) {
else if ((!(this->stateFlags1 & PLAYER_STATE1_11) || (heldActor == NULL)) && else if ((!(this->stateFlags1 & PLAYER_STATE1_11) || (heldActor == NULL)) &&
(interactRangeActor != NULL) && (interactRangeActor != NULL) &&
((!sp1C && (this->getItemId == GI_NONE)) || ((!sp1C && (this->getItemId == GI_NONE)) ||
((this->getItemId < 0 || this->getItemEntry.getItemId < 0) && !(this->stateFlags1 & PLAYER_STATE1_27)))) { ((this->getItemId < 0 && this->getItemEntry.getItemId < 0) && !(this->stateFlags1 & PLAYER_STATE1_27)))) {
if (this->getItemId < 0 || this->getItemEntry.getItemId < 0) { if (this->getItemId < 0 && this->getItemEntry.getItemId < 0) {
doAction = DO_ACTION_OPEN; doAction = DO_ACTION_OPEN;
} else if ((interactRangeActor->id == ACTOR_BG_TOKI_SWD) && LINK_IS_ADULT) { } else if ((interactRangeActor->id == ACTOR_BG_TOKI_SWD) && LINK_IS_ADULT) {
doAction = DO_ACTION_DROP; doAction = DO_ACTION_DROP;
@ -9744,7 +9744,7 @@ void func_808473D4(GlobalContext* globalCtx, Player* this) {
} }
} }
else if (!(this->stateFlags1 & PLAYER_STATE1_27) && func_8083A0D4(this) && else if (!(this->stateFlags1 & PLAYER_STATE1_27) && func_8083A0D4(this) &&
((!gSaveContext.n64ddFlag && this->getItemId < GI_MAX) || (gSaveContext.n64ddFlag && this->getItemEntry.getItemId < RG_MAX))) { (this->getItemId < GI_MAX)) {
doAction = DO_ACTION_GRAB; doAction = DO_ACTION_GRAB;
} }
else if (this->stateFlags2 & PLAYER_STATE2_11) { else if (this->stateFlags2 & PLAYER_STATE2_11) {