mirror of
https://github.com/HarbourMasters/Shipwright.git
synced 2025-02-22 05:31:54 -05:00
Merge branch 'rando-next' of github.com:HarbourMasters/Shipwright into magic-bean-pack
This commit is contained in:
commit
78e506a072
37
README.md
37
README.md
@ -31,10 +31,10 @@ Congratulations, you are now sailing with the Ship of Harkinian! Have fun!
|
||||
|
||||
The Ship of Harkinian uses a proprietary versioning system consisting of a sci-fi film character followed by a phonetic alphabet code word. The film character represents a major release version which increments with the addition of many new features and bug fixes. The code word represents a minor release version which increments with small updates mainly comprised of bug fixes. For example, `DECKARD ALFA`.
|
||||
|
||||
### The Extraction Tool
|
||||
### Windows Rom Extraction
|
||||
|
||||
* Open a rom to initiate generating the `oot.otr` archive file.
|
||||
* If a second button exists then `oot.otr` already exists. To prevent overwriting the old `oot.otr` use this button to choose a new game directory. The new directory must not already contain an `oot.otr` to prevent an error.
|
||||
* Open OTRGui.exe, and select one of the supported roms listed above, to generate the `oot.otr` archive file.
|
||||
* If a second button already exits then `oot.otr` already exists. To prevent overwriting the old `oot.otr` use this button to choose a new game directory. The new directory must not already contain an `oot.otr` to prevent an error.
|
||||
* When the process completes, place `oot.otr` beside `soh.exe` if it is not already.
|
||||
|
||||
This packaging process can take up to **5 minutes**.
|
||||
@ -42,6 +42,37 @@ This packaging process can take up to **5 minutes**.
|
||||
Close the OTRGui when the `Done!` message appears.
|
||||
If you get another message, then you might have selected the wrong rom. Make sure to use a rom consistent with the above checksum.
|
||||
|
||||
### Linux Rom Extraction
|
||||
|
||||
* Place one of the supported roms in the same folder as the appimage.
|
||||
* When you run the soh appimage, it should begin generating the `oot.otr` archive file.
|
||||
* When the process completes, place `oot.otr` in the same folder as the appimage, if it is not already, then run the appimage.
|
||||
|
||||
The packaging process can take up to **5 minutes**.
|
||||
|
||||
If you get any errors, then you might have selected the wrong rom. Make sure to use a rom consistent with the above checksum.
|
||||
|
||||
### MacOS Rom Extraction
|
||||
|
||||
* Run `soh.app`, and when prompted, select one of the supported roms listed above.
|
||||
* You should see a notification saying `Processing OTR`, then, once the process is complete, you should get a notification saying `OTR Successfully Generated`, then the game should start.
|
||||
|
||||
The packing process can take up to **5 minutes**.
|
||||
|
||||
If you get an error saying `Incompatible ROM hash`, you have selected the wrong rom, make sure the checksum matches one of the ones listed above.
|
||||
|
||||
### Nintendo Switch Rom Extraction
|
||||
|
||||
* Download the latest PC release of the Ship of Harkinian, and follow the instructions above for generating the `oot.otr` archive on that platform.
|
||||
* Place the `.nro` and the `oot.otr` archive into a folder called `soh` in your Switch folder on your Switch
|
||||
|
||||
### Nintendo Wii U Rom Extraction
|
||||
|
||||
* Download the latest PC release of the Ship of Harkinian, and follow the instructions above for generating the `oot.otr` archive on that platform.
|
||||
* Copy the `.rpx` and the `oot.otr` archive to `wiiu/apps/soh`
|
||||
|
||||
---
|
||||
|
||||
If you still cannot get the tool to work, join our [Discord Server](https://discord.com/invite/BtBmd55HVH) and ask for help in the `#support` text channel. Keep-in-mind that we do not condone piracy in any way.
|
||||
|
||||
### Running The Ship of Harkinian
|
||||
|
@ -87,6 +87,7 @@ set(Source_Files__Controller
|
||||
"KeyboardController.cpp"
|
||||
"KeyboardController.h"
|
||||
"UltraController.h"
|
||||
"DummyController.cpp"
|
||||
"DummyController.h"
|
||||
)
|
||||
|
||||
|
@ -389,4 +389,20 @@ namespace Ship {
|
||||
Commands[command] = entry;
|
||||
}
|
||||
}
|
||||
|
||||
std::string Console::GetCurrentChannel() {
|
||||
return currentChannel;
|
||||
}
|
||||
|
||||
bool Console::IsOpened() {
|
||||
return opened;
|
||||
}
|
||||
|
||||
void Console::Close() {
|
||||
opened = false;
|
||||
}
|
||||
|
||||
void Console::Open() {
|
||||
opened = true;
|
||||
}
|
||||
}
|
@ -93,10 +93,9 @@ namespace Ship {
|
||||
void Append(const std::string& channel, spdlog::level::level_enum priority, const char* fmt, ...);
|
||||
bool HasCommand(const std::string& command);
|
||||
void AddCommand(const std::string& command, CommandEntry entry);
|
||||
|
||||
std::string GetCurrentChannel() { return currentChannel; }
|
||||
bool IsOpened() { return opened; }
|
||||
void Close() { opened = false; }
|
||||
void Open() { opened = true; }
|
||||
std::string GetCurrentChannel();
|
||||
bool IsOpened();
|
||||
void Close();
|
||||
void Open();
|
||||
};
|
||||
}
|
@ -21,7 +21,7 @@ namespace Ship {
|
||||
size_t GetNumVirtualDevices();
|
||||
uint8_t* GetControllerBits();
|
||||
private:
|
||||
std::vector<int> virtualDevices = {};
|
||||
std::vector<int32_t> virtualDevices = {};
|
||||
std::vector<std::shared_ptr<Controller>> physicalDevices = {};
|
||||
uint8_t* controllerBits = nullptr;
|
||||
};
|
||||
|
@ -112,4 +112,16 @@ namespace Ship {
|
||||
std::shared_ptr<DeviceProfile> Controller::getProfile(int32_t virtualSlot) {
|
||||
return profiles[virtualSlot];
|
||||
}
|
||||
|
||||
std::shared_ptr<ControllerAttachment> Controller::GetAttachment() {
|
||||
return Attachment;
|
||||
}
|
||||
|
||||
bool Controller::IsRumbling() {
|
||||
return isRumbling;
|
||||
}
|
||||
|
||||
std::string Controller::GetGuid() {
|
||||
return GUID;
|
||||
}
|
||||
}
|
||||
|
@ -40,7 +40,6 @@ namespace Ship {
|
||||
public:
|
||||
virtual ~Controller() = default;
|
||||
Controller();
|
||||
void Read(OSContPad* pad, int32_t virtualSlot);
|
||||
virtual void ReadFromSource(int32_t virtualSlot) = 0;
|
||||
virtual void WriteToSource(int32_t virtualSlot, ControllerCallback* controller) = 0;
|
||||
virtual bool Connected() const = 0;
|
||||
@ -49,8 +48,12 @@ namespace Ship {
|
||||
virtual void CreateDefaultBinding(int32_t virtualSlot) = 0;
|
||||
virtual void ClearRawPress() = 0;
|
||||
virtual int32_t ReadRawPress() = 0;
|
||||
virtual const std::string GetButtonName(int32_t virtualSlot, int32_t n64Button) = 0;
|
||||
virtual const std::string GetControllerName() = 0;
|
||||
void Read(OSContPad* pad, int32_t virtualSlot);
|
||||
void SetButtonMapping(int32_t virtualSlot, int32_t n64Button, int32_t dwScancode);
|
||||
std::shared_ptr<ControllerAttachment> GetAttachment() { return Attachment; }
|
||||
std::shared_ptr<ControllerAttachment> GetAttachment();
|
||||
std::shared_ptr<DeviceProfile> getProfile(int32_t virtualSlot);
|
||||
int8_t& getLeftStickX(int32_t virtualSlot);
|
||||
int8_t& getLeftStickY(int32_t virtualSlot);
|
||||
int8_t& getRightStickX(int32_t virtualSlot);
|
||||
@ -58,11 +61,8 @@ namespace Ship {
|
||||
int32_t& getPressedButtons(int32_t virtualSlot);
|
||||
float& getGyroX(int32_t virtualSlot);
|
||||
float& getGyroY(int32_t virtualSlot);
|
||||
std::shared_ptr<DeviceProfile> getProfile(int32_t virtualSlot);
|
||||
bool IsRumbling() { return isRumbling; }
|
||||
std::string GetGuid() { return GUID; }
|
||||
virtual const std::string GetButtonName(int32_t virtualSlot, int32_t n64Button) = 0;
|
||||
virtual const std::string GetControllerName() = 0;
|
||||
bool IsRumbling();
|
||||
std::string GetGuid();
|
||||
|
||||
protected:
|
||||
std::shared_ptr<ControllerAttachment> Attachment;
|
||||
|
@ -251,9 +251,9 @@ extern "C" void CVar_Save()
|
||||
auto keyStr = key.c_str();
|
||||
Color_RGBA8 clr = cvar.second->value.valueRGBA;
|
||||
pConf->setUInt(StringHelper::Sprintf("%s.R", keyStr), clr.r);
|
||||
pConf->setUInt(StringHelper::Sprintf("%s.G", keyStr), clr.r);
|
||||
pConf->setUInt(StringHelper::Sprintf("%s.B", keyStr), clr.r);
|
||||
pConf->setUInt(StringHelper::Sprintf("%s.A", keyStr), clr.r);
|
||||
pConf->setUInt(StringHelper::Sprintf("%s.G", keyStr), clr.g);
|
||||
pConf->setUInt(StringHelper::Sprintf("%s.B", keyStr), clr.b);
|
||||
pConf->setUInt(StringHelper::Sprintf("%s.A", keyStr), clr.a);
|
||||
pConf->setString(StringHelper::Sprintf("%s.Type", keyStr), mercuryRGBAObjectType);
|
||||
}
|
||||
}
|
||||
|
61
libultraship/libultraship/DummyController.cpp
Normal file
61
libultraship/libultraship/DummyController.cpp
Normal file
@ -0,0 +1,61 @@
|
||||
#include "DummyController.h"
|
||||
|
||||
namespace Ship {
|
||||
DummyController::DummyController(const std::string& CUID, const std::string& KeyName, bool Connected) {
|
||||
GUID = CUID;
|
||||
isConnected = Connected;
|
||||
ButtonName = KeyName;
|
||||
}
|
||||
|
||||
void DummyController::ReadFromSource(int32_t virtualSlot) {
|
||||
|
||||
}
|
||||
|
||||
const std::string DummyController::GetControllerName() {
|
||||
return GUID;
|
||||
}
|
||||
|
||||
const std::string DummyController::GetButtonName(int32_t virtualSlot, int32_t n64Button) {
|
||||
return ButtonName;
|
||||
}
|
||||
|
||||
void DummyController::WriteToSource(int32_t virtualSlot, ControllerCallback* controller){
|
||||
|
||||
}
|
||||
|
||||
bool DummyController::Connected() const {
|
||||
return isConnected;
|
||||
}
|
||||
|
||||
bool DummyController::CanRumble() const {
|
||||
return false;
|
||||
}
|
||||
|
||||
bool DummyController::CanGyro() const {
|
||||
return false;
|
||||
}
|
||||
|
||||
void DummyController::CreateDefaultBinding(int32_t slot) {
|
||||
|
||||
}
|
||||
|
||||
std::string DummyController::GetControllerType() {
|
||||
return "Unk";
|
||||
}
|
||||
|
||||
std::string DummyController::GetConfSection() {
|
||||
return "Unk";
|
||||
}
|
||||
|
||||
std::string DummyController::GetBindingConfSection() {
|
||||
return "Unk";
|
||||
}
|
||||
|
||||
void DummyController::ClearRawPress() {
|
||||
|
||||
}
|
||||
|
||||
int32_t DummyController::ReadRawPress() {
|
||||
return -1;
|
||||
}
|
||||
}
|
@ -7,31 +7,25 @@
|
||||
namespace Ship {
|
||||
class DummyController final : public Controller {
|
||||
public:
|
||||
DummyController(const std::string& CUID, const std::string& KeyName, bool Connected) {
|
||||
GUID = CUID;
|
||||
isConnected = Connected;
|
||||
ButtonName = KeyName;
|
||||
}
|
||||
|
||||
DummyController(const std::string& CUID, const std::string& KeyName, bool Connected);
|
||||
std::map<std::vector<std::string>, int32_t> ReadButtonPress();
|
||||
void ReadFromSource(int32_t slot) override {}
|
||||
const std::string GetControllerName() override { return GUID; }
|
||||
const std::string GetButtonName(int slot, int n64Button) override { return ButtonName; }
|
||||
void WriteToSource(int32_t slot, ControllerCallback* controller) override { }
|
||||
bool Connected() const override { return isConnected; }
|
||||
bool CanRumble() const override { return false; }
|
||||
bool CanGyro() const override { return false; }
|
||||
|
||||
void ClearRawPress() override {}
|
||||
int32_t ReadRawPress() override { return -1; }
|
||||
bool HasPadConf() const { return true; }
|
||||
std::optional<std::string> GetPadConfSection() { return "Unk"; }
|
||||
void CreateDefaultBinding(int32_t slot) override {}
|
||||
void ReadFromSource(int32_t virtualSlot) override;
|
||||
const std::string GetControllerName() override;
|
||||
const std::string GetButtonName(int32_t virtualSlot, int32_t n64Button) override;
|
||||
void WriteToSource(int32_t slot, ControllerCallback* controller) override;
|
||||
bool Connected() const override;
|
||||
bool CanRumble() const override;
|
||||
bool CanGyro() const override;
|
||||
void ClearRawPress() override;
|
||||
int32_t ReadRawPress() override;
|
||||
bool HasPadConf() const;
|
||||
std::optional<std::string> GetPadConfSection();
|
||||
void CreateDefaultBinding(int32_t virtualSlot) override;
|
||||
protected:
|
||||
std::string ButtonName;
|
||||
bool isConnected = false;
|
||||
std::string GetControllerType() { return "Unk"; }
|
||||
std::string GetConfSection() { return "Unk"; }
|
||||
std::string GetBindingConfSection() { return "Unk"; }
|
||||
std::string GetControllerType();
|
||||
std::string GetConfSection();
|
||||
std::string GetBindingConfSection();
|
||||
};
|
||||
}
|
5
libultraship/libultraship/Hooks.cpp
Normal file
5
libultraship/libultraship/Hooks.cpp
Normal file
@ -0,0 +1,5 @@
|
||||
#include "Hooks.h"
|
||||
|
||||
namespace Ship {
|
||||
|
||||
}
|
@ -2001,18 +2001,21 @@ namespace SohImGui {
|
||||
|
||||
if (ImGui::BeginMenu("Rando Enhancements"))
|
||||
{
|
||||
EnhancementCheckbox("Quest Item Fanfares", "gRandoQuestItemFanfares");
|
||||
EnhancementCheckbox("Rando-Relevant Navi Hints", "gRandoRelevantNavi");
|
||||
Tooltip(
|
||||
"Play unique fanfares when obtaining quest items "
|
||||
"(medallions/stones/songs). Note that these fanfares are longer than usual."
|
||||
"Replace Navi's overworld quest hints with rando-related gameplay hints."
|
||||
);
|
||||
PaddedEnhancementCheckbox("Random Rupee Names", "gRandomizeRupeeNames", true, false);
|
||||
Tooltip(
|
||||
"When obtaining rupees, randomize what the rupee is called in the textbox."
|
||||
);
|
||||
PaddedEnhancementCheckbox("Rando-Relevant Navi Hints", "gRandoRelevantNavi", true, false);
|
||||
PaddedEnhancementCheckbox("Key Colors Match Dungeon", "gRandoMatchKeyColors", true, false);
|
||||
Tooltip(
|
||||
"Replace Navi's overworld quest hints with rando-related gameplay hints."
|
||||
"Matches the color of small keys and boss keys to the dungeon they belong to. This helps identify keys from afar and adds a little bit of flair.");
|
||||
PaddedEnhancementCheckbox("Quest Item Fanfares", "gRandoQuestItemFanfares", true, false);
|
||||
Tooltip(
|
||||
"Play unique fanfares when obtaining quest items "
|
||||
"(medallions/stones/songs). Note that these fanfares are longer than usual."
|
||||
);
|
||||
ImGui::EndMenu();
|
||||
}
|
||||
|
@ -7,7 +7,7 @@
|
||||
#endif
|
||||
|
||||
#include "Hooks.h"
|
||||
|
||||
|
||||
#include "Window.h"
|
||||
|
||||
namespace Ship {
|
||||
@ -100,4 +100,28 @@ namespace Ship {
|
||||
const std::string KeyboardController::GetControllerName() {
|
||||
return "Keyboard";
|
||||
}
|
||||
|
||||
bool KeyboardController::Connected() const {
|
||||
return true;
|
||||
}
|
||||
|
||||
bool KeyboardController::CanRumble() const {
|
||||
return false;
|
||||
}
|
||||
|
||||
bool KeyboardController::CanGyro() const {
|
||||
return false;
|
||||
}
|
||||
|
||||
void KeyboardController::ClearRawPress() {
|
||||
lastKey = -1;
|
||||
}
|
||||
|
||||
void KeyboardController::SetLastScancode(int32_t key) {
|
||||
lastScancode = key;
|
||||
}
|
||||
|
||||
int32_t KeyboardController::GetLastScancode() {
|
||||
return lastScancode;
|
||||
}
|
||||
}
|
||||
|
@ -9,26 +9,18 @@ namespace Ship {
|
||||
|
||||
void ReadFromSource(int32_t virtualSlot) override;
|
||||
void WriteToSource(int32_t virtualSlot, ControllerCallback* controller) override;
|
||||
bool Connected() const override { return true; }
|
||||
bool CanRumble() const override { return false; }
|
||||
bool CanGyro() const override { return false; }
|
||||
const std::string GetControllerName() override;
|
||||
const std::string GetButtonName(int32_t virtualSlot, int32_t n64Button) override;
|
||||
bool PressButton(int32_t dwScancode);
|
||||
bool ReleaseButton(int32_t dwScancode);
|
||||
|
||||
void ClearRawPress() override {
|
||||
lastKey = -1;
|
||||
}
|
||||
|
||||
bool Connected() const override;
|
||||
bool CanRumble() const override;
|
||||
bool CanGyro() const override;
|
||||
void ClearRawPress() override;
|
||||
int32_t ReadRawPress() override;
|
||||
void ReleaseAllButtons();
|
||||
|
||||
void SetLastScancode(int32_t key) {
|
||||
lastScancode = key;
|
||||
}
|
||||
|
||||
int32_t GetLastScancode() { return lastScancode; }
|
||||
void SetLastScancode(int32_t key);
|
||||
int32_t GetLastScancode();
|
||||
void CreateDefaultBinding(int32_t virtualSlot) override;
|
||||
|
||||
protected:
|
||||
|
@ -333,4 +333,17 @@ namespace Ship {
|
||||
const std::string* ResourceMgr::HashToString(uint64_t Hash) const {
|
||||
return OTR->HashToString(Hash);
|
||||
}
|
||||
|
||||
std::shared_ptr<Archive> ResourceMgr::GetArchive() {
|
||||
return OTR;
|
||||
}
|
||||
|
||||
std::shared_ptr<Window> ResourceMgr::GetContext() {
|
||||
return Context;
|
||||
}
|
||||
|
||||
std::shared_ptr<Resource> ResourceMgr::LoadResource(const std::string& FilePath) {
|
||||
return LoadResource(FilePath.c_str());
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -23,20 +23,17 @@ namespace Ship {
|
||||
bool IsRunning();
|
||||
bool DidLoadSuccessfully();
|
||||
|
||||
std::shared_ptr<Archive> GetArchive() { return OTR; }
|
||||
std::shared_ptr<Window> GetContext() { return Context; }
|
||||
|
||||
std::shared_ptr<Archive> GetArchive();
|
||||
std::shared_ptr<Window> GetContext();
|
||||
const std::string* HashToString(uint64_t Hash) const;
|
||||
|
||||
void InvalidateResourceCache();
|
||||
|
||||
uint32_t GetGameVersion();
|
||||
void SetGameVersion(uint32_t newGameVersion);
|
||||
std::shared_ptr<File> LoadFileAsync(const std::string& FilePath);
|
||||
std::shared_ptr<File> LoadFile(const std::string& FilePath);
|
||||
std::shared_ptr<Resource> GetCachedFile(const char* FilePath) const;
|
||||
std::shared_ptr<Resource> LoadResource(const char* FilePath);
|
||||
std::shared_ptr<Resource> LoadResource(const std::string& FilePath) { return LoadResource(FilePath.c_str()); }
|
||||
std::shared_ptr<Resource> LoadResource(const std::string& FilePath);
|
||||
std::variant<std::shared_ptr<Resource>, std::shared_ptr<ResourcePromise>> LoadResourceAsync(const char* FilePath);
|
||||
std::shared_ptr<std::vector<std::shared_ptr<Resource>>> CacheDirectory(const std::string& SearchMask);
|
||||
std::shared_ptr<std::vector<std::shared_ptr<ResourcePromise>>> CacheDirectoryAsync(const std::string& SearchMask);
|
||||
|
@ -12,6 +12,10 @@ extern "C" uint8_t __osMaxControllers;
|
||||
|
||||
namespace Ship {
|
||||
|
||||
SDLController::SDLController(int32_t physicalSlot) : Controller(), Cont(nullptr), physicalSlot(physicalSlot) {
|
||||
|
||||
}
|
||||
|
||||
bool SDLController::Open() {
|
||||
const auto NewCont = SDL_GameControllerOpen(physicalSlot);
|
||||
|
||||
@ -450,4 +454,23 @@ namespace Ship {
|
||||
profile->GyroData[DRIFT_Y] = 0.0f;
|
||||
profile->GyroData[GYRO_SENSITIVITY] = 1.0f;
|
||||
}
|
||||
|
||||
bool SDLController::Connected() const {
|
||||
return Cont != nullptr;
|
||||
}
|
||||
|
||||
bool SDLController::CanGyro() const {
|
||||
return supportsGyro;
|
||||
}
|
||||
|
||||
bool SDLController::CanRumble() const {
|
||||
#if SDL_COMPILEDVERSION >= SDL_VERSIONNUM(2,0,18)
|
||||
return SDL_GameControllerHasRumble(Cont);
|
||||
#endif
|
||||
return false;
|
||||
}
|
||||
|
||||
void SDLController::ClearRawPress() {
|
||||
|
||||
}
|
||||
}
|
||||
|
@ -5,6 +5,19 @@
|
||||
namespace Ship {
|
||||
class SDLController : public Controller {
|
||||
public:
|
||||
SDLController(int32_t physicalSlot);
|
||||
void ReadFromSource(int32_t virtualSlot) override;
|
||||
const std::string GetControllerName() override;
|
||||
const std::string GetButtonName(int32_t virtualSlot, int32_t n64Button) override;
|
||||
void WriteToSource(int32_t virtualSlot, ControllerCallback* controller) override;
|
||||
bool Connected() const override;
|
||||
bool CanGyro() const override;
|
||||
bool CanRumble() const override;
|
||||
bool Open();
|
||||
void ClearRawPress() override;
|
||||
int32_t ReadRawPress() override;
|
||||
|
||||
protected:
|
||||
inline static const char* AxisNames[] = {
|
||||
"Left Stick X",
|
||||
"Left Stick Y",
|
||||
@ -15,25 +28,6 @@ namespace Ship {
|
||||
"Start Button"
|
||||
};
|
||||
|
||||
SDLController(int32_t physicalSlot) : Controller(), Cont(nullptr), physicalSlot(physicalSlot) { }
|
||||
void ReadFromSource(int32_t virtualSlot) override;
|
||||
const std::string GetControllerName() override;
|
||||
const std::string GetButtonName(int32_t virtualSlot, int32_t n64Button) override;
|
||||
void WriteToSource(int32_t virtualSlot, ControllerCallback* controller) override;
|
||||
bool Connected() const override { return Cont != nullptr; }
|
||||
bool CanGyro() const override { return supportsGyro; }
|
||||
bool CanRumble() const override {
|
||||
#if SDL_COMPILEDVERSION >= SDL_VERSIONNUM(2,0,18)
|
||||
return SDL_GameControllerHasRumble(Cont);
|
||||
#endif
|
||||
return false;
|
||||
}
|
||||
|
||||
bool Open();
|
||||
void ClearRawPress() override {}
|
||||
int32_t ReadRawPress() override;
|
||||
|
||||
protected:
|
||||
void CreateDefaultBinding(int32_t virtualSlot) override;
|
||||
|
||||
private:
|
||||
|
@ -581,4 +581,52 @@ namespace Ship {
|
||||
|
||||
saveFile.close();
|
||||
}
|
||||
|
||||
bool Window::IsFullscreen() {
|
||||
return bIsFullscreen;
|
||||
}
|
||||
|
||||
uint32_t Window::GetMenuBar() {
|
||||
return dwMenubar;
|
||||
}
|
||||
|
||||
void Window::SetMenuBar(uint32_t dwMenuBar) {
|
||||
this->dwMenubar = dwMenuBar;
|
||||
}
|
||||
|
||||
std::string Window::GetName() {
|
||||
return Name;
|
||||
}
|
||||
|
||||
std::shared_ptr<ControlDeck> Window::GetControlDeck() {
|
||||
return ControllerApi;
|
||||
}
|
||||
|
||||
std::shared_ptr<AudioPlayer> Window::GetAudioPlayer() {
|
||||
return APlayer;
|
||||
}
|
||||
|
||||
std::shared_ptr<ResourceMgr> Window::GetResourceManager() {
|
||||
return ResMan;
|
||||
}
|
||||
|
||||
std::shared_ptr<Mercury> Window::GetConfig() {
|
||||
return Config;
|
||||
}
|
||||
|
||||
std::shared_ptr<spdlog::logger> Window::GetLogger() {
|
||||
return Logger;
|
||||
}
|
||||
|
||||
const char* Window::GetKeyName(int32_t scancode) {
|
||||
return WmApi->get_key_name(scancode);
|
||||
}
|
||||
|
||||
int32_t Window::GetLastScancode() {
|
||||
return lastScancode;
|
||||
}
|
||||
|
||||
void Window::SetLastScancode(int32_t scanCode) {
|
||||
lastScancode = scanCode;
|
||||
}
|
||||
}
|
||||
|
@ -36,20 +36,20 @@ namespace Ship {
|
||||
void ToggleFullscreen();
|
||||
void SetFullscreen(bool bIsFullscreen);
|
||||
void ShowCursor(bool hide);
|
||||
bool IsFullscreen() { return bIsFullscreen; }
|
||||
uint32_t GetCurrentWidth();
|
||||
uint32_t GetCurrentHeight();
|
||||
uint32_t GetMenuBar() { return dwMenubar; }
|
||||
void SetMenuBar(uint32_t dwMenuBar) { this->dwMenubar = dwMenuBar; }
|
||||
std::string GetName() { return Name; }
|
||||
std::shared_ptr<ControlDeck> GetControlDeck() { return ControllerApi; };
|
||||
std::shared_ptr<AudioPlayer> GetAudioPlayer() { return APlayer; }
|
||||
std::shared_ptr<ResourceMgr> GetResourceManager() { return ResMan; }
|
||||
std::shared_ptr<Mercury> GetConfig() { return Config; }
|
||||
std::shared_ptr<spdlog::logger> GetLogger() { return Logger; }
|
||||
const char* GetKeyName(int32_t scancode) { return WmApi->get_key_name(scancode); }
|
||||
int32_t GetLastScancode() { return lastScancode; }
|
||||
void SetLastScancode(int32_t scanCode) { lastScancode = scanCode; }
|
||||
bool IsFullscreen();
|
||||
uint32_t GetMenuBar();
|
||||
void SetMenuBar(uint32_t dwMenuBar);
|
||||
std::string GetName();
|
||||
std::shared_ptr<ControlDeck> GetControlDeck();
|
||||
std::shared_ptr<AudioPlayer> GetAudioPlayer();
|
||||
std::shared_ptr<ResourceMgr> GetResourceManager();
|
||||
std::shared_ptr<Mercury> GetConfig();
|
||||
std::shared_ptr<spdlog::logger> GetLogger();
|
||||
const char* GetKeyName(int32_t scancode);
|
||||
int32_t GetLastScancode();
|
||||
void SetLastScancode(int32_t scanCode);
|
||||
|
||||
protected:
|
||||
Window() = default;
|
||||
|
@ -181,9 +181,11 @@ source_group("Header Files\\soh\\Enhancements\\debugger" FILES ${Header_Files__s
|
||||
|
||||
set(Header_Files__soh__Enhancements__randomizer
|
||||
"soh/Enhancements/randomizer/randomizer.h"
|
||||
"soh/Enhancements/randomizer/randomizer_inf.h"
|
||||
"soh/Enhancements/randomizer/randomizer_item_tracker.h"
|
||||
"soh/Enhancements/randomizer/adult_trade_shuffle.h"
|
||||
"soh/Enhancements/randomizer/randomizer_check_objects.h"
|
||||
"soh/Enhancements/randomizer/draw.h"
|
||||
)
|
||||
source_group("Header Files\\soh\\Enhancements\\randomizer" FILES ${Header_Files__soh__Enhancements__randomizer})
|
||||
|
||||
@ -291,6 +293,7 @@ set(Source_Files__soh__Enhancements__randomizer
|
||||
"soh/Enhancements/randomizer/randomizer_item_tracker.cpp"
|
||||
"soh/Enhancements/randomizer/adult_trade_shuffle.c"
|
||||
"soh/Enhancements/randomizer/randomizer_check_objects.cpp"
|
||||
"soh/Enhancements/randomizer/draw.cpp"
|
||||
)
|
||||
source_group("Source Files\\soh\\Enhancements\\randomizer" FILES ${Source_Files__soh__Enhancements__randomizer})
|
||||
|
||||
|
@ -11,6 +11,7 @@ extern "C"
|
||||
|
||||
#include "../../libultraship/libultraship/luslog.h"
|
||||
#include <soh/Enhancements/item-tables/ItemTableTypes.h>
|
||||
#include <soh/Enhancements/randomizer/randomizer_inf.h>
|
||||
|
||||
#if defined(INCLUDE_GAME_PRINTF) && !defined(NDEBUG)
|
||||
#define osSyncPrintf(fmt, ...) lusprintf(__FILE__, __LINE__, 0, fmt, __VA_ARGS__)
|
||||
@ -558,6 +559,8 @@ s32 Flags_GetEventChkInf(s32 flag);
|
||||
void Flags_SetEventChkInf(s32 flag);
|
||||
s32 Flags_GetInfTable(s32 flag);
|
||||
void Flags_SetInfTable(s32 flag);
|
||||
s32 Flags_GetRandomizerInf(RandomizerInf flag);
|
||||
void Flags_SetRandomizerInf(RandomizerInf flag);
|
||||
u16 func_80037C30(GlobalContext* globalCtx, s16 arg1);
|
||||
s32 func_80037D98(GlobalContext* globalCtx, Actor* actor, s16 arg2, s32* arg3);
|
||||
s32 func_80038290(GlobalContext* globalCtx, Actor* actor, Vec3s* arg2, Vec3s* arg3, Vec3f arg4);
|
||||
@ -859,6 +862,7 @@ void Cutscene_HandleEntranceTriggers(GlobalContext* globalCtx);
|
||||
void Cutscene_HandleConditionalTriggers(GlobalContext* globalCtx);
|
||||
void Cutscene_SetSegment(GlobalContext* globalCtx, void* segment);
|
||||
void GetItem_Draw(GlobalContext* globalCtx, s16 drawId);
|
||||
void GetItemEntry_Draw(GlobalContext* globalCtx, GetItemEntry getItemEntry);
|
||||
void SoundSource_InitAll(GlobalContext* globalCtx);
|
||||
void SoundSource_UpdateAll(GlobalContext* globalCtx);
|
||||
void SoundSource_PlaySfxAtFixedWorldPos(GlobalContext* globalCtx, Vec3f* pos, s32 duration, u16 sfxId);
|
||||
|
@ -368,7 +368,7 @@ typedef enum {
|
||||
FLAG_SCENE_CLEAR,
|
||||
FLAG_SCENE_COLLECTIBLE,
|
||||
FLAG_EVENT_CHECK_INF,
|
||||
FLAG_COW_MILKED
|
||||
FLAG_RANDOMIZER_INF
|
||||
} FlagType;
|
||||
|
||||
typedef struct {
|
||||
|
@ -5,6 +5,7 @@
|
||||
#include "z64math.h"
|
||||
#include "z64audio.h"
|
||||
#include "soh/Enhancements/randomizer/randomizerTypes.h"
|
||||
#include "soh/Enhancements/randomizer/randomizer_inf.h"
|
||||
|
||||
typedef struct {
|
||||
/* 0x00 */ u8 buttonItems[8];
|
||||
@ -182,9 +183,7 @@ typedef struct {
|
||||
char ganonHintText[150];
|
||||
char ganonText[250];
|
||||
u8 seedIcons[5];
|
||||
u8 dungeonsDone[8];
|
||||
u8 trialsDone[6];
|
||||
u8 cowsMilked[10];
|
||||
u16 randomizerInf[4];
|
||||
u8 temporaryWeapon;
|
||||
u16 adultTradeItems;
|
||||
} SaveContext; // size = 0x1428
|
||||
|
@ -26,7 +26,7 @@ const char* RainbowColorCvarList[] = {
|
||||
"gCCMapsPrim", "gCCQuestsPrim", "gCCSavePrim", "gCCGameoverPrim"
|
||||
};
|
||||
const char* MarginCvarList[] {
|
||||
"gHearts", "gMagicBar", "gVSOA", "gBBtn", "gABtn", "gStartBtn",
|
||||
"gHearts", "gHeartsCount", "gMagicBar", "gVSOA", "gBBtn", "gABtn", "gStartBtn",
|
||||
"gCBtnU", "gCBtnD", "gCBtnL", "gCBtnR", "gDPad", "gMinimap",
|
||||
"gSKC", "gRC", "gCarrots", "gTimers", "gAS", "gTCM", "gTCB"
|
||||
};
|
||||
@ -44,7 +44,6 @@ ImVec4 GetRandomValue(int MaximumPossible){
|
||||
return NewColor;
|
||||
}
|
||||
void GetRandomColorRGB(CosmeticsColorSection* ColorSection, int SectionSize){
|
||||
//std::random_shuffle(ColorSection, ColorSection + SectionSize);
|
||||
for (int i = 0; i < SectionSize; i++){
|
||||
CosmeticsColorIndividual* Element = ColorSection[i].Element;
|
||||
ImVec4 colors = Element->ModifiedColor;
|
||||
@ -477,7 +476,7 @@ void Draw_Placements(){
|
||||
Table_InitHeader(false);
|
||||
DrawUseMarginsSlider("Hearts counts", "gHearts");
|
||||
DrawPositionsRadioBoxes("gHeartsCount");
|
||||
DrawPositionSlider("gHeartsCount",-22,ImGui::GetWindowViewport()->Size.y,-25,ImGui::GetWindowViewport()->Size.x);
|
||||
DrawPositionSlider("gHeartsCount",-22,ImGui::GetWindowViewport()->Size.y,-125,ImGui::GetWindowViewport()->Size.x);
|
||||
DrawScaleSlider("gHeartsCount",0.7f);
|
||||
ImGui::NewLine();
|
||||
ImGui::EndTable();
|
||||
|
@ -7,12 +7,20 @@
|
||||
#define CHEST_ANIM_LONG 1
|
||||
|
||||
#define GET_ITEM(itemId, objectId, drawId, textId, field, chestAnim, modIndex, getItemId) \
|
||||
{ itemId, field, (chestAnim != CHEST_ANIM_SHORT ? 1 : -1) * (drawId + 1), textId, objectId, modIndex, getItemId, drawId, true }
|
||||
{ itemId, field, (chestAnim != CHEST_ANIM_SHORT ? 1 : -1) * (drawId + 1), textId, objectId, modIndex, getItemId, drawId, true, NULL }
|
||||
|
||||
#define GET_ITEM_NONE \
|
||||
{ ITEM_NONE, 0, 0, 0, 0, 0, 0, 0, false }
|
||||
{ ITEM_NONE, 0, 0, 0, 0, 0, 0, 0, false, NULL }
|
||||
|
||||
typedef struct {
|
||||
#define GET_ITEM_CUSTOM_DRAW(itemId, objectId, drawId, textId, field, chestAnim, modIndex, getItemId, drawFunc) \
|
||||
{ itemId, field (chestAnim != CHEST_ANIM_SHORT ? 1 : -1) * (drawId + 1), textId, objectId, modIndex, getItemId, drawId, true, drawFunc }
|
||||
|
||||
typedef struct GlobalContext GlobalContext;
|
||||
typedef struct GetItemEntry GetItemEntry;
|
||||
|
||||
typedef void (*CustomDrawFunc)(GlobalContext* globalCtx, GetItemEntry* getItemEntry);
|
||||
|
||||
typedef struct GetItemEntry {
|
||||
/* 0x00 */ uint16_t itemId;
|
||||
/* 0x01 */ uint16_t field; // various bit-packed data
|
||||
/* 0x02 */ int16_t gi; // defines the draw id and chest opening animation
|
||||
@ -22,4 +30,5 @@ typedef struct {
|
||||
/* 0x08 */ int16_t getItemId;
|
||||
/* 0x0A */ uint16_t gid; // Stores the GID value unmodified for future reference.
|
||||
/* 0x0C */ uint16_t collectable; // determines whether the item can be collected on the overworld. Will be true in most cases.
|
||||
} GetItemEntry; // size = 0x0F
|
||||
CustomDrawFunc drawFunc;
|
||||
}; // size = 0x0F
|
||||
|
@ -1039,6 +1039,19 @@ int Fill() {
|
||||
//Fast fill for the rest of the pool
|
||||
std::vector<uint32_t> remainingPool = FilterAndEraseFromPool(ItemPool, [](const auto i) { return true; });
|
||||
FastFill(remainingPool, GetAllEmptyLocations(), false);
|
||||
|
||||
//Add prices for scrubsanity, this is unique to SoH because we write/read scrub prices to/from the spoilerfile.
|
||||
if (Scrubsanity.Is(SCRUBSANITY_AFFORDABLE)) {
|
||||
for (size_t i = 0; i < ScrubLocations.size(); i++) {
|
||||
Location(ScrubLocations[i])->SetScrubsanityPrice(10);
|
||||
}
|
||||
} else if (Scrubsanity.Is(SCRUBSANITY_RANDOM_PRICES)) {
|
||||
for (size_t i = 0; i < ScrubLocations.size(); i++) {
|
||||
int randomPrice = GetRandomScrubPrice();
|
||||
Location(ScrubLocations[i])->SetScrubsanityPrice(randomPrice);
|
||||
}
|
||||
}
|
||||
|
||||
GeneratePlaythrough();
|
||||
//Successful placement, produced beatable result
|
||||
if(playthroughBeatable && !placementFailure) {
|
||||
|
@ -1011,6 +1011,56 @@ std::vector<std::vector<uint32_t>> ShopLocationLists = {
|
||||
GC_ShopLocations,
|
||||
};
|
||||
|
||||
//List of scrubs, used for pricing the scrubs
|
||||
std::vector<uint32_t> ScrubLocations = {
|
||||
LW_DEKU_SCRUB_NEAR_DEKU_THEATER_RIGHT,
|
||||
LW_DEKU_SCRUB_NEAR_DEKU_THEATER_LEFT,
|
||||
LW_DEKU_SCRUB_NEAR_BRIDGE,
|
||||
LW_DEKU_SCRUB_GROTTO_REAR,
|
||||
LW_DEKU_SCRUB_GROTTO_FRONT,
|
||||
SFM_DEKU_SCRUB_GROTTO_REAR,
|
||||
SFM_DEKU_SCRUB_GROTTO_FRONT,
|
||||
HF_DEKU_SCRUB_GROTTO,
|
||||
LH_DEKU_SCRUB_GROTTO_LEFT,
|
||||
LH_DEKU_SCRUB_GROTTO_RIGHT,
|
||||
LH_DEKU_SCRUB_GROTTO_CENTER,
|
||||
GV_DEKU_SCRUB_GROTTO_REAR,
|
||||
GV_DEKU_SCRUB_GROTTO_FRONT,
|
||||
COLOSSUS_DEKU_SCRUB_GROTTO_REAR,
|
||||
COLOSSUS_DEKU_SCRUB_GROTTO_FRONT,
|
||||
GC_DEKU_SCRUB_GROTTO_LEFT,
|
||||
GC_DEKU_SCRUB_GROTTO_RIGHT,
|
||||
GC_DEKU_SCRUB_GROTTO_CENTER,
|
||||
DMC_DEKU_SCRUB,
|
||||
DMC_DEKU_SCRUB_GROTTO_LEFT,
|
||||
DMC_DEKU_SCRUB_GROTTO_RIGHT,
|
||||
DMC_DEKU_SCRUB_GROTTO_CENTER,
|
||||
ZR_DEKU_SCRUB_GROTTO_REAR,
|
||||
ZR_DEKU_SCRUB_GROTTO_FRONT,
|
||||
LLR_DEKU_SCRUB_GROTTO_LEFT,
|
||||
LLR_DEKU_SCRUB_GROTTO_RIGHT,
|
||||
LLR_DEKU_SCRUB_GROTTO_CENTER,
|
||||
DEKU_TREE_MQ_DEKU_SCRUB,
|
||||
DODONGOS_CAVERN_DEKU_SCRUB_NEAR_BOMB_BAG_LEFT,
|
||||
DODONGOS_CAVERN_DEKU_SCRUB_SIDE_ROOM_NEAR_DODONGOS,
|
||||
DODONGOS_CAVERN_DEKU_SCRUB_NEAR_BOMB_BAG_RIGHT,
|
||||
DODONGOS_CAVERN_DEKU_SCRUB_LOBBY,
|
||||
DODONGOS_CAVERN_MQ_DEKU_SCRUB_LOBBY_REAR,
|
||||
DODONGOS_CAVERN_MQ_DEKU_SCRUB_LOBBY_FRONT,
|
||||
DODONGOS_CAVERN_MQ_DEKU_SCRUB_STAIRCASE,
|
||||
DODONGOS_CAVERN_MQ_DEKU_SCRUB_SIDE_ROOM_NEAR_LOWER_LIZALFOS,
|
||||
JABU_JABUS_BELLY_DEKU_SCRUB,
|
||||
GANONS_CASTLE_DEKU_SCRUB_CENTER_LEFT,
|
||||
GANONS_CASTLE_DEKU_SCRUB_CENTER_RIGHT,
|
||||
GANONS_CASTLE_DEKU_SCRUB_RIGHT,
|
||||
GANONS_CASTLE_DEKU_SCRUB_LEFT,
|
||||
GANONS_CASTLE_MQ_DEKU_SCRUB_RIGHT,
|
||||
GANONS_CASTLE_MQ_DEKU_SCRUB_CENTER_LEFT,
|
||||
GANONS_CASTLE_MQ_DEKU_SCRUB_CENTER,
|
||||
GANONS_CASTLE_MQ_DEKU_SCRUB_CENTER_RIGHT,
|
||||
GANONS_CASTLE_MQ_DEKU_SCRUB_LEFT,
|
||||
};
|
||||
|
||||
//List of gossip stone locations for hints
|
||||
std::vector<uint32_t> gossipStoneLocations = {
|
||||
DMC_GOSSIP_STONE,
|
||||
|
@ -257,8 +257,8 @@ public:
|
||||
}
|
||||
|
||||
void SetPrice(uint16_t price_) {
|
||||
//don't override price if the price was set for shopsanity
|
||||
if (hasShopsanityPrice) {
|
||||
//don't override price if the price was set for shopsanity/scrubsanity
|
||||
if (hasShopsanityPrice || hasScrubsanityPrice) {
|
||||
return;
|
||||
}
|
||||
price = price_;
|
||||
@ -269,10 +269,19 @@ public:
|
||||
hasShopsanityPrice = true;
|
||||
}
|
||||
|
||||
void SetScrubsanityPrice(uint16_t price_) {
|
||||
price = price_;
|
||||
hasScrubsanityPrice = true;
|
||||
}
|
||||
|
||||
bool HasShopsanityPrice() const {
|
||||
return hasShopsanityPrice;
|
||||
}
|
||||
|
||||
bool HasScrubsanityPrice() const {
|
||||
return hasScrubsanityPrice;
|
||||
}
|
||||
|
||||
bool IsExcluded() const {
|
||||
return excludedOption.Value<bool>();
|
||||
}
|
||||
@ -426,6 +435,7 @@ public:
|
||||
isHintable = false;
|
||||
price = 0;
|
||||
hasShopsanityPrice = false;
|
||||
hasScrubsanityPrice = false;
|
||||
hidden = false;
|
||||
}
|
||||
|
||||
@ -451,6 +461,7 @@ private:
|
||||
bool isHintable = false;
|
||||
uint32_t parentRegion = NONE;
|
||||
bool hasShopsanityPrice = false;
|
||||
bool hasScrubsanityPrice = false;
|
||||
bool hidden = false;
|
||||
};
|
||||
|
||||
@ -467,6 +478,8 @@ ItemLocation* Location(uint32_t locKey);
|
||||
|
||||
extern std::vector<std::vector<uint32_t>> ShopLocationLists;
|
||||
|
||||
extern std::vector<uint32_t> ScrubLocations;
|
||||
|
||||
extern std::vector<uint32_t> gossipStoneLocations;
|
||||
|
||||
extern std::vector<uint32_t> dungeonRewardLocations;
|
||||
|
@ -2532,6 +2532,7 @@ namespace Settings {
|
||||
ShuffleRewards.SetSelectedIndex(cvarSettings[RSK_SHUFFLE_DUNGEON_REWARDS]);
|
||||
ShuffleSongs.SetSelectedIndex(cvarSettings[RSK_SHUFFLE_SONGS]);
|
||||
Tokensanity.SetSelectedIndex(cvarSettings[RSK_SHUFFLE_TOKENS]);
|
||||
Scrubsanity.SetSelectedIndex(cvarSettings[RSK_SHUFFLE_SCRUBS]);
|
||||
ShuffleCows.SetSelectedIndex(cvarSettings[RSK_SHUFFLE_COWS]);
|
||||
ShuffleKokiriSword.SetSelectedIndex(cvarSettings[RSK_SHUFFLE_KOKIRI_SWORD]);
|
||||
ShuffleOcarinas.SetSelectedIndex(cvarSettings[RSK_SHUFFLE_OCARINA]);
|
||||
|
@ -673,15 +673,24 @@ static void WriteHints(int language) {
|
||||
static void WriteAllLocations(int language) {
|
||||
for (const uint32_t key : allLocations) {
|
||||
ItemLocation* location = Location(key);
|
||||
std::string placedItemName;
|
||||
|
||||
switch (language) {
|
||||
case 0:
|
||||
default:
|
||||
jsonData["locations"][location->GetName()] = location->GetPlacedItemName().english;
|
||||
break;
|
||||
case 2:
|
||||
jsonData["locations"][location->GetName()] = location->GetPlacedItemName().french;
|
||||
break;
|
||||
case 0:
|
||||
default:
|
||||
location->GetPlacedItemName().english;
|
||||
break;
|
||||
case 2:
|
||||
location->GetPlacedItemName().french;
|
||||
break;
|
||||
}
|
||||
|
||||
// Eventually check for other things here like fake name
|
||||
if (location->HasScrubsanityPrice() || location->HasShopsanityPrice()) {
|
||||
jsonData["locations"][location->GetName()]["item"] = placedItemName;
|
||||
jsonData["locations"][location->GetName()]["price"] = location->GetPrice();
|
||||
} else {
|
||||
jsonData["locations"][location->GetName()] = placedItemName;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
109
soh/soh/Enhancements/randomizer/draw.cpp
Normal file
109
soh/soh/Enhancements/randomizer/draw.cpp
Normal file
@ -0,0 +1,109 @@
|
||||
#include "draw.h"
|
||||
#include "z64.h"
|
||||
#include "macros.h"
|
||||
#include "functions.h"
|
||||
#include "randomizerTypes.h"
|
||||
#include <array>
|
||||
#include "objects/object_gi_key/object_gi_key.h"
|
||||
#include "objects/object_gi_bosskey/object_gi_bosskey.h"
|
||||
#include "objects/object_gi_hearts/object_gi_hearts.h"
|
||||
|
||||
extern "C" void Randomizer_DrawSmallKey(GlobalContext* globalCtx, GetItemEntry* getItemEntry) {
|
||||
s32 pad;
|
||||
|
||||
s16 color_slot = getItemEntry->getItemId - RG_FOREST_TEMPLE_SMALL_KEY;
|
||||
s16 colors[9][3] = {
|
||||
{ 4, 195, 46 }, // Forest Temple
|
||||
{ 237, 95, 95 }, // Fire Temple
|
||||
{ 85, 180, 223 }, // Water Temple
|
||||
{ 222, 158, 47 }, // Spirit Temple
|
||||
{ 126, 16, 177 }, // Shadow Temple
|
||||
{ 227, 110, 255 }, // Bottom of the Well
|
||||
{ 221, 212, 60 }, // Gerudo Training Grounds
|
||||
{ 255, 255, 255 }, // Theive's Hideout (unused)
|
||||
{ 80, 80, 80 } // Ganon's Castle
|
||||
};
|
||||
|
||||
OPEN_DISPS(globalCtx->state.gfxCtx);
|
||||
|
||||
func_80093D18(globalCtx->state.gfxCtx);
|
||||
|
||||
gSPMatrix(POLY_OPA_DISP++, Matrix_NewMtx(globalCtx->state.gfxCtx, (char*)__FILE__, __LINE__),
|
||||
G_MTX_MODELVIEW | G_MTX_LOAD);
|
||||
|
||||
gsDPSetGrayscaleColor(POLY_OPA_DISP++, colors[color_slot][0], colors[color_slot][1], colors[color_slot][2], 255);
|
||||
gsSPGrayscale(POLY_OPA_DISP++, true);
|
||||
|
||||
gSPDisplayList(POLY_OPA_DISP++, (Gfx*)gGiSmallKeyDL);
|
||||
|
||||
gsSPGrayscale(POLY_OPA_DISP++, false);
|
||||
|
||||
CLOSE_DISPS(globalCtx->state.gfxCtx);
|
||||
}
|
||||
|
||||
extern "C" void Randomizer_DrawBossKey(GlobalContext* globalCtx, GetItemEntry* getItemEntry) {
|
||||
s32 pad;
|
||||
s16 color_slot;
|
||||
color_slot = getItemEntry->getItemId - RG_FOREST_TEMPLE_BOSS_KEY;
|
||||
s16 colors[6][3] = {
|
||||
{ 4, 195, 46 }, // Forest Temple
|
||||
{ 237, 95, 95 }, // Fire Temple
|
||||
{ 85, 180, 223 }, // Water Temple
|
||||
{ 222, 158, 47 }, // Spirit Temple
|
||||
{ 126, 16, 177 }, // Shadow Temple
|
||||
{ 210, 0, 0 } // Ganon's Castle
|
||||
};
|
||||
|
||||
OPEN_DISPS(globalCtx->state.gfxCtx);
|
||||
|
||||
func_80093D18(globalCtx->state.gfxCtx);
|
||||
|
||||
gSPMatrix(POLY_OPA_DISP++, Matrix_NewMtx(globalCtx->state.gfxCtx, (char*)__FILE__, __LINE__),
|
||||
G_MTX_MODELVIEW | G_MTX_LOAD);
|
||||
|
||||
if (color_slot == 5) { // Ganon's Boss Key
|
||||
gsDPSetGrayscaleColor(POLY_OPA_DISP++, 80, 80, 80, 255);
|
||||
gsSPGrayscale(POLY_OPA_DISP++, true);
|
||||
}
|
||||
|
||||
gSPDisplayList(POLY_OPA_DISP++, (Gfx*)gGiBossKeyDL);
|
||||
|
||||
if (color_slot == 5) { // Ganon's Boss Key
|
||||
gsSPGrayscale(POLY_OPA_DISP++, false);
|
||||
}
|
||||
|
||||
func_80093D84(globalCtx->state.gfxCtx);
|
||||
|
||||
gSPMatrix(POLY_XLU_DISP++, Matrix_NewMtx(globalCtx->state.gfxCtx, (char*)__FILE__, __LINE__),
|
||||
G_MTX_MODELVIEW | G_MTX_LOAD);
|
||||
|
||||
gsDPSetGrayscaleColor(POLY_XLU_DISP++, colors[color_slot][0], colors[color_slot][1], colors[color_slot][2],
|
||||
255);
|
||||
gsSPGrayscale(POLY_XLU_DISP++, true);
|
||||
|
||||
gSPDisplayList(POLY_XLU_DISP++, (Gfx*)gGiBossKeyGemDL);
|
||||
|
||||
gsSPGrayscale(POLY_XLU_DISP++, false);
|
||||
|
||||
CLOSE_DISPS(globalCtx->state.gfxCtx);
|
||||
}
|
||||
|
||||
extern "C" void Randomizer_DrawDoubleDefense(GlobalContext* globalCtx, GetItemEntry getItemEntry) {
|
||||
s32 pad;
|
||||
OPEN_DISPS(globalCtx->state.gfxCtx);
|
||||
|
||||
func_80093D84(globalCtx->state.gfxCtx);
|
||||
|
||||
gSPMatrix(POLY_XLU_DISP++, Matrix_NewMtx(globalCtx->state.gfxCtx, (char*)__FILE__, __LINE__), G_MTX_MODELVIEW | G_MTX_LOAD);
|
||||
|
||||
gsDPSetGrayscaleColor(POLY_XLU_DISP++, 255, 255, 255, 255);
|
||||
gsSPGrayscale(POLY_XLU_DISP++, true);
|
||||
|
||||
gSPDisplayList(POLY_XLU_DISP++, (Gfx*)gGiHeartBorderDL);
|
||||
|
||||
gsSPGrayscale(POLY_XLU_DISP++, false);
|
||||
|
||||
gSPDisplayList(POLY_XLU_DISP++, (Gfx*)gGiHeartContainerDL);
|
||||
|
||||
CLOSE_DISPS(globalCtx->state.gfxCtx);
|
||||
}
|
13
soh/soh/Enhancements/randomizer/draw.h
Normal file
13
soh/soh/Enhancements/randomizer/draw.h
Normal file
@ -0,0 +1,13 @@
|
||||
#ifndef RANDODRAW_H
|
||||
#define RANDODRAW_H
|
||||
#pragma once
|
||||
|
||||
#include "../item-tables/ItemTableTypes.h"
|
||||
|
||||
typedef struct GlobalContext GlobalContext;
|
||||
|
||||
extern "C" void Randomizer_DrawSmallKey(GlobalContext* globalCtx, GetItemEntry* getItemEntry);
|
||||
extern "C" void Randomizer_DrawBossKey(GlobalContext* globalCtx, GetItemEntry* getItemEntry);
|
||||
extern "C" void Randomizer_DrawDoubleDefense(GlobalContext* globalCtx, GetItemEntry getItemEntry);
|
||||
|
||||
#endif
|
@ -19,6 +19,7 @@
|
||||
#include <stdexcept>
|
||||
#include "randomizer_check_objects.h"
|
||||
#include <sstream>
|
||||
#include "draw.h"
|
||||
|
||||
using json = nlohmann::json;
|
||||
using namespace std::literals::string_literals;
|
||||
@ -103,6 +104,7 @@ Sprite* Randomizer::GetSeedTexture(uint8_t index) {
|
||||
Randomizer::~Randomizer() {
|
||||
this->randoSettings.clear();
|
||||
this->itemLocations.clear();
|
||||
this->randomizerMerchantPrices.clear();
|
||||
}
|
||||
|
||||
std::unordered_map<s16, s16> getItemIdToItemId = {
|
||||
@ -545,6 +547,7 @@ std::unordered_map<std::string, RandomizerSettingKey> SpoilerfileSettingNameToEn
|
||||
{ "Open Settings:Random Ganon's Trials", RSK_RANDOM_TRIALS },
|
||||
{ "Open Settings:Trial Count", RSK_TRIAL_COUNT },
|
||||
{ "Shuffle Settings:Shuffle Gerudo Card", RSK_SHUFFLE_GERUDO_MEMBERSHIP_CARD },
|
||||
{ "Shuffle Settings:Scrub Shuffle", RSK_SHUFFLE_SCRUBS },
|
||||
{ "Shuffle Settings:Shuffle Cows", RSK_SHUFFLE_COWS },
|
||||
{ "Shuffle Settings:Tokensanity", RSK_SHUFFLE_TOKENS },
|
||||
{ "Shuffle Settings:Shuffle Adult Trade", RSK_SHUFFLE_ADULT_TRADE },
|
||||
@ -772,6 +775,17 @@ void Randomizer::ParseRandomizerSettingsFile(const char* spoilerFileName) {
|
||||
numericValueString = it.value();
|
||||
gSaveContext.randoSettings[index].value = std::stoi(numericValueString);
|
||||
break;
|
||||
case RSK_SHUFFLE_SCRUBS:
|
||||
if(it.value() == "Off") {
|
||||
gSaveContext.randoSettings[index].value = 0;
|
||||
} else if(it.value() == "Affordable") {
|
||||
gSaveContext.randoSettings[index].value = 1;
|
||||
} else if(it.value() == "Expensive") {
|
||||
gSaveContext.randoSettings[index].value = 2;
|
||||
} else if(it.value() == "Random Prices") {
|
||||
gSaveContext.randoSettings[index].value = 3;
|
||||
}
|
||||
break;
|
||||
case RSK_SHUFFLE_GERUDO_MEMBERSHIP_CARD:
|
||||
case RSK_SHUFFLE_COWS:
|
||||
case RSK_SHUFFLE_ADULT_TRADE:
|
||||
@ -1103,9 +1117,10 @@ void Randomizer::ParseItemLocationsFile(const char* spoilerFileName, bool silent
|
||||
for (auto itemit = itemJson.begin(); itemit != itemJson.end(); ++itemit) {
|
||||
// todo handle prices
|
||||
if (itemit.key() == "item") {
|
||||
|
||||
gSaveContext.itemLocations[index].check = SpoilerfileCheckNameToEnum[it.key()];
|
||||
gSaveContext.itemLocations[index].get = SpoilerfileGetNameToEnum[itemit.value()];
|
||||
} else if (itemit.key() == "price") {
|
||||
randomizerMerchantPrices[gSaveContext.itemLocations[index].check] = itemit.value();
|
||||
}
|
||||
}
|
||||
} else {
|
||||
@ -1145,7 +1160,7 @@ s16 Randomizer::GetItemFromGet(RandomizerGet randoGet, GetItemID ogItemId) {
|
||||
case RG_GIANTS_KNIFE:
|
||||
return GI_SWORD_KNIFE;
|
||||
case RG_BIGGORON_SWORD:
|
||||
return !CHECK_OWNED_EQUIP(EQUIP_SWORD, 2) ? GI_SWORD_BGS : GI_RUPEE_BLUE;
|
||||
return !gSaveContext.bgsFlag ? GI_SWORD_BGS : GI_RUPEE_BLUE;
|
||||
|
||||
case RG_DEKU_SHIELD:
|
||||
return GI_SHIELD_DEKU;
|
||||
@ -1587,6 +1602,280 @@ std::string Randomizer::GetGanonHintText() const {
|
||||
return ganonHintText;
|
||||
}
|
||||
|
||||
ScrubIdentity Randomizer::IdentifyScrub(s32 sceneNum, s32 actorParams, s32 respawnData) {
|
||||
struct ScrubIdentity scrubIdentity;
|
||||
|
||||
scrubIdentity.randomizerCheck = RC_UNKNOWN_CHECK;
|
||||
scrubIdentity.getItemId = GI_NONE;
|
||||
scrubIdentity.itemPrice = -1;
|
||||
scrubIdentity.isShuffled = GetRandoSettingValue(RSK_SHUFFLE_SCRUBS) > 0;
|
||||
|
||||
// Based on z_en_dns.c 93-113
|
||||
switch (actorParams) {
|
||||
case 0x00:
|
||||
scrubIdentity.getItemId = GI_NUTS_5_2;
|
||||
break;
|
||||
case 0x01:
|
||||
scrubIdentity.getItemId = GI_STICKS_1;
|
||||
break;
|
||||
case 0x02:
|
||||
scrubIdentity.getItemId = GI_HEART_PIECE;
|
||||
break;
|
||||
case 0x03:
|
||||
scrubIdentity.getItemId = GI_SEEDS_30;
|
||||
break;
|
||||
case 0x04:
|
||||
scrubIdentity.getItemId = GI_SHIELD_DEKU;
|
||||
break;
|
||||
case 0x05:
|
||||
scrubIdentity.getItemId = GI_BOMBS_5;
|
||||
break;
|
||||
case 0x06:
|
||||
scrubIdentity.getItemId = GI_ARROWS_LARGE;
|
||||
break;
|
||||
case 0x07:
|
||||
scrubIdentity.getItemId = GI_POTION_RED;
|
||||
break;
|
||||
case 0x08:
|
||||
scrubIdentity.getItemId = GI_POTION_GREEN;
|
||||
break;
|
||||
case 0x09:
|
||||
scrubIdentity.getItemId = GI_STICK_UPGRADE_20;
|
||||
break;
|
||||
case 0x0A:
|
||||
scrubIdentity.getItemId = GI_NUT_UPGRADE_30;
|
||||
break;
|
||||
}
|
||||
|
||||
// TODO: Handle MQ scrubs
|
||||
switch (sceneNum) {
|
||||
case SCENE_DDAN: // Dodongo's Cavern
|
||||
switch (actorParams) {
|
||||
case 0x00:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_DODONGOS_CAVERN_DEKU_SCRUB_NEAR_BOMB_BAG_LEFT;
|
||||
scrubIdentity.randomizerCheck = RC_DODONGOS_CAVERN_DEKU_SCRUB_NEAR_BOMB_BAG_LEFT;
|
||||
break;
|
||||
case 0x01:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_DODONGOS_CAVERN_DEKU_SCRUB_SIDE_ROOM_NEAR_DODONGOS;
|
||||
scrubIdentity.randomizerCheck = RC_DODONGOS_CAVERN_DEKU_SCRUB_SIDE_ROOM_NEAR_DODONGOS;
|
||||
break;
|
||||
case 0x03:
|
||||
case 0x06:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_DODONGOS_CAVERN_DEKU_SCRUB_NEAR_BOMB_BAG_RIGHT;
|
||||
scrubIdentity.randomizerCheck = RC_DODONGOS_CAVERN_DEKU_SCRUB_NEAR_BOMB_BAG_RIGHT;
|
||||
break;
|
||||
case 0x04:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_DODONGOS_CAVERN_DEKU_SCRUB_LOBBY;
|
||||
scrubIdentity.randomizerCheck = RC_DODONGOS_CAVERN_DEKU_SCRUB_LOBBY;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case SCENE_BDAN: // Jabu Jabu's Belly
|
||||
switch (actorParams) {
|
||||
case 0x00:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_JABU_JABUS_BELLY_DEKU_SCRUB;
|
||||
scrubIdentity.randomizerCheck = RC_JABU_JABUS_BELLY_DEKU_SCRUB;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case SCENE_GANONTIKA: // Ganon's Castle
|
||||
switch (actorParams) {
|
||||
case 0x05:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_GANONS_CASTLE_DEKU_SCRUB_CENTER_LEFT;
|
||||
scrubIdentity.randomizerCheck = RC_GANONS_CASTLE_DEKU_SCRUB_CENTER_LEFT;
|
||||
break;
|
||||
case 0x03:
|
||||
case 0x06:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_GANONS_CASTLE_DEKU_SCRUB_CENTER_RIGHT;
|
||||
scrubIdentity.randomizerCheck = RC_GANONS_CASTLE_DEKU_SCRUB_CENTER_RIGHT;
|
||||
break;
|
||||
case 0x07:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_GANONS_CASTLE_DEKU_SCRUB_RIGHT;
|
||||
scrubIdentity.randomizerCheck = RC_GANONS_CASTLE_DEKU_SCRUB_RIGHT;
|
||||
break;
|
||||
case 0x08:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_GANONS_CASTLE_DEKU_SCRUB_LEFT;
|
||||
scrubIdentity.randomizerCheck = RC_GANONS_CASTLE_DEKU_SCRUB_LEFT;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case SCENE_KAKUSIANA: // Grotto
|
||||
switch (respawnData) {
|
||||
case 0xE6: // Hyrule Field Scrub Grotto
|
||||
switch (actorParams) {
|
||||
case 0x02:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_HF_DEKU_SCRUB_GROTTO;
|
||||
scrubIdentity.randomizerCheck = RC_HF_DEKU_SCRUB_GROTTO;
|
||||
scrubIdentity.isShuffled = true;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case 0xEB: // ZR Scrub Grotto
|
||||
switch (actorParams) {
|
||||
case 0x07:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_ZR_DEKU_SCRUB_GROTTO_REAR;
|
||||
scrubIdentity.randomizerCheck = RC_ZR_DEKU_SCRUB_GROTTO_REAR;
|
||||
break;
|
||||
case 0x08:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_ZR_DEKU_SCRUB_GROTTO_FRONT;
|
||||
scrubIdentity.randomizerCheck = RC_ZR_DEKU_SCRUB_GROTTO_FRONT;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case 0xEE: // Sacred Forest Meadow Scrub Grotto
|
||||
switch (actorParams) {
|
||||
case 0x07:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_SFM_DEKU_SCRUB_GROTTO_REAR;
|
||||
scrubIdentity.randomizerCheck = RC_SFM_DEKU_SCRUB_GROTTO_REAR;
|
||||
break;
|
||||
case 0x08:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_SFM_DEKU_SCRUB_GROTTO_FRONT;
|
||||
scrubIdentity.randomizerCheck = RC_SFM_DEKU_SCRUB_GROTTO_FRONT;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case 0xEF: // Lake Hylia Scrub Grotto
|
||||
switch (actorParams) {
|
||||
case 0x00:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_LH_DEKU_SCRUB_GROTTO_LEFT;
|
||||
scrubIdentity.randomizerCheck = RC_LH_DEKU_SCRUB_GROTTO_LEFT;
|
||||
break;
|
||||
case 0x05:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_LH_DEKU_SCRUB_GROTTO_RIGHT;
|
||||
scrubIdentity.randomizerCheck = RC_LH_DEKU_SCRUB_GROTTO_RIGHT;
|
||||
break;
|
||||
case 0x03:
|
||||
case 0x06:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_LH_DEKU_SCRUB_GROTTO_CENTER;
|
||||
scrubIdentity.randomizerCheck = RC_LH_DEKU_SCRUB_GROTTO_CENTER;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case 0xF0: // Gerudo Valley Scrub Grotto
|
||||
switch (actorParams) {
|
||||
case 0x07:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_GV_DEKU_SCRUB_GROTTO_REAR;
|
||||
scrubIdentity.randomizerCheck = RC_GV_DEKU_SCRUB_GROTTO_REAR;
|
||||
break;
|
||||
case 0x08:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_GV_DEKU_SCRUB_GROTTO_FRONT;
|
||||
scrubIdentity.randomizerCheck = RC_GV_DEKU_SCRUB_GROTTO_FRONT;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case 0xF5: // Lost Woods Scrub Grotto
|
||||
switch (actorParams) {
|
||||
case 0x03:
|
||||
case 0x06:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_LW_DEKU_SCRUB_GROTTO_REAR;
|
||||
scrubIdentity.randomizerCheck = RC_LW_DEKU_SCRUB_GROTTO_REAR;
|
||||
break;
|
||||
case 0x0A:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_LW_DEKU_SCRUB_GROTTO_FRONT;
|
||||
scrubIdentity.randomizerCheck = RC_LW_DEKU_SCRUB_GROTTO_FRONT;
|
||||
scrubIdentity.isShuffled = true;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case 0xF9: // Death Mountain Crater Scrub Grotto
|
||||
switch (actorParams) {
|
||||
case 0x00:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_DMC_DEKU_SCRUB_GROTTO_LEFT;
|
||||
scrubIdentity.randomizerCheck = RC_DMC_DEKU_SCRUB_GROTTO_LEFT;
|
||||
break;
|
||||
case 0x05:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_DMC_DEKU_SCRUB_GROTTO_RIGHT;
|
||||
scrubIdentity.randomizerCheck = RC_DMC_DEKU_SCRUB_GROTTO_RIGHT;
|
||||
break;
|
||||
case 0x03:
|
||||
case 0x06:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_DMC_DEKU_SCRUB_GROTTO_CENTER;
|
||||
scrubIdentity.randomizerCheck = RC_DMC_DEKU_SCRUB_GROTTO_CENTER;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case 0xFB: // Gerudo City Scrub Grotto
|
||||
switch (actorParams) {
|
||||
case 0x00:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_GC_DEKU_SCRUB_GROTTO_LEFT;
|
||||
scrubIdentity.randomizerCheck = RC_GC_DEKU_SCRUB_GROTTO_LEFT;
|
||||
break;
|
||||
case 0x05:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_GC_DEKU_SCRUB_GROTTO_RIGHT;
|
||||
scrubIdentity.randomizerCheck = RC_GC_DEKU_SCRUB_GROTTO_RIGHT;
|
||||
break;
|
||||
case 0x03:
|
||||
case 0x06:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_GC_DEKU_SCRUB_GROTTO_CENTER;
|
||||
scrubIdentity.randomizerCheck = RC_GC_DEKU_SCRUB_GROTTO_CENTER;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case 0xFC: // Lon Lon Ranch Scrub Grotto
|
||||
switch (actorParams) {
|
||||
case 0x00:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_LLR_DEKU_SCRUB_GROTTO_LEFT;
|
||||
scrubIdentity.randomizerCheck = RC_LLR_DEKU_SCRUB_GROTTO_LEFT;
|
||||
break;
|
||||
case 0x05:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_LLR_DEKU_SCRUB_GROTTO_RIGHT;
|
||||
scrubIdentity.randomizerCheck = RC_LLR_DEKU_SCRUB_GROTTO_RIGHT;
|
||||
break;
|
||||
case 0x03:
|
||||
case 0x06:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_LLR_DEKU_SCRUB_GROTTO_CENTER;
|
||||
scrubIdentity.randomizerCheck = RC_LLR_DEKU_SCRUB_GROTTO_CENTER;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case 0xFD: // Desert Colossus Scrub Grotto
|
||||
switch (actorParams) {
|
||||
case 0x07:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_COLOSSUS_DEKU_SCRUB_GROTTO_REAR;
|
||||
scrubIdentity.randomizerCheck = RC_COLOSSUS_DEKU_SCRUB_GROTTO_REAR;
|
||||
break;
|
||||
case 0x08:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_COLOSSUS_DEKU_SCRUB_GROTTO_FRONT;
|
||||
scrubIdentity.randomizerCheck = RC_COLOSSUS_DEKU_SCRUB_GROTTO_FRONT;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case SCENE_SPOT10: // Lost woods
|
||||
switch (actorParams) {
|
||||
case 0x00:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_LW_DEKU_SCRUB_NEAR_DEKU_THEATER_RIGHT;
|
||||
scrubIdentity.randomizerCheck = RC_LW_DEKU_SCRUB_NEAR_DEKU_THEATER_RIGHT;
|
||||
break;
|
||||
case 0x01:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_LW_DEKU_SCRUB_NEAR_DEKU_THEATER_LEFT;
|
||||
scrubIdentity.randomizerCheck = RC_LW_DEKU_SCRUB_NEAR_DEKU_THEATER_LEFT;
|
||||
break;
|
||||
case 0x09:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_LW_DEKU_SCRUB_NEAR_BRIDGE;
|
||||
scrubIdentity.randomizerCheck = RC_LW_DEKU_SCRUB_NEAR_BRIDGE;
|
||||
scrubIdentity.isShuffled = true;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case SCENE_SPOT17: // Death Mountain Crater
|
||||
switch (actorParams) {
|
||||
case 0x05:
|
||||
scrubIdentity.randomizerInf = RAND_INF_SCRUBS_PURCHASED_DMC_DEKU_SCRUB;
|
||||
scrubIdentity.randomizerCheck = RC_DMC_DEKU_SCRUB;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
if (randomizerMerchantPrices.find(scrubIdentity.randomizerCheck) != randomizerMerchantPrices.end()) {
|
||||
scrubIdentity.itemPrice = randomizerMerchantPrices[scrubIdentity.randomizerCheck];
|
||||
}
|
||||
|
||||
return scrubIdentity;
|
||||
}
|
||||
|
||||
u8 Randomizer::GetRandoSettingValue(RandomizerSettingKey randoSettingKey) {
|
||||
return this->randoSettings[randoSettingKey];
|
||||
}
|
||||
@ -2180,10 +2469,6 @@ RandomizerCheck Randomizer::GetCheckFromActor(s16 sceneNum, s16 actorId, s16 act
|
||||
break;
|
||||
case 62:
|
||||
switch (actorParams) {
|
||||
case 2:
|
||||
return RC_HF_DEKU_SCRUB_GROTTO;
|
||||
case 10:
|
||||
return RC_LW_DEKU_SCRUB_GROTTO_FRONT;
|
||||
case 22988:
|
||||
return RC_KF_STORMS_GROTTO_CHEST;
|
||||
case -22988:
|
||||
@ -2448,8 +2733,6 @@ RandomizerCheck Randomizer::GetCheckFromActor(s16 sceneNum, s16 actorId, s16 act
|
||||
break;
|
||||
case 91:
|
||||
switch (actorParams) {
|
||||
case 9:
|
||||
return RC_LW_DEKU_SCRUB_NEAR_BRIDGE;
|
||||
case 14365:
|
||||
return RC_LW_GOSSIP_STONE;
|
||||
case 27905:
|
||||
@ -2614,6 +2897,7 @@ void GenerateRandomizerImgui() {
|
||||
cvarSettings[RSK_SHUFFLE_DUNGEON_REWARDS] = CVar_GetS32("gRandomizeShuffleDungeonReward", 0);
|
||||
cvarSettings[RSK_SHUFFLE_SONGS] = CVar_GetS32("gRandomizeShuffleSongs", 0);
|
||||
cvarSettings[RSK_SHUFFLE_TOKENS] = CVar_GetS32("gRandomizeShuffleTokens", 0);
|
||||
cvarSettings[RSK_SHUFFLE_SCRUBS] = CVar_GetS32("gRandomizeShuffleScrubs", 0);
|
||||
cvarSettings[RSK_SHUFFLE_COWS] = CVar_GetS32("gRandomizeShuffleCows", 0);
|
||||
cvarSettings[RSK_SHUFFLE_ADULT_TRADE] = CVar_GetS32("gRandomizeShuffleAdultTrade", 0);
|
||||
cvarSettings[RSK_SHUFFLE_MAGIC_BEANS] = CVar_GetS32("gRandomizeShuffleBeans", 0);
|
||||
@ -3111,6 +3395,20 @@ void DrawRandoEditor(bool& open) {
|
||||
SohImGui::EnhancementCombobox("gRandomizeShuffleSongs", randoShuffleSongs, 3, 0);
|
||||
PaddedSeparator();
|
||||
|
||||
// Shuffle Scrubs
|
||||
ImGui::Text(Settings::Scrubsanity.GetName().c_str());
|
||||
InsertHelpHoverText(
|
||||
"Off - Scrubs will not be shuffled. The 3 Scrubs that give one-time items in the vanilla game (PoH, Deku Nut capacity, and Deku Stick capacity) will have random items.\n"
|
||||
"\n"
|
||||
"Affordable - Scrubs will be shuffled and their item will cost 10 rupees.\n"
|
||||
"\n"
|
||||
"Expensive - Scrubs will be shuffled and their item will cost the vanilla price.\n"
|
||||
"\n"
|
||||
"Random - Scrubs will be shuffled and their item will cost will be between 0-95 rupees.\n"
|
||||
);
|
||||
SohImGui::EnhancementCombobox("gRandomizeShuffleScrubs", randoShuffleScrubs, 4, 0);
|
||||
PaddedSeparator();
|
||||
|
||||
// Shuffle Tokens
|
||||
ImGui::Text(Settings::Tokensanity.GetName().c_str());
|
||||
InsertHelpHoverText("Shuffles Golden Skulltula Tokens into the item pool. This means "
|
||||
@ -3131,10 +3429,10 @@ void DrawRandoEditor(bool& open) {
|
||||
"expected to be collected after getting Sun's Song.");
|
||||
PaddedSeparator();
|
||||
|
||||
|
||||
// Shuffle Cows
|
||||
SohImGui::EnhancementCheckbox(Settings::ShuffleCows.GetName().c_str(), "gRandomizeShuffleCows");
|
||||
InsertHelpHoverText(
|
||||
"Cows give a randomized item from the pool upon performing Epona's Song in front of them.");
|
||||
InsertHelpHoverText("Cows give a randomized item from the pool upon performing Epona's Song in front of them.");
|
||||
PaddedSeparator();
|
||||
|
||||
// Shuffle Adult Trade Quest
|
||||
@ -3332,8 +3630,8 @@ void DrawRandoEditor(bool& open) {
|
||||
ImGui::PushStyleVar(ImGuiStyleVar_CellPadding, cellPadding);
|
||||
if (ImGui::BeginTable("tableRandoOther", 3, ImGuiTableFlags_BordersH | ImGuiTableFlags_BordersV)) {
|
||||
ImGui::TableSetupColumn("Timesavers", ImGuiTableColumnFlags_WidthStretch, 200.0f);
|
||||
ImGui::TableSetupColumn("Hint Settings", ImGuiTableColumnFlags_WidthStretch, 200.0f);
|
||||
ImGui::TableSetupColumn("Item Pool Settings", ImGuiTableColumnFlags_WidthStretch, 200.0f);
|
||||
ImGui::TableSetupColumn("World Settings", ImGuiTableColumnFlags_WidthStretch, 200.0f);
|
||||
ImGui::TableSetupColumn("Item Pool & Hint Settings", ImGuiTableColumnFlags_WidthStretch, 200.0f);
|
||||
ImGui::PushItemFlag(ImGuiItemFlags_Disabled, true);
|
||||
ImGui::TableHeadersRow();
|
||||
ImGui::PopItemFlag();
|
||||
@ -3405,10 +3703,49 @@ void DrawRandoEditor(bool& open) {
|
||||
"The cutscenes of the Poes in Forest Temple and Darunia in Fire Temple will not be skipped. "
|
||||
"These cutscenes are only useful for glitched gameplay and can be safely skipped otherwise.");
|
||||
|
||||
// COLUMN 2 - HINT SETTINGS
|
||||
// COLUMN 2 - WORLD SETTINGS
|
||||
ImGui::TableNextColumn();
|
||||
window->DC.CurrLineTextBaseOffset = 0.0f;
|
||||
ImGui::PushItemWidth(-FLT_MIN);
|
||||
ImGui::Text("Coming soon");
|
||||
|
||||
ImGui::PopItemWidth();
|
||||
|
||||
// COLUMN 3 - ITEM POOL & HINT SETTINGS
|
||||
ImGui::TableNextColumn();
|
||||
window->DC.CurrLineTextBaseOffset = 0.0f;
|
||||
ImGui::PushItemWidth(-FLT_MIN);
|
||||
|
||||
ImGui::Text(Settings::ItemPoolValue.GetName().c_str());
|
||||
InsertHelpHoverText("Sets how many major items appear in the item pool.\n"
|
||||
"\n"
|
||||
"Plentiful - Extra major items are added to the pool.\n"
|
||||
"\n"
|
||||
"Balanced - Original item pool.\n"
|
||||
"\n"
|
||||
"Scarce - Some excess items are removed, including health upgrades.\n"
|
||||
"\n"
|
||||
"Minimal - Most excess items are removed.");
|
||||
SohImGui::EnhancementCombobox("gRandomizeItemPool", randoItemPool, 4, 1);
|
||||
PaddedSeparator();
|
||||
|
||||
// Ice Traps
|
||||
ImGui::Text(Settings::IceTrapValue.GetName().c_str());
|
||||
InsertHelpHoverText("Sets how many items are replaced by ice traps.\n"
|
||||
"\n"
|
||||
"Off - No ice traps.\n"
|
||||
"\n"
|
||||
"Normal - Only Ice Traps from the base item pool are shuffled in.\n"
|
||||
"\n"
|
||||
"Extra - Chance to replace added junk items with additional ice traps.\n"
|
||||
"\n"
|
||||
"Mayhem - All added junk items will be Ice Traps.\n"
|
||||
"\n"
|
||||
"Onslaught - All junk items will be replaced by Ice Traps, even those "
|
||||
"in the base pool.");
|
||||
SohImGui::EnhancementCombobox("gRandomizeIceTraps", randoIceTraps, 5, 1);
|
||||
|
||||
PaddedSeparator();
|
||||
|
||||
// Gossip Stone Hints
|
||||
ImGui::Text(Settings::GossipStoneHints.GetName().c_str());
|
||||
@ -3458,40 +3795,7 @@ void DrawRandoEditor(bool& open) {
|
||||
SohImGui::EnhancementCombobox("gRandomizeHintDistribution", randoHintDistribution, 4, 1);
|
||||
ImGui::Unindent();
|
||||
}
|
||||
ImGui::PopItemWidth();
|
||||
|
||||
// COLUMN 3 - ITEM POOL SETTINGS
|
||||
ImGui::TableNextColumn();
|
||||
window->DC.CurrLineTextBaseOffset = 0.0f;
|
||||
ImGui::PushItemWidth(-FLT_MIN);
|
||||
ImGui::Text(Settings::ItemPoolValue.GetName().c_str());
|
||||
InsertHelpHoverText("Sets how many major items appear in the item pool.\n"
|
||||
"\n"
|
||||
"Plentiful - Extra major items are added to the pool.\n"
|
||||
"\n"
|
||||
"Balanced - Original item pool.\n"
|
||||
"\n"
|
||||
"Scarce - Some excess items are removed, including health upgrades.\n"
|
||||
"\n"
|
||||
"Minimal - Most excess items are removed.");
|
||||
SohImGui::EnhancementCombobox("gRandomizeItemPool", randoItemPool, 4, 1);
|
||||
PaddedSeparator();
|
||||
|
||||
// Ice Traps
|
||||
ImGui::Text(Settings::IceTrapValue.GetName().c_str());
|
||||
InsertHelpHoverText("Sets how many items are replaced by ice traps.\n"
|
||||
"\n"
|
||||
"Off - No ice traps.\n"
|
||||
"\n"
|
||||
"Normal - Only Ice Traps from the base item pool are shuffled in.\n"
|
||||
"\n"
|
||||
"Extra - Chance to replace added junk items with additional ice traps.\n"
|
||||
"\n"
|
||||
"Mayhem - All added junk items will be Ice Traps.\n"
|
||||
"\n"
|
||||
"Onslaught - All junk items will be replaced by Ice Traps, even those "
|
||||
"in the base pool.");
|
||||
SohImGui::EnhancementCombobox("gRandomizeIceTraps", randoIceTraps, 5, 1);
|
||||
ImGui::PopItemWidth();
|
||||
ImGui::EndTable();
|
||||
}
|
||||
@ -3724,11 +4028,19 @@ void CreateGetItemMessages(std::vector<GetItemMessage> messageEntries) {
|
||||
}
|
||||
}
|
||||
|
||||
// Currently these are generated at runtime, one for each price between 0-95. We're soon going to migrate this
|
||||
// to being generated at save load, with only messages specific to each scrub.
|
||||
void CreateScrubMessages() {
|
||||
CustomMessageManager* customMessageManager = CustomMessageManager::Instance;
|
||||
customMessageManager->AddCustomMessageTable(Randomizer::scrubMessageTableID);
|
||||
const std::vector<u8> prices = { 10, 40 };
|
||||
for (u8 price : prices) {
|
||||
customMessageManager->CreateMessage(Randomizer::scrubMessageTableID, 0,
|
||||
{ TEXTBOX_TYPE_BLACK, TEXTBOX_POS_BOTTOM,
|
||||
"\x12\x38\x82\All right! You win! In return for&sparing me, I will give you a&%gmysterious item%w!&Please, take it!\x07\x10\xA3",
|
||||
"\x12\x38\x82\In Ordnung! Du gewinnst! Im Austausch&dafür, dass du mich verschont hast,&werde ich dir einen %gmysteriösen&Gegenstand%w geben! Bitte nimm ihn!\x07\x10\xA3",
|
||||
"\x12\x38\x82\D'accord! Vous avez gagné! En échange&de m'épargner, je vous donnerai un &%gobjet mystérieux%w! S'il vous plaît,&prenez-le!\x07\x10\xA3",
|
||||
});
|
||||
|
||||
for (u32 price = 5; price <= 95; price += 5) {
|
||||
customMessageManager->CreateMessage(Randomizer::scrubMessageTableID, price,
|
||||
{ TEXTBOX_TYPE_BLACK, TEXTBOX_POS_BOTTOM,
|
||||
"\x12\x38\x82\All right! You win! In return for&sparing me, I will sell you a&%gmysterious item%w!&%r" +
|
||||
@ -4115,6 +4427,14 @@ void InitRandoItemTable() {
|
||||
ItemTableManager::Instance->AddItemEntry(MOD_RANDOMIZER, extendedVanillaGetItemTable[i].getItemId, extendedVanillaGetItemTable[i]);
|
||||
}
|
||||
for (int i = 0; i < ARRAY_COUNT(randoGetItemTable); i++) {
|
||||
if (randoGetItemTable[i].itemId >= RG_FOREST_TEMPLE_SMALL_KEY && randoGetItemTable[i].itemId <= RG_GANONS_CASTLE_SMALL_KEY
|
||||
&& randoGetItemTable[i].itemId != RG_GERUDO_FORTRESS_SMALL_KEY) {
|
||||
randoGetItemTable[i].drawFunc = (CustomDrawFunc)Randomizer_DrawSmallKey;
|
||||
} else if (randoGetItemTable[i].itemId >= RG_FOREST_TEMPLE_BOSS_KEY && randoGetItemTable[i].itemId <= RG_GANONS_CASTLE_BOSS_KEY) {
|
||||
randoGetItemTable[i].drawFunc = (CustomDrawFunc)Randomizer_DrawBossKey;
|
||||
} else if (randoGetItemTable[i].itemId == RG_DOUBLE_DEFENSE) {
|
||||
randoGetItemTable[i].drawFunc = (CustomDrawFunc)Randomizer_DrawDoubleDefense;
|
||||
}
|
||||
ItemTableManager::Instance->AddItemEntry(MOD_RANDOMIZER, randoGetItemTable[i].itemId, randoGetItemTable[i]);
|
||||
}
|
||||
}
|
||||
|
@ -19,6 +19,7 @@ class Randomizer {
|
||||
std::string ganonHintText;
|
||||
std::string ganonText;
|
||||
std::unordered_map<RandomizerSettingKey, u8> randoSettings;
|
||||
std::unordered_map<RandomizerCheck, u16> randomizerMerchantPrices;
|
||||
s16 GetItemFromGet(RandomizerGet randoGet, GetItemID ogItemId);
|
||||
s16 GetItemFromActor(s16 actorId, s16 actorParams, s16 sceneNum, GetItemID ogItemId);
|
||||
void ParseRandomizerSettingsFile(const char* spoilerFileName);
|
||||
@ -50,6 +51,7 @@ class Randomizer {
|
||||
std::string GetAdultAltarText() const;
|
||||
std::string GetGanonText() const;
|
||||
std::string GetGanonHintText() const;
|
||||
ScrubIdentity IdentifyScrub(s32 sceneNum, s32 actorParams, s32 respawnData);
|
||||
s16 GetRandomizedItemIdFromKnownCheck(RandomizerCheck randomizerCheck, GetItemID ogId);
|
||||
s16 GetRandomizedItemId(GetItemID ogId, s16 actorId, s16 actorParams, s16 sceneNum);
|
||||
static void CreateCustomMessages();
|
||||
|
@ -1,6 +1,8 @@
|
||||
#pragma once
|
||||
|
||||
#include <stdint.h>
|
||||
#include "z64item.h"
|
||||
#include "randomizer_inf.h"
|
||||
|
||||
// This should probably go in a less rando-specific location
|
||||
// but the best location will probably be in the modding engine
|
||||
@ -987,6 +989,7 @@ typedef enum {
|
||||
RSK_SHUFFLE_DUNGEON_REWARDS,
|
||||
RSK_SHUFFLE_SONGS,
|
||||
RSK_SHUFFLE_TOKENS,
|
||||
RSK_SHUFFLE_SCRUBS,
|
||||
RSK_SHUFFLE_COWS,
|
||||
RSK_SHUFFLE_WEIRD_EGG,
|
||||
RSK_SHUFFLE_GERUDO_MEMBERSHIP_CARD,
|
||||
@ -1016,3 +1019,11 @@ typedef enum {
|
||||
RSK_SHUFFLE_ADULT_TRADE,
|
||||
RSK_SHUFFLE_MAGIC_BEANS
|
||||
} RandomizerSettingKey;
|
||||
|
||||
typedef struct ScrubIdentity {
|
||||
RandomizerInf randomizerInf;
|
||||
RandomizerCheck randomizerCheck;
|
||||
GetItemID getItemId;
|
||||
int32_t itemPrice;
|
||||
bool isShuffled;
|
||||
} ScrubIdentity;
|
||||
|
72
soh/soh/Enhancements/randomizer/randomizer_inf.h
Normal file
72
soh/soh/Enhancements/randomizer/randomizer_inf.h
Normal file
@ -0,0 +1,72 @@
|
||||
#pragma once
|
||||
|
||||
typedef enum {
|
||||
RAND_INF_DUNGEONS_DONE_DEKU_TREE,
|
||||
RAND_INF_DUNGEONS_DONE_DODONGOS_CAVERN,
|
||||
RAND_INF_DUNGEONS_DONE_JABU_JABUS_BELLY,
|
||||
RAND_INF_DUNGEONS_DONE_FOREST_TEMPLE,
|
||||
RAND_INF_DUNGEONS_DONE_FIRE_TEMPLE,
|
||||
RAND_INF_DUNGEONS_DONE_WATER_TEMPLE,
|
||||
RAND_INF_DUNGEONS_DONE_SPIRIT_TEMPLE,
|
||||
RAND_INF_DUNGEONS_DONE_SHADOW_TEMPLE,
|
||||
|
||||
RAND_INF_TRIALS_DONE_LIGHT_TRIAL,
|
||||
RAND_INF_TRIALS_DONE_FOREST_TRIAL,
|
||||
RAND_INF_TRIALS_DONE_FIRE_TRIAL,
|
||||
RAND_INF_TRIALS_DONE_WATER_TRIAL,
|
||||
RAND_INF_TRIALS_DONE_SPIRIT_TRIAL,
|
||||
RAND_INF_TRIALS_DONE_SHADOW_TRIAL,
|
||||
|
||||
RAND_INF_COWS_MILKED_LINKS_HOUSE_COW,
|
||||
RAND_INF_COWS_MILKED_HF_COW_GROTTO_COW,
|
||||
RAND_INF_COWS_MILKED_LLR_STABLES_LEFT_COW,
|
||||
RAND_INF_COWS_MILKED_LLR_STABLES_RIGHT_COW,
|
||||
RAND_INF_COWS_MILKED_LLR_TOWER_LEFT_COW,
|
||||
RAND_INF_COWS_MILKED_LLR_TOWER_RIGHT_COW,
|
||||
RAND_INF_COWS_MILKED_KAK_IMPAS_HOUSE_COW,
|
||||
RAND_INF_COWS_MILKED_DMT_COW_GROTTO_COW,
|
||||
RAND_INF_COWS_MILKED_GV_COW,
|
||||
RAND_INF_COWS_MILKED_JABU_JABUS_BELLY_MQ_COW,
|
||||
RAND_INF_COWS_MILKED_HF_COW_GROTTO_GOSSIP_STONE,
|
||||
|
||||
RAND_INF_SCRUBS_PURCHASED_DODONGOS_CAVERN_DEKU_SCRUB_NEAR_BOMB_BAG_LEFT,
|
||||
RAND_INF_SCRUBS_PURCHASED_DODONGOS_CAVERN_DEKU_SCRUB_SIDE_ROOM_NEAR_DODONGOS,
|
||||
RAND_INF_SCRUBS_PURCHASED_DODONGOS_CAVERN_DEKU_SCRUB_NEAR_BOMB_BAG_RIGHT,
|
||||
RAND_INF_SCRUBS_PURCHASED_DODONGOS_CAVERN_DEKU_SCRUB_LOBBY,
|
||||
RAND_INF_SCRUBS_PURCHASED_JABU_JABUS_BELLY_DEKU_SCRUB,
|
||||
RAND_INF_SCRUBS_PURCHASED_GANONS_CASTLE_DEKU_SCRUB_CENTER_LEFT,
|
||||
RAND_INF_SCRUBS_PURCHASED_GANONS_CASTLE_DEKU_SCRUB_CENTER_RIGHT,
|
||||
RAND_INF_SCRUBS_PURCHASED_GANONS_CASTLE_DEKU_SCRUB_RIGHT,
|
||||
RAND_INF_SCRUBS_PURCHASED_GANONS_CASTLE_DEKU_SCRUB_LEFT,
|
||||
RAND_INF_SCRUBS_PURCHASED_HF_DEKU_SCRUB_GROTTO,
|
||||
RAND_INF_SCRUBS_PURCHASED_ZR_DEKU_SCRUB_GROTTO_REAR,
|
||||
RAND_INF_SCRUBS_PURCHASED_ZR_DEKU_SCRUB_GROTTO_FRONT,
|
||||
RAND_INF_SCRUBS_PURCHASED_SFM_DEKU_SCRUB_GROTTO_REAR,
|
||||
RAND_INF_SCRUBS_PURCHASED_SFM_DEKU_SCRUB_GROTTO_FRONT,
|
||||
RAND_INF_SCRUBS_PURCHASED_LH_DEKU_SCRUB_GROTTO_LEFT,
|
||||
RAND_INF_SCRUBS_PURCHASED_LH_DEKU_SCRUB_GROTTO_RIGHT,
|
||||
RAND_INF_SCRUBS_PURCHASED_LH_DEKU_SCRUB_GROTTO_CENTER,
|
||||
RAND_INF_SCRUBS_PURCHASED_GV_DEKU_SCRUB_GROTTO_REAR,
|
||||
RAND_INF_SCRUBS_PURCHASED_GV_DEKU_SCRUB_GROTTO_FRONT,
|
||||
RAND_INF_SCRUBS_PURCHASED_LW_DEKU_SCRUB_GROTTO_REAR,
|
||||
RAND_INF_SCRUBS_PURCHASED_LW_DEKU_SCRUB_GROTTO_FRONT,
|
||||
RAND_INF_SCRUBS_PURCHASED_DMC_DEKU_SCRUB_GROTTO_LEFT,
|
||||
RAND_INF_SCRUBS_PURCHASED_DMC_DEKU_SCRUB_GROTTO_RIGHT,
|
||||
RAND_INF_SCRUBS_PURCHASED_DMC_DEKU_SCRUB_GROTTO_CENTER,
|
||||
RAND_INF_SCRUBS_PURCHASED_GC_DEKU_SCRUB_GROTTO_LEFT,
|
||||
RAND_INF_SCRUBS_PURCHASED_GC_DEKU_SCRUB_GROTTO_RIGHT,
|
||||
RAND_INF_SCRUBS_PURCHASED_GC_DEKU_SCRUB_GROTTO_CENTER,
|
||||
RAND_INF_SCRUBS_PURCHASED_LLR_DEKU_SCRUB_GROTTO_LEFT,
|
||||
RAND_INF_SCRUBS_PURCHASED_LLR_DEKU_SCRUB_GROTTO_RIGHT,
|
||||
RAND_INF_SCRUBS_PURCHASED_LLR_DEKU_SCRUB_GROTTO_CENTER,
|
||||
RAND_INF_SCRUBS_PURCHASED_COLOSSUS_DEKU_SCRUB_GROTTO_REAR,
|
||||
RAND_INF_SCRUBS_PURCHASED_COLOSSUS_DEKU_SCRUB_GROTTO_FRONT,
|
||||
RAND_INF_SCRUBS_PURCHASED_LW_DEKU_SCRUB_NEAR_DEKU_THEATER_RIGHT,
|
||||
RAND_INF_SCRUBS_PURCHASED_LW_DEKU_SCRUB_NEAR_DEKU_THEATER_LEFT,
|
||||
RAND_INF_SCRUBS_PURCHASED_LW_DEKU_SCRUB_NEAR_BRIDGE,
|
||||
RAND_INF_SCRUBS_PURCHASED_DMC_DEKU_SCRUB,
|
||||
|
||||
// If you add anything to this list, you need to update the size of randomizerInf in z64save.h to be ceil(RAND_INF_MAX / 16)
|
||||
|
||||
RAND_INF_MAX,
|
||||
} RandomizerInf;
|
@ -76,7 +76,34 @@ std::vector<ItemTrackerItem> songItems = {
|
||||
ITEM_TRACKER_ITEM(QUEST_SONG_REQUIEM, 0, DrawSong), ITEM_TRACKER_ITEM(QUEST_SONG_NOCTURNE, 0, DrawSong), ITEM_TRACKER_ITEM(QUEST_SONG_PRELUDE, 0, DrawSong),
|
||||
};
|
||||
|
||||
std::vector<ItemTrackerDungeon> itemTrackerDungeons = {
|
||||
std::vector<ItemTrackerDungeon> itemTrackerDungeonsWithMapsHorizontal = {
|
||||
{ SCENE_YDAN, { ITEM_DUNGEON_MAP, ITEM_COMPASS } },
|
||||
{ SCENE_DDAN, { ITEM_DUNGEON_MAP, ITEM_COMPASS } },
|
||||
{ SCENE_BDAN, { ITEM_DUNGEON_MAP, ITEM_COMPASS } },
|
||||
{ SCENE_BMORI1, { ITEM_KEY_SMALL, ITEM_KEY_BOSS, ITEM_DUNGEON_MAP, ITEM_COMPASS } },
|
||||
{ SCENE_HIDAN, { ITEM_KEY_SMALL, ITEM_KEY_BOSS, ITEM_DUNGEON_MAP, ITEM_COMPASS } },
|
||||
{ SCENE_MIZUSIN, { ITEM_KEY_SMALL, ITEM_KEY_BOSS, ITEM_DUNGEON_MAP, ITEM_COMPASS } },
|
||||
{ SCENE_JYASINZOU, { ITEM_KEY_SMALL, ITEM_KEY_BOSS, ITEM_DUNGEON_MAP, ITEM_COMPASS } },
|
||||
{ SCENE_HAKADAN, { ITEM_KEY_SMALL, ITEM_KEY_BOSS, ITEM_DUNGEON_MAP, ITEM_COMPASS } },
|
||||
{ SCENE_GANONTIKA, { ITEM_KEY_SMALL, ITEM_KEY_BOSS } },
|
||||
{ SCENE_HAKADANCH, { ITEM_KEY_SMALL, ITEM_DUNGEON_MAP, ITEM_COMPASS } },
|
||||
{ SCENE_ICE_DOUKUTO, { ITEM_DUNGEON_MAP, ITEM_COMPASS } },
|
||||
{ SCENE_MEN, { ITEM_KEY_SMALL } },
|
||||
};
|
||||
|
||||
std::vector<ItemTrackerDungeon> itemTrackerDungeonsHorizontal = {
|
||||
{ SCENE_BMORI1, { ITEM_KEY_SMALL, ITEM_KEY_BOSS } },
|
||||
{ SCENE_HIDAN, { ITEM_KEY_SMALL, ITEM_KEY_BOSS } },
|
||||
{ SCENE_MIZUSIN, { ITEM_KEY_SMALL, ITEM_KEY_BOSS } },
|
||||
{ SCENE_JYASINZOU, { ITEM_KEY_SMALL, ITEM_KEY_BOSS } },
|
||||
{ SCENE_HAKADAN, { ITEM_KEY_SMALL, ITEM_KEY_BOSS } },
|
||||
{ SCENE_GANONTIKA, { ITEM_KEY_SMALL, ITEM_KEY_BOSS } },
|
||||
{ SCENE_HAKADANCH, { ITEM_KEY_SMALL } },
|
||||
{ SCENE_MEN, { ITEM_KEY_SMALL } },
|
||||
};
|
||||
|
||||
|
||||
std::vector<ItemTrackerDungeon> itemTrackerDungeonsWithMapsCompact = {
|
||||
{ SCENE_BMORI1, { ITEM_KEY_SMALL, ITEM_KEY_BOSS, ITEM_DUNGEON_MAP, ITEM_COMPASS } },
|
||||
{ SCENE_HIDAN, { ITEM_KEY_SMALL, ITEM_KEY_BOSS, ITEM_DUNGEON_MAP, ITEM_COMPASS } },
|
||||
{ SCENE_MIZUSIN, { ITEM_KEY_SMALL, ITEM_KEY_BOSS, ITEM_DUNGEON_MAP, ITEM_COMPASS } },
|
||||
@ -87,9 +114,20 @@ std::vector<ItemTrackerDungeon> itemTrackerDungeons = {
|
||||
{ SCENE_DDAN, { ITEM_DUNGEON_MAP, ITEM_COMPASS } },
|
||||
{ SCENE_BDAN, { ITEM_DUNGEON_MAP, ITEM_COMPASS } },
|
||||
{ SCENE_ICE_DOUKUTO, { ITEM_DUNGEON_MAP, ITEM_COMPASS } },
|
||||
{ SCENE_GANON, { ITEM_KEY_SMALL, ITEM_KEY_BOSS } },
|
||||
{ SCENE_GANONTIKA, { ITEM_KEY_SMALL, ITEM_KEY_BOSS } },
|
||||
{ SCENE_MEN, { ITEM_KEY_SMALL } },
|
||||
// { SCENE_GERUDOWAY, { ITEM_KEY_SMALL } }, // We're adding this manually for space
|
||||
};
|
||||
|
||||
std::vector<ItemTrackerDungeon> itemTrackerDungeonsCompact = {
|
||||
{ SCENE_BMORI1, { ITEM_KEY_SMALL, ITEM_KEY_BOSS } },
|
||||
{ SCENE_HIDAN, { ITEM_KEY_SMALL, ITEM_KEY_BOSS } },
|
||||
{ SCENE_MIZUSIN, { ITEM_KEY_SMALL, ITEM_KEY_BOSS } },
|
||||
{ SCENE_JYASINZOU, { ITEM_KEY_SMALL, ITEM_KEY_BOSS } },
|
||||
{ SCENE_HAKADAN, { ITEM_KEY_SMALL, ITEM_KEY_BOSS } },
|
||||
{ SCENE_GANONTIKA, { ITEM_KEY_SMALL, ITEM_KEY_BOSS } },
|
||||
{ SCENE_HAKADANCH, { ITEM_KEY_SMALL } },
|
||||
{ SCENE_MEN, { ITEM_KEY_SMALL } },
|
||||
{ SCENE_GERUDOWAY, { ITEM_KEY_SMALL } },
|
||||
};
|
||||
|
||||
std::map<uint16_t, std::string> itemTrackerDungeonShortNames = {
|
||||
@ -103,7 +141,7 @@ std::map<uint16_t, std::string> itemTrackerDungeonShortNames = {
|
||||
{ SCENE_DDAN, "DCVN" },
|
||||
{ SCENE_BDAN, "JABU" },
|
||||
{ SCENE_ICE_DOUKUTO, "ICE" },
|
||||
{ SCENE_GANON, "GANON" },
|
||||
{ SCENE_GANONTIKA, "GANON" },
|
||||
{ SCENE_MEN, "GTG" },
|
||||
{ SCENE_GERUDOWAY, "HIDE" },
|
||||
};
|
||||
@ -250,7 +288,7 @@ ImVec2 GetItemCurrentAndMax(ItemTrackerItem item) {
|
||||
case SCENE_HAKADANCH:
|
||||
result.y = 3;
|
||||
break;
|
||||
case SCENE_GANON:
|
||||
case SCENE_GANONTIKA:
|
||||
result.y = 2;
|
||||
break;
|
||||
case SCENE_MEN:
|
||||
@ -491,6 +529,7 @@ void BeginFloatingWindows(std::string UniqueName, ImGuiWindowFlags flags = 0) {
|
||||
}
|
||||
|
||||
if (!CVar_GetS32("gItemTrackerWindowType", 0)) {
|
||||
ImGui::SetNextWindowViewport(ImGui::GetMainViewport()->ID);
|
||||
windowFlags |= ImGuiWindowFlags_NoDocking | ImGuiWindowFlags_NoNav | ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoScrollWithMouse | ImGuiWindowFlags_NoScrollbar;
|
||||
|
||||
if (!CVar_GetS32("gItemTrackerHudEditMode", 0)) {
|
||||
@ -516,11 +555,12 @@ void EndFloatingWindows() {
|
||||
void DrawItemsInRows(std::vector<ItemTrackerItem> items, int columns = 6) {
|
||||
int iconSize = CVar_GetS32("gItemTrackerIconSize", 36);
|
||||
int iconSpacing = CVar_GetS32("gItemTrackerIconSpacing", 12);
|
||||
int topPadding = CVar_GetS32("gItemTrackerWindowType", 0) ? 20 : 0;
|
||||
|
||||
for (int i = 0; i < items.size(); i++) {
|
||||
int row = i / columns;
|
||||
int column = i % columns;
|
||||
ImGui::SetCursorPos(ImVec2((column * (iconSize + iconSpacing) + 8), (row * (iconSize + iconSpacing)) + 8));
|
||||
ImGui::SetCursorPos(ImVec2((column * (iconSize + iconSpacing) + 8), (row * (iconSize + iconSpacing)) + 8 + topPadding));
|
||||
items[i].drawFunc(items[i]);
|
||||
}
|
||||
}
|
||||
@ -555,13 +595,12 @@ std::vector<ItemTrackerItem> GetDungeonItemsVector(std::vector<ItemTrackerDungeo
|
||||
int iconSpacing = CVar_GetS32("gItemTrackerIconSpacing", 12);
|
||||
std::vector<ItemTrackerItem> dungeonItems = {};
|
||||
|
||||
// if (!CVar_GetS32("gItemTrackerDisplayDungeonItemsMaps", 1)) {
|
||||
// dungeons.erase(std::remove_if(dungeons.begin(), dungeons.end(), [](ItemTrackerDungeon d) {
|
||||
// return (d.id == SCENE_YDAN || d.id == SCENE_DDAN || d.id == SCENE_BDAN || d.id == SCENE_ICE_DOUKUTO);
|
||||
// }), dungeons.end());
|
||||
// }
|
||||
int rowCount = 0;
|
||||
for (int i = 0; i < dungeons.size(); i++) {
|
||||
if (dungeons[i].items.size() > rowCount) rowCount = dungeons[i].items.size();
|
||||
}
|
||||
|
||||
for (int i = 0; i < dungeons[i].items.size(); i++) {
|
||||
for (int i = 0; i < rowCount; i++) {
|
||||
for (int j = 0; j < MIN(dungeons.size(), columns); j++) {
|
||||
if (dungeons[j].items.size() > i) {
|
||||
switch (dungeons[j].items[i]) {
|
||||
@ -569,7 +608,12 @@ std::vector<ItemTrackerItem> GetDungeonItemsVector(std::vector<ItemTrackerDungeo
|
||||
dungeonItems.push_back(ITEM_TRACKER_ITEM(ITEM_KEY_SMALL, dungeons[j].id, DrawDungeonItem));
|
||||
break;
|
||||
case ITEM_KEY_BOSS:
|
||||
dungeonItems.push_back(ITEM_TRACKER_ITEM(ITEM_KEY_BOSS, dungeons[j].id, DrawDungeonItem));
|
||||
// Swap Ganon's Castle boss key to the right scene ID manually
|
||||
if (dungeons[j].id == SCENE_GANONTIKA) {
|
||||
dungeonItems.push_back(ITEM_TRACKER_ITEM(ITEM_KEY_BOSS, SCENE_GANON, DrawDungeonItem));
|
||||
} else {
|
||||
dungeonItems.push_back(ITEM_TRACKER_ITEM(ITEM_KEY_BOSS, dungeons[j].id, DrawDungeonItem));
|
||||
}
|
||||
break;
|
||||
case ITEM_DUNGEON_MAP:
|
||||
dungeonItems.push_back(ITEM_TRACKER_ITEM(ITEM_DUNGEON_MAP, dungeons[j].id, DrawDungeonItem));
|
||||
@ -640,11 +684,23 @@ void UpdateVectors() {
|
||||
|
||||
dungeonItems.clear();
|
||||
if (CVar_GetS32("gItemTrackerDisplayDungeonItemsHorizontal", 1) && CVar_GetS32("gItemTrackerDungeonItemsDisplayType", 2) == 2) {
|
||||
dungeonItems = GetDungeonItemsVector(itemTrackerDungeons, 12);
|
||||
dungeonItems[23] = ITEM_TRACKER_ITEM(ITEM_KEY_SMALL, SCENE_GERUDOWAY, DrawDungeonItem);
|
||||
if (CVar_GetS32("gItemTrackerDisplayDungeonItemsMaps", 1)) {
|
||||
dungeonItems = GetDungeonItemsVector(itemTrackerDungeonsWithMapsHorizontal, 12);
|
||||
// Manually adding Thieves Hideout to an open spot so we don't get an additional row for one item
|
||||
dungeonItems[23] = ITEM_TRACKER_ITEM(ITEM_KEY_SMALL, SCENE_GERUDOWAY, DrawDungeonItem);
|
||||
} else {
|
||||
// Manually adding Thieves Hideout to an open spot so we don't get an additional row for one item
|
||||
dungeonItems = GetDungeonItemsVector(itemTrackerDungeonsHorizontal, 8);
|
||||
dungeonItems[15] = ITEM_TRACKER_ITEM(ITEM_KEY_SMALL, SCENE_GERUDOWAY, DrawDungeonItem);
|
||||
}
|
||||
} else {
|
||||
dungeonItems = GetDungeonItemsVector(itemTrackerDungeons);
|
||||
dungeonItems[35] = ITEM_TRACKER_ITEM(ITEM_KEY_SMALL, SCENE_GERUDOWAY, DrawDungeonItem);
|
||||
if (CVar_GetS32("gItemTrackerDisplayDungeonItemsMaps", 1)) {
|
||||
dungeonItems = GetDungeonItemsVector(itemTrackerDungeonsWithMapsCompact);
|
||||
// Manually adding Thieves Hideout to an open spot so we don't get an additional row for one item
|
||||
dungeonItems[35] = ITEM_TRACKER_ITEM(ITEM_KEY_SMALL, SCENE_GERUDOWAY, DrawDungeonItem);
|
||||
} else {
|
||||
dungeonItems = GetDungeonItemsVector(itemTrackerDungeonsCompact);
|
||||
}
|
||||
}
|
||||
|
||||
mainWindowItems.clear();
|
||||
@ -693,7 +749,7 @@ void DrawItemTracker(bool& open) {
|
||||
bool comboButtonsHeld = buttonsPressed != nullptr && buttonsPressed[0].button & comboButton1Mask && buttonsPressed[0].button & comboButton2Mask;
|
||||
bool isPaused = CVar_GetS32("gItemTrackerShowOnlyPaused", 0) == 0 || gGlobalCtx != nullptr && gGlobalCtx->pauseCtx.state > 0;
|
||||
|
||||
if (isPaused && (CVar_GetS32("gItemTrackerDisplayType", 0) == 0 ? CVar_GetS32("gItemTrackerEnabled", 0) : comboButtonsHeld)) {
|
||||
if (CVar_GetS32("gItemTrackerWindowType", 0) == 1 || isPaused && (CVar_GetS32("gItemTrackerDisplayType", 0) == 0 ? CVar_GetS32("gItemTrackerEnabled", 0) : comboButtonsHeld)) {
|
||||
if (
|
||||
(CVar_GetS32("gItemTrackerInventoryItemsDisplayType", 1) == 1) ||
|
||||
(CVar_GetS32("gItemTrackerEquipmentItemsDisplayType", 1) == 1) ||
|
||||
@ -754,7 +810,11 @@ void DrawItemTracker(bool& open) {
|
||||
if (CVar_GetS32("gItemTrackerDungeonItemsDisplayType", 2) == 2) {
|
||||
BeginFloatingWindows("Dungeon Items Tracker");
|
||||
if (CVar_GetS32("gItemTrackerDisplayDungeonItemsHorizontal", 1)) {
|
||||
DrawItemsInRows(dungeonItems, 12);
|
||||
if (CVar_GetS32("gItemTrackerDisplayDungeonItemsMaps", 1)) {
|
||||
DrawItemsInRows(dungeonItems, 12);
|
||||
} else {
|
||||
DrawItemsInRows(dungeonItems, 8);
|
||||
}
|
||||
} else {
|
||||
DrawItemsInRows(dungeonItems);
|
||||
}
|
||||
@ -789,15 +849,7 @@ void DrawItemTrackerOptions(bool& open) {
|
||||
ImGui::TableSetupColumn("Section settings", ImGuiTableColumnFlags_WidthStretch, 200.0f);
|
||||
ImGui::TableHeadersRow();
|
||||
ImGui::TableNextRow();
|
||||
|
||||
ImGui::TableNextColumn();
|
||||
LabeledComboBoxRightAligned("Display Mode", "gItemTrackerDisplayType", { "Always", "Combo Button Hold" }, 0);
|
||||
if (CVar_GetS32("gItemTrackerDisplayType", 0) > 0) {
|
||||
LabeledComboBoxRightAligned("Combo Button 1", "gItemTrackerComboButton1", { "A", "B", "C-Up", "C-Down", "C-Left", "C-Right", "L", "Z", "R", "Start", "D-Up", "D-Down", "D-Left", "D-Right" }, 6);
|
||||
LabeledComboBoxRightAligned("Combo Button 2", "gItemTrackerComboButton2", { "A", "B", "C-Up", "C-Down", "C-Left", "C-Right", "L", "Z", "R", "Start", "D-Up", "D-Down", "D-Left", "D-Right" }, 8);
|
||||
}
|
||||
PaddedEnhancementCheckbox("Only enable while paused", "gItemTrackerShowOnlyPaused", 0);
|
||||
PaddedSeparator();
|
||||
ImGui::Text("BG Color");
|
||||
ImGui::SameLine();
|
||||
ImGui::PushItemWidth(ImGui::GetContentRegionAvail().x);
|
||||
@ -814,6 +866,12 @@ void DrawItemTrackerOptions(bool& open) {
|
||||
|
||||
if (CVar_GetS32("gItemTrackerWindowType", 0) == 0) {
|
||||
PaddedEnhancementCheckbox("Enable Dragging", "gItemTrackerHudEditMode", 0);
|
||||
PaddedEnhancementCheckbox("Only enable while paused", "gItemTrackerShowOnlyPaused", 0);
|
||||
LabeledComboBoxRightAligned("Display Mode", "gItemTrackerDisplayType", { "Always", "Combo Button Hold" }, 0);
|
||||
if (CVar_GetS32("gItemTrackerDisplayType", 0) > 0) {
|
||||
LabeledComboBoxRightAligned("Combo Button 1", "gItemTrackerComboButton1", { "A", "B", "C-Up", "C-Down", "C-Left", "C-Right", "L", "Z", "R", "Start", "D-Up", "D-Down", "D-Left", "D-Right" }, 6);
|
||||
LabeledComboBoxRightAligned("Combo Button 2", "gItemTrackerComboButton2", { "A", "B", "C-Up", "C-Down", "C-Left", "C-Right", "L", "Z", "R", "Start", "D-Up", "D-Down", "D-Left", "D-Right" }, 8);
|
||||
}
|
||||
}
|
||||
PaddedSeparator();
|
||||
SohImGui::EnhancementSliderInt("Icon size : %dpx", "##ITEMTRACKERICONSIZE", "gItemTrackerIconSize", 25, 128, "", 36, true);
|
||||
@ -838,8 +896,7 @@ void DrawItemTrackerOptions(bool& open) {
|
||||
if (CVar_GetS32("gItemTrackerDungeonItemsDisplayType", 2) == 2) {
|
||||
PaddedEnhancementCheckbox("Horizontal display", "gItemTrackerDisplayDungeonItemsHorizontal", 1);
|
||||
}
|
||||
// TODO: Re-add this, kinda complicated
|
||||
// PaddedEnhancementCheckbox("Maps and compasses", "gItemTrackerDisplayDungeonItemsMaps", 1);
|
||||
PaddedEnhancementCheckbox("Maps and compasses", "gItemTrackerDisplayDungeonItemsMaps", 1);
|
||||
}
|
||||
|
||||
if (CVar_GetS32("gItemTrackerDisplayType", 0) != 1) {
|
||||
|
@ -1578,18 +1578,12 @@ extern "C" RandomizerCheck Randomizer_GetCheckFromActor(s16 sceneNum, s16 actorI
|
||||
return OTRGlobals::Instance->gRandomizer->GetCheckFromActor(sceneNum, actorId, actorParams);
|
||||
}
|
||||
|
||||
extern "C" CustomMessageEntry Randomizer_GetScrubMessage(u16 scrubTextId) {
|
||||
int price = 0;
|
||||
switch (scrubTextId) {
|
||||
case TEXT_SCRUB_POH:
|
||||
price = 10;
|
||||
break;
|
||||
case TEXT_SCRUB_STICK_UPGRADE:
|
||||
case TEXT_SCRUB_NUT_UPGRADE:
|
||||
price = 40;
|
||||
break;
|
||||
}
|
||||
return CustomMessageManager::Instance->RetrieveMessage(Randomizer::scrubMessageTableID, price);
|
||||
extern "C" ScrubIdentity Randomizer_IdentifyScrub(s32 sceneNum, s32 actorParams, s32 respawnData) {
|
||||
return OTRGlobals::Instance->gRandomizer->IdentifyScrub(sceneNum, actorParams, respawnData);
|
||||
}
|
||||
|
||||
extern "C" CustomMessageEntry Randomizer_GetScrubMessage(s16 itemPrice) {
|
||||
return CustomMessageManager::Instance->RetrieveMessage(Randomizer::scrubMessageTableID, itemPrice);
|
||||
}
|
||||
|
||||
extern "C" CustomMessageEntry Randomizer_GetNaviMessage() {
|
||||
@ -1718,8 +1712,8 @@ extern "C" int CustomMessage_RetrieveIfExists(GlobalContext* globalCtx) {
|
||||
} else {
|
||||
messageEntry = Randomizer_GetGanonHintText();
|
||||
}
|
||||
} else if (textId == TEXT_SCRUB_POH || textId == TEXT_SCRUB_STICK_UPGRADE || textId == TEXT_SCRUB_NUT_UPGRADE) {
|
||||
messageEntry = Randomizer_GetScrubMessage(textId);
|
||||
} else if (textId >= 0x9000 && textId <= 0x905F) {
|
||||
messageEntry = Randomizer_GetScrubMessage((textId & ((1 << 8) - 1)));
|
||||
} else if (CVar_GetS32("gRandomizeRupeeNames", 0) &&
|
||||
(textId == TEXT_BLUE_RUPEE || textId == TEXT_RED_RUPEE || textId == TEXT_PURPLE_RUPEE ||
|
||||
textId == TEXT_HUGE_RUPEE)) {
|
||||
|
@ -96,6 +96,7 @@ Sprite* GetSeedTexture(uint8_t index);
|
||||
void Randomizer_LoadSettings(const char* spoilerFileName);
|
||||
u8 Randomizer_GetSettingValue(RandomizerSettingKey randoSettingKey);
|
||||
RandomizerCheck Randomizer_GetCheckFromActor(s16 actorId, s16 actorParams, s16 sceneNum);
|
||||
ScrubIdentity Randomizer_IdentifyScrub(s32 sceneNum, s32 actorParams, s32 respawnData);
|
||||
void Randomizer_LoadHintLocations(const char* spoilerFileName);
|
||||
void Randomizer_LoadItemLocations(const char* spoilerFileName, bool silent);
|
||||
GetItemEntry Randomizer_GetRandomizedItem(GetItemID ogId, s16 actorId, s16 actorParams, s16 sceneNum);
|
||||
|
@ -758,15 +758,8 @@ void SaveManager::LoadBaseVersion1() {
|
||||
SaveManager::Instance->LoadData("angle", gSaveContext.horseData.angle);
|
||||
});
|
||||
|
||||
SaveManager::Instance->LoadArray("dungeonsDone", ARRAY_COUNT(gSaveContext.dungeonsDone), [](size_t i) {
|
||||
SaveManager::Instance->LoadData("", gSaveContext.dungeonsDone[i]);
|
||||
});
|
||||
|
||||
SaveManager::Instance->LoadArray("trialsDone", ARRAY_COUNT(gSaveContext.trialsDone),
|
||||
[](size_t i) { SaveManager::Instance->LoadData("", gSaveContext.trialsDone[i]); });
|
||||
|
||||
SaveManager::Instance->LoadArray("cowsMilked", ARRAY_COUNT(gSaveContext.cowsMilked), [](size_t i) {
|
||||
SaveManager::Instance->LoadData("", gSaveContext.cowsMilked[i]);
|
||||
SaveManager::Instance->LoadArray("randomizerInf", ARRAY_COUNT(gSaveContext.randomizerInf), [](size_t i) {
|
||||
SaveManager::Instance->LoadData("", gSaveContext.randomizerInf[i]);
|
||||
});
|
||||
}
|
||||
|
||||
@ -922,15 +915,8 @@ void SaveManager::LoadBaseVersion2() {
|
||||
SaveManager::Instance->LoadData("angle", gSaveContext.horseData.angle);
|
||||
});
|
||||
|
||||
SaveManager::Instance->LoadArray("dungeonsDone", ARRAY_COUNT(gSaveContext.dungeonsDone), [](size_t i) {
|
||||
SaveManager::Instance->LoadData("", gSaveContext.dungeonsDone[i]);
|
||||
});
|
||||
|
||||
SaveManager::Instance->LoadArray("trialsDone", ARRAY_COUNT(gSaveContext.trialsDone),
|
||||
[](size_t i) { SaveManager::Instance->LoadData("", gSaveContext.trialsDone[i]); });
|
||||
|
||||
SaveManager::Instance->LoadArray("cowsMilked", ARRAY_COUNT(gSaveContext.cowsMilked), [](size_t i) {
|
||||
SaveManager::Instance->LoadData("", gSaveContext.cowsMilked[i]);
|
||||
SaveManager::Instance->LoadArray("randomizerInf", ARRAY_COUNT(gSaveContext.randomizerInf), [](size_t i) {
|
||||
SaveManager::Instance->LoadData("", gSaveContext.randomizerInf[i]);
|
||||
});
|
||||
}
|
||||
|
||||
@ -1082,15 +1068,8 @@ void SaveManager::SaveBase() {
|
||||
SaveManager::Instance->SaveData("angle", gSaveContext.horseData.angle);
|
||||
});
|
||||
|
||||
SaveManager::Instance->SaveArray("dungeonsDone", ARRAY_COUNT(gSaveContext.dungeonsDone), [](size_t i) {
|
||||
SaveManager::Instance->SaveData("", gSaveContext.dungeonsDone[i]);
|
||||
});
|
||||
|
||||
SaveManager::Instance->SaveArray("trialsDone", ARRAY_COUNT(gSaveContext.trialsDone),
|
||||
[](size_t i) { SaveManager::Instance->SaveData("", gSaveContext.trialsDone[i]); });
|
||||
|
||||
SaveManager::Instance->SaveArray("cowsMilked", ARRAY_COUNT(gSaveContext.cowsMilked), [](size_t i) {
|
||||
SaveManager::Instance->SaveData("", gSaveContext.cowsMilked[i]);
|
||||
SaveManager::Instance->SaveArray("randomizerInf", ARRAY_COUNT(gSaveContext.randomizerInf), [](size_t i) {
|
||||
SaveManager::Instance->SaveData("", gSaveContext.randomizerInf[i]);
|
||||
});
|
||||
}
|
||||
|
||||
|
@ -4705,6 +4705,20 @@ void Flags_SetInfTable(s32 flag) {
|
||||
gSaveContext.infTable[flag >> 4] |= (1 << (flag & 0xF));
|
||||
}
|
||||
|
||||
/**
|
||||
* Tests if "randomizerInf" flag is set.
|
||||
*/
|
||||
s32 Flags_GetRandomizerInf(RandomizerInf flag) {
|
||||
return gSaveContext.randomizerInf[flag >> 4] & (1 << (flag & 0xF));
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets "randomizerInf" flag.
|
||||
*/
|
||||
void Flags_SetRandomizerInf(RandomizerInf flag) {
|
||||
gSaveContext.randomizerInf[flag >> 4] |= (1 << (flag & 0xF));
|
||||
}
|
||||
|
||||
u32 func_80035BFC(GlobalContext* globalCtx, s16 arg1) {
|
||||
u16 retTextId = 0;
|
||||
|
||||
|
@ -395,6 +395,20 @@ void GetItem_Draw(GlobalContext* globalCtx, s16 drawId) {
|
||||
sDrawItemTable[drawId].drawFunc(globalCtx, drawId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Draw "Get Item" Model from a `GetItemEntry`
|
||||
* Uses the Custom Draw Function if it exists, or just calls `GetItem_Draw`
|
||||
*/
|
||||
void GetItemEntry_Draw(GlobalContext* globalCtx, GetItemEntry getItemEntry) {
|
||||
// RANDOTODO: Make this more flexible for easier toggling of individual item recolors in the future.
|
||||
if (getItemEntry.drawFunc != NULL &&
|
||||
(CVar_GetS32("gRandoMatchKeyColors", 0) || getItemEntry.getItemId == RG_DOUBLE_DEFENSE)) {
|
||||
getItemEntry.drawFunc(globalCtx, &getItemEntry);
|
||||
} else {
|
||||
GetItem_Draw(globalCtx, getItemEntry.gid);
|
||||
}
|
||||
}
|
||||
|
||||
// All remaining functions in this file are draw functions referenced in the table and called by the function above
|
||||
|
||||
/* 0x0178 */ u8 primXluColor[3];
|
||||
|
@ -1293,7 +1293,7 @@ void EnItem00_CustomItemsParticles(Actor* Parent, GlobalContext* globalCtx, GetI
|
||||
color_slot = 0;
|
||||
break;
|
||||
case RG_DOUBLE_DEFENSE:
|
||||
color_slot = 1;
|
||||
color_slot = 8;
|
||||
break;
|
||||
default:
|
||||
return;
|
||||
@ -1305,14 +1305,14 @@ void EnItem00_CustomItemsParticles(Actor* Parent, GlobalContext* globalCtx, GetI
|
||||
|
||||
s16* colors[9][3] = {
|
||||
{ 34, 255, 76 }, // Minuet and Magic Upgrades Colors
|
||||
{ 177, 35, 35 }, // Bolero and Double Defense Colors
|
||||
{ 177, 35, 35 }, // Bolero Colors
|
||||
{ 115, 251, 253 }, // Serenade Color
|
||||
{ 177, 122, 35 }, // Requiem Color
|
||||
{ 177, 28, 212 }, // Nocturne Color
|
||||
{ 255, 255, 92 }, // Prelude Color
|
||||
{ 31, 152, 49 }, // Stick Upgrade Color
|
||||
{ 222, 182, 20 }, // Nut Upgrade Color
|
||||
{ 255, 255, 255 } // White Color placeholder
|
||||
{ 255, 255, 255 } // Double Defense Color
|
||||
};
|
||||
|
||||
s16* colorsEnv[9][3] = {
|
||||
@ -1381,7 +1381,7 @@ void EnItem00_DrawCollectible(EnItem00* this, GlobalContext* globalCtx) {
|
||||
GetItemEntry randoGetItemEntry =
|
||||
Randomizer_GetRandomizedItem(this->getItemId, this->actor.id, this->ogParams, globalCtx->sceneNum);
|
||||
EnItem00_CustomItemsParticles(&this->actor, globalCtx, randoGetItemEntry);
|
||||
GetItem_Draw(globalCtx, randoGetItemEntry.gid);
|
||||
GetItemEntry_Draw(globalCtx, randoGetItemEntry);
|
||||
} else {
|
||||
s32 texIndex = this->actor.params - 3;
|
||||
|
||||
@ -1443,7 +1443,7 @@ void EnItem00_DrawHeartPiece(EnItem00* this, GlobalContext* globalCtx) {
|
||||
GetItemEntry randoGetItemEntry =
|
||||
Randomizer_GetRandomizedItem(GI_HEART_PIECE, this->actor.id, this->ogParams, globalCtx->sceneNum);
|
||||
EnItem00_CustomItemsParticles(&this->actor, globalCtx, randoGetItemEntry);
|
||||
GetItem_Draw(globalCtx, randoGetItemEntry.gid);
|
||||
GetItemEntry_Draw(globalCtx, randoGetItemEntry);
|
||||
} else {
|
||||
s32 pad;
|
||||
|
||||
|
@ -1642,12 +1642,16 @@ u8 Item_Give(GlobalContext* globalCtx, u8 item) {
|
||||
} else if ((item >= ITEM_SWORD_KOKIRI) && (item <= ITEM_SWORD_BGS)) {
|
||||
gSaveContext.inventory.equipment |= gBitFlags[item - ITEM_SWORD_KOKIRI] << gEquipShifts[EQUIP_SWORD];
|
||||
|
||||
// Both Giant's Knife and Biggoron Sword have the same Item ID, so this part handles both of them
|
||||
if (item == ITEM_SWORD_BGS) {
|
||||
gSaveContext.swordHealth = 8;
|
||||
|
||||
if (ALL_EQUIP_VALUE(EQUIP_SWORD) == 0xF
|
||||
||(gSaveContext.n64ddFlag && ALL_EQUIP_VALUE(EQUIP_SWORD) == 0xE)) { // In rando, when buying Giant's Knife, also check
|
||||
gSaveContext.inventory.equipment ^= 8 << gEquipShifts[EQUIP_SWORD]; // for 0xE in case we don't have Kokiri Sword
|
||||
// In rando, when buying Giant's Knife, also check
|
||||
// for 0xE in case we don't have Kokiri Sword
|
||||
if (ALL_EQUIP_VALUE(EQUIP_SWORD) == 0xF || (gSaveContext.n64ddFlag && ALL_EQUIP_VALUE(EQUIP_SWORD) == 0xE)) {
|
||||
|
||||
gSaveContext.inventory.equipment ^= 8 << gEquipShifts[EQUIP_SWORD];
|
||||
|
||||
if (gSaveContext.equips.buttonItems[0] == ITEM_SWORD_KNIFE) {
|
||||
gSaveContext.equips.buttonItems[0] = ITEM_SWORD_BGS;
|
||||
Interface_LoadItemIcon1(globalCtx, 0);
|
||||
@ -3597,15 +3601,15 @@ void Interface_DrawItemButtons(GlobalContext* globalCtx) {
|
||||
}
|
||||
int CUp_factor = (1 << 10) * C_Up_BTN_Size / CUpScaled;
|
||||
if (CVar_GetS32("gCBtnUPosType", 0) != 0) {
|
||||
C_Up_BTN_Pos[1] = CVar_GetS32("gCBtnUPosY", 0)-(CUpScale*13)+Y_Margins_CU;
|
||||
C_Up_BTN_Pos[1] = CVar_GetS32("gCBtnUPosY", 0)+Y_Margins_CU;
|
||||
if (CVar_GetS32("gCBtnUPosType", 0) == 1) {//Anchor Left
|
||||
if (CVar_GetS32("gCBtnUUseMargins", 0) != 0) {X_Margins_CU = Left_HUD_Margin;};
|
||||
C_Up_BTN_Pos[0] = OTRGetDimensionFromLeftEdge(CVar_GetS32("gCBtnUPosX", 0)-(CUpScale*13)+X_Margins_CU);
|
||||
C_Up_BTN_Pos[0] = OTRGetDimensionFromLeftEdge(CVar_GetS32("gCBtnUPosX", 0)+X_Margins_CU);
|
||||
} else if (CVar_GetS32("gCBtnUPosType", 0) == 2) {//Anchor Right
|
||||
if (CVar_GetS32("gCBtnUUseMargins", 0) != 0) {X_Margins_CU = Right_HUD_Margin;};
|
||||
C_Up_BTN_Pos[0] = OTRGetDimensionFromRightEdge(CVar_GetS32("gCBtnUPosX", 0)-(CUpScale*13)+X_Margins_CU);
|
||||
C_Up_BTN_Pos[0] = OTRGetDimensionFromRightEdge(CVar_GetS32("gCBtnUPosX", 0)+X_Margins_CU);
|
||||
} else if (CVar_GetS32("gCBtnUPosType", 0) == 3) {//Anchor None
|
||||
C_Up_BTN_Pos[0] = CVar_GetS32("gCBtnUPosX", 0)-(CUpScale*13);
|
||||
C_Up_BTN_Pos[0] = CVar_GetS32("gCBtnUPosX", 0);
|
||||
} else if (CVar_GetS32("gCBtnUPosType", 0) == 4) {//Hidden
|
||||
C_Up_BTN_Pos[0] = -9999;
|
||||
}
|
||||
@ -3623,15 +3627,15 @@ void Interface_DrawItemButtons(GlobalContext* globalCtx) {
|
||||
int CDown_factor = (1 << 10) * C_Down_BTN_Size / CDownScaled;
|
||||
int PositionAdjustment = CDownScaled/2;
|
||||
if (CVar_GetS32("gCBtnDPosType", 0) != 0) {
|
||||
C_Down_BTN_Pos[1] = CVar_GetS32("gCBtnDPosY", 0)-PositionAdjustment+Y_Margins_CD;
|
||||
C_Down_BTN_Pos[1] = CVar_GetS32("gCBtnDPosY", 0)+Y_Margins_CD;
|
||||
if (CVar_GetS32("gCBtnDPosType", 0) == 1) {//Anchor Left
|
||||
if (CVar_GetS32("gCBtnDUseMargins", 0) != 0) {X_Margins_CD = Left_HUD_Margin;};
|
||||
C_Down_BTN_Pos[0] = OTRGetDimensionFromLeftEdge(CVar_GetS32("gCBtnDPosX", 0)-PositionAdjustment+X_Margins_CD);
|
||||
C_Down_BTN_Pos[0] = OTRGetDimensionFromLeftEdge(CVar_GetS32("gCBtnDPosX", 0)+X_Margins_CD);
|
||||
} else if (CVar_GetS32("gCBtnDPosType", 0) == 2) {//Anchor Right
|
||||
if (CVar_GetS32("gCBtnDUseMargins", 0) != 0) {X_Margins_CD = Right_HUD_Margin;};
|
||||
C_Down_BTN_Pos[0] = OTRGetDimensionFromRightEdge(CVar_GetS32("gCBtnDPosX", 0)-PositionAdjustment+X_Margins_CD);
|
||||
C_Down_BTN_Pos[0] = OTRGetDimensionFromRightEdge(CVar_GetS32("gCBtnDPosX", 0)+X_Margins_CD);
|
||||
} else if (CVar_GetS32("gCBtnDPosType", 0) == 3) {//Anchor None
|
||||
C_Down_BTN_Pos[0] = CVar_GetS32("gCBtnDPosX", 0)-PositionAdjustment;
|
||||
C_Down_BTN_Pos[0] = CVar_GetS32("gCBtnDPosX", 0);
|
||||
} else if (CVar_GetS32("gCBtnDPosType", 0) == 4) {//Hidden
|
||||
C_Down_BTN_Pos[0] = -9999;
|
||||
}
|
||||
@ -3669,9 +3673,9 @@ void Interface_DrawItemButtons(GlobalContext* globalCtx) {
|
||||
gDPSetPrimColor(OVERLAY_DISP++, 0, 0, C_button_L.r, C_button_L.g, C_button_L.b, interfaceCtx->cLeftAlpha);
|
||||
}
|
||||
gSPWideTextureRectangle(OVERLAY_DISP++, C_Left_BTN_Pos[0] << 2, C_Left_BTN_Pos[1] << 2,
|
||||
(C_Left_BTN_Pos[0] + CLeftScaled) << 2,
|
||||
(C_Left_BTN_Pos[1] + CLeftScaled) << 2,
|
||||
G_TX_RENDERTILE, 0, 0, CLeft_factor, CLeft_factor);
|
||||
(C_Left_BTN_Pos[0] + R_ITEM_BTN_WIDTH(1)) << 2,
|
||||
(C_Left_BTN_Pos[1] + R_ITEM_BTN_WIDTH(1)) << 2,
|
||||
G_TX_RENDERTILE, 0, 0, R_ITEM_BTN_DD(1) << 1, R_ITEM_BTN_DD(1) << 1);
|
||||
|
||||
// C-Down Button Color & Texture
|
||||
if (CVar_GetS32("gHudColors", 1) == 0) {
|
||||
@ -3684,9 +3688,9 @@ void Interface_DrawItemButtons(GlobalContext* globalCtx) {
|
||||
gDPSetPrimColor(OVERLAY_DISP++, 0, 0, C_button_D.r, C_button_D.g, C_button_D.b, interfaceCtx->cDownAlpha);
|
||||
}
|
||||
gSPWideTextureRectangle(OVERLAY_DISP++, C_Down_BTN_Pos[0] << 2, C_Down_BTN_Pos[1] << 2,
|
||||
(C_Down_BTN_Pos[0] + CDownScaled) << 2,
|
||||
(C_Down_BTN_Pos[1] + CDownScaled) << 2,
|
||||
G_TX_RENDERTILE, 0, 0, CDown_factor, CDown_factor);
|
||||
(C_Down_BTN_Pos[0] + R_ITEM_BTN_WIDTH(2)) << 2,
|
||||
(C_Down_BTN_Pos[1] + R_ITEM_BTN_WIDTH(2)) << 2,
|
||||
G_TX_RENDERTILE, 0, 0, R_ITEM_BTN_DD(2) << 1, R_ITEM_BTN_DD(2) << 1);
|
||||
|
||||
// C-Right Button Color & Texture
|
||||
if (CVar_GetS32("gHudColors", 1) == 0) {
|
||||
@ -3699,9 +3703,9 @@ void Interface_DrawItemButtons(GlobalContext* globalCtx) {
|
||||
gDPSetPrimColor(OVERLAY_DISP++, 0, 0, C_button_R.r, C_button_R.g, C_button_R.b, interfaceCtx->cRightAlpha);
|
||||
}
|
||||
gSPWideTextureRectangle(OVERLAY_DISP++, C_Right_BTN_Pos[0] << 2, C_Right_BTN_Pos[1] << 2,
|
||||
(C_Right_BTN_Pos[0] + CRightScaled) << 2,
|
||||
(C_Right_BTN_Pos[1] + CRightScaled) << 2,
|
||||
G_TX_RENDERTILE, 0, 0, CRight_factor, CRight_factor);
|
||||
(C_Right_BTN_Pos[0] + R_ITEM_BTN_WIDTH(3)) << 2,
|
||||
(C_Right_BTN_Pos[1] + R_ITEM_BTN_WIDTH(3)) << 2,
|
||||
G_TX_RENDERTILE, 0, 0, R_ITEM_BTN_DD(3) << 1, R_ITEM_BTN_DD(3) << 1);
|
||||
|
||||
if ((pauseCtx->state < 8) || (pauseCtx->state >= 18)) {
|
||||
if ((globalCtx->pauseCtx.state != 0) || (globalCtx->pauseCtx.debugState != 0)) {
|
||||
@ -3998,43 +4002,16 @@ void Interface_DrawItemIconTexture(GlobalContext* globalCtx, void* texture, s16
|
||||
X_Margins_DPad_Items = 0;
|
||||
Y_Margins_DPad_Items = 0;
|
||||
}
|
||||
const float ItemsScale_offset[8][2] = {
|
||||
// Y X
|
||||
{ 104.0f, 144.0f }, //B
|
||||
{ 108.0f, 148.0f }, //C L
|
||||
{ 108.0f, 148.0f }, //C D
|
||||
{ 108.0f, 148.0f }, //C R
|
||||
{ 112.0f, 152.0f }, //Dpad ^
|
||||
{ 112.0f, 152.0f }, //Dpad V
|
||||
{ 112.0f, 152.0f }, //Dpad <
|
||||
{ 112.0f, 152.0f } //Dpad >
|
||||
};
|
||||
float ItemScale_ori[8] = {
|
||||
1.0f, //B BTN
|
||||
0.87f, 0.87f, 0.87f, //C BTNs L / D / R
|
||||
0.6f, 0.6f, 0.6f, 0.6f //Dpad U/D/L/R
|
||||
};
|
||||
const s16 ItemIconPos_ori[8][2] = {
|
||||
{ B_BUTTON_X+X_Margins_BtnB-ItemsScale_offset[0][1], B_BUTTON_Y+Y_Margins_BtnB-ItemsScale_offset[0][0] },
|
||||
{ C_LEFT_BUTTON_X+X_Margins_CL-ItemsScale_offset[1][1], C_LEFT_BUTTON_Y+Y_Margins_CL-ItemsScale_offset[1][0] },
|
||||
{ C_DOWN_BUTTON_X+X_Margins_CD-ItemsScale_offset[2][1], C_DOWN_BUTTON_Y+Y_Margins_CD-ItemsScale_offset[2][0] },
|
||||
{ C_RIGHT_BUTTON_X+X_Margins_CR-ItemsScale_offset[3][1], C_RIGHT_BUTTON_Y+Y_Margins_CR-ItemsScale_offset[3][0] },
|
||||
{ DPAD_UP_X+X_Margins_DPad_Items-ItemsScale_offset[4][1], DPAD_UP_Y+Y_Margins_DPad_Items-ItemsScale_offset[4][0] },
|
||||
{ DPAD_DOWN_X+X_Margins_DPad_Items-ItemsScale_offset[5][1], DPAD_DOWN_Y+Y_Margins_DPad_Items-ItemsScale_offset[5][0] },
|
||||
{ DPAD_LEFT_X+X_Margins_DPad_Items-ItemsScale_offset[6][1], DPAD_LEFT_Y+Y_Margins_DPad_Items-ItemsScale_offset[6][0] },
|
||||
{ DPAD_RIGHT_X+X_Margins_DPad_Items-ItemsScale_offset[7][1], DPAD_RIGHT_Y+Y_Margins_DPad_Items-ItemsScale_offset[7][0] }
|
||||
{ B_BUTTON_X+X_Margins_BtnB, B_BUTTON_Y+Y_Margins_BtnB },
|
||||
{ C_LEFT_BUTTON_X+X_Margins_CL, C_LEFT_BUTTON_Y+Y_Margins_CL },
|
||||
{ C_DOWN_BUTTON_X+X_Margins_CD, C_DOWN_BUTTON_Y+Y_Margins_CD },
|
||||
{ C_RIGHT_BUTTON_X+X_Margins_CR, C_RIGHT_BUTTON_Y+Y_Margins_CR },
|
||||
{ DPAD_UP_X+X_Margins_DPad_Items, DPAD_UP_Y+Y_Margins_DPad_Items },
|
||||
{ DPAD_DOWN_X+X_Margins_DPad_Items, DPAD_DOWN_Y+Y_Margins_DPad_Items },
|
||||
{ DPAD_LEFT_X+X_Margins_DPad_Items, DPAD_LEFT_Y+Y_Margins_DPad_Items },
|
||||
{ DPAD_RIGHT_X+X_Margins_DPad_Items, DPAD_RIGHT_Y+Y_Margins_DPad_Items }
|
||||
};
|
||||
float ItemScale[8] = {
|
||||
CVar_GetFloat("gBBtnScale", 1.0f),
|
||||
CVar_GetFloat("gCBtnLScale", 0.87f),
|
||||
CVar_GetFloat("gCBtnDScale", 0.87f),
|
||||
CVar_GetFloat("gCBtnRScale", 0.87f),
|
||||
CVar_GetFloat("gDPadScale", 0.425f),
|
||||
CVar_GetFloat("gDPadScale", 0.425f),
|
||||
CVar_GetFloat("gDPadScale", 0.425f),
|
||||
CVar_GetFloat("gDPadScale", 0.425f),
|
||||
};
|
||||
float ItemScaleCurrent[8]; //Hold the array with modified scale
|
||||
u16 ItemsSlotsAlpha[8] = {
|
||||
interfaceCtx->bAlpha,
|
||||
interfaceCtx->cLeftAlpha,
|
||||
@ -4054,10 +4031,6 @@ void Interface_DrawItemIconTexture(GlobalContext* globalCtx, void* texture, s16
|
||||
s16 ItemIconPos[8][2]; //(X,Y)
|
||||
//DPadItems
|
||||
if (CVar_GetS32("gDPadPosType", 0) != 0) {
|
||||
ItemScaleCurrent[4] = ItemScale[4];
|
||||
ItemScaleCurrent[5] = ItemScale[5];
|
||||
ItemScaleCurrent[6] = ItemScale[6];
|
||||
ItemScaleCurrent[7] = ItemScale[7];
|
||||
ItemIconPos[4][1] = CVar_GetS32("gDPadPosY", 0)+Y_Margins_DPad_Items+DPad_ItemsOffset[0][1];//Up
|
||||
ItemIconPos[5][1] = CVar_GetS32("gDPadPosY", 0)+Y_Margins_DPad_Items+DPad_ItemsOffset[1][1];//Down
|
||||
ItemIconPos[6][1] = CVar_GetS32("gDPadPosY", 0)+Y_Margins_DPad_Items+DPad_ItemsOffset[2][1];//Left
|
||||
@ -4086,10 +4059,6 @@ void Interface_DrawItemIconTexture(GlobalContext* globalCtx, void* texture, s16
|
||||
ItemIconPos[7][0] = -9999;
|
||||
}
|
||||
} else {
|
||||
ItemScaleCurrent[4] = ItemScale_ori[4];
|
||||
ItemScaleCurrent[5] = ItemScale_ori[5];
|
||||
ItemScaleCurrent[6] = ItemScale_ori[6];
|
||||
ItemScaleCurrent[7] = ItemScale_ori[7];
|
||||
ItemIconPos[4][0] = OTRGetDimensionFromRightEdge(ItemIconPos_ori[4][0]);
|
||||
ItemIconPos[5][0] = OTRGetDimensionFromRightEdge(ItemIconPos_ori[5][0]);
|
||||
ItemIconPos[6][0] = OTRGetDimensionFromRightEdge(ItemIconPos_ori[6][0]);
|
||||
@ -4101,81 +4070,73 @@ void Interface_DrawItemIconTexture(GlobalContext* globalCtx, void* texture, s16
|
||||
}
|
||||
//B Button
|
||||
if (CVar_GetS32("gBBtnPosType", 0) != 0) {
|
||||
ItemScaleCurrent[0] = ItemScale[0];
|
||||
ItemIconPos[0][1] = CVar_GetS32("gBBtnPosY", 0)+Y_Margins_BtnB-ItemsScale_offset[0][0];
|
||||
ItemIconPos[0][1] = CVar_GetS32("gBBtnPosY", 0)+Y_Margins_BtnB;
|
||||
if (CVar_GetS32("gBBtnPosType", 0) == 1) {//Anchor Left
|
||||
if (CVar_GetS32("gBBtnUseMargins", 0) != 0) {X_Margins_BtnB = Left_HUD_Margin;};
|
||||
ItemIconPos[0][0] = OTRGetDimensionFromLeftEdge(CVar_GetS32("gBBtnPosX", 0)+X_Margins_BtnB-ItemsScale_offset[0][1]);
|
||||
ItemIconPos[0][0] = OTRGetDimensionFromLeftEdge(CVar_GetS32("gBBtnPosX", 0)+X_Margins_BtnB);
|
||||
} else if (CVar_GetS32("gBBtnPosType", 0) == 2) {//Anchor Right
|
||||
if (CVar_GetS32("gBBtnUseMargins", 0) != 0) {X_Margins_BtnB = Right_HUD_Margin;};
|
||||
ItemIconPos[0][0] = OTRGetDimensionFromRightEdge(CVar_GetS32("gBBtnPosX", 0)+X_Margins_BtnB-ItemsScale_offset[0][1]);
|
||||
ItemIconPos[0][0] = OTRGetDimensionFromRightEdge(CVar_GetS32("gBBtnPosX", 0)+X_Margins_BtnB);
|
||||
} else if (CVar_GetS32("gBBtnPosType", 0) == 3) {//Anchor None
|
||||
ItemIconPos[0][0] = CVar_GetS32("gBBtnPosX", 0)-ItemsScale_offset[0][1];
|
||||
ItemIconPos[0][0] = CVar_GetS32("gBBtnPosX", 0);
|
||||
} else if (CVar_GetS32("gBBtnPosType", 0) == 4) {//Hidden
|
||||
ItemIconPos[0][0] = -9999;
|
||||
}
|
||||
} else {
|
||||
ItemScaleCurrent[0] = ItemScale_ori[0];
|
||||
ItemIconPos[0][0] = OTRGetRectDimensionFromRightEdge(ItemIconPos_ori[0][0]);
|
||||
ItemIconPos[0][1] = ItemIconPos_ori[0][1];
|
||||
}
|
||||
//C button Left
|
||||
if (CVar_GetS32("gCBtnLPosType", 0) != 0) {
|
||||
ItemScaleCurrent[1] = ItemScale[1];
|
||||
ItemIconPos[1][1] = CVar_GetS32("gCBtnLPosY", 0)+Y_Margins_CL-ItemsScale_offset[1][0];
|
||||
ItemIconPos[1][1] = CVar_GetS32("gCBtnLPosY", 0)+Y_Margins_CL;
|
||||
if (CVar_GetS32("gCBtnLPosType", 0) == 1) {//Anchor Left
|
||||
if (CVar_GetS32("gCBtnLUseMargins", 0) != 0) {X_Margins_CL = Left_HUD_Margin;};
|
||||
ItemIconPos[1][0] = OTRGetDimensionFromLeftEdge(CVar_GetS32("gCBtnLPosX", 0)+X_Margins_CL-ItemsScale_offset[1][1]);
|
||||
ItemIconPos[1][0] = OTRGetDimensionFromLeftEdge(CVar_GetS32("gCBtnLPosX", 0)+X_Margins_CL);
|
||||
} else if (CVar_GetS32("gCBtnLPosType", 0) == 2) {//Anchor Right
|
||||
if (CVar_GetS32("gCBtnLUseMargins", 0) != 0) {X_Margins_CL = Right_HUD_Margin;};
|
||||
ItemIconPos[1][0] = OTRGetDimensionFromRightEdge(CVar_GetS32("gCBtnLPosX", 0)+X_Margins_CL-ItemsScale_offset[1][1]);
|
||||
ItemIconPos[1][0] = OTRGetDimensionFromRightEdge(CVar_GetS32("gCBtnLPosX", 0)+X_Margins_CL);
|
||||
} else if (CVar_GetS32("gCBtnLPosType", 0) == 3) {//Anchor None
|
||||
ItemIconPos[1][0] = CVar_GetS32("gCBtnLPosX", 0)-ItemsScale_offset[1][1];
|
||||
ItemIconPos[1][0] = CVar_GetS32("gCBtnLPosX", 0);
|
||||
} else if (CVar_GetS32("gCBtnLPosType", 0) == 4) {//Hidden
|
||||
ItemIconPos[1][0] = -9999;
|
||||
}
|
||||
} else {
|
||||
ItemScaleCurrent[1] = ItemScale_ori[1];
|
||||
ItemIconPos[1][0] = OTRGetRectDimensionFromRightEdge(ItemIconPos_ori[1][0]);
|
||||
ItemIconPos[1][1] = ItemIconPos_ori[1][1];
|
||||
}
|
||||
//C Button down
|
||||
if (CVar_GetS32("gCBtnDPosType", 0) != 0) {
|
||||
ItemScaleCurrent[2] = ItemScale[2];
|
||||
ItemIconPos[2][1] = CVar_GetS32("gCBtnDPosY", 0)+Y_Margins_CD-ItemsScale_offset[2][0];
|
||||
ItemIconPos[2][1] = CVar_GetS32("gCBtnDPosY", 0)+Y_Margins_CD;
|
||||
if (CVar_GetS32("gCBtnDPosType", 0) == 1) {//Anchor Left
|
||||
if (CVar_GetS32("gCBtnDUseMargins", 0) != 0) {X_Margins_CD = Left_HUD_Margin;};
|
||||
ItemIconPos[2][0] = OTRGetDimensionFromLeftEdge(CVar_GetS32("gCBtnDPosX", 0)+X_Margins_CD-ItemsScale_offset[2][1]);
|
||||
ItemIconPos[2][0] = OTRGetDimensionFromLeftEdge(CVar_GetS32("gCBtnDPosX", 0)+X_Margins_CD);
|
||||
} else if (CVar_GetS32("gCBtnDPosType", 0) == 2) {//Anchor Right
|
||||
if (CVar_GetS32("gCBtnDUseMargins", 0) != 0) {X_Margins_CD = Right_HUD_Margin;};
|
||||
ItemIconPos[2][0] = OTRGetDimensionFromRightEdge(CVar_GetS32("gCBtnDPosX", 0)+X_Margins_CD-ItemsScale_offset[2][1]);
|
||||
ItemIconPos[2][0] = OTRGetDimensionFromRightEdge(CVar_GetS32("gCBtnDPosX", 0)+X_Margins_CD);
|
||||
} else if (CVar_GetS32("gCBtnDPosType", 0) == 3) {//Anchor None
|
||||
ItemIconPos[2][0] = CVar_GetS32("gCBtnDPosX", 0)-ItemsScale_offset[2][1];
|
||||
ItemIconPos[2][0] = CVar_GetS32("gCBtnDPosX", 0);
|
||||
} else if (CVar_GetS32("gCBtnDPosType", 0) == 4) {//Hidden
|
||||
ItemIconPos[2][0] = -9999;
|
||||
}
|
||||
} else {
|
||||
ItemScaleCurrent[2] = ItemScale_ori[2];
|
||||
ItemIconPos[2][0] = OTRGetRectDimensionFromRightEdge(ItemIconPos_ori[2][0]);
|
||||
ItemIconPos[2][1] = ItemIconPos_ori[2][1];
|
||||
}
|
||||
//C button Right
|
||||
if (CVar_GetS32("gCBtnRPosType", 0) != 0) {
|
||||
ItemScaleCurrent[3] = ItemScale[3];
|
||||
ItemIconPos[3][1] = CVar_GetS32("gCBtnRPosY", 0)+Y_Margins_CR-ItemsScale_offset[3][0];
|
||||
ItemIconPos[3][1] = CVar_GetS32("gCBtnRPosY", 0)+Y_Margins_CR;
|
||||
if (CVar_GetS32("gCBtnRPosType", 0) == 1) {//Anchor Left
|
||||
if (CVar_GetS32("gCBtnRUseMargins", 0) != 0) {X_Margins_CR = Left_HUD_Margin;};
|
||||
ItemIconPos[3][0] = OTRGetDimensionFromLeftEdge(CVar_GetS32("gCBtnRPosX", 0)+X_Margins_CR-ItemsScale_offset[3][1]);
|
||||
ItemIconPos[3][0] = OTRGetDimensionFromLeftEdge(CVar_GetS32("gCBtnRPosX", 0)+X_Margins_CR);
|
||||
} else if (CVar_GetS32("gCBtnRPosType", 0) == 2) {//Anchor Right
|
||||
if (CVar_GetS32("gCBtnRUseMargins", 0) != 0) {X_Margins_CR = Right_HUD_Margin;};
|
||||
ItemIconPos[3][0] = OTRGetDimensionFromRightEdge(CVar_GetS32("gCBtnRPosX", 0)+X_Margins_CR-ItemsScale_offset[3][1]);
|
||||
ItemIconPos[3][0] = OTRGetDimensionFromRightEdge(CVar_GetS32("gCBtnRPosX", 0)+X_Margins_CR);
|
||||
} else if (CVar_GetS32("gCBtnRPosType", 0) == 3) {//Anchor None
|
||||
ItemIconPos[3][0] = CVar_GetS32("gCBtnRPosX", 0)-ItemsScale_offset[3][1];
|
||||
ItemIconPos[3][0] = CVar_GetS32("gCBtnRPosX", 0);
|
||||
} else if (CVar_GetS32("gCBtnRPosType", 0) == 4) {//Hidden
|
||||
ItemIconPos[3][0] = -9999;
|
||||
}
|
||||
} else {
|
||||
ItemScaleCurrent[3] = ItemScale_ori[3];
|
||||
ItemIconPos[3][0] = OTRGetRectDimensionFromRightEdge(ItemIconPos_ori[3][0]);
|
||||
ItemIconPos[3][1] = ItemIconPos_ori[3][1];
|
||||
}
|
||||
@ -4183,23 +4144,10 @@ void Interface_DrawItemIconTexture(GlobalContext* globalCtx, void* texture, s16
|
||||
gDPLoadTextureBlock(OVERLAY_DISP++, texture, G_IM_FMT_RGBA, G_IM_SIZ_32b, 32, 32, 0, G_TX_NOMIRROR | G_TX_WRAP,
|
||||
G_TX_NOMIRROR | G_TX_WRAP, G_TX_NOMASK, G_TX_NOMASK, G_TX_NOLOD, G_TX_NOLOD);
|
||||
|
||||
gDPPipeSync(OVERLAY_DISP++);
|
||||
gSPSetGeometryMode(OVERLAY_DISP++, G_CULL_BACK);
|
||||
gDPSetCombineLERP(OVERLAY_DISP++, PRIMITIVE, ENVIRONMENT, TEXEL0, ENVIRONMENT, TEXEL0, 0, PRIMITIVE, 0, PRIMITIVE, ENVIRONMENT, TEXEL0, ENVIRONMENT, TEXEL0, 0, PRIMITIVE, 0);
|
||||
gDPSetPrimColor(OVERLAY_DISP++, 0, 0, 255, 255, 255, ItemsSlotsAlpha[button]);
|
||||
gDPSetEnvColor(OVERLAY_DISP++, 0, 0, 0, 0);
|
||||
Matrix_Translate(
|
||||
ItemIconPos[button][0],
|
||||
ItemIconPos[button][1] * -1, 1.0f, MTXMODE_NEW);
|
||||
|
||||
Matrix_Scale(
|
||||
ItemScaleCurrent[button]/1,
|
||||
ItemScaleCurrent[button]/1,
|
||||
ItemScaleCurrent[button]/1, MTXMODE_APPLY);
|
||||
gSPMatrix(OVERLAY_DISP++, MATRIX_NEWMTX(globalCtx->state.gfxCtx), G_MTX_MODELVIEW | G_MTX_LOAD);
|
||||
gSPVertex(OVERLAY_DISP++, &interfaceCtx->actionVtx[0], 4, 0);
|
||||
gSP1Quadrangle(OVERLAY_DISP++, 0, 2, 3, 1, 0);
|
||||
gDPPipeSync(OVERLAY_DISP++);
|
||||
gSPWideTextureRectangle(OVERLAY_DISP++, ItemIconPos[button][0] << 2, ItemIconPos[button][1] << 2,
|
||||
(ItemIconPos[button][0] + gItemIconWidth[button]) << 2,
|
||||
(ItemIconPos[button][1] + gItemIconWidth[button]) << 2, G_TX_RENDERTILE, 0, 0,
|
||||
gItemIconDD[button] << 1, gItemIconDD[button] << 1);
|
||||
|
||||
CLOSE_DISPS(globalCtx->state.gfxCtx);
|
||||
}
|
||||
|
@ -255,10 +255,10 @@ void GivePlayerRandoRewardSariaGift(GlobalContext* globalCtx, RandomizerCheck ch
|
||||
if (gSaveContext.entranceIndex == 0x05E0) {
|
||||
GetItemEntry getItemEntry = Randomizer_GetItemFromKnownCheck(check, RG_ZELDAS_LULLABY);
|
||||
|
||||
if ((!Flags_GetEventChkInf(0xC1) || (player->getItemId == getItemEntry.getItemId && getItemEntry.getItemId != GI_ICE_TRAP)) &&
|
||||
player != NULL && !Player_InBlockingCsMode(globalCtx, player)) {
|
||||
if (!Flags_GetEventChkInf(0xC1) && player != NULL && !Player_InBlockingCsMode(globalCtx, player)) {
|
||||
GiveItemEntryWithoutActor(globalCtx, getItemEntry);
|
||||
Flags_SetEventChkInf(0xC1);
|
||||
player->pendingFlag.flagType = FLAG_EVENT_CHECK_INF;
|
||||
player->pendingFlag.flagID = 0xC1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1170,7 +1170,13 @@ void Player_DrawGetItemImpl(GlobalContext* globalCtx, Player* this, Vec3f* refPo
|
||||
Matrix_RotateZYX(0, globalCtx->gameplayFrames * 1000, 0, MTXMODE_APPLY);
|
||||
Matrix_Scale(0.2f, 0.2f, 0.2f, MTXMODE_APPLY);
|
||||
|
||||
GetItem_Draw(globalCtx, drawIdPlusOne - 1);
|
||||
// RANDOTODO: Make this more flexible for easier toggling of individual item recolors in the future.
|
||||
if (this->getItemEntry.drawFunc != NULL &&
|
||||
(CVar_GetS32("gRandoMatchKeyColors", 0) || this->getItemEntry.getItemId == RG_DOUBLE_DEFENSE)) {
|
||||
this->getItemEntry.drawFunc(globalCtx, &this->getItemEntry);
|
||||
} else {
|
||||
GetItem_Draw(globalCtx, drawIdPlusOne - 1);
|
||||
}
|
||||
|
||||
CLOSE_DISPS(globalCtx->state.gfxCtx);
|
||||
}
|
||||
|
@ -3,10 +3,12 @@
|
||||
|
||||
#include <string.h>
|
||||
#include <soh/Enhancements/randomizer/randomizerTypes.h>
|
||||
#include <soh/Enhancements/randomizer/randomizer_inf.h>
|
||||
|
||||
#define NUM_DUNGEONS 8
|
||||
#define NUM_TRIALS 6
|
||||
#define NUM_COWS 10
|
||||
#define NUM_SCRUBS 35
|
||||
|
||||
/**
|
||||
* Initialize new save.
|
||||
@ -702,19 +704,9 @@ void Sram_InitSave(FileChooseContext* fileChooseCtx) {
|
||||
fileChooseCtx->n64ddFlag = 1;
|
||||
gSaveContext.n64ddFlag = 1;
|
||||
|
||||
// Sets all the dungeons to incomplete when generating a rando save. Fixes https://github.com/briaguya-ai/rando-issue-tracker/issues/82
|
||||
for (u8 i = 0; i < NUM_DUNGEONS; i++) {
|
||||
gSaveContext.dungeonsDone[i] = 0;
|
||||
}
|
||||
|
||||
// Sets all Ganon's Trials to incomplete when generating a rando save. Fixes https://github.com/briaguya-ai/rando-issue-tracker/issues/131
|
||||
for (u8 i = 0; i < NUM_TRIALS; i++) {
|
||||
gSaveContext.trialsDone[i] = 0;
|
||||
}
|
||||
|
||||
// Sets all cows to unmilked when generating a rando save.
|
||||
for (u8 i = 0; i < NUM_COWS; i++) {
|
||||
gSaveContext.cowsMilked[i] = 0;
|
||||
// Sets all rando flags to false
|
||||
for (s32 i = 0; i < ARRAY_COUNT(gSaveContext.randomizerInf); i++) {
|
||||
gSaveContext.randomizerInf[i] = 0;
|
||||
}
|
||||
|
||||
// Set Cutscene flags to skip them
|
||||
@ -800,7 +792,7 @@ void Sram_InitSave(FileChooseContext* fileChooseCtx) {
|
||||
s32 giid = getItem.getItemId;
|
||||
|
||||
if (getItem.modIndex == MOD_NONE) {
|
||||
if(getItem.itemId >= ITEM_KOKIRI_EMERALD && getItem.itemId <= ITEM_MEDALLION_LIGHT) {
|
||||
if (getItem.itemId >= ITEM_MEDALLION_FOREST && getItem.itemId <= ITEM_ZORA_SAPPHIRE) {
|
||||
GiveLinkDungeonReward(getItem.getItemId);
|
||||
} else if (giid == GI_RUPEE_GREEN || giid == GI_RUPEE_BLUE || giid == GI_RUPEE_RED ||
|
||||
giid == GI_RUPEE_PURPLE || giid == GI_RUPEE_GOLD) {
|
||||
|
@ -132,35 +132,35 @@ u8 CheckMedallionCount() {
|
||||
u8 CheckDungeonCount() {
|
||||
u8 dungeonCount = 0;
|
||||
|
||||
if (gSaveContext.dungeonsDone[0] == 1) {
|
||||
if (Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_DEKU_TREE)) {
|
||||
dungeonCount++;
|
||||
}
|
||||
|
||||
if (gSaveContext.dungeonsDone[1] == 1) {
|
||||
if (Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_DODONGOS_CAVERN)) {
|
||||
dungeonCount++;
|
||||
}
|
||||
|
||||
if (gSaveContext.dungeonsDone[2] == 1) {
|
||||
if (Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_JABU_JABUS_BELLY)) {
|
||||
dungeonCount++;
|
||||
}
|
||||
|
||||
if (gSaveContext.dungeonsDone[3] == 1) {
|
||||
if (Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_FOREST_TEMPLE)) {
|
||||
dungeonCount++;
|
||||
}
|
||||
|
||||
if (gSaveContext.dungeonsDone[4] == 1) {
|
||||
if (Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_FIRE_TEMPLE)) {
|
||||
dungeonCount++;
|
||||
}
|
||||
|
||||
if (gSaveContext.dungeonsDone[5] == 1) {
|
||||
if (Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_WATER_TEMPLE)) {
|
||||
dungeonCount++;
|
||||
}
|
||||
|
||||
if (gSaveContext.dungeonsDone[6] == 1) {
|
||||
if (Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_SPIRIT_TEMPLE)) {
|
||||
dungeonCount++;
|
||||
}
|
||||
|
||||
if (gSaveContext.dungeonsDone[7] == 1) {
|
||||
if (Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_SHADOW_TEMPLE)) {
|
||||
dungeonCount++;
|
||||
}
|
||||
|
||||
|
@ -152,7 +152,7 @@ void BgSpot06Objects_Init(Actor* thisx, GlobalContext* globalCtx) {
|
||||
|
||||
if (LINK_IS_ADULT &&
|
||||
((!gSaveContext.n64ddFlag && !(gSaveContext.eventChkInf[6] & 0x200)) ||
|
||||
(gSaveContext.n64ddFlag && !gSaveContext.dungeonsDone[5]))) {
|
||||
(gSaveContext.n64ddFlag && !Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_WATER_TEMPLE)))) {
|
||||
if (gSaveContext.sceneSetupIndex < 4) {
|
||||
this->lakeHyliaWaterLevel = -681.0f;
|
||||
globalCtx->colCtx.colHeader->waterBoxes[LHWB_GERUDO_VALLEY_RIVER_LOWER].ySurface =
|
||||
|
@ -2089,6 +2089,10 @@ void DemoEffect_DrawGetItem(Actor* thisx, GlobalContext* globalCtx) {
|
||||
if (gSaveContext.n64ddFlag && globalCtx->sceneNum == SCENE_BDAN) {
|
||||
GetItemEntry getItemEntry = Randomizer_GetItemFromKnownCheck(RC_BARINADE, RG_ZORA_SAPPHIRE);
|
||||
this->getItem.drawId = getItemEntry.gid;
|
||||
func_8002EBCC(thisx, globalCtx, 0);
|
||||
func_8002ED80(thisx, globalCtx, 0);
|
||||
GetItemEntry_Draw(globalCtx, getItemEntry);
|
||||
return;
|
||||
}
|
||||
func_8002EBCC(thisx, globalCtx, 0);
|
||||
func_8002ED80(thisx, globalCtx, 0);
|
||||
|
@ -76,27 +76,27 @@ s32 DemoKekkai_CheckEventFlag(s32 params) {
|
||||
u32 TrialsDoneCount() {
|
||||
u8 trialCount = 0;
|
||||
|
||||
if (gSaveContext.trialsDone[0] == 1) {
|
||||
if (Flags_GetRandomizerInf(RAND_INF_TRIALS_DONE_LIGHT_TRIAL)) {
|
||||
trialCount++;
|
||||
}
|
||||
|
||||
if (gSaveContext.trialsDone[1] == 1) {
|
||||
if (Flags_GetRandomizerInf(RAND_INF_TRIALS_DONE_FOREST_TRIAL)) {
|
||||
trialCount++;
|
||||
}
|
||||
|
||||
if (gSaveContext.trialsDone[2] == 1) {
|
||||
if (Flags_GetRandomizerInf(RAND_INF_TRIALS_DONE_FIRE_TRIAL)) {
|
||||
trialCount++;
|
||||
}
|
||||
|
||||
if (gSaveContext.trialsDone[3] == 1) {
|
||||
if (Flags_GetRandomizerInf(RAND_INF_TRIALS_DONE_WATER_TRIAL)) {
|
||||
trialCount++;
|
||||
}
|
||||
|
||||
if (gSaveContext.trialsDone[4] == 1) {
|
||||
if (Flags_GetRandomizerInf(RAND_INF_TRIALS_DONE_SPIRIT_TRIAL)) {
|
||||
trialCount++;
|
||||
}
|
||||
|
||||
if (gSaveContext.trialsDone[5] == 1) {
|
||||
if (Flags_GetRandomizerInf(RAND_INF_TRIALS_DONE_SHADOW_TRIAL)) {
|
||||
trialCount++;
|
||||
}
|
||||
|
||||
@ -249,22 +249,22 @@ void DemoKekkai_TrialBarrierDispel(Actor* thisx, GlobalContext* globalCtx) {
|
||||
if (gSaveContext.n64ddFlag) {
|
||||
switch (thisx->params) {
|
||||
case KEKKAI_WATER:
|
||||
gSaveContext.trialsDone[2] = 1;
|
||||
Flags_SetRandomizerInf(RAND_INF_TRIALS_DONE_WATER_TRIAL);
|
||||
break;
|
||||
case KEKKAI_LIGHT:
|
||||
gSaveContext.trialsDone[5] = 1;
|
||||
Flags_SetRandomizerInf(RAND_INF_TRIALS_DONE_LIGHT_TRIAL);
|
||||
break;
|
||||
case KEKKAI_FIRE:
|
||||
gSaveContext.trialsDone[1] = 1;
|
||||
Flags_SetRandomizerInf(RAND_INF_TRIALS_DONE_FIRE_TRIAL);
|
||||
break;
|
||||
case KEKKAI_SHADOW:
|
||||
gSaveContext.trialsDone[3] = 1;
|
||||
Flags_SetRandomizerInf(RAND_INF_TRIALS_DONE_SHADOW_TRIAL);
|
||||
break;
|
||||
case KEKKAI_SPIRIT:
|
||||
gSaveContext.trialsDone[4] = 1;
|
||||
Flags_SetRandomizerInf(RAND_INF_TRIALS_DONE_SPIRIT_TRIAL);
|
||||
break;
|
||||
case KEKKAI_FOREST:
|
||||
gSaveContext.trialsDone[0] = 1;
|
||||
Flags_SetRandomizerInf(RAND_INF_TRIALS_DONE_FOREST_TRIAL);
|
||||
break;
|
||||
}
|
||||
Flags_SetEventChkInf(eventFlags[thisx->params]);
|
||||
|
@ -546,7 +546,7 @@ void DoorWarp1_ChildWarpOut(DoorWarp1* this, GlobalContext* globalCtx) {
|
||||
if (globalCtx->sceneNum == SCENE_DDAN_BOSS) {
|
||||
if (!Flags_GetEventChkInf(0x25)) {
|
||||
Flags_SetEventChkInf(0x25);
|
||||
gSaveContext.dungeonsDone[0] = 1;
|
||||
Flags_SetRandomizerInf(RAND_INF_DUNGEONS_DONE_DODONGOS_CAVERN);
|
||||
if (gSaveContext.n64ddFlag) {
|
||||
globalCtx->nextEntranceIndex = 0x47A;
|
||||
gSaveContext.nextCutsceneIndex = 0;
|
||||
@ -563,7 +563,7 @@ void DoorWarp1_ChildWarpOut(DoorWarp1* this, GlobalContext* globalCtx) {
|
||||
if (!Flags_GetEventChkInf(7) || gSaveContext.n64ddFlag) {
|
||||
Flags_SetEventChkInf(7);
|
||||
Flags_SetEventChkInf(9);
|
||||
gSaveContext.dungeonsDone[1] = 1;
|
||||
Flags_SetRandomizerInf(RAND_INF_DUNGEONS_DONE_DEKU_TREE);
|
||||
if (gSaveContext.n64ddFlag) {
|
||||
globalCtx->nextEntranceIndex = 0x0457;
|
||||
gSaveContext.nextCutsceneIndex = 0;
|
||||
@ -671,7 +671,7 @@ void DoorWarp1_RutoWarpOut(DoorWarp1* this, GlobalContext* globalCtx) {
|
||||
|
||||
if (this->warpTimer > sWarpTimerTarget && gSaveContext.nextCutsceneIndex == 0xFFEF) {
|
||||
gSaveContext.eventChkInf[3] |= 0x80;
|
||||
gSaveContext.dungeonsDone[2] = 1;
|
||||
Flags_SetRandomizerInf(RAND_INF_DUNGEONS_DONE_JABU_JABUS_BELLY);
|
||||
|
||||
if (gSaveContext.n64ddFlag) {
|
||||
globalCtx->nextEntranceIndex = 0x10E;
|
||||
@ -785,7 +785,7 @@ void DoorWarp1_AdultWarpOut(DoorWarp1* this, GlobalContext* globalCtx) {
|
||||
if (globalCtx->sceneNum == SCENE_MORIBOSSROOM) {
|
||||
if (!(gSaveContext.eventChkInf[4] & 0x100)) {
|
||||
gSaveContext.eventChkInf[4] |= 0x100;
|
||||
gSaveContext.dungeonsDone[3] = 1;
|
||||
Flags_SetRandomizerInf(RAND_INF_DUNGEONS_DONE_FOREST_TEMPLE);
|
||||
|
||||
if (gSaveContext.n64ddFlag) {
|
||||
globalCtx->nextEntranceIndex = 0x608;
|
||||
@ -807,7 +807,7 @@ void DoorWarp1_AdultWarpOut(DoorWarp1* this, GlobalContext* globalCtx) {
|
||||
} else if (globalCtx->sceneNum == SCENE_FIRE_BS) {
|
||||
if (!(gSaveContext.eventChkInf[4] & 0x200)) {
|
||||
gSaveContext.eventChkInf[4] |= 0x200;
|
||||
gSaveContext.dungeonsDone[4] = 1;
|
||||
Flags_SetRandomizerInf(RAND_INF_DUNGEONS_DONE_FIRE_TEMPLE);
|
||||
|
||||
if (gSaveContext.n64ddFlag) {
|
||||
globalCtx->nextEntranceIndex = 0x564;
|
||||
@ -828,7 +828,7 @@ void DoorWarp1_AdultWarpOut(DoorWarp1* this, GlobalContext* globalCtx) {
|
||||
} else if (globalCtx->sceneNum == SCENE_MIZUSIN_BS) {
|
||||
if (!(gSaveContext.eventChkInf[4] & 0x400)) {
|
||||
gSaveContext.eventChkInf[4] |= 0x400;
|
||||
gSaveContext.dungeonsDone[5] = 1;
|
||||
Flags_SetRandomizerInf(RAND_INF_DUNGEONS_DONE_WATER_TEMPLE);
|
||||
|
||||
if (gSaveContext.n64ddFlag) {
|
||||
globalCtx->nextEntranceIndex = 0x60C;
|
||||
@ -849,7 +849,7 @@ void DoorWarp1_AdultWarpOut(DoorWarp1* this, GlobalContext* globalCtx) {
|
||||
}
|
||||
} else if (globalCtx->sceneNum == SCENE_JYASINBOSS) {
|
||||
if (!CHECK_QUEST_ITEM(QUEST_MEDALLION_SPIRIT) || gSaveContext.n64ddFlag) {
|
||||
gSaveContext.dungeonsDone[6] = 1;
|
||||
Flags_SetRandomizerInf(RAND_INF_DUNGEONS_DONE_SPIRIT_TEMPLE);
|
||||
|
||||
if (gSaveContext.n64ddFlag) {
|
||||
globalCtx->nextEntranceIndex = 0x610;
|
||||
@ -870,7 +870,7 @@ void DoorWarp1_AdultWarpOut(DoorWarp1* this, GlobalContext* globalCtx) {
|
||||
}
|
||||
} else if (globalCtx->sceneNum == SCENE_HAKADAN_BS) {
|
||||
if (!CHECK_QUEST_ITEM(QUEST_MEDALLION_SHADOW) || gSaveContext.n64ddFlag) {
|
||||
gSaveContext.dungeonsDone[7] = 1;
|
||||
Flags_SetRandomizerInf(RAND_INF_DUNGEONS_DONE_SHADOW_TEMPLE);
|
||||
|
||||
if (gSaveContext.n64ddFlag) {
|
||||
globalCtx->nextEntranceIndex = 0x580;
|
||||
|
@ -218,51 +218,51 @@ void func_809DF730(EnCow* this, GlobalContext* globalCtx) {
|
||||
CowInfo EnCow_GetInfo(EnCow* this, GlobalContext* globalCtx) {
|
||||
struct CowInfo cowInfo;
|
||||
|
||||
cowInfo.cowId = -1;
|
||||
cowInfo.randomizerInf = -1;
|
||||
cowInfo.randomizerCheck = RC_UNKNOWN_CHECK;
|
||||
|
||||
switch (globalCtx->sceneNum) {
|
||||
case SCENE_SOUKO: // Lon Lon Tower
|
||||
if (this->actor.world.pos.x == -229 && this->actor.world.pos.z == 157) {
|
||||
cowInfo.cowId = 0;
|
||||
cowInfo.randomizerInf = RAND_INF_COWS_MILKED_LLR_TOWER_LEFT_COW;
|
||||
cowInfo.randomizerCheck = RC_LLR_TOWER_LEFT_COW;
|
||||
} else if (this->actor.world.pos.x == -142 && this->actor.world.pos.z == -140) {
|
||||
cowInfo.cowId = 1;
|
||||
cowInfo.randomizerInf = RAND_INF_COWS_MILKED_LLR_TOWER_RIGHT_COW;
|
||||
cowInfo.randomizerCheck = RC_LLR_TOWER_RIGHT_COW;
|
||||
}
|
||||
break;
|
||||
case SCENE_MALON_STABLE:
|
||||
if (this->actor.world.pos.x == 116 && this->actor.world.pos.z == -254) {
|
||||
cowInfo.cowId = 2;
|
||||
cowInfo.randomizerInf = RAND_INF_COWS_MILKED_LLR_STABLES_RIGHT_COW;
|
||||
cowInfo.randomizerCheck = RC_LLR_STABLES_RIGHT_COW;
|
||||
} else if (this->actor.world.pos.x == -122 && this->actor.world.pos.z == -254) {
|
||||
cowInfo.cowId = 3;
|
||||
cowInfo.randomizerInf = RAND_INF_COWS_MILKED_LLR_STABLES_LEFT_COW;
|
||||
cowInfo.randomizerCheck = RC_LLR_STABLES_LEFT_COW;
|
||||
}
|
||||
break;
|
||||
case SCENE_KAKUSIANA: // Grotto
|
||||
if (this->actor.world.pos.x == 2444 && this->actor.world.pos.z == -471) {
|
||||
cowInfo.cowId = 4;
|
||||
cowInfo.randomizerInf = RAND_INF_COWS_MILKED_DMT_COW_GROTTO_COW;
|
||||
cowInfo.randomizerCheck = RC_DMT_COW_GROTTO_COW;
|
||||
} else if (this->actor.world.pos.x == 3485 && this->actor.world.pos.z == -291) {
|
||||
cowInfo.cowId = 5;
|
||||
cowInfo.randomizerInf = RAND_INF_COWS_MILKED_HF_COW_GROTTO_COW;
|
||||
cowInfo.randomizerCheck = RC_HF_COW_GROTTO_COW;
|
||||
}
|
||||
break;
|
||||
case SCENE_LINK_HOME:
|
||||
cowInfo.cowId = 6;
|
||||
cowInfo.randomizerInf = RAND_INF_COWS_MILKED_LINKS_HOUSE_COW;
|
||||
cowInfo.randomizerCheck = RC_KF_LINKS_HOUSE_COW;
|
||||
break;
|
||||
case SCENE_LABO: // Impa's house
|
||||
cowInfo.cowId = 7;
|
||||
cowInfo.randomizerInf = RAND_INF_COWS_MILKED_KAK_IMPAS_HOUSE_COW;
|
||||
cowInfo.randomizerCheck = RC_KAK_IMPAS_HOUSE_COW;
|
||||
break;
|
||||
case SCENE_SPOT09: // Gerudo Valley
|
||||
cowInfo.cowId = 8;
|
||||
cowInfo.randomizerInf = RAND_INF_COWS_MILKED_GV_COW;
|
||||
cowInfo.randomizerCheck = RC_GV_COW;
|
||||
break;
|
||||
case SCENE_SPOT08: // Jabu's Belly
|
||||
cowInfo.cowId = 9;
|
||||
case SCENE_BDAN: // Jabu's Belly
|
||||
cowInfo.randomizerInf = RAND_INF_COWS_MILKED_JABU_JABUS_BELLY_MQ_COW;
|
||||
cowInfo.randomizerCheck = RC_JABU_JABUS_BELLY_MQ_COW;
|
||||
break;
|
||||
}
|
||||
@ -290,8 +290,8 @@ void EnCow_MoveForRandomizer(EnCow* this, GlobalContext* globalCtx) {
|
||||
void EnCow_SetCowMilked(EnCow* this, GlobalContext* globalCtx) {
|
||||
CowInfo cowInfo = EnCow_GetInfo(this, globalCtx);
|
||||
Player* player = GET_PLAYER(globalCtx);
|
||||
player->pendingFlag.flagID = cowInfo.cowId;
|
||||
player->pendingFlag.flagType = FLAG_COW_MILKED;
|
||||
player->pendingFlag.flagID = cowInfo.randomizerInf;
|
||||
player->pendingFlag.flagType = FLAG_RANDOMIZER_INF;
|
||||
}
|
||||
|
||||
void func_809DF778(EnCow* this, GlobalContext* globalCtx) {
|
||||
@ -337,7 +337,7 @@ void func_809DF8FC(EnCow* this, GlobalContext* globalCtx) {
|
||||
|
||||
bool EnCow_HasBeenMilked(EnCow* this, GlobalContext* globalCtx) {
|
||||
CowInfo cowInfo = EnCow_GetInfo(this, globalCtx);
|
||||
return gSaveContext.cowsMilked[cowInfo.cowId];
|
||||
return Flags_GetRandomizerInf(cowInfo.randomizerInf);
|
||||
}
|
||||
|
||||
void EnCow_GivePlayerRandomizedItem(EnCow* this, GlobalContext* globalCtx) {
|
||||
|
@ -22,7 +22,7 @@ typedef struct EnCow {
|
||||
} EnCow; // size = 0x0280
|
||||
|
||||
typedef struct CowInfo {
|
||||
int cowId;
|
||||
RandomizerInf randomizerInf;
|
||||
RandomizerCheck randomizerCheck;
|
||||
} CowInfo;
|
||||
|
||||
|
@ -15,6 +15,7 @@ void EnDns_Destroy(Actor* thisx, GlobalContext* globalCtx);
|
||||
void EnDns_Update(Actor* thisx, GlobalContext* globalCtx);
|
||||
void EnDns_Draw(Actor* thisx, GlobalContext* globalCtx);
|
||||
|
||||
u32 EnDns_RandomizerPurchaseableCheck(EnDns* this);
|
||||
u32 func_809EF5A4(EnDns* this);
|
||||
u32 func_809EF658(EnDns* this);
|
||||
u32 func_809EF70C(EnDns* this);
|
||||
@ -24,6 +25,7 @@ u32 func_809EF854(EnDns* this);
|
||||
u32 func_809EF8F4(EnDns* this);
|
||||
u32 func_809EF9A4(EnDns* this);
|
||||
|
||||
void EnDns_RandomizerPurchase(EnDns* this);
|
||||
void func_809EF9F8(EnDns* this);
|
||||
void func_809EFA28(EnDns* this);
|
||||
void func_809EFA58(EnDns* this);
|
||||
@ -155,7 +157,6 @@ void EnDns_Init(Actor* thisx, GlobalContext* globalCtx) {
|
||||
Collider_InitCylinder(globalCtx, &this->collider);
|
||||
Collider_SetCylinderType1(globalCtx, &this->collider, &this->actor, &sCylinderInit);
|
||||
ActorShape_Init(&this->actor.shape, 0.0f, ActorShadow_DrawCircle, 35.0f);
|
||||
this->actor.textId = D_809F040C[this->actor.params];
|
||||
Actor_SetScale(&this->actor, 0.01f);
|
||||
this->actor.colChkInfo.mass = MASS_IMMOVABLE;
|
||||
this->maintainCollider = 1;
|
||||
@ -164,7 +165,27 @@ void EnDns_Init(Actor* thisx, GlobalContext* globalCtx) {
|
||||
this->actor.speedXZ = 0.0f;
|
||||
this->actor.velocity.y = 0.0f;
|
||||
this->actor.gravity = -1.0f;
|
||||
this->actor.textId = D_809F040C[this->actor.params];
|
||||
this->dnsItemEntry = sItemEntries[this->actor.params];
|
||||
if (gSaveContext.n64ddFlag) {
|
||||
// Ugly, but the best way we can identify which grotto we are in, same method 3DRando uses, but we'll need to account for entrance rando
|
||||
s16 respawnData = gSaveContext.respawn[RESPAWN_MODE_RETURN].data & ((1 << 8) - 1);
|
||||
this->scrubIdentity = Randomizer_IdentifyScrub(globalCtx->sceneNum, this->actor.params, respawnData);
|
||||
|
||||
if (Randomizer_GetSettingValue(RSK_SHUFFLE_SCRUBS) == 1 || Randomizer_GetSettingValue(RSK_SHUFFLE_SCRUBS) == 3 && this->scrubIdentity.itemPrice != -1) {
|
||||
this->dnsItemEntry->itemPrice = this->scrubIdentity.itemPrice;
|
||||
}
|
||||
|
||||
if (this->scrubIdentity.isShuffled) {
|
||||
this->dnsItemEntry->getItemId = this->scrubIdentity.getItemId;
|
||||
this->dnsItemEntry->purchaseableCheck = EnDns_RandomizerPurchaseableCheck;
|
||||
this->dnsItemEntry->setRupeesAndFlags = EnDns_RandomizerPurchase;
|
||||
this->dnsItemEntry->itemAmount = 1;
|
||||
// Currently the textID is simply identified by the item price since that is the only thing
|
||||
// unique to it, later on this will change to identifying by scrubIdentity.randomizerInf
|
||||
this->actor.textId = 0x9000 + this->dnsItemEntry->itemPrice;
|
||||
}
|
||||
}
|
||||
this->actionFunc = EnDns_SetupWait;
|
||||
}
|
||||
|
||||
@ -185,6 +206,13 @@ void EnDns_ChangeAnim(EnDns* this, u8 index) {
|
||||
|
||||
/* Item give checking functions */
|
||||
|
||||
u32 EnDns_RandomizerPurchaseableCheck(EnDns* this) {
|
||||
if (gSaveContext.rupees < this->dnsItemEntry->itemPrice || Flags_GetRandomizerInf(this->scrubIdentity.randomizerInf)) {
|
||||
return 0;
|
||||
}
|
||||
return 4;
|
||||
}
|
||||
|
||||
u32 func_809EF5A4(EnDns* this) {
|
||||
if ((CUR_CAPACITY(UPG_NUTS) != 0) && (AMMO(ITEM_NUT) >= CUR_CAPACITY(UPG_NUTS))) {
|
||||
return 1;
|
||||
@ -281,6 +309,10 @@ u32 func_809EF9A4(EnDns* this) {
|
||||
}
|
||||
|
||||
/* Paying and flagging functions */
|
||||
void EnDns_RandomizerPurchase(EnDns* this) {
|
||||
Rupees_ChangeBy(-this->dnsItemEntry->itemPrice);
|
||||
Flags_SetRandomizerInf(this->scrubIdentity.randomizerInf);
|
||||
}
|
||||
|
||||
void func_809EF9F8(EnDns* this) {
|
||||
Rupees_ChangeBy(-this->dnsItemEntry->itemPrice);
|
||||
@ -369,31 +401,25 @@ void EnDns_Talk(EnDns* this, GlobalContext* globalCtx) {
|
||||
}
|
||||
|
||||
void func_809EFDD0(EnDns* this, GlobalContext* globalCtx) {
|
||||
if (this->actor.params == 0x9) {
|
||||
if (gSaveContext.n64ddFlag) {
|
||||
GetItemEntry getItemEntry = Randomizer_GetRandomizedItem(GI_STICK_UPGRADE_30, this->actor.id, this->actor.params, globalCtx->sceneNum);
|
||||
GiveItemEntryFromActor(&this->actor, globalCtx, getItemEntry, 130.0f, 100.0f);
|
||||
} else if (CUR_UPG_VALUE(UPG_STICKS) < 2) {
|
||||
func_8002F434(&this->actor, globalCtx, GI_STICK_UPGRADE_20, 130.0f, 100.0f);
|
||||
if (!gSaveContext.n64ddFlag || !this->scrubIdentity.isShuffled) {
|
||||
if (this->actor.params == 0x9) {
|
||||
if (CUR_UPG_VALUE(UPG_STICKS) < 2) {
|
||||
func_8002F434(&this->actor, globalCtx, GI_STICK_UPGRADE_20, 130.0f, 100.0f);
|
||||
} else {
|
||||
func_8002F434(&this->actor, globalCtx, GI_STICK_UPGRADE_30, 130.0f, 100.0f);
|
||||
}
|
||||
} else if (this->actor.params == 0xA) {
|
||||
if (CUR_UPG_VALUE(UPG_NUTS) < 2) {
|
||||
func_8002F434(&this->actor, globalCtx, GI_NUT_UPGRADE_30, 130.0f, 100.0f);
|
||||
} else {
|
||||
func_8002F434(&this->actor, globalCtx, GI_NUT_UPGRADE_40, 130.0f, 100.0f);
|
||||
}
|
||||
} else {
|
||||
func_8002F434(&this->actor, globalCtx, GI_STICK_UPGRADE_30, 130.0f, 100.0f);
|
||||
}
|
||||
} else if (this->actor.params == 0xA) {
|
||||
if (gSaveContext.n64ddFlag) {
|
||||
GetItemEntry getItemEntry = Randomizer_GetRandomizedItem(GI_NUT_UPGRADE_40, this->actor.id, this->actor.params, globalCtx->sceneNum);
|
||||
GiveItemEntryFromActor(&this->actor, globalCtx, getItemEntry, 130.0f, 100.0f);
|
||||
} else if (CUR_UPG_VALUE(UPG_NUTS) < 2) {
|
||||
func_8002F434(&this->actor, globalCtx, GI_NUT_UPGRADE_30, 130.0f, 100.0f);
|
||||
} else {
|
||||
func_8002F434(&this->actor, globalCtx, GI_NUT_UPGRADE_40, 130.0f, 100.0f);
|
||||
func_8002F434(&this->actor, globalCtx, this->dnsItemEntry->getItemId, 130.0f, 100.0f);
|
||||
}
|
||||
} else {
|
||||
if (!gSaveContext.n64ddFlag) {
|
||||
func_8002F434(&this->actor, globalCtx, this->dnsItemEntry->getItemId, 130.0f, 100.0f);
|
||||
} else {
|
||||
GetItemEntry getItemEntry = Randomizer_GetRandomizedItem(this->dnsItemEntry->getItemId, this->actor.id, this->actor.params, globalCtx->sceneNum);
|
||||
GiveItemEntryFromActor(&this->actor, globalCtx, getItemEntry, 130.0f, 100.0f);
|
||||
}
|
||||
GetItemEntry itemEntry = Randomizer_GetItemFromKnownCheck(this->scrubIdentity.randomizerCheck, this->scrubIdentity.getItemId);
|
||||
GiveItemEntryFromActor(&this->actor, globalCtx, itemEntry, 130.0f, 100.0f);
|
||||
}
|
||||
}
|
||||
|
||||
@ -489,6 +515,11 @@ void EnDns_Update(Actor* thisx, GlobalContext* globalCtx) {
|
||||
|
||||
this->dustTimer++;
|
||||
this->actor.textId = D_809F040C[this->actor.params];
|
||||
if (gSaveContext.n64ddFlag && this->scrubIdentity.isShuffled) {
|
||||
// Currently the textID is simply identified by the item price since that is the only thing
|
||||
// unique to it, later on this will change to identifying by scrubIdentity.randomizerInf
|
||||
this->actor.textId = 0x9000 + this->dnsItemEntry->itemPrice;
|
||||
}
|
||||
Actor_SetFocus(&this->actor, 60.0f);
|
||||
Actor_SetScale(&this->actor, 0.01f);
|
||||
SkelAnime_Update(&this->skelAnime);
|
||||
|
@ -32,6 +32,7 @@ typedef struct EnDns {
|
||||
/* 0x02BD */ u8 dropCollectible;
|
||||
/* 0x02C0 */ DnsItemEntry* dnsItemEntry;
|
||||
/* 0x02C4 */ f32 yInitPos;
|
||||
/* */ ScrubIdentity scrubIdentity;
|
||||
} EnDns; // size = 0x02C8
|
||||
|
||||
#endif
|
||||
|
@ -521,9 +521,14 @@ void EnExItem_DrawItems(EnExItem* this, GlobalContext* globalCtx) {
|
||||
case EXITEM_BOMBCHUS_COUNTER:
|
||||
randoGetItem = Randomizer_GetItemFromKnownCheck(RC_MARKET_BOMBCHU_BOWLING_BOMBCHUS, GI_BOMBCHUS_10);
|
||||
break;
|
||||
case EXITEM_BULLET_BAG:
|
||||
randoGetItem = Randomizer_GetItemFromKnownCheck(RC_LW_TARGET_IN_WOODS, GI_BULLET_BAG_50);
|
||||
break;
|
||||
}
|
||||
|
||||
EnItem00_CustomItemsParticles(&this->actor, globalCtx, randoGetItem);
|
||||
GetItemEntry_Draw(globalCtx, randoGetItem);
|
||||
return;
|
||||
}
|
||||
|
||||
GetItem_Draw(globalCtx, this->giDrawId);
|
||||
@ -536,7 +541,7 @@ void EnExItem_DrawHeartPiece(EnExItem* this, GlobalContext* globalCtx) {
|
||||
GetItemEntry randoGetItem =
|
||||
Randomizer_GetItemFromKnownCheck(RC_MARKET_BOMBCHU_BOWLING_SECOND_PRIZE, GI_HEART_PIECE);
|
||||
EnItem00_CustomItemsParticles(&this->actor, globalCtx, randoGetItem);
|
||||
GetItem_Draw(globalCtx, randoGetItem.gid);
|
||||
GetItemEntry_Draw(globalCtx, randoGetItem);
|
||||
} else {
|
||||
GetItem_Draw(globalCtx, GID_HEART_PIECE);
|
||||
}
|
||||
|
@ -114,7 +114,7 @@ u16 EnGo_GetTextID(GlobalContext* globalCtx, Actor* thisx) {
|
||||
}
|
||||
case 0x00:
|
||||
if ((!gSaveContext.n64ddFlag && CHECK_QUEST_ITEM(QUEST_MEDALLION_FIRE)) ||
|
||||
(gSaveContext.n64ddFlag && gSaveContext.dungeonsDone[4])) {
|
||||
(gSaveContext.n64ddFlag && Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_FIRE_TEMPLE))) {
|
||||
if (gSaveContext.infTable[16] & 0x8000) {
|
||||
return 0x3042;
|
||||
} else {
|
||||
|
@ -416,10 +416,10 @@ s16 EnGo2_GetStateGoronDmtRollingSmall(GlobalContext* globalCtx, EnGo2* this) {
|
||||
|
||||
u16 EnGo2_GetTextIdGoronDmtDcEntrance(GlobalContext* globalCtx, EnGo2* this) {
|
||||
if (((!gSaveContext.n64ddFlag && CHECK_QUEST_ITEM(QUEST_MEDALLION_FIRE)) ||
|
||||
(gSaveContext.n64ddFlag && gSaveContext.dungeonsDone[4])) && LINK_IS_ADULT) {
|
||||
(gSaveContext.n64ddFlag && Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_FIRE_TEMPLE))) && LINK_IS_ADULT) {
|
||||
return 0x3043;
|
||||
} else if ((!gSaveContext.n64ddFlag && CHECK_QUEST_ITEM(QUEST_GORON_RUBY)) ||
|
||||
(gSaveContext.n64ddFlag && gSaveContext.dungeonsDone[0])) {
|
||||
(gSaveContext.n64ddFlag && Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_DODONGOS_CAVERN))) {
|
||||
return 0x3027;
|
||||
} else {
|
||||
return gSaveContext.eventChkInf[2] & 0x8 ? 0x3021 : gSaveContext.infTable[14] & 0x1 ? 0x302A : 0x3008;
|
||||
@ -439,10 +439,10 @@ s16 EnGo2_GetStateGoronDmtDcEntrance(GlobalContext* globalCtx, EnGo2* this) {
|
||||
|
||||
u16 EnGo2_GetTextIdGoronCityEntrance(GlobalContext* globalCtx, EnGo2* this) {
|
||||
if (((!gSaveContext.n64ddFlag && CHECK_QUEST_ITEM(QUEST_MEDALLION_FIRE)) ||
|
||||
(gSaveContext.n64ddFlag && gSaveContext.dungeonsDone[4])) && LINK_IS_ADULT) {
|
||||
(gSaveContext.n64ddFlag && Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_FIRE_TEMPLE))) && LINK_IS_ADULT) {
|
||||
return 0x3043;
|
||||
} else if ((!gSaveContext.n64ddFlag && CHECK_QUEST_ITEM(QUEST_GORON_RUBY)) ||
|
||||
(gSaveContext.n64ddFlag && gSaveContext.dungeonsDone[0])) {
|
||||
(gSaveContext.n64ddFlag && Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_DODONGOS_CAVERN))) {
|
||||
return 0x3027;
|
||||
} else {
|
||||
return gSaveContext.infTable[15] & 0x1 ? 0x3015 : 0x3014;
|
||||
@ -462,10 +462,10 @@ s16 EnGo2_GetStateGoronCityEntrance(GlobalContext* globalCtx, EnGo2* this) {
|
||||
|
||||
u16 EnGo2_GetTextIdGoronCityIsland(GlobalContext* globalCtx, EnGo2* this) {
|
||||
if (((!gSaveContext.n64ddFlag && CHECK_QUEST_ITEM(QUEST_MEDALLION_FIRE)) ||
|
||||
(gSaveContext.n64ddFlag && gSaveContext.dungeonsDone[4])) && LINK_IS_ADULT) {
|
||||
(gSaveContext.n64ddFlag && Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_FIRE_TEMPLE))) && LINK_IS_ADULT) {
|
||||
return 0x3043;
|
||||
} else if ((!gSaveContext.n64ddFlag && CHECK_QUEST_ITEM(QUEST_GORON_RUBY)) ||
|
||||
(gSaveContext.n64ddFlag && gSaveContext.dungeonsDone[0])) {
|
||||
(gSaveContext.n64ddFlag && Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_DODONGOS_CAVERN))) {
|
||||
return 0x3027;
|
||||
} else {
|
||||
return gSaveContext.infTable[15] & 0x10 ? 0x3017 : 0x3016;
|
||||
@ -485,10 +485,10 @@ s16 EnGo2_GetStateGoronCityIsland(GlobalContext* globalCtx, EnGo2* this) {
|
||||
|
||||
u16 EnGo2_GetTextIdGoronCityLowestFloor(GlobalContext* globalCtx, EnGo2* this) {
|
||||
if (((!gSaveContext.n64ddFlag && CHECK_QUEST_ITEM(QUEST_MEDALLION_FIRE)) ||
|
||||
(gSaveContext.n64ddFlag && gSaveContext.dungeonsDone[4])) && LINK_IS_ADULT) {
|
||||
(gSaveContext.n64ddFlag && Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_FIRE_TEMPLE))) && LINK_IS_ADULT) {
|
||||
return 0x3043;
|
||||
} else if ((!gSaveContext.n64ddFlag && CHECK_QUEST_ITEM(QUEST_GORON_RUBY)) ||
|
||||
(gSaveContext.n64ddFlag && gSaveContext.dungeonsDone[0])) {
|
||||
(gSaveContext.n64ddFlag && Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_DODONGOS_CAVERN))) {
|
||||
return 0x3027;
|
||||
} else {
|
||||
return CUR_UPG_VALUE(UPG_STRENGTH) != 0 ? 0x302C
|
||||
@ -1589,7 +1589,7 @@ void EnGo2_Init(Actor* thisx, GlobalContext* globalCtx) {
|
||||
case GORON_CITY_STAIRWELL:
|
||||
case GORON_CITY_LOST_WOODS:
|
||||
if (((!gSaveContext.n64ddFlag && !CHECK_QUEST_ITEM(QUEST_MEDALLION_FIRE)) ||
|
||||
(gSaveContext.n64ddFlag && !gSaveContext.dungeonsDone[4])) && LINK_IS_ADULT) {
|
||||
(gSaveContext.n64ddFlag && !Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_FIRE_TEMPLE))) && LINK_IS_ADULT) {
|
||||
Actor_Kill(&this->actor);
|
||||
}
|
||||
this->actionFunc = EnGo2_CurledUp;
|
||||
|
@ -73,7 +73,7 @@ static AnimationInfo sAnimationInfo[] = {
|
||||
u16 EnKz_GetTextNoMaskChild(GlobalContext* globalCtx, EnKz* this) {
|
||||
Player* player = GET_PLAYER(globalCtx);
|
||||
|
||||
if ((gSaveContext.n64ddFlag && gSaveContext.dungeonsDone[2]) ||
|
||||
if ((gSaveContext.n64ddFlag && Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_JABU_JABUS_BELLY)) ||
|
||||
(!gSaveContext.n64ddFlag && CHECK_QUEST_ITEM(QUEST_ZORA_SAPPHIRE))) {
|
||||
return 0x402B;
|
||||
} else if (gSaveContext.eventChkInf[3] & 8) {
|
||||
|
@ -373,7 +373,7 @@ u16 EnMd_GetTextKokiriForest(GlobalContext* globalCtx, EnMd* this) {
|
||||
this->unk_209 = TEXT_STATE_NONE;
|
||||
|
||||
if ((!gSaveContext.n64ddFlag && CHECK_QUEST_ITEM(QUEST_KOKIRI_EMERALD)) ||
|
||||
(gSaveContext.n64ddFlag && gSaveContext.dungeonsDone[1])) {
|
||||
(gSaveContext.n64ddFlag && Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_DEKU_TREE))) {
|
||||
return 0x1045;
|
||||
}
|
||||
|
||||
@ -486,7 +486,7 @@ u8 EnMd_ShouldSpawn(EnMd* this, GlobalContext* globalCtx) {
|
||||
if (gSaveContext.n64ddFlag) {
|
||||
// if we have beaten deku tree or have open forest turned on
|
||||
// or have already shown mido we have an equipped sword/shield
|
||||
if (gSaveContext.dungeonsDone[1] ||
|
||||
if (Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_DEKU_TREE) ||
|
||||
Randomizer_GetSettingValue(RSK_FOREST) == 1 ||
|
||||
gSaveContext.eventChkInf[0] & 0x10) {
|
||||
return 0;
|
||||
|
@ -518,7 +518,7 @@ void EnOssan_TalkGoronShopkeeper(GlobalContext* globalCtx) {
|
||||
Message_ContinueTextbox(globalCtx, 0x300F);
|
||||
}
|
||||
} else if ((!gSaveContext.n64ddFlag && !CHECK_QUEST_ITEM(QUEST_MEDALLION_FIRE)) ||
|
||||
(gSaveContext.n64ddFlag && !gSaveContext.dungeonsDone[4])) {
|
||||
(gSaveContext.n64ddFlag && !Flags_GetRandomizerInf(RAND_INF_DUNGEONS_DONE_FIRE_TEMPLE))) {
|
||||
Message_ContinueTextbox(globalCtx, 0x3057);
|
||||
} else {
|
||||
Message_ContinueTextbox(globalCtx, 0x305B);
|
||||
|
@ -69,6 +69,15 @@ void EnShopnuts_Init(Actor* thisx, GlobalContext* globalCtx) {
|
||||
CollisionCheck_SetInfo(&this->actor.colChkInfo, NULL, &sColChkInfoInit);
|
||||
Collider_UpdateCylinder(&this->actor, &this->collider);
|
||||
|
||||
if (gSaveContext.n64ddFlag) {
|
||||
s16 respawnData = gSaveContext.respawn[RESPAWN_MODE_RETURN].data & ((1 << 8) - 1);
|
||||
ScrubIdentity scrubIdentity = Randomizer_IdentifyScrub(globalCtx->sceneNum, this->actor.params, respawnData);
|
||||
|
||||
if (scrubIdentity.isShuffled && Flags_GetRandomizerInf(scrubIdentity.randomizerInf)) {
|
||||
Actor_Kill(&this->actor);
|
||||
}
|
||||
}
|
||||
|
||||
if (((this->actor.params == 0x0002) && (gSaveContext.itemGetInf[0] & 0x800)) ||
|
||||
((this->actor.params == 0x0009) && (gSaveContext.infTable[25] & 4)) ||
|
||||
((this->actor.params == 0x000A) && (gSaveContext.infTable[25] & 8))) {
|
||||
|
@ -17,7 +17,8 @@ s32 func_80AFB748(EnSi* this, GlobalContext* globalCtx);
|
||||
void func_80AFB768(EnSi* this, GlobalContext* globalCtx);
|
||||
void func_80AFB89C(EnSi* this, GlobalContext* globalCtx);
|
||||
void func_80AFB950(EnSi* this, GlobalContext* globalCtx);
|
||||
void Randomizer_GrantSkullReward(EnSi* this, GlobalContext* globalCtx);
|
||||
void Randomizer_UpdateSkullReward(EnSi* this, GlobalContext* globalCtx);
|
||||
void Randomizer_GiveSkullReward(EnSi* this, GlobalContext* globalCtx);
|
||||
|
||||
s32 textId = 0xB4;
|
||||
s32 giveItemId = ITEM_SKULL_TOKEN;
|
||||
@ -99,21 +100,25 @@ void func_80AFB768(EnSi* this, GlobalContext* globalCtx) {
|
||||
|
||||
if (this->collider.base.ocFlags2 & OC2_HIT_PLAYER) {
|
||||
this->collider.base.ocFlags2 &= ~OC2_HIT_PLAYER;
|
||||
|
||||
if (gSaveContext.n64ddFlag) {
|
||||
Randomizer_GrantSkullReward(this, globalCtx);
|
||||
Randomizer_UpdateSkullReward(this, globalCtx);
|
||||
} else {
|
||||
Item_Give(globalCtx, giveItemId);
|
||||
}
|
||||
if ((CVar_GetS32("gSkulltulaFreeze", 0) != 1 || giveItemId != ITEM_SKULL_TOKEN) && getItemId != RG_ICE_TRAP) {
|
||||
player->actor.freezeTimer = 20;
|
||||
}
|
||||
|
||||
Message_StartTextbox(globalCtx, textId, NULL);
|
||||
|
||||
if (gSaveContext.n64ddFlag && getItemId != RG_ICE_TRAP) {
|
||||
Randomizer_GiveSkullReward(this, globalCtx);
|
||||
Audio_PlayFanfare_Rando(getItem);
|
||||
} else {
|
||||
Audio_PlayFanfare(NA_BGM_SMALL_ITEM_GET);
|
||||
}
|
||||
|
||||
player->getItemEntry = (GetItemEntry)GET_ITEM_NONE;
|
||||
this->actionFunc = func_80AFB950;
|
||||
} else {
|
||||
@ -133,16 +138,20 @@ void func_80AFB89C(EnSi* this, GlobalContext* globalCtx) {
|
||||
|
||||
if (!CHECK_FLAG_ALL(this->actor.flags, ACTOR_FLAG_13)) {
|
||||
if (gSaveContext.n64ddFlag) {
|
||||
Randomizer_GrantSkullReward(this, globalCtx);
|
||||
Randomizer_UpdateSkullReward(this, globalCtx);
|
||||
} else {
|
||||
Item_Give(globalCtx, giveItemId);
|
||||
}
|
||||
|
||||
Message_StartTextbox(globalCtx, textId, NULL);
|
||||
|
||||
if (gSaveContext.n64ddFlag && getItemId != RG_ICE_TRAP) {
|
||||
Randomizer_GiveSkullReward(this, globalCtx);
|
||||
Audio_PlayFanfare_Rando(getItem);
|
||||
} else {
|
||||
Audio_PlayFanfare(NA_BGM_SMALL_ITEM_GET);
|
||||
}
|
||||
|
||||
player->getItemEntry = (GetItemEntry)GET_ITEM_NONE;
|
||||
this->actionFunc = func_80AFB950;
|
||||
}
|
||||
@ -184,13 +193,13 @@ void EnSi_Draw(Actor* thisx, GlobalContext* globalCtx) {
|
||||
f32 mtxScale = 1.5f;
|
||||
Matrix_Scale(mtxScale, mtxScale, mtxScale, MTXMODE_APPLY);
|
||||
}
|
||||
GetItem_Draw(globalCtx, getItem.gid);
|
||||
GetItemEntry_Draw(globalCtx, getItem);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
void Randomizer_GrantSkullReward(EnSi* this, GlobalContext* globalCtx) {
|
||||
void Randomizer_UpdateSkullReward(EnSi* this, GlobalContext* globalCtx) {
|
||||
Player* player = GET_PLAYER(globalCtx);
|
||||
|
||||
getItem = Randomizer_GetRandomizedItem(GI_SKULL_TOKEN, this->actor.id, this->actor.params, globalCtx->sceneNum);
|
||||
@ -201,12 +210,20 @@ void Randomizer_GrantSkullReward(EnSi* this, GlobalContext* globalCtx) {
|
||||
} else {
|
||||
textId = getItem.textId;
|
||||
giveItemId = getItem.itemId;
|
||||
if (getItem.modIndex == MOD_NONE) {
|
||||
Item_Give(globalCtx, giveItemId);
|
||||
} else if (getItem.modIndex == MOD_RANDOMIZER) {
|
||||
Randomizer_Item_Give(globalCtx, getItem);
|
||||
}
|
||||
}
|
||||
// player->getItemId = getItemId;
|
||||
player->getItemEntry = getItem;
|
||||
}
|
||||
|
||||
void Randomizer_GiveSkullReward(EnSi* this, GlobalContext* globalCtx) {
|
||||
Player* player = GET_PLAYER(globalCtx);
|
||||
|
||||
if (getItem.modIndex == MOD_NONE) {
|
||||
Item_Give(globalCtx, giveItemId);
|
||||
} else if (getItem.modIndex == MOD_RANDOMIZER) {
|
||||
Randomizer_Item_Give(globalCtx, getItem);
|
||||
}
|
||||
// RANDOTOD: Move this into Item_Give() or some other more central location
|
||||
if (getItem.getItemId == GI_SWORD_BGS) {
|
||||
gSaveContext.bgsFlag = true;
|
||||
}
|
||||
}
|
||||
|
@ -99,8 +99,8 @@ void ItemBHeart_Draw(Actor* thisx, GlobalContext* globalCtx) {
|
||||
}
|
||||
|
||||
if (gSaveContext.n64ddFlag) {
|
||||
GetItem_Draw(globalCtx, Randomizer_GetRandomizedItem(GI_HEART_CONTAINER_2,
|
||||
this->actor.id,this->actor.params, globalCtx->sceneNum).gid);
|
||||
GetItemEntry_Draw(globalCtx, Randomizer_GetRandomizedItem(GI_HEART_CONTAINER_2,
|
||||
this->actor.id,this->actor.params, globalCtx->sceneNum));
|
||||
} else {
|
||||
if (flag) {
|
||||
func_80093D84(globalCtx->state.gfxCtx);
|
||||
|
@ -233,7 +233,7 @@ void ItemEtcetera_DrawThroughLens(Actor* thisx, GlobalContext* globalCtx) {
|
||||
GetItemEntry randoGetItem = GetChestGameRandoGetItem(this->actor.room, this->giDrawId, globalCtx);
|
||||
EnItem00_CustomItemsParticles(&this->actor, globalCtx, randoGetItem);
|
||||
if (randoGetItem.itemId != ITEM_NONE) {
|
||||
GetItem_Draw(globalCtx, randoGetItem.gid);
|
||||
GetItemEntry_Draw(globalCtx, randoGetItem);
|
||||
return;
|
||||
}
|
||||
}
|
||||
@ -257,7 +257,10 @@ void ItemEtcetera_Draw(Actor* thisx, GlobalContext* globalCtx) {
|
||||
EnItem00_CustomItemsParticles(&this->actor, globalCtx, randoGetItem);
|
||||
|
||||
if (randoGetItem.itemId != RG_NONE) {
|
||||
this->giDrawId = randoGetItem.gid;
|
||||
func_8002EBCC(&this->actor, globalCtx, 0);
|
||||
func_8002ED80(&this->actor, globalCtx, 0);
|
||||
GetItemEntry_Draw(globalCtx, randoGetItem);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -218,7 +218,7 @@ void ItemOcarina_Draw(Actor* thisx, GlobalContext* globalCtx) {
|
||||
if (gSaveContext.n64ddFlag) {
|
||||
GetItemEntry randoGetItem = Randomizer_GetItemFromKnownCheck(RC_HF_OCARINA_OF_TIME_ITEM, GI_OCARINA_OOT);
|
||||
EnItem00_CustomItemsParticles(&this->actor, globalCtx, randoGetItem);
|
||||
GetItem_Draw(globalCtx, randoGetItem.gid);
|
||||
GetItemEntry_Draw(globalCtx, randoGetItem);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -6083,8 +6083,8 @@ void Player_SetPendingFlag(Player* this, GlobalContext* globalCtx) {
|
||||
case FLAG_SCENE_TREASURE:
|
||||
Flags_SetTreasure(globalCtx, this->pendingFlag.flagID);
|
||||
break;
|
||||
case FLAG_COW_MILKED:
|
||||
gSaveContext.cowsMilked[this->pendingFlag.flagID] = 1;
|
||||
case FLAG_RANDOMIZER_INF:
|
||||
Flags_SetRandomizerInf(this->pendingFlag.flagID);
|
||||
break;
|
||||
case FLAG_EVENT_CHECK_INF:
|
||||
Flags_SetEventChkInf(this->pendingFlag.flagID);
|
||||
@ -12667,6 +12667,14 @@ s32 func_8084DFF4(GlobalContext* globalCtx, Player* this) {
|
||||
this->stateFlags1 &= ~PLAYER_STATE1_29;
|
||||
func_80852FFC(globalCtx, NULL, 8);
|
||||
}
|
||||
|
||||
// Set unk_862 to 0 early to not have the game draw non-custom colored models for a split second.
|
||||
// This unk is what the game normally uses to decide what item to draw when holding up an item above Link's head.
|
||||
// Only do this when the item actually has a custom draw function.
|
||||
if (this->getItemEntry.drawFunc != NULL) {
|
||||
this->unk_862 = 0;
|
||||
}
|
||||
|
||||
this->getItemId = GI_NONE;
|
||||
this->getItemEntry = (GetItemEntry)GET_ITEM_NONE;
|
||||
}
|
||||
|
@ -598,6 +598,170 @@ void KaleidoScope_UpdateItemEquip(GlobalContext* globalCtx) {
|
||||
u16 offsetX;
|
||||
u16 offsetY;
|
||||
|
||||
s16 Top_HUD_Margin = CVar_GetS32("gHUDMargin_T", 0);
|
||||
s16 Left_HUD_Margin = CVar_GetS32("gHUDMargin_L", 0);
|
||||
s16 Right_HUD_Margin = CVar_GetS32("gHUDMargin_R", 0);
|
||||
s16 Bottom_HUD_Margin = CVar_GetS32("gHUDMargin_B", 0);
|
||||
|
||||
s16 X_Margins_CL;
|
||||
s16 X_Margins_CR;
|
||||
s16 X_Margins_CD;
|
||||
s16 Y_Margins_CL;
|
||||
s16 Y_Margins_CR;
|
||||
s16 Y_Margins_CD;
|
||||
s16 X_Margins_BtnB;
|
||||
s16 Y_Margins_BtnB;
|
||||
s16 X_Margins_DPad_Items;
|
||||
s16 Y_Margins_DPad_Items;
|
||||
if (CVar_GetS32("gBBtnUseMargins", 0) != 0) {
|
||||
if (CVar_GetS32("gBBtnPosType", 0) == 0) {X_Margins_BtnB = Right_HUD_Margin;};
|
||||
Y_Margins_BtnB = (Top_HUD_Margin*-1);
|
||||
} else {
|
||||
X_Margins_BtnB = 0;
|
||||
Y_Margins_BtnB = 0;
|
||||
}
|
||||
if (CVar_GetS32("gCBtnLUseMargins", 0) != 0) {
|
||||
if (CVar_GetS32("gCBtnLPosType", 0) == 0) {X_Margins_CL = Right_HUD_Margin;};
|
||||
Y_Margins_CL = (Top_HUD_Margin*-1);
|
||||
} else {
|
||||
X_Margins_CL = 0;
|
||||
Y_Margins_CL = 0;
|
||||
}
|
||||
if (CVar_GetS32("gCBtnRUseMargins", 0) != 0) {
|
||||
if (CVar_GetS32("gCBtnRPosType", 0) == 0) {X_Margins_CR = Right_HUD_Margin;};
|
||||
Y_Margins_CR = (Top_HUD_Margin*-1);
|
||||
} else {
|
||||
X_Margins_CR = 0;
|
||||
Y_Margins_CR = 0;
|
||||
}
|
||||
if (CVar_GetS32("gCBtnDUseMargins", 0) != 0) {
|
||||
if (CVar_GetS32("gCBtnDPosType", 0) == 0) {X_Margins_CD = Right_HUD_Margin;};
|
||||
Y_Margins_CD = (Top_HUD_Margin*-1);
|
||||
} else {
|
||||
X_Margins_CD = 0;
|
||||
Y_Margins_CD = 0;
|
||||
}
|
||||
if (CVar_GetS32("gDPadUseMargins", 0) != 0) {
|
||||
if (CVar_GetS32("gDPadPosType", 0) == 0) {X_Margins_DPad_Items = Right_HUD_Margin;};
|
||||
Y_Margins_DPad_Items = (Top_HUD_Margin*-1);
|
||||
} else {
|
||||
X_Margins_DPad_Items = 0;
|
||||
Y_Margins_DPad_Items = 0;
|
||||
}
|
||||
const s16 ItemIconPos_ori[7][2] = {
|
||||
{ C_LEFT_BUTTON_X+X_Margins_CL, C_LEFT_BUTTON_Y+Y_Margins_CL },
|
||||
{ C_DOWN_BUTTON_X+X_Margins_CD, C_DOWN_BUTTON_Y+Y_Margins_CD },
|
||||
{ C_RIGHT_BUTTON_X+X_Margins_CR, C_RIGHT_BUTTON_Y+Y_Margins_CR },
|
||||
{ DPAD_UP_X+X_Margins_DPad_Items, DPAD_UP_Y+Y_Margins_DPad_Items },
|
||||
{ DPAD_DOWN_X+X_Margins_DPad_Items, DPAD_DOWN_Y+Y_Margins_DPad_Items },
|
||||
{ DPAD_LEFT_X+X_Margins_DPad_Items, DPAD_LEFT_Y+Y_Margins_DPad_Items },
|
||||
{ DPAD_RIGHT_X+X_Margins_DPad_Items, DPAD_RIGHT_Y+Y_Margins_DPad_Items }
|
||||
};
|
||||
s16 DPad_ItemsOffset[4][2] = {
|
||||
{ 7,-8},//Up
|
||||
{ 7,24},//Down
|
||||
{-9, 8},//Left
|
||||
{23, 8},//Right
|
||||
}; //(X,Y) Used with custom position to place it properly.
|
||||
|
||||
//DPadItems
|
||||
if (CVar_GetS32("gDPadPosType", 0) != 0) {
|
||||
sCButtonPosY[3] = CVar_GetS32("gDPadPosY", 0)+Y_Margins_DPad_Items+DPad_ItemsOffset[0][1];//Up
|
||||
sCButtonPosY[4] = CVar_GetS32("gDPadPosY", 0)+Y_Margins_DPad_Items+DPad_ItemsOffset[1][1];//Down
|
||||
sCButtonPosY[5] = CVar_GetS32("gDPadPosY", 0)+Y_Margins_DPad_Items+DPad_ItemsOffset[2][1];//Left
|
||||
sCButtonPosY[6] = CVar_GetS32("gDPadPosY", 0)+Y_Margins_DPad_Items+DPad_ItemsOffset[3][1];//Right
|
||||
if (CVar_GetS32("gDPadPosType", 0) == 1) {//Anchor Left
|
||||
if (CVar_GetS32("gDPadUseMargins", 0) != 0) {X_Margins_DPad_Items = Left_HUD_Margin;};
|
||||
sCButtonPosX[3] = OTRGetDimensionFromLeftEdge(CVar_GetS32("gDPadPosX", 0)+X_Margins_DPad_Items+DPad_ItemsOffset[0][0]);
|
||||
sCButtonPosX[4] = OTRGetDimensionFromLeftEdge(CVar_GetS32("gDPadPosX", 0)+X_Margins_DPad_Items+DPad_ItemsOffset[1][0]);
|
||||
sCButtonPosX[5] = OTRGetDimensionFromLeftEdge(CVar_GetS32("gDPadPosX", 0)+X_Margins_DPad_Items+DPad_ItemsOffset[2][0]);
|
||||
sCButtonPosX[6] = OTRGetDimensionFromLeftEdge(CVar_GetS32("gDPadPosX", 0)+X_Margins_DPad_Items+DPad_ItemsOffset[3][0]);
|
||||
} else if (CVar_GetS32("gDPadPosType", 0) == 2) {//Anchor Right
|
||||
if (CVar_GetS32("gDPadUseMargins", 0) != 0) {X_Margins_DPad_Items = Right_HUD_Margin;};
|
||||
sCButtonPosX[3] = OTRGetDimensionFromRightEdge(CVar_GetS32("gDPadPosX", 0)+X_Margins_DPad_Items+DPad_ItemsOffset[0][0]);
|
||||
sCButtonPosX[4] = OTRGetDimensionFromRightEdge(CVar_GetS32("gDPadPosX", 0)+X_Margins_DPad_Items+DPad_ItemsOffset[1][0]);
|
||||
sCButtonPosX[5] = OTRGetDimensionFromRightEdge(CVar_GetS32("gDPadPosX", 0)+X_Margins_DPad_Items+DPad_ItemsOffset[2][0]);
|
||||
sCButtonPosX[6] = OTRGetDimensionFromRightEdge(CVar_GetS32("gDPadPosX", 0)+X_Margins_DPad_Items+DPad_ItemsOffset[3][0]);
|
||||
} else if (CVar_GetS32("gDPadPosType", 0) == 3) {//Anchor None
|
||||
sCButtonPosX[3] = CVar_GetS32("gDPadPosX", 0)+DPad_ItemsOffset[0][0];
|
||||
sCButtonPosX[4] = CVar_GetS32("gDPadPosX", 0)+DPad_ItemsOffset[1][0];
|
||||
sCButtonPosX[5] = CVar_GetS32("gDPadPosX", 0)+DPad_ItemsOffset[2][0];
|
||||
sCButtonPosX[6] = CVar_GetS32("gDPadPosX", 0)+DPad_ItemsOffset[3][0];
|
||||
}
|
||||
} else {
|
||||
sCButtonPosX[3] = OTRGetDimensionFromRightEdge(ItemIconPos_ori[3][0]);
|
||||
sCButtonPosX[4] = OTRGetDimensionFromRightEdge(ItemIconPos_ori[4][0]);
|
||||
sCButtonPosX[5] = OTRGetDimensionFromRightEdge(ItemIconPos_ori[5][0]);
|
||||
sCButtonPosX[6] = OTRGetDimensionFromRightEdge(ItemIconPos_ori[6][0]);
|
||||
sCButtonPosY[3] = ItemIconPos_ori[3][1];
|
||||
sCButtonPosY[4] = ItemIconPos_ori[4][1];
|
||||
sCButtonPosY[5] = ItemIconPos_ori[5][1];
|
||||
sCButtonPosY[6] = ItemIconPos_ori[6][1];
|
||||
}
|
||||
//C button Left
|
||||
if (CVar_GetS32("gCBtnLPosType", 0) != 0) {
|
||||
sCButtonPosY[0] = CVar_GetS32("gCBtnLPosY", 0)+Y_Margins_CL;
|
||||
if (CVar_GetS32("gCBtnLPosType", 0) == 1) {//Anchor Left
|
||||
if (CVar_GetS32("gCBtnLUseMargins", 0) != 0) {X_Margins_CL = Left_HUD_Margin;};
|
||||
sCButtonPosX[0] = OTRGetDimensionFromLeftEdge(CVar_GetS32("gCBtnLPosX", 0)+X_Margins_CL);
|
||||
} else if (CVar_GetS32("gCBtnLPosType", 0) == 2) {//Anchor Right
|
||||
if (CVar_GetS32("gCBtnLUseMargins", 0) != 0) {X_Margins_CL = Right_HUD_Margin;};
|
||||
sCButtonPosX[0] = OTRGetDimensionFromRightEdge(CVar_GetS32("gCBtnLPosX", 0)+X_Margins_CL);
|
||||
} else if (CVar_GetS32("gCBtnLPosType", 0) == 3) {//Anchor None
|
||||
sCButtonPosX[0] = CVar_GetS32("gCBtnLPosX", 0);
|
||||
}
|
||||
} else {
|
||||
sCButtonPosX[0] = OTRGetRectDimensionFromRightEdge(ItemIconPos_ori[0][0]);
|
||||
sCButtonPosY[0] = ItemIconPos_ori[0][1];
|
||||
}
|
||||
//C Button down
|
||||
if (CVar_GetS32("gCBtnDPosType", 0) != 0) {
|
||||
sCButtonPosY[1] = CVar_GetS32("gCBtnDPosY", 0)+Y_Margins_CD;
|
||||
if (CVar_GetS32("gCBtnDPosType", 0) == 1) {//Anchor Left
|
||||
if (CVar_GetS32("gCBtnDUseMargins", 0) != 0) {X_Margins_CD = Left_HUD_Margin;};
|
||||
sCButtonPosX[1] = OTRGetDimensionFromLeftEdge(CVar_GetS32("gCBtnDPosX", 0)+X_Margins_CD);
|
||||
} else if (CVar_GetS32("gCBtnDPosType", 0) == 2) {//Anchor Right
|
||||
if (CVar_GetS32("gCBtnDUseMargins", 0) != 0) {X_Margins_CD = Right_HUD_Margin;};
|
||||
sCButtonPosX[1] = OTRGetDimensionFromRightEdge(CVar_GetS32("gCBtnDPosX", 0)+X_Margins_CD);
|
||||
} else if (CVar_GetS32("gCBtnDPosType", 0) == 3) {//Anchor None
|
||||
sCButtonPosX[1] = CVar_GetS32("gCBtnDPosX", 0);
|
||||
}
|
||||
} else {
|
||||
sCButtonPosX[1] = OTRGetRectDimensionFromRightEdge(ItemIconPos_ori[1][0]);
|
||||
sCButtonPosY[1] = ItemIconPos_ori[1][1];
|
||||
}
|
||||
//C button Right
|
||||
if (CVar_GetS32("gCBtnRPosType", 0) != 0) {
|
||||
sCButtonPosY[2] = CVar_GetS32("gCBtnRPosY", 0)+Y_Margins_CR;
|
||||
if (CVar_GetS32("gCBtnRPosType", 0) == 1) {//Anchor Left
|
||||
if (CVar_GetS32("gCBtnRUseMargins", 0) != 0) {X_Margins_CR = Left_HUD_Margin;};
|
||||
sCButtonPosX[2] = OTRGetDimensionFromLeftEdge(CVar_GetS32("gCBtnRPosX", 0)+X_Margins_CR);
|
||||
} else if (CVar_GetS32("gCBtnRPosType", 0) == 2) {//Anchor Right
|
||||
if (CVar_GetS32("gCBtnRUseMargins", 0) != 0) {X_Margins_CR = Right_HUD_Margin;};
|
||||
sCButtonPosX[2] = OTRGetDimensionFromRightEdge(CVar_GetS32("gCBtnRPosX", 0)+X_Margins_CR);
|
||||
} else if (CVar_GetS32("gCBtnRPosType", 0) == 3) {//Anchor None
|
||||
sCButtonPosX[2] = CVar_GetS32("gCBtnRPosX", 0);
|
||||
}
|
||||
} else {
|
||||
sCButtonPosX[2] = OTRGetRectDimensionFromRightEdge(ItemIconPos_ori[2][0]);
|
||||
sCButtonPosY[2] = ItemIconPos_ori[2][1];
|
||||
}
|
||||
|
||||
sCButtonPosX[0] = sCButtonPosX[0] - 160;
|
||||
sCButtonPosY[0] = 120 - sCButtonPosY[0];
|
||||
sCButtonPosX[1] = sCButtonPosX[1] - 160;
|
||||
sCButtonPosY[1] = 120 - sCButtonPosY[1];
|
||||
sCButtonPosX[2] = sCButtonPosX[2] - 160;
|
||||
sCButtonPosY[2] = 120 - sCButtonPosY[2];
|
||||
sCButtonPosX[3] = sCButtonPosX[3] - 160;
|
||||
sCButtonPosY[3] = 120 - sCButtonPosY[3];
|
||||
sCButtonPosX[4] = sCButtonPosX[4] - 160;
|
||||
sCButtonPosY[4] = 120 - sCButtonPosY[4];
|
||||
sCButtonPosX[5] = sCButtonPosX[5] - 160;
|
||||
sCButtonPosY[5] = 120 - sCButtonPosY[5];
|
||||
sCButtonPosX[6] = sCButtonPosX[6] - 160;
|
||||
sCButtonPosY[6] = 120 - sCButtonPosY[6];
|
||||
|
||||
if (sEquipState == 0) {
|
||||
pauseCtx->equipAnimAlpha += 14;
|
||||
if (pauseCtx->equipAnimAlpha > 255) {
|
||||
@ -628,7 +792,7 @@ void KaleidoScope_UpdateItemEquip(GlobalContext* globalCtx) {
|
||||
offsetX = ABS(pauseCtx->equipAnimX - bowItemVtx->v.ob[0] * 10) / sEquipMoveTimer;
|
||||
offsetY = ABS(pauseCtx->equipAnimY - bowItemVtx->v.ob[1] * 10) / sEquipMoveTimer;
|
||||
} else {
|
||||
offsetX = ABS(pauseCtx->equipAnimX - OTRGetRectDimensionFromRightEdge(sCButtonPosX[pauseCtx->equipTargetCBtn]) * 10) / sEquipMoveTimer;
|
||||
offsetX = ABS(pauseCtx->equipAnimX - sCButtonPosX[pauseCtx->equipTargetCBtn] * 10) / sEquipMoveTimer;
|
||||
offsetY = ABS(pauseCtx->equipAnimY - sCButtonPosY[pauseCtx->equipTargetCBtn] * 10) / sEquipMoveTimer;
|
||||
}
|
||||
|
||||
@ -658,7 +822,7 @@ void KaleidoScope_UpdateItemEquip(GlobalContext* globalCtx) {
|
||||
pauseCtx->equipAnimY += offsetY;
|
||||
}
|
||||
} else {
|
||||
if (pauseCtx->equipAnimX >= OTRGetRectDimensionFromRightEdge(sCButtonPosX[pauseCtx->equipTargetCBtn]) * 10) {
|
||||
if (pauseCtx->equipAnimX >= sCButtonPosX[pauseCtx->equipTargetCBtn] * 10) {
|
||||
pauseCtx->equipAnimX -= offsetX;
|
||||
} else {
|
||||
pauseCtx->equipAnimX += offsetX;
|
||||
|
Loading…
x
Reference in New Issue
Block a user