Merge branch 'develop-zhora' into z-to-rando-next

This commit is contained in:
briaguya 2022-09-03 03:47:09 -04:00
commit 975a854054
55 changed files with 2949 additions and 2579 deletions

View File

@ -121,6 +121,7 @@ set(Source_Files__CustomImpl
source_group("Source Files\\CustomImpl" FILES ${Source_Files__CustomImpl}) source_group("Source Files\\CustomImpl" FILES ${Source_Files__CustomImpl})
set(Source_Files__CustomImpl__Hooks set(Source_Files__CustomImpl__Hooks
"Hooks.cpp"
"Hooks.h" "Hooks.h"
) )
source_group("Source Files\\CustomImpl\\Hooks" FILES ${Source_Files__CustomImpl__Hooks}) source_group("Source Files\\CustomImpl\\Hooks" FILES ${Source_Files__CustomImpl__Hooks})

View File

@ -1,6 +1,9 @@
#include "spdlog/spdlog.h" #include "spdlog/spdlog.h"
#include "Utils/StringHelper.h" #include "Utils/StringHelper.h"
#include "CrashHandler.h" #include "CrashHandler.h"
#include "Window.h"
extern "C" void DeinitOTR(void);
#if defined(__linux__) #if defined(__linux__)
#include <csignal> #include <csignal>
@ -10,163 +13,343 @@
#include <execinfo.h> #include <execinfo.h>
#include <unistd.h> #include <unistd.h>
extern "C" void DeinitOTR(void);
static void PrintRegisters(ucontext_t* ctx) { static void PrintRegisters(ucontext_t* ctx) {
char regbuffer[1024]; char regbuffer[1024];
SPDLOG_CRITICAL("Registers:"); SPDLOG_CRITICAL("Registers:");
#if defined(__x86_64__) #if defined(__x86_64__)
snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_RAX]); snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_RAX]);
SPDLOG_CRITICAL("RAX: {} ", regbuffer); SPDLOG_CRITICAL("RAX: {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_RDI]); snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_RDI]);
SPDLOG_CRITICAL("RDI: {} ", regbuffer); SPDLOG_CRITICAL("RDI: {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_RSI]); snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_RSI]);
SPDLOG_CRITICAL("RSI: {} ", regbuffer); SPDLOG_CRITICAL("RSI: {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_RDX]); snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_RDX]);
SPDLOG_CRITICAL("RDX: {} ", regbuffer); SPDLOG_CRITICAL("RDX: {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_RCX]); snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_RCX]);
SPDLOG_CRITICAL("RCX: {} ", regbuffer); SPDLOG_CRITICAL("RCX: {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_R8]); snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_R8]);
SPDLOG_CRITICAL("R8 : {} ", regbuffer); SPDLOG_CRITICAL("R8 : {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_R9]); snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_R9]);
SPDLOG_CRITICAL("R9 : {} ", regbuffer); SPDLOG_CRITICAL("R9 : {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_R10]); snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_R10]);
SPDLOG_CRITICAL("R10: {} ", regbuffer); SPDLOG_CRITICAL("R10: {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_R11]); snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_R11]);
SPDLOG_CRITICAL("R11: {} ", regbuffer); SPDLOG_CRITICAL("R11: {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_RSP]); snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_RSP]);
SPDLOG_CRITICAL("RSP: {} ", regbuffer); SPDLOG_CRITICAL("RSP: {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_RBX]); snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_RBX]);
SPDLOG_CRITICAL("RBX: {} ", regbuffer); SPDLOG_CRITICAL("RBX: {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_RBP]); snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_RBP]);
SPDLOG_CRITICAL("RBP: {} ", regbuffer); SPDLOG_CRITICAL("RBP: {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_R12]); snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_R12]);
SPDLOG_CRITICAL("R12: {} ", regbuffer); SPDLOG_CRITICAL("R12: {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_R13]); snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_R13]);
SPDLOG_CRITICAL("R13: {} ", regbuffer); SPDLOG_CRITICAL("R13: {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_R14]); snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_R14]);
SPDLOG_CRITICAL("R14: {} ", regbuffer); SPDLOG_CRITICAL("R14: {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_R15]); snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_R15]);
SPDLOG_CRITICAL("R15: {} ", regbuffer); SPDLOG_CRITICAL("R15: {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_RIP]); snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_RIP]);
SPDLOG_CRITICAL("RIP: {} ", regbuffer); SPDLOG_CRITICAL("RIP: {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_EFL]); snprintf(regbuffer, std::size(regbuffer), "0x%016llX", ctx->uc_mcontext.gregs[REG_EFL]);
SPDLOG_CRITICAL("EFLAGS: {} ", regbuffer); SPDLOG_CRITICAL("EFLAGS: {} ", regbuffer);
#else #else
snprintf(regbuffer, std::size(regbuffer),"0x%08lX", ctx->uc_mcontext.gregs[REG_EDI]); snprintf(regbuffer, std::size(regbuffer),"0x%08lX", ctx->uc_mcontext.gregs[REG_EDI]);
SPDLOG_CRITICAL("EDI : {} ", regbuffer); SPDLOG_CRITICAL("EDI : {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer),"0x%08lX", ctx->uc_mcontext.gregs[REG_ESI]); snprintf(regbuffer, std::size(regbuffer),"0x%08lX", ctx->uc_mcontext.gregs[REG_ESI]);
SPDLOG_CRITICAL("ESI : {} ", regbuffer); SPDLOG_CRITICAL("ESI : {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer),"0x%08lX", ctx->uc_mcontext.gregs[REG_EBP]); snprintf(regbuffer, std::size(regbuffer),"0x%08lX", ctx->uc_mcontext.gregs[REG_EBP]);
SPDLOG_CRITICAL("EBP : {} ", regbuffer); SPDLOG_CRITICAL("EBP : {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer),"0x%08lX", ctx->uc_mcontext.gregs[REG_ESP]); snprintf(regbuffer, std::size(regbuffer),"0x%08lX", ctx->uc_mcontext.gregs[REG_ESP]);
SPDLOG_CRITICAL("ESP : {} ", regbuffer); SPDLOG_CRITICAL("ESP : {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer),"0x%08lX", ctx->uc_mcontext.gregs[REG_EBX]); snprintf(regbuffer, std::size(regbuffer),"0x%08lX", ctx->uc_mcontext.gregs[REG_EBX]);
SPDLOG_CRITICAL("EBX : {} ", regbuffer); SPDLOG_CRITICAL("EBX : {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer),"0x%08lX", ctx->uc_mcontext.gregs[REG_EDX]); snprintf(regbuffer, std::size(regbuffer),"0x%08lX", ctx->uc_mcontext.gregs[REG_EDX]);
SPDLOG_CRITICAL("EDX : {} ", regbuffer); SPDLOG_CRITICAL("EDX : {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer),"0x%08lX", ctx->uc_mcontext.gregs[REG_ECX]); snprintf(regbuffer, std::size(regbuffer),"0x%08lX", ctx->uc_mcontext.gregs[REG_ECX]);
SPDLOG_CRITICAL("ECX : {} ", regbuffer); SPDLOG_CRITICAL("ECX : {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer),"0x%08lX", ctx->uc_mcontext.gregs[REG_EAX]); snprintf(regbuffer, std::size(regbuffer),"0x%08lX", ctx->uc_mcontext.gregs[REG_EAX]);
SPDLOG_CRITICAL("EAX : {} ", regbuffer); SPDLOG_CRITICAL("EAX : {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer),"0x%08lX", ctx->uc_mcontext.gregs[REG_EIP]); snprintf(regbuffer, std::size(regbuffer),"0x%08lX", ctx->uc_mcontext.gregs[REG_EIP]);
SPDLOG_CRITICAL("EIP : {} ", regbuffer); SPDLOG_CRITICAL("EIP : {} ", regbuffer);
snprintf(regbuffer, std::size(regbuffer),"0x%08lX", ctx->uc_mcontext.gregs[REG_EFL]); snprintf(regbuffer, std::size(regbuffer),"0x%08lX", ctx->uc_mcontext.gregs[REG_EFL]);
SPDLOG_CRITICAL("EFL : {} ", regbuffer); SPDLOG_CRITICAL("EFL : {} ", regbuffer);
#endif #endif
} }
static void ErrorHandler(int sig, siginfo_t* sigInfo, void* data) static void ErrorHandler(int sig, siginfo_t* sigInfo, void* data) {
{ std::array<void*, 4096> arr;
std::array<void*, 4096> arr; ucontext_t* ctx = static_cast<ucontext_t*>(data);
ucontext_t* ctx = static_cast<ucontext_t*>(data); constexpr size_t nMaxFrames = arr.size();
constexpr size_t nMaxFrames = arr.size(); size_t size = backtrace(arr.data(), nMaxFrames);
size_t size = backtrace(arr.data(), nMaxFrames); char** symbols = backtrace_symbols(arr.data(), nMaxFrames);
char** symbols = backtrace_symbols(arr.data(), nMaxFrames);
SPDLOG_CRITICAL("(Signal: {})\n", sig); SPDLOG_CRITICAL("(Signal: {})", sig);
switch (sig) { switch (sig) {
case SIGILL: case SIGILL:
SPDLOG_CRITICAL("ILLEGAL INSTRUCTION"); SPDLOG_CRITICAL("ILLEGAL INSTRUCTION");
break; break;
case SIGABRT: case SIGABRT:
SPDLOG_CRITICAL("ABORT"); SPDLOG_CRITICAL("ABORT");
break; break;
case SIGFPE: case SIGFPE:
SPDLOG_CRITICAL("ERRONEUS ARITHEMETIC OPERATION"); SPDLOG_CRITICAL("ERRONEUS ARITHEMETIC OPERATION");
break; break;
case SIGSEGV: case SIGSEGV:
SPDLOG_CRITICAL("INVALID ACCESS TO STORAGE"); SPDLOG_CRITICAL("INVALID ACCESS TO STORAGE");
break; break;
} }
PrintRegisters(ctx); PrintRegisters(ctx);
SPDLOG_CRITICAL("Traceback:\n"); SPDLOG_CRITICAL("Traceback:");
for (size_t i = 1; i < size; i++) for (size_t i = 1; i < size; i++) {
{ Dl_info info;
Dl_info info; int gotAddress = dladdr(arr[i], &info);
int gotAddress = dladdr(arr[i], &info); std::string functionName(symbols[i]);
std::string functionName(symbols[i]);
if (gotAddress != 0 && info.dli_sname != nullptr) if (gotAddress != 0 && info.dli_sname != nullptr) {
{
FILE* pipe; FILE* pipe;
int32_t status; int32_t status;
char* demangled = abi::__cxa_demangle(info.dli_sname, nullptr, nullptr, &status); char* demangled = abi::__cxa_demangle(info.dli_sname, nullptr, nullptr, &status);
const char* nameFound = info.dli_sname; const char* nameFound = info.dli_sname;
if (status == 0) if (status == 0) {
{ nameFound = demangled;
nameFound = demangled; }
}
#if 0 #if 0
char command[256]; char command[256];
char addrLine[128]; char addrLine[128];
snprintf(command, sizeof(command), "addr2line -e soh.elf %s + 0x%lX", nameFound, (uintptr_t)arr[i] - (uintptr_t)info.dli_saddr); snprintf(command, sizeof(command), "addr2line -e soh.elf %s + 0x%lX", nameFound, (uintptr_t)arr[i] - (uintptr_t)info.dli_saddr);
pipe = popen(command, "r"); pipe = popen(command, "r");
fgets(addrLine, 128, pipe); fgets(addrLine, 128, pipe);
#endif #endif
functionName = StringHelper::Sprintf("%s (+0x%X)", nameFound, functionName = StringHelper::Sprintf("%s (+0x%X)", nameFound,
(char*)arr[i] - (char*)info.dli_saddr); (char*)arr[i] - (char*)info.dli_saddr);
free(demangled); free(demangled);
} }
SPDLOG_CRITICAL("{} {}", i, functionName.c_str()); SPDLOG_CRITICAL("{} {}", i, functionName.c_str());
} }
free(symbols); free(symbols);
DeinitOTR(); DeinitOTR();
exit(1); exit(1);
} }
static void ShutdownHandler(int sig, siginfo_t* sigInfo, void* data) { static void ShutdownHandler(int sig, siginfo_t* sigInfo, void* data) {
DeinitOTR(); DeinitOTR();
exit(1); exit(1);
} }
extern "C" void SetupHandlerLinux() { extern "C" void SetupHandlerLinux() {
struct sigaction action; struct sigaction action;
struct sigaction shutdownAction; struct sigaction shutdownAction;
action.sa_flags = SA_SIGINFO; action.sa_flags = SA_SIGINFO;
action.sa_sigaction = ErrorHandler; action.sa_sigaction = ErrorHandler;
sigaction(SIGILL, &action, nullptr);
sigaction(SIGABRT, &action, nullptr);
sigaction(SIGFPE, &action, nullptr);
sigaction(SIGSEGV, &action, nullptr);
shutdownAction.sa_flags = SA_SIGINFO;
shutdownAction.sa_sigaction = ShutdownHandler;
sigaction(SIGINT, &shutdownAction, nullptr);
sigaction(SIGTERM, &shutdownAction, nullptr);
sigaction(SIGQUIT, &shutdownAction, nullptr);
sigaction(SIGKILL, &shutdownAction, nullptr);
sigaction(SIGILL, &action, nullptr);
sigaction(SIGABRT, &action, nullptr);
sigaction(SIGFPE, &action, nullptr);
sigaction(SIGSEGV, &action, nullptr);
shutdownAction.sa_flags = SA_SIGINFO;
shutdownAction.sa_sigaction = ShutdownHandler;
sigaction(SIGINT, &shutdownAction, nullptr);
sigaction(SIGTERM, &shutdownAction, nullptr);
sigaction(SIGQUIT, &shutdownAction, nullptr);
sigaction(SIGKILL, &shutdownAction, nullptr);
} }
#elif _WIN32
#if defined(_WIN32) && !defined(_WIN64)
#define WINDOWS_32_BIT
#endif
static void PrintRegisters(CONTEXT* ctx) {
SPDLOG_CRITICAL("Register dump");
char regBuff[50];
#if defined(_M_AMD64)
snprintf(regBuff, std::size(regBuff), "0x%016llX", ctx->Rax);
SPDLOG_CRITICAL("RAX: {}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%016llX", ctx->Rcx);
SPDLOG_CRITICAL("RCX: {}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%016llX", ctx->Rdx);
SPDLOG_CRITICAL("RDX: {}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%016llX", ctx->Rbx);
SPDLOG_CRITICAL("RBX: {}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%016llX", ctx->Rsp);
SPDLOG_CRITICAL("RSP: {}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%016llX", ctx->Rbp);
SPDLOG_CRITICAL("RBP: {}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%016llX", ctx->Rsi);
SPDLOG_CRITICAL("RSI: {}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%016llX", ctx->Rdi);
SPDLOG_CRITICAL("RDI: {}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%016llX", ctx->R9);
SPDLOG_CRITICAL("R9: {}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%016llX", ctx->R10);
SPDLOG_CRITICAL("R10: {}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%016llX", ctx->R11);
SPDLOG_CRITICAL("R11: {}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%016llX", ctx->R12);
SPDLOG_CRITICAL("R12: {}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%016llX", ctx->R13);
SPDLOG_CRITICAL("R13: {}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%016llX", ctx->R14);
SPDLOG_CRITICAL("R14: {}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%016llX", ctx->R15);
SPDLOG_CRITICAL("R15: {}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%016llX", ctx->Rip);
SPDLOG_CRITICAL("RIP: {}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%08lX", ctx->EFlags);
SPDLOG_CRITICAL("EFLAGS: {}", regBuff);
#elif WINDOWS_32_BIT
snprintf(regBuff, std::size(regBuff), "0x%08lX", ctx->Edi);
SPDLOG_CRITICAL("EDI: 0x{}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%08lX", ctx->Esi);
SPDLOG_CRITICAL("ESI: 0x{}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%08lX", ctx->Ebx);
SPDLOG_CRITICAL("EBX: 0x{}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%08lX", ctx->Ecx);
SPDLOG_CRITICAL("ECX: 0x{}", ctx->Ecx);
snprintf(regBuff, std::size(regBuff), "0x%08lX", ctx->Eax);
SPDLOG_CRITICAL("EAX: 0x{}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%08lX", ctx->Ebp);
SPDLOG_CRITICAL("EBP: 0x{}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%08lX", ctx->Esp);
SPDLOG_CRITICAL("ESP: 0x{}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%08lX", ctx->EFlags);
SPDLOG_CRITICAL("EFLAGS: 0x{}", regBuff);
snprintf(regBuff, std::size(regBuff), "0x%08lX", ctx->Eip);
SPDLOG_CRITICAL("EIP: 0x{}", regBuff);
#endif
}
static void printStack(CONTEXT* ctx) {
BOOL result;
HANDLE process;
HANDLE thread;
HMODULE hModule;
ULONG frame;
DWORD64 displacement;
DWORD disp;
#if defined(_M_AMD64)
STACKFRAME64 stack;
memset(&stack, 0, sizeof(STACKFRAME64));
#elif WINDOWS_32_BIT
STACKFRAME stack;
memset(&stack, 0, sizeof(STACKFRAME));
stack.AddrPC.Offset = (*ctx).Eip;
stack.AddrPC.Mode = AddrModeFlat;
stack.AddrStack.Offset = (*ctx).Esp;
stack.AddrStack.Mode = AddrModeFlat;
stack.AddrFrame.Offset = (*ctx).Ebp;
stack.AddrFrame.Mode = AddrModeFlat;
#endif
char buffer[sizeof(SYMBOL_INFO) + MAX_SYM_NAME + sizeof(TCHAR)];
char module[512];
PSYMBOL_INFO symbol = (PSYMBOL_INFO)buffer;
CONTEXT ctx2;
memcpy(&ctx2, ctx, sizeof(CONTEXT));
PrintRegisters(&ctx2);
process = GetCurrentProcess();
thread = GetCurrentThread();
SymInitialize(process, nullptr, true);
constexpr DWORD machineType =
#if defined(_M_AMD64)
IMAGE_FILE_MACHINE_AMD64;
#elif WINDOWS_32_BIT
IMAGE_FILE_MACHINE_I386;
#endif
displacement = 0;
for (frame = 0;; frame++) {
result = StackWalk(machineType, process, thread, &stack, &ctx2, nullptr, SymFunctionTableAccess,
SymGetModuleBase, nullptr);
if (!result) {
break;
}
symbol->SizeOfStruct = sizeof(SYMBOL_INFO);
symbol->MaxNameLen = MAX_SYM_NAME;
SymFromAddr(process, (ULONG64)stack.AddrPC.Offset, &displacement, symbol);
#if defined(_M_AMD64)
IMAGEHLP_LINE64 line;
line.SizeOfStruct = sizeof(IMAGEHLP_LINE64);
#elif WINDOWS_32_BIT
IMAGEHLP_LINE line;
line.SizeOfStruct = sizeof(IMAGEHLP_LINE);
#endif
if (SymGetLineFromAddr(process, stack.AddrPC.Offset, &disp, &line)) {
SPDLOG_CRITICAL("{} in {}: line: {}: ", symbol->Name, line.FileName, line.LineNumber);
}
else {
char addrString[25];
snprintf(addrString, std::size(addrString), "0x%016llX", symbol->Address);
SPDLOG_CRITICAL("at {}, addr 0x{}", symbol->Name, addrString);
hModule = nullptr;
GetModuleHandleEx(GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS | GET_MODULE_HANDLE_EX_FLAG_UNCHANGED_REFCOUNT,
(LPCTSTR)(stack.AddrPC.Offset), &hModule);
if (hModule != nullptr) {
GetModuleFileNameA(hModule, module, sizeof(module));
}
SPDLOG_CRITICAL("In {}", module);
}
}
Ship::Window::GetInstance()->GetLogger()->flush();
spdlog::shutdown();
DeinitOTR();
}
extern "C" LONG seh_filter(struct _EXCEPTION_POINTERS* ex) {
char exceptionString[20];
snprintf(exceptionString, std::size(exceptionString), "0x%x", ex->ExceptionRecord->ExceptionCode);
SPDLOG_CRITICAL("EXCEPTION {} occurred", exceptionString);
printStack(ex->ContextRecord);
MessageBox(nullptr, L"SoH Has crashed. Please upload the logs to the support channel in discord.", L"Crash", MB_OK | MB_ICONERROR);
return EXCEPTION_EXECUTE_HANDLER;
}
#endif #endif

View File

@ -13,6 +13,25 @@ void SetupHandlerLinux(void);
} }
#endif #endif
#endif // __linux__ #elif _WIN32 // __linux__ ^^^^ _WIN32 vvvvv
#include <windows.h>
#include <DbgHelp.h>
#endif // CRASH_HANDLER_H #include <inttypes.h>
#include <excpt.h>
#ifdef __cplusplus
extern "C" {
#endif
LONG seh_filter(struct _EXCEPTION_POINTERS* ex);
#ifdef __cplusplus
}
#endif
#pragma comment(lib, "Dbghelp.lib")
#endif
#endif // CRASH_HANDLER_H

View File

@ -16,28 +16,28 @@ namespace Ship {
if (CVar_Get(args[2].c_str()) != nullptr) { if (CVar_Get(args[2].c_str()) != nullptr) {
const char* key = args[2].c_str(); const char* key = args[2].c_str();
GameOverlay* overlay = SohImGui::overlay; GameOverlay* overlay = SohImGui::GetGameOverlay();
if (args[1] == "add") { if (args[1] == "add") {
if (!overlay->RegisteredOverlays.contains(key)) { if (!overlay->RegisteredOverlays.contains(key)) {
overlay->RegisteredOverlays[key] = new Overlay({ OverlayType::TEXT, ImStrdup(key), -1.0f }); overlay->RegisteredOverlays[key] = new Overlay({ OverlayType::TEXT, ImStrdup(key), -1.0f });
SohImGui::console->SendInfoMessage("Added overlay: %s", key); SohImGui::GetConsole()->SendInfoMessage("Added overlay: %s", key);
} }
else { else {
SohImGui::console->SendErrorMessage("Overlay already exists: %s", key); SohImGui::GetConsole()->SendErrorMessage("Overlay already exists: %s", key);
} }
} }
else if (args[1] == "remove") { else if (args[1] == "remove") {
if (overlay->RegisteredOverlays.contains(key)) { if (overlay->RegisteredOverlays.contains(key)) {
overlay->RegisteredOverlays.erase(key); overlay->RegisteredOverlays.erase(key);
SohImGui::console->SendInfoMessage("Removed overlay: %s", key); SohImGui::GetConsole()->SendInfoMessage("Removed overlay: %s", key);
} }
else { else {
SohImGui::console->SendErrorMessage("Overlay not found: %s", key); SohImGui::GetConsole()->SendErrorMessage("Overlay not found: %s", key);
} }
} }
} }
else { else {
SohImGui::console->SendErrorMessage("CVar {} does not exist", args[2].c_str()); SohImGui::GetConsole()->SendErrorMessage("CVar {} does not exist", args[2].c_str());
} }
return CMD_SUCCESS; return CMD_SUCCESS;
@ -124,7 +124,7 @@ namespace Ship {
else else
text_display_end = text_end; text_display_end = text_end;
GameOverlay* overlay = SohImGui::overlay; GameOverlay* overlay = SohImGui::GetGameOverlay();
ImFont* font = overlay->CurrentFont == "Default" ? g.Font : overlay->Fonts[overlay->CurrentFont]; ImFont* font = overlay->CurrentFont == "Default" ? g.Font : overlay->Fonts[overlay->CurrentFont];
const float font_size = font->FontSize; const float font_size = font->FontSize;
@ -157,7 +157,7 @@ namespace Ship {
} }
} }
SohImGui::console->AddCommand("overlay", { OverlayCommand, "Draw an overlay using a cvar value" }); SohImGui::GetConsole()->AddCommand("overlay", { OverlayCommand, "Draw an overlay using a cvar value" });
} }
void GameOverlay::DrawSettings() { void GameOverlay::DrawSettings() {
@ -167,7 +167,7 @@ namespace Ship {
if (ImGui::Selectable(name.c_str(), name == this->CurrentFont)) { if (ImGui::Selectable(name.c_str(), name == this->CurrentFont)) {
this->CurrentFont = name; this->CurrentFont = name;
CVar_SetString("gOverlayFont", ImStrdup(name.c_str())); CVar_SetString("gOverlayFont", ImStrdup(name.c_str()));
SohImGui::needs_save = true; SohImGui::RequestCvarSaveOnNextTick();
} }
} }

File diff suppressed because it is too large Load Diff

View File

@ -1,14 +1,5 @@
#pragma once #pragma once
#ifdef __cplusplus
extern "C" {
#endif
void enableBetaQuest();
void disableBetaQuest();
#ifdef __cplusplus
}
#endif
#ifdef __cplusplus #ifdef __cplusplus
#include "GameOverlay.h" #include "GameOverlay.h"
#include "Lib/ImGui/imgui.h" #include "Lib/ImGui/imgui.h"
@ -34,14 +25,6 @@ namespace SohImGui {
dLoadSettings, dLoadSettings,
}; };
// Enumeration for disabled checkbox graphics
enum class ImGuiCheckboxGraphics
{
Cross,
Checkmark,
None
};
typedef struct { typedef struct {
Backend backend; Backend backend;
union { union {
@ -76,8 +59,6 @@ namespace SohImGui {
} gx2; } gx2;
} EventImpl; } EventImpl;
extern WindowImpl impl;
using WindowDrawFunc = void(*)(bool& enabled); using WindowDrawFunc = void(*)(bool& enabled);
typedef struct { typedef struct {
@ -85,55 +66,49 @@ namespace SohImGui {
WindowDrawFunc drawFunc; WindowDrawFunc drawFunc;
} CustomWindow; } CustomWindow;
extern std::shared_ptr<Ship::Console> console;
extern Ship::InputEditor* controller;
extern Ship::GameOverlay* overlay;
extern bool needs_save;
void Init(WindowImpl window_impl); void Init(WindowImpl window_impl);
void Update(EventImpl event); void Update(EventImpl event);
void Tooltip(const char* text);
void EnhancementRadioButton(const char* text, const char* cvarName, int id);
void EnhancementCheckbox(const char* text, const char* cvarName, bool disabled = false, const char* disabledTooltipText = "", ImGuiCheckboxGraphics disabledGraphic = ImGuiCheckboxGraphics::Cross);
void EnhancementButton(const char* text, const char* cvarName);
void EnhancementSliderInt(const char* text, const char* id, const char* cvarName, int min, int max, const char* format, int defaultValue = 0, bool PlusMinusButton = false);
void EnhancementSliderFloat(const char* text, const char* id, const char* cvarName, float min, float max, const char* format, float defaultValue, bool isPercentage, bool PlusMinusButton = false);
void EnhancementCombobox(const char* name, const char* ComboArray[], size_t arraySize, uint8_t FirstTimeValue);
void EnhancementColor(const char* text, const char* cvarName, ImVec4 ColorRGBA, ImVec4 default_colors, bool allow_rainbow = true, bool has_alpha=false, bool TitleSameLine=false);
void EnhancementCombo(const std::string& name, const char* cvarName, const std::vector<std::string>& items, int defaultValue = 0);
void applyEnhancementPresets(void);
void applyEnhancementPresetDefault(void);
void applyEnhancementPresetVanillaPlus(void);
void applyEnhancementPresetEnhanced(void);
void applyEnhancementPresetRandomizer(void);
void DrawMainMenuAndCalculateGameSize(void); void DrawMainMenuAndCalculateGameSize(void);
void RegisterMenuDrawMethod(std::function<void(void)> drawMethod);
void AddSetupHooksDelegate(std::function<void(void)> setupHooksMethod);
void DrawFramebufferAndGameInput(void); void DrawFramebufferAndGameInput(void);
void Render(void); void Render(void);
void CancelFrame(void); void CancelFrame(void);
void ShowCursor(bool hide, Dialogues w); void DrawSettings();
void BindCmd(const std::string& cmd, Ship::CommandEntry entry);
void AddWindow(const std::string& category, const std::string& name, WindowDrawFunc drawFunc, bool isEnabled=false, bool isHidden=false); Backend WindowBackend();
void LoadResource(const std::string& name, const std::string& path, const ImVec4& tint = ImVec4(1, 1, 1, 1)); float WindowRefreshRate();
void LoadPickersColors(ImVec4& ColorArray, const char* cvarname, const ImVec4& default_colors, bool has_alpha=false); std::pair<const char*, const char*>* GetAvailableRenderingBackends();
int ClampFloatToInt(float value, int min, int max); std::pair<const char*, const char*> GetCurrentRenderingBackend();
void RandomizeColor(const char* cvarName, ImVec4* colors); void SetCurrentRenderingBackend(uint8_t index, std::pair<const char*, const char*>);
void RainbowColor(const char* cvarName, ImVec4* colors); const char** GetSupportedTextureFilters();
void ResetColor(const char* cvarName, ImVec4* colors, ImVec4 defaultcolors, bool has_alpha); void SetResolutionMultiplier(float multiplier);
void SetMSAALevel(uint32_t value);
void AddWindow(const std::string& category, const std::string& name, WindowDrawFunc drawFunc, bool isEnabled = false, bool isHidden = false);
void EnableWindow(const std::string& name, bool isEnabled = true);
Ship::GameOverlay* GetGameOverlay();
Ship::InputEditor* GetInputEditor();
void ToggleInputEditorWindow(bool isOpen = true);
void ToggleStatisticsWindow(bool isOpen = true);
std::shared_ptr<Ship::Console> GetConsole();
void ToggleConsoleWindow(bool isOpen = true);
void DispatchConsoleCommand(const std::string& line);
void RequestCvarSaveOnNextTick();
ImTextureID GetTextureByID(int id); ImTextureID GetTextureByID(int id);
ImTextureID GetTextureByName(const std::string& name); ImTextureID GetTextureByName(const std::string& name);
void LoadResource(const std::string& name, const std::string& path, const ImVec4& tint = ImVec4(1, 1, 1, 1));
void ShowCursor(bool hide, Dialogues w);
void BeginGroupPanel(const char* name, const ImVec2 & size = ImVec2(0.0f, 0.0f)); void BeginGroupPanel(const char* name, const ImVec2 & size = ImVec2(0.0f, 0.0f));
void EndGroupPanel(float minHeight = 0.0f); void EndGroupPanel(float minHeight = 0.0f);
std::string BreakTooltip(const char* text, int lineLength = 60);
std::string BreakTooltip(const std::string& text, int lineLength = 60);
void InsertPadding(float extraVerticalPadding = 0.0f);
void PaddedSeparator(bool padTop = true, bool padBottom = true, float extraVerticalTopPadding = 0.0f, float extraVerticalBottomPadding = 0.0f);
void PaddedEnhancementSliderInt(const char* text, const char* id, const char* cvarName, int min, int max, const char* format, int defaultValue = 0, bool PlusMinusButton = false, bool padTop = true, bool padBottom = true);
void PaddedEnhancementCheckbox(const char* text, const char* cvarName, bool padTop = true, bool padBottom = true, bool disabled = false, const char* disabledTooltipText = "", ImGuiCheckboxGraphics disabledGraphic = ImGuiCheckboxGraphics::Cross);
void PaddedText(const char* text, bool padTop = true, bool padBottom = true);
std::string GetWindowButtonText(const char* text, bool menuOpen);
} }
#endif #endif

View File

@ -2134,6 +2134,10 @@ static void gfx_run_dl(Gfx* cmd) {
switch (opcode) { switch (opcode) {
// RSP commands: // RSP commands:
case G_LOAD_UCODE:
rsp.fog_mul = 0;
rsp.fog_offset = 0;
break;
case G_MARKER: case G_MARKER:
{ {
cmd++; cmd++;

View File

@ -41,8 +41,8 @@ protected:
} }
formatted.push_back('\0'); formatted.push_back('\0');
const char* msg_output = formatted.data(); const char* msg_output = formatted.data();
if (CVar_GetS32("gSinkEnabled", 0) && SohImGui::console->IsOpened()) { if (CVar_GetS32("gSinkEnabled", 0) && SohImGui::GetConsole()->IsOpened()) {
SohImGui::console->Append("Logs", msg.level, "%s", msg_output); SohImGui::GetConsole()->Append("Logs", msg.level, "%s", msg_output);
} }
} }
@ -57,4 +57,4 @@ private:
using soh_sink_mt = sohconsole_sink<std::mutex>; using soh_sink_mt = sohconsole_sink<std::mutex>;
using soh_sink_st = sohconsole_sink<details::null_mutex>; using soh_sink_st = sohconsole_sink<details::null_mutex>;
} // namespace sinks } // namespace sinks
} // namespace spdlog } // namespace spdlog

View File

@ -86,7 +86,7 @@ extern "C" {
pad->gyro_x = 0; pad->gyro_x = 0;
pad->gyro_y = 0; pad->gyro_y = 0;
if (SohImGui::controller->IsOpened()) return; if (SohImGui::GetInputEditor()->IsOpened()) return;
Ship::Window::GetInstance()->GetControlDeck()->WriteToPad(pad); Ship::Window::GetInstance()->GetControlDeck()->WriteToPad(pad);
Ship::ExecuteHooks<Ship::ControllerRead>(pad); Ship::ExecuteHooks<Ship::ControllerRead>(pad);

View File

@ -165,6 +165,7 @@ set(Header_Files__soh__Enhancements__controls
) )
source_group("Header Files\\soh\\Enhancements\\controls" FILES ${Header_Files__soh__Enhancements__controls}) source_group("Header Files\\soh\\Enhancements\\controls" FILES ${Header_Files__soh__Enhancements__controls})
set(Header_Files__soh__Enhancements__cosmetics set(Header_Files__soh__Enhancements__cosmetics
"soh/Enhancements/cosmetics/CosmeticsEditor.h" "soh/Enhancements/cosmetics/CosmeticsEditor.h"
) )
@ -175,7 +176,6 @@ set(Header_Files__soh__Enhancements__debugger
"soh/Enhancements/debugger/colViewer.h" "soh/Enhancements/debugger/colViewer.h"
"soh/Enhancements/debugger/debugger.h" "soh/Enhancements/debugger/debugger.h"
"soh/Enhancements/debugger/debugSaveEditor.h" "soh/Enhancements/debugger/debugSaveEditor.h"
"soh/Enhancements/debugger/ImGuiHelpers.h"
) )
source_group("Header Files\\soh\\Enhancements\\debugger" FILES ${Header_Files__soh__Enhancements__debugger}) source_group("Header Files\\soh\\Enhancements\\debugger" FILES ${Header_Files__soh__Enhancements__debugger})
@ -258,6 +258,10 @@ set(Source_Files__soh
"soh/z_message_OTR.cpp" "soh/z_message_OTR.cpp"
"soh/z_play_otr.cpp" "soh/z_play_otr.cpp"
"soh/z_scene_otr.cpp" "soh/z_scene_otr.cpp"
"soh/GameMenuBar.hpp"
"soh/GameMenuBar.cpp"
"soh/UIWidgets.hpp"
"soh/UIWidgets.cpp"
) )
source_group("Source Files\\soh" FILES ${Source_Files__soh}) source_group("Source Files\\soh" FILES ${Source_Files__soh})
@ -284,7 +288,6 @@ set(Source_Files__soh__Enhancements__debugger
"soh/Enhancements/debugger/colViewer.cpp" "soh/Enhancements/debugger/colViewer.cpp"
"soh/Enhancements/debugger/debugger.cpp" "soh/Enhancements/debugger/debugger.cpp"
"soh/Enhancements/debugger/debugSaveEditor.cpp" "soh/Enhancements/debugger/debugSaveEditor.cpp"
"soh/Enhancements/debugger/ImGuiHelpers.cpp"
) )
source_group("Source Files\\soh\\Enhancements\\debugger" FILES ${Source_Files__soh__Enhancements__debugger}) source_group("Source Files\\soh\\Enhancements\\debugger" FILES ${Source_Files__soh__Enhancements__debugger})
@ -1679,14 +1682,13 @@ set(SDL2-INCLUDE ${SDL2_INCLUDE_DIRS})
target_include_directories(${PROJECT_NAME} PRIVATE assets target_include_directories(${PROJECT_NAME} PRIVATE assets
${CMAKE_CURRENT_SOURCE_DIR}/include/ ${CMAKE_CURRENT_SOURCE_DIR}/include/
${CMAKE_CURRENT_SOURCE_DIR}/src/ ${CMAKE_CURRENT_SOURCE_DIR}/src/
${CMAKE_CURRENT_SOURCE_DIR}/../libultraship
${CMAKE_CURRENT_SOURCE_DIR}/../libultraship/libultraship/Lib/
${CMAKE_CURRENT_SOURCE_DIR}/../libultraship/libultraship/Lib/libjpeg/include/ ${CMAKE_CURRENT_SOURCE_DIR}/../libultraship/libultraship/Lib/libjpeg/include/
${CMAKE_CURRENT_SOURCE_DIR}/../libultraship/libultraship/
${CMAKE_CURRENT_SOURCE_DIR}/../libultraship/libultraship/Lib/spdlog/include/ ${CMAKE_CURRENT_SOURCE_DIR}/../libultraship/libultraship/Lib/spdlog/include/
${CMAKE_CURRENT_SOURCE_DIR}/../libultraship/libultraship/Lib/Fast3D/U64/PR
${CMAKE_CURRENT_SOURCE_DIR}/../ZAPDTR/ZAPDUtils ${CMAKE_CURRENT_SOURCE_DIR}/../ZAPDTR/ZAPDUtils
${CMAKE_CURRENT_SOURCE_DIR}/../libultraship/libultraship/Lib/Fast3D/U64
${CMAKE_CURRENT_SOURCE_DIR}/../libultraship/libultraship/Lib/Fast3D/U64/PR
${SDL2-INCLUDE} ${SDL2-INCLUDE}
${CMAKE_CURRENT_SOURCE_DIR}/../libultraship/libultraship/
${CMAKE_CURRENT_SOURCE_DIR}/assets/ ${CMAKE_CURRENT_SOURCE_DIR}/assets/
. .
) )

View File

@ -6,7 +6,7 @@
#include "macros.h" #include "macros.h"
#include "soh/OTRGlobals.h" #include "soh/OTRGlobals.h"
#include "soh/Enhancements/gameconsole.h" #include "soh/Enhancements/gameconsole.h"
#include "Cvar.h" #include <libultraship/Cvar.h>

View File

@ -1,7 +1,7 @@
#ifndef MACROS_H #ifndef MACROS_H
#define MACROS_H #define MACROS_H
#include "endianness.h" #include <libultraship/endianness.h>
#define ARRAY_COUNT(arr) (s32)(sizeof(arr) / sizeof(arr[0])) #define ARRAY_COUNT(arr) (s32)(sizeof(arr) / sizeof(arr[0]))
#define ARRAY_COUNTU(arr) (u32)(sizeof(arr) / sizeof(arr[0])) #define ARRAY_COUNTU(arr) (u32)(sizeof(arr) / sizeof(arr[0]))

View File

@ -26,7 +26,7 @@
#include "z64interface.h" #include "z64interface.h"
#include "sequence.h" #include "sequence.h"
#include "sfx.h" #include "sfx.h"
#include "color.h" #include <libultraship/color.h>
#include "ichain.h" #include "ichain.h"
#include "regs.h" #include "regs.h"

View File

@ -1,7 +1,7 @@
#ifndef Z64_AUDIO_H #ifndef Z64_AUDIO_H
#define Z64_AUDIO_H #define Z64_AUDIO_H
#include "endianness.h" #include <libultraship/endianness.h>
#define MK_CMD(b0,b1,b2,b3) ((((b0) & 0xFF) << 0x18) | (((b1) & 0xFF) << 0x10) | (((b2) & 0xFF) << 0x8) | (((b3) & 0xFF) << 0)) #define MK_CMD(b0,b1,b2,b3) ((((b0) & 0xFF) << 0x18) | (((b1) & 0xFF) << 0x10) | (((b2) & 0xFF) << 0x8) | (((b3) & 0xFF) << 0))
@ -815,7 +815,7 @@ typedef struct {
/* 0x0E */ u8 ttl; // duration after which the DMA can be discarded /* 0x0E */ u8 ttl; // duration after which the DMA can be discarded
} SampleDma; // size = 0x10 } SampleDma; // size = 0x10
#include <PR/ultra64/abi.h> #include <ultra64/abi.h>
typedef struct { typedef struct {
/* 0x0000 */ char unk_0000; /* 0x0000 */ char unk_0000;
@ -1122,4 +1122,4 @@ float Audio_GetGameVolume(int player_id);
#ifdef __cplusplus #ifdef __cplusplus
} }
#endif #endif
#endif #endif

View File

@ -1,7 +1,7 @@
#ifndef Z64EFFECT_H #ifndef Z64EFFECT_H
#define Z64EFFECT_H #define Z64EFFECT_H
#include "color.h" #include <libultraship/color.h>
struct GraphicsContext; struct GraphicsContext;
struct GlobalContext; struct GlobalContext;

View File

@ -4,7 +4,7 @@
#include "ultra64.h" #include "ultra64.h"
#include "ultra64/gbi.h" #include "ultra64/gbi.h"
#include "z64math.h" #include "z64math.h"
#include "color.h" #include <libultraship/color.h>
typedef struct { typedef struct {
/* 0x0 */ s16 x; /* 0x0 */ s16 x;

View File

@ -2,7 +2,7 @@
#define Z64TRANSITION_H #define Z64TRANSITION_H
#include "ultra64.h" #include "ultra64.h"
#include "color.h" #include <libultraship/color.h>
typedef struct { typedef struct {
f32 unk_0; f32 unk_0;

View File

@ -6,12 +6,14 @@
#include <utility> #include <utility>
#include <iterator> #include <iterator>
#include "Lib/ImGui/imgui.h" #include <ImGui/imgui.h>
#include "Lib/ImGui/imgui_internal.h" #include <ImGui/imgui_internal.h>
#include "Cvar.h" #include <libultraship/Cvar.h>
#include "UltraController.h" #include <libultraship/UltraController.h>
#include "Utils/StringHelper.h" #include <Utils/StringHelper.h>
#include "../libultraship/ImGuiImpl.h" #include <libultraship/ImGuiImpl.h>
#include "../../UIWidgets.hpp"
namespace GameControlEditor { namespace GameControlEditor {
const ImGuiTableFlags PANEL_TABLE_FLAGS = const ImGuiTableFlags PANEL_TABLE_FLAGS =
@ -50,7 +52,11 @@ namespace GameControlEditor {
// place the ? button to the most of the right side of the cell it is using. // place the ? button to the most of the right side of the cell it is using.
ImGui::SetCursorPosX(ImGui::GetCursorPosX() + ImGui::GetContentRegionAvail().x - 15); ImGui::SetCursorPosX(ImGui::GetCursorPosX() + ImGui::GetContentRegionAvail().x - 15);
ImGui::SmallButton("?"); ImGui::SmallButton("?");
SohImGui::Tooltip(helptext.c_str());
if (ImGui::IsItemHovered()) {
ImGui::SetTooltip("%s", helptext.c_str());
}
if (sameline) { if (sameline) {
//I do not use ImGui::SameLine(); because it make some element vanish. //I do not use ImGui::SameLine(); because it make some element vanish.
ImGui::SetCursorPosY(ImGui::GetCursorPosY() - 22); ImGui::SetCursorPosY(ImGui::GetCursorPosY() - 22);
@ -119,7 +125,7 @@ namespace GameControlEditor {
preview = "Unknown"; preview = "Unknown";
} }
SohImGui::InsertPadding(); UIWidgets::Spacer(0);
ImVec2 cursorPos = ImGui::GetCursorPos(); ImVec2 cursorPos = ImGui::GetCursorPos();
ImVec2 textSize = ImGui::CalcTextSize(mapping.label); ImVec2 textSize = ImGui::CalcTextSize(mapping.label);
ImGui::SetCursorPosY(cursorPos.y + textSize.y / 4); ImGui::SetCursorPosY(cursorPos.y + textSize.y / 4);
@ -140,7 +146,7 @@ namespace GameControlEditor {
} }
ImGui::EndCombo(); ImGui::EndCombo();
} }
SohImGui::InsertPadding(); UIWidgets::Spacer(0);
} }
void DrawOcarinaControlPanel() { void DrawOcarinaControlPanel() {
@ -157,7 +163,7 @@ namespace GameControlEditor {
ImVec2 cursor = ImGui::GetCursorPos(); ImVec2 cursor = ImGui::GetCursorPos();
ImGui::SetCursorPos(ImVec2(cursor.x + 5, cursor.y + 5)); ImGui::SetCursorPos(ImVec2(cursor.x + 5, cursor.y + 5));
SohImGui::EnhancementCheckbox("Customize Ocarina Controls", "gCustomOcarinaControls"); UIWidgets::EnhancementCheckbox("Customize Ocarina Controls", "gCustomOcarinaControls");
if (CVar_GetS32("gCustomOcarinaControls", 0) == 1) { if (CVar_GetS32("gCustomOcarinaControls", 0) == 1) {
if (ImGui::BeginTable("tableCustomMainOcarinaControls", 2, ImGuiTableFlags_SizingStretchProp)) { if (ImGui::BeginTable("tableCustomMainOcarinaControls", 2, ImGuiTableFlags_SizingStretchProp)) {
@ -194,10 +200,10 @@ namespace GameControlEditor {
ImGui::EndTable(); ImGui::EndTable();
} }
} else { } else {
SohImGui::InsertPadding(); UIWidgets::Spacer(0);
ImGui::SetCursorPosX(ImGui::GetCursorPosX() + 5); ImGui::SetCursorPosX(ImGui::GetCursorPosX() + 5);
ImGui::TextWrapped("To modify the main ocarina controls, select the \"Customize Ocarina Controls\" checkbox."); ImGui::TextWrapped("To modify the main ocarina controls, select the \"Customize Ocarina Controls\" checkbox.");
SohImGui::InsertPadding(); UIWidgets::Spacer(0);
} }
SohImGui::BeginGroupPanel("Alternate controls", ImGui::GetContentRegionAvail()); SohImGui::BeginGroupPanel("Alternate controls", ImGui::GetContentRegionAvail());
@ -206,9 +212,9 @@ namespace GameControlEditor {
ImGui::TableSetupColumn("Right stick", PANEL_TABLE_COLUMN_FLAGS); ImGui::TableSetupColumn("Right stick", PANEL_TABLE_COLUMN_FLAGS);
TableHelper::InitHeader(false); TableHelper::InitHeader(false);
ImGui::SetCursorPosX(ImGui::GetCursorPosX() + 5); ImGui::SetCursorPosX(ImGui::GetCursorPosX() + 5);
SohImGui::EnhancementCheckbox("Play with D-pad", "gDpadOcarina"); UIWidgets::EnhancementCheckbox("Play with D-pad", "gDpadOcarina");
TableHelper::NextCol(); TableHelper::NextCol();
SohImGui::EnhancementCheckbox("Play with camera stick", "gRStickOcarina"); UIWidgets::EnhancementCheckbox("Play with camera stick", "gRStickOcarina");
ImGui::EndTable(); ImGui::EndTable();
} }
SohImGui::EndGroupPanel(); SohImGui::EndGroupPanel();
@ -223,17 +229,17 @@ namespace GameControlEditor {
ImVec2 cursor = ImGui::GetCursorPos(); ImVec2 cursor = ImGui::GetCursorPos();
ImGui::SetCursorPos(ImVec2(cursor.x + 5, cursor.y + 5)); ImGui::SetCursorPos(ImVec2(cursor.x + 5, cursor.y + 5));
SohImGui::PaddedEnhancementCheckbox("Invert Camera X Axis", "gInvertXAxis"); UIWidgets::PaddedEnhancementCheckbox("Invert Camera X Axis", "gInvertXAxis");
SohImGui::Tooltip("Inverts the Camera X Axis in:\n-Free camera\n-C-Up view\n-Weapon Aiming"); UIWidgets::Tooltip("Inverts the Camera X Axis in:\n-Free camera\n-C-Up view\n-Weapon Aiming");
ImGui::SetCursorPosX(ImGui::GetCursorPosX() + 5); ImGui::SetCursorPosX(ImGui::GetCursorPosX() + 5);
SohImGui::PaddedEnhancementCheckbox("Invert Camera Y Axis", "gInvertYAxis"); UIWidgets::PaddedEnhancementCheckbox("Invert Camera Y Axis", "gInvertYAxis");
SohImGui::Tooltip("Inverts the Camera Y Axis in:\n-Free camera\n-C-Up view\n-Weapon Aiming"); UIWidgets::Tooltip("Inverts the Camera Y Axis in:\n-Free camera\n-C-Up view\n-Weapon Aiming");
ImGui::SetCursorPosX(ImGui::GetCursorPosX() + 5); ImGui::SetCursorPosX(ImGui::GetCursorPosX() + 5);
SohImGui::PaddedEnhancementCheckbox("Right Stick Aiming", "gRightStickAiming"); UIWidgets::PaddedEnhancementCheckbox("Right Stick Aiming", "gRightStickAiming");
SohImGui::Tooltip("Allows for aiming with the rights stick when:\n-Aiming in the C-Up view\n-Aiming with weapons"); UIWidgets::Tooltip("Allows for aiming with the rights stick when:\n-Aiming in the C-Up view\n-Aiming with weapons");
ImGui::SetCursorPosX(ImGui::GetCursorPosX() + 5); ImGui::SetCursorPosX(ImGui::GetCursorPosX() + 5);
SohImGui::PaddedEnhancementCheckbox("Auto-Center First Person View", "gAutoCenterView"); UIWidgets::PaddedEnhancementCheckbox("Auto-Center First Person View", "gAutoCenterView");
SohImGui::Tooltip("Prevents the C-Up view from auto-centering, allowing for Gyro Aiming"); UIWidgets::Tooltip("Prevents the C-Up view from auto-centering, allowing for Gyro Aiming");
} }
void DrawUI(bool& open) { void DrawUI(bool& open) {

View File

@ -1,11 +1,13 @@
#include "CosmeticsEditor.h" #include "CosmeticsEditor.h"
#include "../libultraship/ImGuiImpl.h" #include <libultraship/ImGuiImpl.h>
#include <string> #include <string>
#include <Cvar.h> #include <libultraship/Cvar.h>
#include <random> #include <random>
#include <algorithm> #include <algorithm>
#include <PR/ultra64/types.h> #include <ultra64/types.h>
#include "../../UIWidgets.hpp"
const char* RainbowColorCvarList[] = { const char* RainbowColorCvarList[] = {
//This is the list of possible CVars that has rainbow effect. //This is the list of possible CVars that has rainbow effect.
@ -51,9 +53,9 @@ void GetRandomColorRGB(CosmeticsColorSection* ColorSection, int SectionSize){
std::string cvarName = Element->CvarName; std::string cvarName = Element->CvarName;
std::string Cvar_RBM = cvarName + "RBM"; std::string Cvar_RBM = cvarName + "RBM";
colors = RANDOMIZE_32(255); colors = RANDOMIZE_32(255);
NewColors.r = SohImGui::ClampFloatToInt(colors.x * 255, 0, 255); NewColors.r = fmin(fmax(colors.x * 255, 0), 255);
NewColors.g = SohImGui::ClampFloatToInt(colors.y * 255, 0, 255); NewColors.g = fmin(fmax(colors.y * 255, 0), 255);
NewColors.b = SohImGui::ClampFloatToInt(colors.z * 255, 0, 255); NewColors.b = fmin(fmax(colors.z * 255, 0), 255);
Element->ModifiedColor = colors; Element->ModifiedColor = colors;
CVar_SetRGBA(cvarName.c_str(), NewColors); CVar_SetRGBA(cvarName.c_str(), NewColors);
CVar_SetS32(Cvar_RBM.c_str(), 0); CVar_SetS32(Cvar_RBM.c_str(), 0);
@ -149,9 +151,9 @@ void LoadRainbowColor(bool& open) {
case 6: NewColor.x = 255; NewColor.y = 0; NewColor.z = a; break; case 6: NewColor.x = 255; NewColor.y = 0; NewColor.z = a; break;
} }
Color_RGBA8 NewColorRGB = { Color_RGBA8 NewColorRGB = {
SohImGui::ClampFloatToInt(NewColor.x, 0, 255), fmin(fmax(NewColor.x, 0), 255),
SohImGui::ClampFloatToInt(NewColor.y, 0, 255), fmin(fmax(NewColor.y, 0), 255),
SohImGui::ClampFloatToInt(NewColor.z, 0, 255), fmin(fmax(NewColor.z, 0), 255),
255 255
}; };
if (CVar_GetS32(Cvar_RBM.c_str(), 0) != 0) { if (CVar_GetS32(Cvar_RBM.c_str(), 0) != 0) {
@ -187,7 +189,7 @@ void Draw_HelpIcon(const std::string& helptext, bool sameline = true, int Pos =
ImGui::PushItemWidth(ImGui::GetContentRegionAvail().x-60); ImGui::PushItemWidth(ImGui::GetContentRegionAvail().x-60);
ImGui::SetCursorPosX(ImGui::GetCursorPosX() + ImGui::GetContentRegionAvail().x - 15); ImGui::SetCursorPosX(ImGui::GetCursorPosX() + ImGui::GetContentRegionAvail().x - 15);
ImGui::SmallButton("?"); ImGui::SmallButton("?");
SohImGui::Tooltip(helptext.c_str()); UIWidgets::Tooltip(helptext.c_str());
if (sameline) { if (sameline) {
//I do not use ImGui::SameLine(); because it make some element vanish. //I do not use ImGui::SameLine(); because it make some element vanish.
ImGui::SetCursorPosY(ImGui::GetCursorPosY() - 22); ImGui::SetCursorPosY(ImGui::GetCursorPosY() - 22);
@ -197,96 +199,96 @@ void Draw_HelpIcon(const std::string& helptext, bool sameline = true, int Pos =
void DrawUseMarginsSlider(const std::string ElementName, const std::string CvarName){ void DrawUseMarginsSlider(const std::string ElementName, const std::string CvarName){
std::string CvarLabel = CvarName + "UseMargins"; std::string CvarLabel = CvarName + "UseMargins";
std::string Label = ElementName + " use margins"; std::string Label = ElementName + " use margins";
SohImGui::EnhancementCheckbox(Label.c_str(), CvarLabel.c_str()); UIWidgets::EnhancementCheckbox(Label.c_str(), CvarLabel.c_str());
SohImGui::Tooltip("Using this allow you move the element with General margins sliders"); UIWidgets::Tooltip("Using this allow you move the element with General margins sliders");
} }
void DrawPositionsRadioBoxes(const std::string CvarName, bool NoAnchorEnabled = true){ void DrawPositionsRadioBoxes(const std::string CvarName, bool NoAnchorEnabled = true){
std::string CvarLabel = CvarName + "PosType"; std::string CvarLabel = CvarName + "PosType";
SohImGui::EnhancementRadioButton("Original position", CvarLabel.c_str(), 0); UIWidgets::EnhancementRadioButton("Original position", CvarLabel.c_str(), 0);
SohImGui::Tooltip("This will use original intended elements position"); UIWidgets::Tooltip("This will use original intended elements position");
SohImGui::EnhancementRadioButton("Anchor to the left", CvarLabel.c_str(), 1); UIWidgets::EnhancementRadioButton("Anchor to the left", CvarLabel.c_str(), 1);
SohImGui::Tooltip("This will make your elements follow the left side of your game window"); UIWidgets::Tooltip("This will make your elements follow the left side of your game window");
SohImGui::EnhancementRadioButton("Anchor to the right", CvarLabel.c_str(), 2); UIWidgets::EnhancementRadioButton("Anchor to the right", CvarLabel.c_str(), 2);
SohImGui::Tooltip("This will make your elements follow the right side of your game window"); UIWidgets::Tooltip("This will make your elements follow the right side of your game window");
if (NoAnchorEnabled) { if (NoAnchorEnabled) {
SohImGui::EnhancementRadioButton("No anchors", CvarLabel.c_str(), 3); UIWidgets::EnhancementRadioButton("No anchors", CvarLabel.c_str(), 3);
SohImGui::Tooltip("This will make your elements to not follow any side\nBetter used for center elements"); UIWidgets::Tooltip("This will make your elements to not follow any side\nBetter used for center elements");
} }
SohImGui::EnhancementRadioButton("Hidden", CvarLabel.c_str(), 4); UIWidgets::EnhancementRadioButton("Hidden", CvarLabel.c_str(), 4);
SohImGui::Tooltip("This will make your elements hidden"); UIWidgets::Tooltip("This will make your elements hidden");
} }
void DrawTransitions(const std::string CvarName){ void DrawTransitions(const std::string CvarName){
SohImGui::EnhancementRadioButton("Really slow fade (white)", CvarName.c_str(), 8); UIWidgets::EnhancementRadioButton("Really slow fade (white)", CvarName.c_str(), 8);
Table_NextCol(); Table_NextCol();
SohImGui::EnhancementRadioButton("Really slow fade (black)", CvarName.c_str(), 7); UIWidgets::EnhancementRadioButton("Really slow fade (black)", CvarName.c_str(), 7);
Table_NextLine(); Table_NextLine();
SohImGui::EnhancementRadioButton("Slow fade (white)", CvarName.c_str(), 10); UIWidgets::EnhancementRadioButton("Slow fade (white)", CvarName.c_str(), 10);
Table_NextCol(); Table_NextCol();
SohImGui::EnhancementRadioButton("Slow fade (black)", CvarName.c_str(), 9); UIWidgets::EnhancementRadioButton("Slow fade (black)", CvarName.c_str(), 9);
Table_NextLine(); Table_NextLine();
SohImGui::EnhancementRadioButton("Normal fade (white)", CvarName.c_str(), 3); UIWidgets::EnhancementRadioButton("Normal fade (white)", CvarName.c_str(), 3);
Table_NextCol(); Table_NextCol();
SohImGui::EnhancementRadioButton("Normal fade (black)", CvarName.c_str(), 2); UIWidgets::EnhancementRadioButton("Normal fade (black)", CvarName.c_str(), 2);
Table_NextLine(); Table_NextLine();
SohImGui::EnhancementRadioButton("Fast fade (white)", CvarName.c_str(), 5); UIWidgets::EnhancementRadioButton("Fast fade (white)", CvarName.c_str(), 5);
Table_NextCol(); Table_NextCol();
SohImGui::EnhancementRadioButton("Fast fade (black)", CvarName.c_str(), 4); UIWidgets::EnhancementRadioButton("Fast fade (black)", CvarName.c_str(), 4);
Table_NextLine(); Table_NextLine();
SohImGui::EnhancementRadioButton("Fast circle (white)", CvarName.c_str(), 40); UIWidgets::EnhancementRadioButton("Fast circle (white)", CvarName.c_str(), 40);
Table_NextCol(); Table_NextCol();
SohImGui::EnhancementRadioButton("Normal circle (black)", CvarName.c_str(), 32); UIWidgets::EnhancementRadioButton("Normal circle (black)", CvarName.c_str(), 32);
Table_NextLine(); Table_NextLine();
SohImGui::EnhancementRadioButton("Slow circle (white)", CvarName.c_str(), 41); UIWidgets::EnhancementRadioButton("Slow circle (white)", CvarName.c_str(), 41);
Table_NextCol(); Table_NextCol();
SohImGui::EnhancementRadioButton("Slow circle (black)", CvarName.c_str(), 33); UIWidgets::EnhancementRadioButton("Slow circle (black)", CvarName.c_str(), 33);
Table_NextLine(); Table_NextLine();
SohImGui::EnhancementRadioButton("Fast noise circle (white)", CvarName.c_str(), 42); UIWidgets::EnhancementRadioButton("Fast noise circle (white)", CvarName.c_str(), 42);
Table_NextCol(); Table_NextCol();
SohImGui::EnhancementRadioButton("Fast noise circle (black)", CvarName.c_str(), 34); UIWidgets::EnhancementRadioButton("Fast noise circle (black)", CvarName.c_str(), 34);
Table_NextLine(); Table_NextLine();
SohImGui::EnhancementRadioButton("Slow noise circle (white)", CvarName.c_str(), 43); UIWidgets::EnhancementRadioButton("Slow noise circle (white)", CvarName.c_str(), 43);
Table_NextCol(); Table_NextCol();
SohImGui::EnhancementRadioButton("Slow noise circle (black)", CvarName.c_str(), 35); UIWidgets::EnhancementRadioButton("Slow noise circle (black)", CvarName.c_str(), 35);
Table_NextLine(); Table_NextLine();
SohImGui::EnhancementRadioButton("Normal waves circle (white)", CvarName.c_str(), 44); UIWidgets::EnhancementRadioButton("Normal waves circle (white)", CvarName.c_str(), 44);
Table_NextCol(); Table_NextCol();
SohImGui::EnhancementRadioButton("Normal waves circle (black)", CvarName.c_str(), 36); UIWidgets::EnhancementRadioButton("Normal waves circle (black)", CvarName.c_str(), 36);
Table_NextLine(); Table_NextLine();
SohImGui::EnhancementRadioButton("Slow waves circle (white)", CvarName.c_str(), 45); UIWidgets::EnhancementRadioButton("Slow waves circle (white)", CvarName.c_str(), 45);
Table_NextCol(); Table_NextCol();
SohImGui::EnhancementRadioButton("Slow waves circle (black)", CvarName.c_str(), 37); UIWidgets::EnhancementRadioButton("Slow waves circle (black)", CvarName.c_str(), 37);
Table_NextLine(); Table_NextLine();
SohImGui::EnhancementRadioButton("Normal close circle (white)", CvarName.c_str(), 46); UIWidgets::EnhancementRadioButton("Normal close circle (white)", CvarName.c_str(), 46);
Table_NextCol(); Table_NextCol();
SohImGui::EnhancementRadioButton("Normal close circle (black)", CvarName.c_str(), 38); UIWidgets::EnhancementRadioButton("Normal close circle (black)", CvarName.c_str(), 38);
Table_NextLine(); Table_NextLine();
SohImGui::EnhancementRadioButton("Slow close circle (white)", CvarName.c_str(), 47); UIWidgets::EnhancementRadioButton("Slow close circle (white)", CvarName.c_str(), 47);
Table_NextCol(); Table_NextCol();
SohImGui::EnhancementRadioButton("Slow close circle (black)", CvarName.c_str(), 39); UIWidgets::EnhancementRadioButton("Slow close circle (black)", CvarName.c_str(), 39);
Table_NextLine(); Table_NextLine();
SohImGui::EnhancementRadioButton("Super fast circle (white)", CvarName.c_str(), 56); UIWidgets::EnhancementRadioButton("Super fast circle (white)", CvarName.c_str(), 56);
Table_NextCol(); Table_NextCol();
SohImGui::EnhancementRadioButton("Super fast circle (black)", CvarName.c_str(), 58); UIWidgets::EnhancementRadioButton("Super fast circle (black)", CvarName.c_str(), 58);
Table_NextLine(); Table_NextLine();
SohImGui::EnhancementRadioButton("Super fast noise circle (white)", CvarName.c_str(), 57); UIWidgets::EnhancementRadioButton("Super fast noise circle (white)", CvarName.c_str(), 57);
Table_NextCol(); Table_NextCol();
SohImGui::EnhancementRadioButton("Super fast noise circle (black)", CvarName.c_str(), 59); UIWidgets::EnhancementRadioButton("Super fast noise circle (black)", CvarName.c_str(), 59);
} }
void DrawPositionSlider(const std::string CvarName, int MinY, int MaxY, int MinX, int MaxX){ void DrawPositionSlider(const std::string CvarName, int MinY, int MaxY, int MinX, int MaxX){
std::string PosXCvar = CvarName+"PosX"; std::string PosXCvar = CvarName+"PosX";
std::string PosYCvar = CvarName+"PosY"; std::string PosYCvar = CvarName+"PosY";
std::string InvisibleLabelX = "##"+PosXCvar; std::string InvisibleLabelX = "##"+PosXCvar;
std::string InvisibleLabelY = "##"+PosYCvar; std::string InvisibleLabelY = "##"+PosYCvar;
SohImGui::EnhancementSliderInt("Up <-> Down : %d", InvisibleLabelY.c_str(), PosYCvar.c_str(), MinY, MaxY, "", 0, true); UIWidgets::EnhancementSliderInt("Up <-> Down : %d", InvisibleLabelY.c_str(), PosYCvar.c_str(), MinY, MaxY, "", 0, true);
SohImGui::Tooltip("This slider is used to move Up and Down your elements."); UIWidgets::Tooltip("This slider is used to move Up and Down your elements.");
SohImGui::EnhancementSliderInt("Left <-> Right : %d", InvisibleLabelX.c_str(), PosXCvar.c_str(), MinX, MaxX, "", 0, true); UIWidgets::EnhancementSliderInt("Left <-> Right : %d", InvisibleLabelX.c_str(), PosXCvar.c_str(), MinX, MaxX, "", 0, true);
SohImGui::Tooltip("This slider is used to move Left and Right your elements."); UIWidgets::Tooltip("This slider is used to move Left and Right your elements.");
} }
void DrawScaleSlider(const std::string CvarName,float DefaultValue){ void DrawScaleSlider(const std::string CvarName,float DefaultValue){
std::string InvisibleLabel = "##"+CvarName; std::string InvisibleLabel = "##"+CvarName;
std::string CvarLabel = CvarName+"Scale"; std::string CvarLabel = CvarName+"Scale";
//Disabled for now. feature not done and several fixes needed to be merged. //Disabled for now. feature not done and several fixes needed to be merged.
//SohImGui::EnhancementSliderFloat("Scale : %dx", InvisibleLabel.c_str(), CvarLabel.c_str(), 0.1f, 3.0f,"",DefaultValue,true,true); //UIWidgets::EnhancementSliderFloat("Scale : %dx", InvisibleLabel.c_str(), CvarLabel.c_str(), 0.1f, 3.0f,"",DefaultValue,true,true);
} }
void DrawColorSection(CosmeticsColorSection* ColorSection, int SectionSize) { void DrawColorSection(CosmeticsColorSection* ColorSection, int SectionSize) {
for (s16 i = 0; i < SectionSize; i++) { for (s16 i = 0; i < SectionSize; i++) {
@ -308,7 +310,7 @@ void DrawColorSection(CosmeticsColorSection* ColorSection, int SectionSize) {
Table_NextLine(); Table_NextLine();
} }
Draw_HelpIcon(Tooltip.c_str()); Draw_HelpIcon(Tooltip.c_str());
SohImGui::EnhancementColor(Name.c_str(), Cvar.c_str(), ModifiedColor, DefaultColor, canRainbow, hasAlpha, sameLine); UIWidgets::EnhancementColor(Name.c_str(), Cvar.c_str(), ModifiedColor, DefaultColor, canRainbow, hasAlpha, sameLine);
} }
} }
void DrawRandomizeResetButton(const std::string Identifier, CosmeticsColorSection* ColorSection, int SectionSize, bool isAllCosmetics = false){ void DrawRandomizeResetButton(const std::string Identifier, CosmeticsColorSection* ColorSection, int SectionSize, bool isAllCosmetics = false){
@ -335,21 +337,21 @@ void DrawRandomizeResetButton(const std::string Identifier, CosmeticsColorSectio
CVar_SetS32("gCCparated", 1); CVar_SetS32("gCCparated", 1);
GetRandomColorRGB(ColorSection, SectionSize); GetRandomColorRGB(ColorSection, SectionSize);
} }
SohImGui::Tooltip(Tooltip_RNG.c_str()); UIWidgets::Tooltip(Tooltip_RNG.c_str());
Table_NextCol(); Table_NextCol();
if(ImGui::Button(Reset_BtnText.c_str(), ImVec2( ImGui::GetContentRegionAvail().x, 20.0f))){ if(ImGui::Button(Reset_BtnText.c_str(), ImVec2( ImGui::GetContentRegionAvail().x, 20.0f))){
GetDefaultColorRGB(ColorSection, SectionSize); GetDefaultColorRGB(ColorSection, SectionSize);
} }
SohImGui::Tooltip("Enable/Disable custom Link's tunics colors\nIf disabled you will have original colors for Link's tunics."); UIWidgets::Tooltip("Enable/Disable custom Link's tunics colors\nIf disabled you will have original colors for Link's tunics.");
SohImGui::Tooltip(Tooltip_RNG.c_str()); UIWidgets::Tooltip(Tooltip_RNG.c_str());
ImGui::EndTable(); ImGui::EndTable();
} }
} }
void Draw_Npcs(){ void Draw_Npcs(){
DrawRandomizeResetButton("all NPCs", NPCs_section, SECTION_SIZE(NPCs_section)); DrawRandomizeResetButton("all NPCs", NPCs_section, SECTION_SIZE(NPCs_section));
SohImGui::EnhancementCheckbox("Custom colors for Navi", "gUseNaviCol"); UIWidgets::EnhancementCheckbox("Custom colors for Navi", "gUseNaviCol");
SohImGui::Tooltip("Enable/Disable custom Navi colors\nIf disabled, default colors will be used\nColors go into effect when Navi goes back into your pockets"); UIWidgets::Tooltip("Enable/Disable custom Navi colors\nIf disabled, default colors will be used\nColors go into effect when Navi goes back into your pockets");
if (CVar_GetS32("gUseNaviCol",0)) { if (CVar_GetS32("gUseNaviCol",0)) {
DrawRandomizeResetButton("Navi's", Navi_Section, SECTION_SIZE(Navi_Section)); DrawRandomizeResetButton("Navi's", Navi_Section, SECTION_SIZE(Navi_Section));
}; };
@ -360,8 +362,8 @@ void Draw_Npcs(){
DrawColorSection(Navi_Section, SECTION_SIZE(Navi_Section)); DrawColorSection(Navi_Section, SECTION_SIZE(Navi_Section));
ImGui::EndTable(); ImGui::EndTable();
} }
SohImGui::EnhancementCheckbox("Custom colors for Keese", "gUseKeeseCol"); UIWidgets::EnhancementCheckbox("Custom colors for Keese", "gUseKeeseCol");
SohImGui::Tooltip("Enable/Disable custom Keese element colors\nIf disabled, default element colors will be used\nColors go into effect when Keese respawn (or when the room is reloaded)"); UIWidgets::Tooltip("Enable/Disable custom Keese element colors\nIf disabled, default element colors will be used\nColors go into effect when Keese respawn (or when the room is reloaded)");
if (CVar_GetS32("gUseKeeseCol",0) && ImGui::BeginTable("tableKeese", 2, FlagsTable)) { if (CVar_GetS32("gUseKeeseCol",0) && ImGui::BeginTable("tableKeese", 2, FlagsTable)) {
ImGui::TableSetupColumn("Fire colors##Keese", FlagsCell, TablesCellsWidth/2); ImGui::TableSetupColumn("Fire colors##Keese", FlagsCell, TablesCellsWidth/2);
ImGui::TableSetupColumn("Ice colors##Keese", FlagsCell, TablesCellsWidth/2); ImGui::TableSetupColumn("Ice colors##Keese", FlagsCell, TablesCellsWidth/2);
@ -369,8 +371,8 @@ void Draw_Npcs(){
DrawColorSection(Keese_Section, SECTION_SIZE(Keese_Section)); DrawColorSection(Keese_Section, SECTION_SIZE(Keese_Section));
ImGui::EndTable(); ImGui::EndTable();
} }
SohImGui::EnhancementCheckbox("Custom colors for Dogs", "gUseDogsCol"); UIWidgets::EnhancementCheckbox("Custom colors for Dogs", "gUseDogsCol");
SohImGui::Tooltip("Enable/Disable custom colors for the two Dog variants\nIf disabled, default colors will be used"); UIWidgets::Tooltip("Enable/Disable custom colors for the two Dog variants\nIf disabled, default colors will be used");
if (CVar_GetS32("gUseDogsCol",0) && ImGui::BeginTable("tableDogs", 2, FlagsTable)) { if (CVar_GetS32("gUseDogsCol",0) && ImGui::BeginTable("tableDogs", 2, FlagsTable)) {
ImGui::TableSetupColumn("White Dog color", FlagsCell, TablesCellsWidth/2); ImGui::TableSetupColumn("White Dog color", FlagsCell, TablesCellsWidth/2);
ImGui::TableSetupColumn("Brown Dog color", FlagsCell, TablesCellsWidth/2); ImGui::TableSetupColumn("Brown Dog color", FlagsCell, TablesCellsWidth/2);
@ -381,8 +383,8 @@ void Draw_Npcs(){
} }
void Draw_ItemsSkills(){ void Draw_ItemsSkills(){
DrawRandomizeResetButton("all skills and items", AllItemsSkills_section, SECTION_SIZE(AllItemsSkills_section)); DrawRandomizeResetButton("all skills and items", AllItemsSkills_section, SECTION_SIZE(AllItemsSkills_section));
SohImGui::EnhancementCheckbox("Custom tunics color", "gUseTunicsCol"); UIWidgets::EnhancementCheckbox("Custom tunics color", "gUseTunicsCol");
SohImGui::Tooltip("Enable/Disable custom Link's tunics colors\nIf disabled you will have original colors for Link's tunics."); UIWidgets::Tooltip("Enable/Disable custom Link's tunics colors\nIf disabled you will have original colors for Link's tunics.");
if (CVar_GetS32("gUseTunicsCol",0)) { if (CVar_GetS32("gUseTunicsCol",0)) {
DrawRandomizeResetButton("Link's tunics", Tunics_Section, SECTION_SIZE(Tunics_Section)); DrawRandomizeResetButton("Link's tunics", Tunics_Section, SECTION_SIZE(Tunics_Section));
}; };
@ -394,7 +396,7 @@ void Draw_ItemsSkills(){
DrawColorSection(Tunics_Section, SECTION_SIZE(Tunics_Section)); DrawColorSection(Tunics_Section, SECTION_SIZE(Tunics_Section));
ImGui::EndTable(); ImGui::EndTable();
} }
SohImGui::EnhancementCheckbox("Custom arrows colors", "gUseArrowsCol"); UIWidgets::EnhancementCheckbox("Custom arrows colors", "gUseArrowsCol");
if (CVar_GetS32("gUseArrowsCol",0)) { if (CVar_GetS32("gUseArrowsCol",0)) {
DrawRandomizeResetButton("elemental arrows", Arrows_section, SECTION_SIZE(Arrows_section)); DrawRandomizeResetButton("elemental arrows", Arrows_section, SECTION_SIZE(Arrows_section));
} }
@ -405,7 +407,7 @@ void Draw_ItemsSkills(){
DrawColorSection(Arrows_section, SECTION_SIZE(Arrows_section)); DrawColorSection(Arrows_section, SECTION_SIZE(Arrows_section));
ImGui::EndTable(); ImGui::EndTable();
} }
SohImGui::EnhancementCheckbox("Custom spells colors", "gUseSpellsCol"); UIWidgets::EnhancementCheckbox("Custom spells colors", "gUseSpellsCol");
if (CVar_GetS32("gUseSpellsCol",0)) { if (CVar_GetS32("gUseSpellsCol",0)) {
DrawRandomizeResetButton("spells", Spells_section, SECTION_SIZE(Spells_section)); DrawRandomizeResetButton("spells", Spells_section, SECTION_SIZE(Spells_section));
} }
@ -416,7 +418,7 @@ void Draw_ItemsSkills(){
DrawColorSection(Spells_section, SECTION_SIZE(Spells_section)); DrawColorSection(Spells_section, SECTION_SIZE(Spells_section));
ImGui::EndTable(); ImGui::EndTable();
} }
SohImGui::EnhancementCheckbox("Custom spin attack colors", "gUseChargedCol"); UIWidgets::EnhancementCheckbox("Custom spin attack colors", "gUseChargedCol");
if (CVar_GetS32("gUseChargedCol",0)) { if (CVar_GetS32("gUseChargedCol",0)) {
DrawRandomizeResetButton("spins attack", SpinAtk_section, SECTION_SIZE(SpinAtk_section)); DrawRandomizeResetButton("spins attack", SpinAtk_section, SECTION_SIZE(SpinAtk_section));
} }
@ -427,13 +429,13 @@ void Draw_ItemsSkills(){
DrawColorSection(SpinAtk_section, SECTION_SIZE(SpinAtk_section)); DrawColorSection(SpinAtk_section, SECTION_SIZE(SpinAtk_section));
ImGui::EndTable(); ImGui::EndTable();
} }
SohImGui::EnhancementCheckbox("Custom trails color", "gUseTrailsCol"); UIWidgets::EnhancementCheckbox("Custom trails color", "gUseTrailsCol");
if (CVar_GetS32("gUseTrailsCol",0) && ImGui::BeginTable("tabletrails", 1, FlagsTable)) { if (CVar_GetS32("gUseTrailsCol",0) && ImGui::BeginTable("tabletrails", 1, FlagsTable)) {
ImGui::TableSetupColumn("Custom Trails", FlagsCell, TablesCellsWidth); ImGui::TableSetupColumn("Custom Trails", FlagsCell, TablesCellsWidth);
Table_InitHeader(); Table_InitHeader();
DrawColorSection(Trails_section, SECTION_SIZE(Trails_section)); DrawColorSection(Trails_section, SECTION_SIZE(Trails_section));
SohImGui::EnhancementSliderInt("Trails duration: %dx", "##TrailsMul", "gTrailDurantion", 1, 5, ""); UIWidgets::EnhancementSliderInt("Trails duration: %dx", "##TrailsMul", "gTrailDurantion", 1, 5, "");
SohImGui::Tooltip("The longer the trails the weirder it become"); UIWidgets::Tooltip("The longer the trails the weirder it become");
ImGui::NewLine(); ImGui::NewLine();
ImGui::EndTable(); ImGui::EndTable();
} }
@ -455,18 +457,18 @@ void Draw_Placements(){
if (ImGui::BeginTable("tableMargins", 1, FlagsTable)) { if (ImGui::BeginTable("tableMargins", 1, FlagsTable)) {
ImGui::TableSetupColumn("General margins settings", FlagsCell, TablesCellsWidth); ImGui::TableSetupColumn("General margins settings", FlagsCell, TablesCellsWidth);
Table_InitHeader(); Table_InitHeader();
SohImGui::EnhancementSliderInt("Top : %dx", "##UIMARGINT", "gHUDMargin_T", (ImGui::GetWindowViewport()->Size.y/2)*-1, 25, "", 0, true); UIWidgets::EnhancementSliderInt("Top : %dx", "##UIMARGINT", "gHUDMargin_T", (ImGui::GetWindowViewport()->Size.y/2)*-1, 25, "", 0, true);
SohImGui::EnhancementSliderInt("Left: %dx", "##UIMARGINL", "gHUDMargin_L", -25, ImGui::GetWindowViewport()->Size.x, "", 0, true); UIWidgets::EnhancementSliderInt("Left: %dx", "##UIMARGINL", "gHUDMargin_L", -25, ImGui::GetWindowViewport()->Size.x, "", 0, true);
SohImGui::EnhancementSliderInt("Right: %dx", "##UIMARGINR", "gHUDMargin_R", (ImGui::GetWindowViewport()->Size.x)*-1, 25, "", 0, true); UIWidgets::EnhancementSliderInt("Right: %dx", "##UIMARGINR", "gHUDMargin_R", (ImGui::GetWindowViewport()->Size.x)*-1, 25, "", 0, true);
SohImGui::EnhancementSliderInt("Bottom: %dx", "##UIMARGINB", "gHUDMargin_B", (ImGui::GetWindowViewport()->Size.y/2)*-1, 25, "", 0, true); UIWidgets::EnhancementSliderInt("Bottom: %dx", "##UIMARGINB", "gHUDMargin_B", (ImGui::GetWindowViewport()->Size.y/2)*-1, 25, "", 0, true);
SetMarginAll("All margins on",true); SetMarginAll("All margins on",true);
SohImGui::Tooltip("Set most of the element to use margin\nSome elements with default position will not be affected\nElements without Archor or Hidden will not be turned on"); UIWidgets::Tooltip("Set most of the element to use margin\nSome elements with default position will not be affected\nElements without Archor or Hidden will not be turned on");
ImGui::SameLine(); ImGui::SameLine();
SetMarginAll("All margins off",false); SetMarginAll("All margins off",false);
SohImGui::Tooltip("Set all of the element to not use margin"); UIWidgets::Tooltip("Set all of the element to not use margin");
ImGui::SameLine(); ImGui::SameLine();
ResetPositionAll(); ResetPositionAll();
SohImGui::Tooltip("Revert every element to use their original position and no margins"); UIWidgets::Tooltip("Revert every element to use their original position and no margins");
ImGui::NewLine(); ImGui::NewLine();
ImGui::EndTable(); ImGui::EndTable();
} }
@ -775,7 +777,7 @@ void Draw_HUDButtons(){
DrawColorSection(C_Btn_Unified_section, SECTION_SIZE(C_Btn_Unified_section)); DrawColorSection(C_Btn_Unified_section, SECTION_SIZE(C_Btn_Unified_section));
ImGui::EndTable(); ImGui::EndTable();
} }
SohImGui::EnhancementCheckbox("C-Buttons use separate colors", "gCCparated"); UIWidgets::EnhancementCheckbox("C-Buttons use separate colors", "gCCparated");
if (CVar_GetS32("gCCparated",0) && ImGui::CollapsingHeader("C Button individual colors")) { if (CVar_GetS32("gCCparated",0) && ImGui::CollapsingHeader("C Button individual colors")) {
if (ImGui::BeginTable("tableBTN_CSep", 1, FlagsTable)) { if (ImGui::BeginTable("tableBTN_CSep", 1, FlagsTable)) {
ImGui::TableSetupColumn("C-Buttons individual colors", FlagsCell, TablesCellsWidth); ImGui::TableSetupColumn("C-Buttons individual colors", FlagsCell, TablesCellsWidth);
@ -813,19 +815,19 @@ void Draw_General(){
ImGui::TableSetupColumn("Custom Schemes", FlagsCell, TablesCellsWidth); ImGui::TableSetupColumn("Custom Schemes", FlagsCell, TablesCellsWidth);
Table_InitHeader(); Table_InitHeader();
Draw_HelpIcon("Change interface color to N64 style"); Draw_HelpIcon("Change interface color to N64 style");
SohImGui::EnhancementRadioButton("N64 Colors", "gHudColors", 0); UIWidgets::EnhancementRadioButton("N64 Colors", "gHudColors", 0);
Table_NextCol(); Table_NextCol();
Draw_HelpIcon("Change interface color to GameCube style"); Draw_HelpIcon("Change interface color to GameCube style");
SohImGui::EnhancementRadioButton("GCN Colors", "gHudColors", 1); UIWidgets::EnhancementRadioButton("GCN Colors", "gHudColors", 1);
Table_NextCol(); Table_NextCol();
Draw_HelpIcon("Lets you change every interface color to your liking"); Draw_HelpIcon("Lets you change every interface color to your liking");
SohImGui::EnhancementRadioButton("Custom Colors", "gHudColors", 2); UIWidgets::EnhancementRadioButton("Custom Colors", "gHudColors", 2);
ImGui::EndTable(); ImGui::EndTable();
} }
if (CVar_GetS32("gHudColors",0) ==2 ){ if (CVar_GetS32("gHudColors",0) ==2 ){
DrawRandomizeResetButton("interface (excluding buttons)", Misc_Interface_section, SECTION_SIZE(Misc_Interface_section)); DrawRandomizeResetButton("interface (excluding buttons)", Misc_Interface_section, SECTION_SIZE(Misc_Interface_section));
if (ImGui::CollapsingHeader("Hearts colors")) { if (ImGui::CollapsingHeader("Hearts colors")) {
SohImGui::Tooltip("Hearts colors in general\nDD stand for Double Defense"); UIWidgets::Tooltip("Hearts colors in general\nDD stand for Double Defense");
if (ImGui::BeginTable("tableHearts", 3, FlagsTable | ImGuiTableFlags_Hideable)) { if (ImGui::BeginTable("tableHearts", 3, FlagsTable | ImGuiTableFlags_Hideable)) {
ImGui::TableSetupColumn("Hearts (normal)", ImGuiTableColumnFlags_WidthStretch | ImGuiTableColumnFlags_IndentEnable, TablesCellsWidth/3); ImGui::TableSetupColumn("Hearts (normal)", ImGuiTableColumnFlags_WidthStretch | ImGuiTableColumnFlags_IndentEnable, TablesCellsWidth/3);
ImGui::TableSetupColumn("Hearts (DD)", ImGuiTableColumnFlags_WidthStretch | ImGuiTableColumnFlags_IndentEnable, TablesCellsWidth/3); ImGui::TableSetupColumn("Hearts (DD)", ImGuiTableColumnFlags_WidthStretch | ImGuiTableColumnFlags_IndentEnable, TablesCellsWidth/3);
@ -874,25 +876,25 @@ void Draw_General(){
ImGui::TableSetupColumn("transitionother1", FlagsCell, TablesCellsWidth/2); ImGui::TableSetupColumn("transitionother1", FlagsCell, TablesCellsWidth/2);
ImGui::TableSetupColumn("transitionother2", FlagsCell, TablesCellsWidth/2); ImGui::TableSetupColumn("transitionother2", FlagsCell, TablesCellsWidth/2);
Table_InitHeader(false); Table_InitHeader(false);
SohImGui::EnhancementRadioButton("Originals", "gSceneTransitions", 255); UIWidgets::EnhancementRadioButton("Originals", "gSceneTransitions", 255);
SohImGui::Tooltip("This will make the game use original scenes transitions"); UIWidgets::Tooltip("This will make the game use original scenes transitions");
Table_NextCol(); Table_NextCol();
SohImGui::EnhancementRadioButton("None", "gSceneTransitions", 11); UIWidgets::EnhancementRadioButton("None", "gSceneTransitions", 11);
SohImGui::Tooltip("This will make the game use no any scenes transitions"); UIWidgets::Tooltip("This will make the game use no any scenes transitions");
Table_NextLine(); Table_NextLine();
SohImGui::EnhancementRadioButton("Desert mode (persistant)", "gSceneTransitions", 14); UIWidgets::EnhancementRadioButton("Desert mode (persistant)", "gSceneTransitions", 14);
SohImGui::Tooltip("This will make the game use the sand storm scenes transitions that will persist in map"); UIWidgets::Tooltip("This will make the game use the sand storm scenes transitions that will persist in map");
Table_NextCol(); Table_NextCol();
SohImGui::EnhancementRadioButton("Desert mode (non persistant)", "gSceneTransitions", 15); UIWidgets::EnhancementRadioButton("Desert mode (non persistant)", "gSceneTransitions", 15);
SohImGui::Tooltip("This will make the game use the sand storm scenes transitions"); UIWidgets::Tooltip("This will make the game use the sand storm scenes transitions");
Table_NextLine(); Table_NextLine();
SohImGui::EnhancementRadioButton("Normal fade (green)", "gSceneTransitions", 18); UIWidgets::EnhancementRadioButton("Normal fade (green)", "gSceneTransitions", 18);
SohImGui::Tooltip("This will make the game use a greenish fade in/out scenes transitions"); UIWidgets::Tooltip("This will make the game use a greenish fade in/out scenes transitions");
Table_NextCol(); Table_NextCol();
SohImGui::EnhancementRadioButton("Normal fade (blue)", "gSceneTransitions", 19); UIWidgets::EnhancementRadioButton("Normal fade (blue)", "gSceneTransitions", 19);
SohImGui::Tooltip("This will make the game use a blue fade in/out scenes transitions"); UIWidgets::Tooltip("This will make the game use a blue fade in/out scenes transitions");
Table_NextLine(); Table_NextLine();
SohImGui::EnhancementRadioButton("Triforce", "gSceneTransitions", 1); UIWidgets::EnhancementRadioButton("Triforce", "gSceneTransitions", 1);
ImGui::EndTable(); ImGui::EndTable();
} }
if (ImGui::BeginTable("tabletransitionCol", 2, FlagsTable | ImGuiTableFlags_Hideable)) { if (ImGui::BeginTable("tabletransitionCol", 2, FlagsTable | ImGuiTableFlags_Hideable)) {
@ -948,6 +950,7 @@ void DrawCosmeticsEditor(bool& open) {
} }
ImGui::End(); ImGui::End();
} }
void InitCosmeticsEditor() { void InitCosmeticsEditor() {
//This allow to hide a window without disturbing the player nor adding things in menu //This allow to hide a window without disturbing the player nor adding things in menu
//LoadRainbowColor() will this way run in background once it's window is activated //LoadRainbowColor() will this way run in background once it's window is activated
@ -955,4 +958,4 @@ void InitCosmeticsEditor() {
SohImGui::AddWindow("Enhancements", "Rainbowfunction", LoadRainbowColor, true, true); SohImGui::AddWindow("Enhancements", "Rainbowfunction", LoadRainbowColor, true, true);
//Draw the bar in the menu. //Draw the bar in the menu.
SohImGui::AddWindow("Enhancements", "Cosmetics Editor", DrawCosmeticsEditor); SohImGui::AddWindow("Enhancements", "Cosmetics Editor", DrawCosmeticsEditor);
} }

View File

@ -1,5 +1,5 @@
#pragma once #pragma once
#include "../libultraship/ImGuiImpl.h" #include <libultraship/ImGuiImpl.h>
#define SECTION_SIZE(arr) (s32)(sizeof(arr) / sizeof(arr[0])) #define SECTION_SIZE(arr) (s32)(sizeof(arr) / sizeof(arr[0]))
#define RANDOMIZE_32(Max) GetRandomValue(Max); #define RANDOMIZE_32(Max) GetRandomValue(Max);
#define CATEGORY_NPC 0 #define CATEGORY_NPC 0
@ -405,4 +405,4 @@ static CosmeticsColorSection AllItemsSkills_section[]{
void InitCosmeticsEditor();//Init the menu itself void InitCosmeticsEditor();//Init the menu itself
void LoadRainbowColor(); void LoadRainbowColor();
void NewSliderInt(const char* text, const char* id, const char* cvarName, int min, int max, const char* format, int defaultValue = 0); void NewSliderInt(const char* text, const char* id, const char* cvarName, int min, int max, const char* format, int defaultValue = 0);

View File

@ -1,7 +1,7 @@
#include "debugconsole.h" #include "debugconsole.h"
#include "../libultraship/ImGuiImpl.h" #include <libultraship/ImGuiImpl.h>
#include "savestates.h" #include "savestates.h"
#include "Console.h" #include <libultraship/Console.h>
#include <vector> #include <vector>
#include <string> #include <string>
@ -12,8 +12,8 @@
#define PATH_HACK #define PATH_HACK
#include <Utils/StringHelper.h> #include <Utils/StringHelper.h>
#include "Window.h" #include <libultraship/Window.h>
#include "Lib/ImGui/imgui_internal.h" #include <ImGui/imgui_internal.h>
#undef PATH_HACK #undef PATH_HACK
#undef Path #undef Path
@ -25,18 +25,18 @@ extern "C" {
extern GlobalContext* gGlobalCtx; extern GlobalContext* gGlobalCtx;
} }
#include "Cvar.h" #include <libultraship/Cvar.h>
#define CMD_REGISTER SohImGui::BindCmd #define CMD_REGISTER SohImGui::GetConsole()->AddCommand
static bool ActorSpawnHandler(std::shared_ptr<Ship::Console> Console, const std::vector<std::string>& args) { static bool ActorSpawnHandler(std::shared_ptr<Ship::Console> Console, const std::vector<std::string>& args) {
if ((args.size() != 9) && (args.size() != 3) && (args.size() != 6)) { if ((args.size() != 9) && (args.size() != 3) && (args.size() != 6)) {
SohImGui::console->SendErrorMessage("Not enough arguments passed to actorspawn"); SohImGui::GetConsole()->SendErrorMessage("Not enough arguments passed to actorspawn");
return CMD_FAILED; return CMD_FAILED;
} }
if (gGlobalCtx == nullptr) { if (gGlobalCtx == nullptr) {
SohImGui::console->SendErrorMessage("GlobalCtx == nullptr"); SohImGui::GetConsole()->SendErrorMessage("GlobalCtx == nullptr");
return CMD_FAILED; return CMD_FAILED;
} }
@ -72,7 +72,7 @@ static bool ActorSpawnHandler(std::shared_ptr<Ship::Console> Console, const std:
if (Actor_Spawn(&gGlobalCtx->actorCtx, gGlobalCtx, actorId, spawnPoint.pos.x, spawnPoint.pos.y, spawnPoint.pos.z, if (Actor_Spawn(&gGlobalCtx->actorCtx, gGlobalCtx, actorId, spawnPoint.pos.x, spawnPoint.pos.y, spawnPoint.pos.z,
spawnPoint.rot.x, spawnPoint.rot.y, spawnPoint.rot.z, params) == NULL) { spawnPoint.rot.x, spawnPoint.rot.y, spawnPoint.rot.z, params) == NULL) {
SohImGui::console->SendErrorMessage("Failed to spawn actor. Actor_Spawn returned NULL"); SohImGui::GetConsole()->SendErrorMessage("Failed to spawn actor. Actor_Spawn returned NULL");
return CMD_FAILED; return CMD_FAILED;
} }
return CMD_SUCCESS; return CMD_SUCCESS;
@ -81,13 +81,13 @@ static bool ActorSpawnHandler(std::shared_ptr<Ship::Console> Console, const std:
static bool KillPlayerHandler(std::shared_ptr<Ship::Console> Console, const std::vector<std::string>&) { static bool KillPlayerHandler(std::shared_ptr<Ship::Console> Console, const std::vector<std::string>&) {
gSaveContext.health = 0; gSaveContext.health = 0;
SohImGui::console->SendInfoMessage("[SOH] You've met with a terrible fate, haven't you?"); SohImGui::GetConsole()->SendInfoMessage("[SOH] You've met with a terrible fate, haven't you?");
return CMD_SUCCESS; return CMD_SUCCESS;
} }
static bool SetPlayerHealthHandler(std::shared_ptr<Ship::Console> Console, const std::vector<std::string>& args) { static bool SetPlayerHealthHandler(std::shared_ptr<Ship::Console> Console, const std::vector<std::string>& args) {
if (args.size() != 2) { if (args.size() != 2) {
SohImGui::console->SendErrorMessage("[SOH] Unexpected arguments passed"); SohImGui::GetConsole()->SendErrorMessage("[SOH] Unexpected arguments passed");
return CMD_FAILED; return CMD_FAILED;
} }
@ -96,18 +96,18 @@ static bool SetPlayerHealthHandler(std::shared_ptr<Ship::Console> Console, const
try { try {
health = std::stoi(args[1]); health = std::stoi(args[1]);
} catch (std::invalid_argument const& ex) { } catch (std::invalid_argument const& ex) {
SohImGui::console->SendErrorMessage("[SOH] Health value must be an integer."); SohImGui::GetConsole()->SendErrorMessage("[SOH] Health value must be an integer.");
return CMD_FAILED; return CMD_FAILED;
} }
if (health < 0) { if (health < 0) {
SohImGui::console->SendErrorMessage("[SOH] Health value must be a positive integer"); SohImGui::GetConsole()->SendErrorMessage("[SOH] Health value must be a positive integer");
return CMD_SUCCESS; return CMD_SUCCESS;
} }
gSaveContext.health = health * 0x10; gSaveContext.health = health * 0x10;
SohImGui::console->SendInfoMessage("[SOH] Player health updated to %d", health); SohImGui::GetConsole()->SendInfoMessage("[SOH] Player health updated to %d", health);
return CMD_SUCCESS; return CMD_SUCCESS;
} }
@ -129,31 +129,31 @@ static bool RuppeHandler(std::shared_ptr<Ship::Console> Console, const std::vect
rupeeAmount = std::stoi(args[1]); rupeeAmount = std::stoi(args[1]);
} }
catch (std::invalid_argument const& ex) { catch (std::invalid_argument const& ex) {
SohImGui::console->SendErrorMessage("[SOH] Rupee count must be an integer."); SohImGui::GetConsole()->SendErrorMessage("[SOH] Rupee count must be an integer.");
return CMD_FAILED; return CMD_FAILED;
} }
if (rupeeAmount < 0) { if (rupeeAmount < 0) {
SohImGui::console->SendErrorMessage("[SOH] Rupee count must be positive"); SohImGui::GetConsole()->SendErrorMessage("[SOH] Rupee count must be positive");
return CMD_FAILED; return CMD_FAILED;
} }
gSaveContext.rupees = rupeeAmount; gSaveContext.rupees = rupeeAmount;
SohImGui::console->SendInfoMessage("Set rupee count to %u", rupeeAmount); SohImGui::GetConsole()->SendInfoMessage("Set rupee count to %u", rupeeAmount);
return CMD_SUCCESS; return CMD_SUCCESS;
} }
static bool SetPosHandler(std::shared_ptr<Ship::Console> Console, const std::vector<std::string> args) { static bool SetPosHandler(std::shared_ptr<Ship::Console> Console, const std::vector<std::string> args) {
if (gGlobalCtx == nullptr) { if (gGlobalCtx == nullptr) {
SohImGui::console->SendErrorMessage("GlobalCtx == nullptr"); SohImGui::GetConsole()->SendErrorMessage("GlobalCtx == nullptr");
return CMD_FAILED; return CMD_FAILED;
} }
Player* player = GET_PLAYER(gGlobalCtx); Player* player = GET_PLAYER(gGlobalCtx);
if (args.size() == 1) { if (args.size() == 1) {
SohImGui::console->SendInfoMessage("Player position is [ %.2f, %.2f, %.2f ]", player->actor.world.pos.x, SohImGui::GetConsole()->SendInfoMessage("Player position is [ %.2f, %.2f, %.2f ]", player->actor.world.pos.x,
player->actor.world.pos.y, player->actor.world.pos.y,
player->actor.world.pos.z); player->actor.world.pos.z);
return CMD_SUCCESS; return CMD_SUCCESS;
@ -165,7 +165,7 @@ static bool SetPosHandler(std::shared_ptr<Ship::Console> Console, const std::vec
player->actor.world.pos.y = std::stof(args[2]); player->actor.world.pos.y = std::stof(args[2]);
player->actor.world.pos.z = std::stof(args[3]); player->actor.world.pos.z = std::stof(args[3]);
SohImGui::console->SendInfoMessage("Set player position to [ %.2f, %.2f, %.2f ]", player->actor.world.pos.x, SohImGui::GetConsole()->SendInfoMessage("Set player position to [ %.2f, %.2f, %.2f ]", player->actor.world.pos.x,
player->actor.world.pos.y, player->actor.world.pos.y,
player->actor.world.pos.z); player->actor.world.pos.z);
return CMD_SUCCESS; return CMD_SUCCESS;
@ -173,7 +173,7 @@ static bool SetPosHandler(std::shared_ptr<Ship::Console> Console, const std::vec
static bool ResetHandler(std::shared_ptr<Ship::Console> Console, std::vector<std::string> args) { static bool ResetHandler(std::shared_ptr<Ship::Console> Console, std::vector<std::string> args) {
if (gGlobalCtx == nullptr) { if (gGlobalCtx == nullptr) {
SohImGui::console->SendErrorMessage("GlobalCtx == nullptr"); SohImGui::GetConsole()->SendErrorMessage("GlobalCtx == nullptr");
return CMD_FAILED; return CMD_FAILED;
} }
@ -194,7 +194,7 @@ const static std::map<std::string, uint16_t> ammoItems{
static bool AmmoHandler(std::shared_ptr<Ship::Console> Console, const std::vector<std::string>& args) { static bool AmmoHandler(std::shared_ptr<Ship::Console> Console, const std::vector<std::string>& args) {
if (args.size() != 3) { if (args.size() != 3) {
SohImGui::console->SendErrorMessage("[SOH] Unexpected arguments passed"); SohImGui::GetConsole()->SendErrorMessage("[SOH] Unexpected arguments passed");
return CMD_FAILED; return CMD_FAILED;
} }
@ -203,19 +203,19 @@ static bool AmmoHandler(std::shared_ptr<Ship::Console> Console, const std::vecto
try { try {
count = std::stoi(args[2]); count = std::stoi(args[2]);
} catch (std::invalid_argument const& ex) { } catch (std::invalid_argument const& ex) {
SohImGui::console->SendErrorMessage("Ammo count must be an integer"); SohImGui::GetConsole()->SendErrorMessage("Ammo count must be an integer");
return CMD_FAILED; return CMD_FAILED;
} }
if (count < 0) { if (count < 0) {
SohImGui::console->SendErrorMessage("Ammo count must be positive"); SohImGui::GetConsole()->SendErrorMessage("Ammo count must be positive");
return CMD_FAILED; return CMD_FAILED;
} }
const auto& it = ammoItems.find(args[1]); const auto& it = ammoItems.find(args[1]);
if (it == ammoItems.end()) { if (it == ammoItems.end()) {
SohImGui::console->SendErrorMessage("Invalid item passed"); SohImGui::GetConsole()->SendErrorMessage("Invalid item passed");
return CMD_FAILED; return CMD_FAILED;
} }
@ -237,7 +237,7 @@ const static std::map<std::string, uint16_t> bottleItems{
static bool BottleHandler(std::shared_ptr<Ship::Console> Console, const std::vector<std::string>& args) { static bool BottleHandler(std::shared_ptr<Ship::Console> Console, const std::vector<std::string>& args) {
if (args.size() != 3) { if (args.size() != 3) {
SohImGui::console->SendErrorMessage("[SOH] Unexpected arguments passed"); SohImGui::GetConsole()->SendErrorMessage("[SOH] Unexpected arguments passed");
return CMD_FAILED; return CMD_FAILED;
} }
@ -245,19 +245,19 @@ static bool BottleHandler(std::shared_ptr<Ship::Console> Console, const std::vec
try { try {
slot = std::stoi(args[2]); slot = std::stoi(args[2]);
} catch (std::invalid_argument const& ex) { } catch (std::invalid_argument const& ex) {
SohImGui::console->SendErrorMessage("[SOH] Bottle slot must be an integer."); SohImGui::GetConsole()->SendErrorMessage("[SOH] Bottle slot must be an integer.");
return CMD_FAILED; return CMD_FAILED;
} }
if ((slot < 1) || (slot > 4)) { if ((slot < 1) || (slot > 4)) {
SohImGui::console->SendErrorMessage("Invalid slot passed"); SohImGui::GetConsole()->SendErrorMessage("Invalid slot passed");
return CMD_FAILED; return CMD_FAILED;
} }
const auto& it = bottleItems.find(args[1]); const auto& it = bottleItems.find(args[1]);
if (it == bottleItems.end()) { if (it == bottleItems.end()) {
SohImGui::console->SendErrorMessage("Invalid item passed"); SohImGui::GetConsole()->SendErrorMessage("Invalid item passed");
return CMD_FAILED; return CMD_FAILED;
} }
@ -269,7 +269,7 @@ static bool BottleHandler(std::shared_ptr<Ship::Console> Console, const std::vec
static bool BHandler(std::shared_ptr<Ship::Console> Console, const std::vector<std::string>& args) { static bool BHandler(std::shared_ptr<Ship::Console> Console, const std::vector<std::string>& args) {
if (args.size() != 2) { if (args.size() != 2) {
SohImGui::console->SendErrorMessage("[SOH] Unexpected arguments passed"); SohImGui::GetConsole()->SendErrorMessage("[SOH] Unexpected arguments passed");
return CMD_FAILED; return CMD_FAILED;
} }
@ -279,7 +279,7 @@ static bool BHandler(std::shared_ptr<Ship::Console> Console, const std::vector<s
static bool ItemHandler(std::shared_ptr<Ship::Console> Console, const std::vector<std::string>& args) { static bool ItemHandler(std::shared_ptr<Ship::Console> Console, const std::vector<std::string>& args) {
if (args.size() != 3) { if (args.size() != 3) {
SohImGui::console->SendErrorMessage("[SOH] Unexpected arguments passed"); SohImGui::GetConsole()->SendErrorMessage("[SOH] Unexpected arguments passed");
return CMD_FAILED; return CMD_FAILED;
} }
@ -290,7 +290,7 @@ static bool ItemHandler(std::shared_ptr<Ship::Console> Console, const std::vecto
static bool EntranceHandler(std::shared_ptr<Ship::Console> Console, const std::vector<std::string>& args) { static bool EntranceHandler(std::shared_ptr<Ship::Console> Console, const std::vector<std::string>& args) {
if (args.size() != 2) { if (args.size() != 2) {
SohImGui::console->SendErrorMessage("[SOH] Unexpected arguments passed"); SohImGui::GetConsole()->SendErrorMessage("[SOH] Unexpected arguments passed");
return CMD_FAILED; return CMD_FAILED;
} }
@ -299,7 +299,7 @@ static bool EntranceHandler(std::shared_ptr<Ship::Console> Console, const std::v
try { try {
entrance = std::stoi(args[1], nullptr, 16); entrance = std::stoi(args[1], nullptr, 16);
} catch (std::invalid_argument const& ex) { } catch (std::invalid_argument const& ex) {
SohImGui::console->SendErrorMessage("[SOH] Entrance value must be a Hex number."); SohImGui::GetConsole()->SendErrorMessage("[SOH] Entrance value must be a Hex number.");
return CMD_FAILED; return CMD_FAILED;
} }
@ -319,7 +319,7 @@ static bool VoidHandler(std::shared_ptr<Ship::Console> Console, const std::vecto
gGlobalCtx->fadeTransition = 2; gGlobalCtx->fadeTransition = 2;
gSaveContext.nextTransition = 2; gSaveContext.nextTransition = 2;
} else { } else {
SohImGui::console->SendErrorMessage("gGlobalCtx == nullptr"); SohImGui::GetConsole()->SendErrorMessage("gGlobalCtx == nullptr");
return CMD_FAILED; return CMD_FAILED;
} }
return CMD_SUCCESS; return CMD_SUCCESS;
@ -332,7 +332,7 @@ static bool ReloadHandler(std::shared_ptr<Ship::Console> Console, const std::vec
gGlobalCtx->fadeTransition = 11; gGlobalCtx->fadeTransition = 11;
gSaveContext.nextTransition = 11; gSaveContext.nextTransition = 11;
} else { } else {
SohImGui::console->SendErrorMessage("gGlobalCtx == nullptr"); SohImGui::GetConsole()->SendErrorMessage("gGlobalCtx == nullptr");
return CMD_FAILED; return CMD_FAILED;
} }
return CMD_SUCCESS; return CMD_SUCCESS;
@ -345,11 +345,11 @@ static bool FWHandler(std::shared_ptr<Ship::Console> Console, const std::vector<
gGlobalCtx->nextEntranceIndex = gSaveContext.respawn[RESPAWN_MODE_TOP].entranceIndex; gGlobalCtx->nextEntranceIndex = gSaveContext.respawn[RESPAWN_MODE_TOP].entranceIndex;
gGlobalCtx->fadeTransition = 5; gGlobalCtx->fadeTransition = 5;
} else { } else {
SohImGui::console->SendErrorMessage("Farore's wind not set!"); SohImGui::GetConsole()->SendErrorMessage("Farore's wind not set!");
} }
} }
else { else {
SohImGui::console->SendErrorMessage("gGlobalCtx == nullptr"); SohImGui::GetConsole()->SendErrorMessage("gGlobalCtx == nullptr");
return CMD_FAILED; return CMD_FAILED;
} }
@ -361,7 +361,7 @@ static bool FileSelectHandler(std::shared_ptr<Ship::Console> Console, const std:
SET_NEXT_GAMESTATE(&gGlobalCtx->state, FileChoose_Init, FileChooseContext); SET_NEXT_GAMESTATE(&gGlobalCtx->state, FileChoose_Init, FileChooseContext);
gGlobalCtx->state.running = 0; gGlobalCtx->state.running = 0;
} else { } else {
SohImGui::console->SendErrorMessage("gGlobalCtx == nullptr"); SohImGui::GetConsole()->SendErrorMessage("gGlobalCtx == nullptr");
return CMD_FAILED; return CMD_FAILED;
} }
return CMD_SUCCESS; return CMD_SUCCESS;
@ -378,10 +378,10 @@ static bool SaveStateHandler(std::shared_ptr<Ship::Console> Console, const std::
switch (rtn) { switch (rtn) {
case SaveStateReturn::SUCCESS: case SaveStateReturn::SUCCESS:
SohImGui::console->SendInfoMessage("[SOH] Saved state to slot %u", slot); SohImGui::GetConsole()->SendInfoMessage("[SOH] Saved state to slot %u", slot);
return CMD_SUCCESS; return CMD_SUCCESS;
case SaveStateReturn::FAIL_WRONG_GAMESTATE: case SaveStateReturn::FAIL_WRONG_GAMESTATE:
SohImGui::console->SendErrorMessage("[SOH] Can not save a state outside of \"GamePlay\""); SohImGui::GetConsole()->SendErrorMessage("[SOH] Can not save a state outside of \"GamePlay\"");
return CMD_FAILED; return CMD_FAILED;
} }
} }
@ -392,16 +392,16 @@ static bool LoadStateHandler(std::shared_ptr<Ship::Console> Console, const std::
switch (rtn) { switch (rtn) {
case SaveStateReturn::SUCCESS: case SaveStateReturn::SUCCESS:
SohImGui::console->SendInfoMessage("[SOH] Loaded state from slot (%u)", slot); SohImGui::GetConsole()->SendInfoMessage("[SOH] Loaded state from slot (%u)", slot);
return CMD_SUCCESS; return CMD_SUCCESS;
case SaveStateReturn::FAIL_INVALID_SLOT: case SaveStateReturn::FAIL_INVALID_SLOT:
SohImGui::console->SendErrorMessage("[SOH] Invalid State Slot Number (%u)", slot); SohImGui::GetConsole()->SendErrorMessage("[SOH] Invalid State Slot Number (%u)", slot);
return CMD_FAILED; return CMD_FAILED;
case SaveStateReturn::FAIL_STATE_EMPTY: case SaveStateReturn::FAIL_STATE_EMPTY:
SohImGui::console->SendErrorMessage("[SOH] State Slot (%u) is empty", slot); SohImGui::GetConsole()->SendErrorMessage("[SOH] State Slot (%u) is empty", slot);
return CMD_FAILED; return CMD_FAILED;
case SaveStateReturn::FAIL_WRONG_GAMESTATE: case SaveStateReturn::FAIL_WRONG_GAMESTATE:
SohImGui::console->SendErrorMessage("[SOH] Can not load a state outside of \"GamePlay\""); SohImGui::GetConsole()->SendErrorMessage("[SOH] Can not load a state outside of \"GamePlay\"");
return CMD_FAILED; return CMD_FAILED;
} }
@ -409,7 +409,7 @@ static bool LoadStateHandler(std::shared_ptr<Ship::Console> Console, const std::
static bool StateSlotSelectHandler(std::shared_ptr<Ship::Console> Console, const std::vector<std::string>& args) { static bool StateSlotSelectHandler(std::shared_ptr<Ship::Console> Console, const std::vector<std::string>& args) {
if (args.size() != 2) { if (args.size() != 2) {
SohImGui::console->SendErrorMessage("[SOH] Unexpected arguments passed"); SohImGui::GetConsole()->SendErrorMessage("[SOH] Unexpected arguments passed");
return CMD_FAILED; return CMD_FAILED;
} }
int slot; int slot;
@ -417,17 +417,17 @@ static bool StateSlotSelectHandler(std::shared_ptr<Ship::Console> Console, const
try { try {
slot = std::stoi(args[1], nullptr, 10); slot = std::stoi(args[1], nullptr, 10);
} catch (std::invalid_argument const& ex) { } catch (std::invalid_argument const& ex) {
SohImGui::console->SendErrorMessage("[SOH] SaveState slot value must be a number."); SohImGui::GetConsole()->SendErrorMessage("[SOH] SaveState slot value must be a number.");
return CMD_FAILED; return CMD_FAILED;
} }
if (slot < 0) { if (slot < 0) {
SohImGui::console->SendErrorMessage("[SOH] Invalid slot passed. Slot must be between 0 and 2"); SohImGui::GetConsole()->SendErrorMessage("[SOH] Invalid slot passed. Slot must be between 0 and 2");
return CMD_FAILED; return CMD_FAILED;
} }
OTRGlobals::Instance->gSaveStateMgr->SetCurrentSlot(slot); OTRGlobals::Instance->gSaveStateMgr->SetCurrentSlot(slot);
SohImGui::console->SendInfoMessage("[SOH] Slot %u selected", SohImGui::GetConsole()->SendInfoMessage("[SOH] Slot %u selected",
OTRGlobals::Instance->gSaveStateMgr->GetCurrentSlot()); OTRGlobals::Instance->gSaveStateMgr->GetCurrentSlot());
return CMD_SUCCESS; return CMD_SUCCESS;
} }
@ -488,7 +488,7 @@ static bool SetCVarHandler(std::shared_ptr<Ship::Console> Console, const std::ve
CVar_Save(); CVar_Save();
//SohImGui::console->SendInfoMessage("[SOH] Updated player position to [ %.2f, %.2f, %.2f ]", pos.x, pos.y, pos.z); //SohImGui::GetConsole()->SendInfoMessage("[SOH] Updated player position to [ %.2f, %.2f, %.2f ]", pos.x, pos.y, pos.z);
return CMD_SUCCESS; return CMD_SUCCESS;
} }
@ -502,17 +502,17 @@ static bool GetCVarHandler(std::shared_ptr<Ship::Console> Console, const std::ve
if (cvar != nullptr) if (cvar != nullptr)
{ {
if (cvar->type == CVarType::S32) if (cvar->type == CVarType::S32)
SohImGui::console->SendInfoMessage("[SOH] Variable %s is %i", args[1].c_str(), cvar->value.valueS32); SohImGui::GetConsole()->SendInfoMessage("[SOH] Variable %s is %i", args[1].c_str(), cvar->value.valueS32);
else if (cvar->type == CVarType::Float) else if (cvar->type == CVarType::Float)
SohImGui::console->SendInfoMessage("[SOH] Variable %s is %f", args[1].c_str(), cvar->value.valueFloat); SohImGui::GetConsole()->SendInfoMessage("[SOH] Variable %s is %f", args[1].c_str(), cvar->value.valueFloat);
else if (cvar->type == CVarType::String) else if (cvar->type == CVarType::String)
SohImGui::console->SendInfoMessage("[SOH] Variable %s is %s", args[1].c_str(), cvar->value.valueStr); SohImGui::GetConsole()->SendInfoMessage("[SOH] Variable %s is %s", args[1].c_str(), cvar->value.valueStr);
else if (cvar->type == CVarType::RGBA) else if (cvar->type == CVarType::RGBA)
SohImGui::console->SendInfoMessage("[SOH] Variable %s is %08X", args[1].c_str(), cvar->value.valueRGBA); SohImGui::GetConsole()->SendInfoMessage("[SOH] Variable %s is %08X", args[1].c_str(), cvar->value.valueRGBA);
} }
else else
{ {
SohImGui::console->SendInfoMessage("[SOH] Could not find variable %s", args[1].c_str()); SohImGui::GetConsole()->SendInfoMessage("[SOH] Could not find variable %s", args[1].c_str());
} }

View File

@ -1,13 +1,13 @@
#include "actorViewer.h" #include "actorViewer.h"
#include "../../util.h" #include "../../util.h"
#include "../libultraship/ImGuiImpl.h" #include "../../UIWidgets.hpp"
#include "ImGuiHelpers.h" #include <libultraship/ImGuiImpl.h>
#include <array> #include <array>
#include <bit> #include <bit>
#include <map> #include <map>
#include <string> #include <string>
#include <Cvar.h> #include <libultraship/Cvar.h>
extern "C" { extern "C" {
#include <z64.h> #include <z64.h>
@ -632,7 +632,7 @@ void DrawActorViewer(bool& open) {
if (display.category == ACTORCAT_BOSS || display.category == ACTORCAT_ENEMY) { if (display.category == ACTORCAT_BOSS || display.category == ACTORCAT_ENEMY) {
ImGui::InputScalar("Enemy Health", ImGuiDataType_U8, &display.colChkInfo.health); ImGui::InputScalar("Enemy Health", ImGuiDataType_U8, &display.colChkInfo.health);
InsertHelpHoverText("Some actors might not use this!"); UIWidgets::InsertHelpHoverText("Some actors might not use this!");
} }
if (ImGui::Button("Refresh")) { if (ImGui::Button("Refresh")) {
@ -667,7 +667,7 @@ void DrawActorViewer(bool& open) {
rm = TARGET; rm = TARGET;
} }
} }
InsertHelpHoverText("Grabs actor with target arrow above it. You might need C-Up for enemies"); UIWidgets::InsertHelpHoverText("Grabs actor with target arrow above it. You might need C-Up for enemies");
if (ImGui::Button("Fetch from Held")) { if (ImGui::Button("Fetch from Held")) {
Player* player = GET_PLAYER(gGlobalCtx); Player* player = GET_PLAYER(gGlobalCtx);
fetch = player->heldActor; fetch = player->heldActor;
@ -678,7 +678,7 @@ void DrawActorViewer(bool& open) {
rm = HELD; rm = HELD;
} }
} }
InsertHelpHoverText("Grabs actor that Link is holding"); UIWidgets::InsertHelpHoverText("Grabs actor that Link is holding");
if (ImGui::Button("Fetch from Interaction")) { if (ImGui::Button("Fetch from Interaction")) {
Player* player = GET_PLAYER(gGlobalCtx); Player* player = GET_PLAYER(gGlobalCtx);
fetch = player->interactRangeActor; fetch = player->interactRangeActor;
@ -689,7 +689,7 @@ void DrawActorViewer(bool& open) {
rm = INTERACT; rm = INTERACT;
} }
} }
InsertHelpHoverText("Grabs actor from \"interaction range\""); UIWidgets::InsertHelpHoverText("Grabs actor from \"interaction range\"");
ImGui::TreePop(); ImGui::TreePop();
} }
@ -776,4 +776,4 @@ void DrawActorViewer(bool& open) {
void InitActorViewer() { void InitActorViewer() {
SohImGui::AddWindow("Developer Tools", "Actor Viewer", DrawActorViewer); SohImGui::AddWindow("Developer Tools", "Actor Viewer", DrawActorViewer);
} }

View File

@ -1,12 +1,12 @@
#include "colViewer.h" #include "colViewer.h"
#include "../libultraship/ImGuiImpl.h" #include <libultraship/ImGuiImpl.h>
#include "ImGuiHelpers.h"
#include "../../frame_interpolation.h" #include "../../frame_interpolation.h"
#include "../../UIWidgets.hpp"
#include <vector> #include <vector>
#include <string> #include <string>
#include <cmath> #include <cmath>
#include <Cvar.h> #include <libultraship/Cvar.h>
extern "C" { extern "C" {
#include <z64.h> #include <z64.h>
@ -62,42 +62,42 @@ void DrawColViewerWindow(bool& open) {
ImGui::End(); ImGui::End();
return; return;
} }
SohImGui::EnhancementCheckbox("Enabled", "gColViewerEnabled"); UIWidgets::EnhancementCheckbox("Enabled", "gColViewerEnabled");
SohImGui::EnhancementCombo("Scene", "gColViewerScene", ColRenderSettingNames); UIWidgets::EnhancementCombo("Scene", "gColViewerScene", ColRenderSettingNames);
SohImGui::EnhancementCombo("Bg Actors", "gColViewerBgActors", ColRenderSettingNames); UIWidgets::EnhancementCombo("Bg Actors", "gColViewerBgActors", ColRenderSettingNames);
SohImGui::EnhancementCombo("Col Check", "gColViewerColCheck", ColRenderSettingNames); UIWidgets::EnhancementCombo("Col Check", "gColViewerColCheck", ColRenderSettingNames);
SohImGui::EnhancementCombo("Waterbox", "gColViewerWaterbox", ColRenderSettingNames); UIWidgets::EnhancementCombo("Waterbox", "gColViewerWaterbox", ColRenderSettingNames);
SohImGui::EnhancementCheckbox("Apply as decal", "gColViewerDecal"); UIWidgets::EnhancementCheckbox("Apply as decal", "gColViewerDecal");
InsertHelpHoverText("Applies the collision as a decal display. This can be useful if there is z-fighting occuring " UIWidgets::InsertHelpHoverText("Applies the collision as a decal display. This can be useful if there is z-fighting occuring "
"with the scene geometry, but can cause other artifacts."); "with the scene geometry, but can cause other artifacts.");
SohImGui::EnhancementCheckbox("Shaded", "gColViewerShaded"); UIWidgets::EnhancementCheckbox("Shaded", "gColViewerShaded");
InsertHelpHoverText("Applies the scene's shading to the collision display."); UIWidgets::InsertHelpHoverText("Applies the scene's shading to the collision display.");
// This has to be duplicated in both code paths due to the nature of ImGui::IsItemHovered() // This has to be duplicated in both code paths due to the nature of ImGui::IsItemHovered()
const std::string colorHelpText = "View and change the colors used for collision display."; const std::string colorHelpText = "View and change the colors used for collision display.";
if (ImGui::TreeNode("Colors")) { if (ImGui::TreeNode("Colors")) {
InsertHelpHoverText(colorHelpText); UIWidgets::InsertHelpHoverText(colorHelpText);
SohImGui::EnhancementColor("Normal", "gColViewerColorNormal", scene_col, ImVec4(255, 255, 255, 255), false); UIWidgets::EnhancementColor("Normal", "gColViewerColorNormal", scene_col, ImVec4(255, 255, 255, 255), false);
SohImGui::EnhancementColor("Hookshot", "gColViewerColorHookshot", hookshot_col, ImVec4(128, 128, 255, 255), UIWidgets::EnhancementColor("Hookshot", "gColViewerColorHookshot", hookshot_col, ImVec4(128, 128, 255, 255),
false); false);
SohImGui::EnhancementColor("Entrance", "gColViewerColorEntrance", entrance_col, ImVec4(0, 255, 0, 255), false); UIWidgets::EnhancementColor("Entrance", "gColViewerColorEntrance", entrance_col, ImVec4(0, 255, 0, 255), false);
SohImGui::EnhancementColor("Special Surface (Grass/Sand/Etc)", "gColViewerColorSpecialSurface", UIWidgets::EnhancementColor("Special Surface (Grass/Sand/Etc)", "gColViewerColorSpecialSurface",
specialSurface_col, ImVec4(192, 255, 192, 255), false); specialSurface_col, ImVec4(192, 255, 192, 255), false);
SohImGui::EnhancementColor("Interactable (Vines/Crawlspace/Etc)", "gColViewerColorInteractable", UIWidgets::EnhancementColor("Interactable (Vines/Crawlspace/Etc)", "gColViewerColorInteractable",
interactable_col, ImVec4(192, 0, 192, 255), false); interactable_col, ImVec4(192, 0, 192, 255), false);
SohImGui::EnhancementColor("Slope", "gColViewerColorSlope", slope_col, ImVec4(255, 255, 128, 255), false); UIWidgets::EnhancementColor("Slope", "gColViewerColorSlope", slope_col, ImVec4(255, 255, 128, 255), false);
SohImGui::EnhancementColor("Void", "gColViewerColorVoid", void_col, ImVec4(255, 0, 0, 255), false); UIWidgets::EnhancementColor("Void", "gColViewerColorVoid", void_col, ImVec4(255, 0, 0, 255), false);
SohImGui::EnhancementColor("OC", "gColViewerColorOC", oc_col, ImVec4(255, 255, 255, 255), false); UIWidgets::EnhancementColor("OC", "gColViewerColorOC", oc_col, ImVec4(255, 255, 255, 255), false);
SohImGui::EnhancementColor("AC", "gColViewerColorAC", ac_col, ImVec4(0, 0, 255, 255), false); UIWidgets::EnhancementColor("AC", "gColViewerColorAC", ac_col, ImVec4(0, 0, 255, 255), false);
SohImGui::EnhancementColor("AT", "gColViewerColorAT", at_col, ImVec4(255, 0, 0, 255), false); UIWidgets::EnhancementColor("AT", "gColViewerColorAT", at_col, ImVec4(255, 0, 0, 255), false);
SohImGui::EnhancementColor("Waterbox", "gColViewerColorWaterbox", waterbox_col, ImVec4(0, 0, 255, 255), false); UIWidgets::EnhancementColor("Waterbox", "gColViewerColorWaterbox", waterbox_col, ImVec4(0, 0, 255, 255), false);
ImGui::TreePop(); ImGui::TreePop();
} else { } else {
InsertHelpHoverText(colorHelpText); UIWidgets::InsertHelpHoverText(colorHelpText);
} }
ImGui::End(); ImGui::End();

View File

@ -1,14 +1,13 @@
#include "debugSaveEditor.h" #include "debugSaveEditor.h"
#include "../../util.h" #include "../../util.h"
#include "../../OTRGlobals.h" #include <libultraship/ImGuiImpl.h>
#include "../libultraship/ImGuiImpl.h" #include "../../UIWidgets.hpp"
#include "ImGuiHelpers.h"
#include <array> #include <array>
#include <bit> #include <bit>
#include <map> #include <map>
#include <string> #include <string>
#include <Cvar.h> #include <libultraship/Cvar.h>
extern "C" { extern "C" {
#include <z64.h> #include <z64.h>
@ -311,7 +310,7 @@ void DrawInfoTab() {
ImGui::PushItemWidth(ImGui::GetFontSize() * 6); ImGui::PushItemWidth(ImGui::GetFontSize() * 6);
ImGui::Text("Name: %s", name.c_str()); ImGui::Text("Name: %s", name.c_str());
InsertHelpHoverText("Player Name"); UIWidgets::InsertHelpHoverText("Player Name");
std::string nameID; std::string nameID;
for (int i = 0; i < 8; i++) { for (int i = 0; i < 8; i++) {
nameID = z2ASCII(i); nameID = z2ASCII(i);
@ -328,7 +327,7 @@ void DrawInfoTab() {
if (ImGui::IsItemDeactivated()) { if (ImGui::IsItemDeactivated()) {
gSaveContext.healthCapacity = healthIntermediary; gSaveContext.healthCapacity = healthIntermediary;
} }
InsertHelpHoverText("Maximum health. 16 units per full heart"); UIWidgets::InsertHelpHoverText("Maximum health. 16 units per full heart");
if (gSaveContext.health > gSaveContext.healthCapacity) { if (gSaveContext.health > gSaveContext.healthCapacity) {
gSaveContext.health = gSaveContext.healthCapacity; // Clamp health to new max gSaveContext.health = gSaveContext.healthCapacity; // Clamp health to new max
} }
@ -337,7 +336,7 @@ void DrawInfoTab() {
const uint16_t healthMax = gSaveContext.healthCapacity; const uint16_t healthMax = gSaveContext.healthCapacity;
ImGui::SetNextItemWidth(ImGui::GetFontSize() * 15); ImGui::SetNextItemWidth(ImGui::GetFontSize() * 15);
ImGui::SliderScalar("Health", ImGuiDataType_S16, &gSaveContext.health, &healthMin, &healthMax); ImGui::SliderScalar("Health", ImGuiDataType_S16, &gSaveContext.health, &healthMin, &healthMax);
InsertHelpHoverText("Current health. 16 units per full heart"); UIWidgets::InsertHelpHoverText("Current health. 16 units per full heart");
bool doubleDefense = gSaveContext.doubleDefense != 0; bool doubleDefense = gSaveContext.doubleDefense != 0;
if (ImGui::Checkbox("Double Defense", &doubleDefense)) { if (ImGui::Checkbox("Double Defense", &doubleDefense)) {
@ -345,7 +344,7 @@ void DrawInfoTab() {
gSaveContext.inventory.defenseHearts = gSaveContext.inventory.defenseHearts =
gSaveContext.doubleDefense ? 20 : 0; // Set to get the border drawn in the UI gSaveContext.doubleDefense ? 20 : 0; // Set to get the border drawn in the UI
} }
InsertHelpHoverText("Is double defense unlocked?"); UIWidgets::InsertHelpHoverText("Is double defense unlocked?");
std::string magicName; std::string magicName;
if (gSaveContext.magicLevel == 2) { if (gSaveContext.magicLevel == 2) {
@ -375,7 +374,7 @@ void DrawInfoTab() {
ImGui::EndCombo(); ImGui::EndCombo();
} }
InsertHelpHoverText("Current magic level"); UIWidgets::InsertHelpHoverText("Current magic level");
gSaveContext.unk_13F4 = gSaveContext.magicLevel * 0x30; // Set to get the bar drawn in the UI gSaveContext.unk_13F4 = gSaveContext.magicLevel * 0x30; // Set to get the bar drawn in the UI
if (gSaveContext.magic > gSaveContext.unk_13F4) { if (gSaveContext.magic > gSaveContext.unk_13F4) {
gSaveContext.magic = gSaveContext.unk_13F4; // Clamp magic to new max gSaveContext.magic = gSaveContext.unk_13F4; // Clamp magic to new max
@ -385,16 +384,16 @@ void DrawInfoTab() {
const uint8_t magicMax = gSaveContext.unk_13F4; const uint8_t magicMax = gSaveContext.unk_13F4;
ImGui::SetNextItemWidth(ImGui::GetFontSize() * 15); ImGui::SetNextItemWidth(ImGui::GetFontSize() * 15);
ImGui::SliderScalar("Magic", ImGuiDataType_S8, &gSaveContext.magic, &magicMin, &magicMax); ImGui::SliderScalar("Magic", ImGuiDataType_S8, &gSaveContext.magic, &magicMin, &magicMax);
InsertHelpHoverText("Current magic. 48 units per magic level"); UIWidgets::InsertHelpHoverText("Current magic. 48 units per magic level");
ImGui::InputScalar("Rupees", ImGuiDataType_S16, &gSaveContext.rupees); ImGui::InputScalar("Rupees", ImGuiDataType_S16, &gSaveContext.rupees);
InsertHelpHoverText("Current rupees"); UIWidgets::InsertHelpHoverText("Current rupees");
const uint16_t dayTimeMin = 0; const uint16_t dayTimeMin = 0;
const uint16_t dayTimeMax = 0xFFFF; const uint16_t dayTimeMax = 0xFFFF;
ImGui::SetNextItemWidth(ImGui::GetFontSize() * 15); ImGui::SetNextItemWidth(ImGui::GetFontSize() * 15);
ImGui::SliderScalar("Time", ImGuiDataType_U16, &gSaveContext.dayTime, &dayTimeMin, &dayTimeMax); ImGui::SliderScalar("Time", ImGuiDataType_U16, &gSaveContext.dayTime, &dayTimeMin, &dayTimeMax);
InsertHelpHoverText("Time of day"); UIWidgets::InsertHelpHoverText("Time of day");
if (ImGui::Button("Dawn")) { if (ImGui::Button("Dawn")) {
gSaveContext.dayTime = 0x4000; gSaveContext.dayTime = 0x4000;
} }
@ -412,43 +411,43 @@ void DrawInfoTab() {
} }
ImGui::InputScalar("Total Days", ImGuiDataType_S32, &gSaveContext.totalDays); ImGui::InputScalar("Total Days", ImGuiDataType_S32, &gSaveContext.totalDays);
InsertHelpHoverText("Total number of days elapsed since the start of the game"); UIWidgets::InsertHelpHoverText("Total number of days elapsed since the start of the game");
ImGui::InputScalar("Deaths", ImGuiDataType_U16, &gSaveContext.deaths); ImGui::InputScalar("Deaths", ImGuiDataType_U16, &gSaveContext.deaths);
InsertHelpHoverText("Total number of deaths"); UIWidgets::InsertHelpHoverText("Total number of deaths");
bool bgsFlag = gSaveContext.bgsFlag != 0; bool bgsFlag = gSaveContext.bgsFlag != 0;
if (ImGui::Checkbox("Has BGS", &bgsFlag)) { if (ImGui::Checkbox("Has BGS", &bgsFlag)) {
gSaveContext.bgsFlag = bgsFlag; gSaveContext.bgsFlag = bgsFlag;
} }
InsertHelpHoverText("Is Biggoron sword unlocked? Replaces Giant's knife"); UIWidgets::InsertHelpHoverText("Is Biggoron sword unlocked? Replaces Giant's knife");
ImGui::InputScalar("Sword Health", ImGuiDataType_U16, &gSaveContext.swordHealth); ImGui::InputScalar("Sword Health", ImGuiDataType_U16, &gSaveContext.swordHealth);
InsertHelpHoverText("Giant's knife health. Default is 8. Must be >0 for Biggoron sword to work"); UIWidgets::InsertHelpHoverText("Giant's knife health. Default is 8. Must be >0 for Biggoron sword to work");
ImGui::InputScalar("Bgs Day Count", ImGuiDataType_S32, &gSaveContext.bgsDayCount); ImGui::InputScalar("Bgs Day Count", ImGuiDataType_S32, &gSaveContext.bgsDayCount);
InsertHelpHoverText("Total number of days elapsed since giving Biggoron the claim check"); UIWidgets::InsertHelpHoverText("Total number of days elapsed since giving Biggoron the claim check");
ImGui::InputScalar("Entrance Index", ImGuiDataType_S32, &gSaveContext.entranceIndex); ImGui::InputScalar("Entrance Index", ImGuiDataType_S32, &gSaveContext.entranceIndex);
InsertHelpHoverText("From which entrance did Link arrive?"); UIWidgets::InsertHelpHoverText("From which entrance did Link arrive?");
ImGui::InputScalar("Cutscene Index", ImGuiDataType_S32, &gSaveContext.cutsceneIndex); ImGui::InputScalar("Cutscene Index", ImGuiDataType_S32, &gSaveContext.cutsceneIndex);
InsertHelpHoverText("Which cutscene is this?"); UIWidgets::InsertHelpHoverText("Which cutscene is this?");
ImGui::InputScalar("Navi Timer", ImGuiDataType_U16, &gSaveContext.naviTimer); ImGui::InputScalar("Navi Timer", ImGuiDataType_U16, &gSaveContext.naviTimer);
InsertHelpHoverText("Navi wants to talk at 600 units, decides not to at 3000."); UIWidgets::InsertHelpHoverText("Navi wants to talk at 600 units, decides not to at 3000.");
ImGui::InputScalar("Timer 1 State", ImGuiDataType_S16, &gSaveContext.timer1State); ImGui::InputScalar("Timer 1 State", ImGuiDataType_S16, &gSaveContext.timer1State);
InsertHelpHoverText("Heat timer, race timer, etc. Has white font"); UIWidgets::InsertHelpHoverText("Heat timer, race timer, etc. Has white font");
ImGui::InputScalar("Timer 1 Value", ImGuiDataType_S16, &gSaveContext.timer1Value, &one, NULL); ImGui::InputScalar("Timer 1 Value", ImGuiDataType_S16, &gSaveContext.timer1Value, &one, NULL);
InsertHelpHoverText("Time, in seconds"); UIWidgets::InsertHelpHoverText("Time, in seconds");
ImGui::InputScalar("Timer 2 State", ImGuiDataType_S16, &gSaveContext.timer2State); ImGui::InputScalar("Timer 2 State", ImGuiDataType_S16, &gSaveContext.timer2State);
InsertHelpHoverText("Trade timer, Ganon collapse timer, etc. Has yellow font"); UIWidgets::InsertHelpHoverText("Trade timer, Ganon collapse timer, etc. Has yellow font");
ImGui::InputScalar("Timer 2 Value", ImGuiDataType_S16, &gSaveContext.timer2Value, &one, NULL); ImGui::InputScalar("Timer 2 Value", ImGuiDataType_S16, &gSaveContext.timer2Value, &one, NULL);
InsertHelpHoverText("Time, in seconds"); UIWidgets::InsertHelpHoverText("Time, in seconds");
const char* audioName; const char* audioName;
switch (gSaveContext.audioSetting) { switch (gSaveContext.audioSetting) {
@ -483,13 +482,13 @@ void DrawInfoTab() {
ImGui::EndCombo(); ImGui::EndCombo();
} }
InsertHelpHoverText("Sound setting"); UIWidgets::InsertHelpHoverText("Sound setting");
bool n64DDFlag = gSaveContext.n64ddFlag != 0; bool n64DDFlag = gSaveContext.n64ddFlag != 0;
if (ImGui::Checkbox("64 DD file?", &n64DDFlag)) { if (ImGui::Checkbox("64 DD file?", &n64DDFlag)) {
gSaveContext.n64ddFlag = n64DDFlag; gSaveContext.n64ddFlag = n64DDFlag;
} }
InsertHelpHoverText("WARNING! If you save, your file may be locked! Use caution!"); UIWidgets::InsertHelpHoverText("WARNING! If you save, your file may be locked! Use caution!");
if (ImGui::BeginCombo("Z Target Mode", gSaveContext.zTargetSetting ? "Hold" : "Switch")) { if (ImGui::BeginCombo("Z Target Mode", gSaveContext.zTargetSetting ? "Hold" : "Switch")) {
if (ImGui::Selectable("Switch")) { if (ImGui::Selectable("Switch")) {
@ -500,7 +499,7 @@ void DrawInfoTab() {
} }
ImGui::EndCombo(); ImGui::EndCombo();
} }
InsertHelpHoverText("Z-Targeting behavior"); UIWidgets::InsertHelpHoverText("Z-Targeting behavior");
ImGui::PushItemWidth(ImGui::GetFontSize() * 10); ImGui::PushItemWidth(ImGui::GetFontSize() * 10);
@ -552,7 +551,7 @@ void DrawInventoryTab() {
static bool restrictToValid = true; static bool restrictToValid = true;
ImGui::Checkbox("Restrict to valid items", &restrictToValid); ImGui::Checkbox("Restrict to valid items", &restrictToValid);
InsertHelpHoverText("Restricts items and ammo to only what is possible to legally acquire in-game"); UIWidgets::InsertHelpHoverText("Restricts items and ammo to only what is possible to legally acquire in-game");
for (int32_t y = 0; y < 4; y++) { for (int32_t y = 0; y < 4; y++) {
for (int32_t x = 0; x < 6; x++) { for (int32_t x = 0; x < 6; x++) {
@ -594,7 +593,7 @@ void DrawInventoryTab() {
} }
ImGui::CloseCurrentPopup(); ImGui::CloseCurrentPopup();
} }
SetLastItemHoverText("None"); UIWidgets::SetLastItemHoverText("None");
std::vector<ItemMapEntry> possibleItems; std::vector<ItemMapEntry> possibleItems;
if (restrictToValid) { if (restrictToValid) {
@ -631,7 +630,7 @@ void DrawInventoryTab() {
} }
ImGui::CloseCurrentPopup(); ImGui::CloseCurrentPopup();
} }
SetLastItemHoverText(SohUtils::GetItemName(slotEntry.id)); UIWidgets::SetLastItemHoverText(SohUtils::GetItemName(slotEntry.id));
} }
ImGui::EndPopup(); ImGui::EndPopup();
@ -725,7 +724,7 @@ void DrawFlagsTab() {
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("Switch"); ImGui::Text("Switch");
InsertHelpHoverText("Permanently-saved switch flags"); UIWidgets::InsertHelpHoverText("Permanently-saved switch flags");
DrawFlagArray32("Switch", act->flags.swch); DrawFlagArray32("Switch", act->flags.swch);
}); });
@ -733,13 +732,13 @@ void DrawFlagsTab() {
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("Temp Switch"); ImGui::Text("Temp Switch");
InsertHelpHoverText("Temporary switch flags. Unset on scene transitions"); UIWidgets::InsertHelpHoverText("Temporary switch flags. Unset on scene transitions");
DrawFlagArray32("Temp Switch", act->flags.tempSwch); DrawFlagArray32("Temp Switch", act->flags.tempSwch);
}); });
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("Clear"); ImGui::Text("Clear");
InsertHelpHoverText("Permanently-saved room-clear flags"); UIWidgets::InsertHelpHoverText("Permanently-saved room-clear flags");
DrawFlagArray32("Clear", act->flags.clear); DrawFlagArray32("Clear", act->flags.clear);
}); });
@ -747,13 +746,13 @@ void DrawFlagsTab() {
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("Temp Clear"); ImGui::Text("Temp Clear");
InsertHelpHoverText("Temporary room-clear flags. Unset on scene transitions"); UIWidgets::InsertHelpHoverText("Temporary room-clear flags. Unset on scene transitions");
DrawFlagArray32("Temp Clear", act->flags.tempClear); DrawFlagArray32("Temp Clear", act->flags.tempClear);
}); });
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("Collect"); ImGui::Text("Collect");
InsertHelpHoverText("Permanently-saved collect flags"); UIWidgets::InsertHelpHoverText("Permanently-saved collect flags");
DrawFlagArray32("Collect", act->flags.collect); DrawFlagArray32("Collect", act->flags.collect);
}); });
@ -761,13 +760,13 @@ void DrawFlagsTab() {
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("Temp Collect"); ImGui::Text("Temp Collect");
InsertHelpHoverText("Temporary collect flags. Unset on scene transitions"); UIWidgets::InsertHelpHoverText("Temporary collect flags. Unset on scene transitions");
DrawFlagArray32("Temp Collect", act->flags.tempCollect); DrawFlagArray32("Temp Collect", act->flags.tempCollect);
}); });
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("Chest"); ImGui::Text("Chest");
InsertHelpHoverText("Permanently-saved chest flags"); UIWidgets::InsertHelpHoverText("Permanently-saved chest flags");
DrawFlagArray32("Chest", act->flags.chest); DrawFlagArray32("Chest", act->flags.chest);
}); });
@ -781,7 +780,7 @@ void DrawFlagsTab() {
act->flags.collect = gSaveContext.sceneFlags[gGlobalCtx->sceneNum].collect; act->flags.collect = gSaveContext.sceneFlags[gGlobalCtx->sceneNum].collect;
act->flags.chest = gSaveContext.sceneFlags[gGlobalCtx->sceneNum].chest; act->flags.chest = gSaveContext.sceneFlags[gGlobalCtx->sceneNum].chest;
} }
SetLastItemHoverText("Load flags from saved scene flags. Normally happens on scene load"); UIWidgets::SetLastItemHoverText("Load flags from saved scene flags. Normally happens on scene load");
if (ImGui::Button("Save Flags")) { if (ImGui::Button("Save Flags")) {
gSaveContext.sceneFlags[gGlobalCtx->sceneNum].swch = act->flags.swch; gSaveContext.sceneFlags[gGlobalCtx->sceneNum].swch = act->flags.swch;
@ -789,7 +788,7 @@ void DrawFlagsTab() {
gSaveContext.sceneFlags[gGlobalCtx->sceneNum].collect = act->flags.collect; gSaveContext.sceneFlags[gGlobalCtx->sceneNum].collect = act->flags.collect;
gSaveContext.sceneFlags[gGlobalCtx->sceneNum].chest = act->flags.chest; gSaveContext.sceneFlags[gGlobalCtx->sceneNum].chest = act->flags.chest;
} }
SetLastItemHoverText("Save current scene flags. Normally happens on scene exit"); UIWidgets::SetLastItemHoverText("Save current scene flags. Normally happens on scene exit");
ImGui::EndGroup(); ImGui::EndGroup();
} else { } else {
@ -819,12 +818,12 @@ void DrawFlagsTab() {
if (ImGui::Button("Current")) { if (ImGui::Button("Current")) {
selectedSceneFlagMap = gGlobalCtx->sceneNum; selectedSceneFlagMap = gGlobalCtx->sceneNum;
} }
SetLastItemHoverText("Open flags for current scene"); UIWidgets::SetLastItemHoverText("Open flags for current scene");
} }
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("Switch"); ImGui::Text("Switch");
InsertHelpHoverText("Switch flags"); UIWidgets::InsertHelpHoverText("Switch flags");
DrawFlagArray32("Switch", gSaveContext.sceneFlags[selectedSceneFlagMap].swch); DrawFlagArray32("Switch", gSaveContext.sceneFlags[selectedSceneFlagMap].swch);
}); });
@ -832,13 +831,13 @@ void DrawFlagsTab() {
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("Clear"); ImGui::Text("Clear");
InsertHelpHoverText("Room-clear flags"); UIWidgets::InsertHelpHoverText("Room-clear flags");
DrawFlagArray32("Clear", gSaveContext.sceneFlags[selectedSceneFlagMap].clear); DrawFlagArray32("Clear", gSaveContext.sceneFlags[selectedSceneFlagMap].clear);
}); });
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("Collect"); ImGui::Text("Collect");
InsertHelpHoverText("Collect flags"); UIWidgets::InsertHelpHoverText("Collect flags");
DrawFlagArray32("Collect", gSaveContext.sceneFlags[selectedSceneFlagMap].collect); DrawFlagArray32("Collect", gSaveContext.sceneFlags[selectedSceneFlagMap].collect);
}); });
@ -846,13 +845,13 @@ void DrawFlagsTab() {
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("Chest"); ImGui::Text("Chest");
InsertHelpHoverText("Chest flags"); UIWidgets::InsertHelpHoverText("Chest flags");
DrawFlagArray32("Chest", gSaveContext.sceneFlags[selectedSceneFlagMap].chest); DrawFlagArray32("Chest", gSaveContext.sceneFlags[selectedSceneFlagMap].chest);
}); });
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("Rooms"); ImGui::Text("Rooms");
InsertHelpHoverText("Flags for visted rooms"); UIWidgets::InsertHelpHoverText("Flags for visted rooms");
DrawFlagArray32("Rooms", gSaveContext.sceneFlags[selectedSceneFlagMap].rooms); DrawFlagArray32("Rooms", gSaveContext.sceneFlags[selectedSceneFlagMap].rooms);
}); });
@ -860,7 +859,7 @@ void DrawFlagsTab() {
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("Floors"); ImGui::Text("Floors");
InsertHelpHoverText("Flags for visted floors"); UIWidgets::InsertHelpHoverText("Flags for visted floors");
DrawFlagArray32("Floors", gSaveContext.sceneFlags[selectedSceneFlagMap].floors); DrawFlagArray32("Floors", gSaveContext.sceneFlags[selectedSceneFlagMap].floors);
}); });
@ -916,7 +915,7 @@ void DrawFlagsTab() {
if (!(gSaveContext.n64ddFlag && OTRGlobals::Instance->gRandomizer->GetRandoSettingValue(RSK_SHUFFLE_TOKENS))) { if (!(gSaveContext.n64ddFlag && OTRGlobals::Instance->gRandomizer->GetRandoSettingValue(RSK_SHUFFLE_TOKENS))) {
static bool keepGsCountUpdated = true; static bool keepGsCountUpdated = true;
ImGui::Checkbox("Keep GS Count Updated", &keepGsCountUpdated); ImGui::Checkbox("Keep GS Count Updated", &keepGsCountUpdated);
InsertHelpHoverText("Automatically adjust the number of gold skulltula tokens acquired based on set flags."); UIWidgets::InsertHelpHoverText("Automatically adjust the number of gold skulltula tokens acquired based on set flags.");
int32_t gsCount = 0; int32_t gsCount = 0;
if (keepGsCountUpdated) { if (keepGsCountUpdated) {
for (int32_t gsFlagIndex = 0; gsFlagIndex < 6; gsFlagIndex++) { for (int32_t gsFlagIndex = 0; gsFlagIndex < 6; gsFlagIndex++) {
@ -930,85 +929,85 @@ void DrawFlagsTab() {
if (ImGui::TreeNode("Event Check Inf Flags")) { if (ImGui::TreeNode("Event Check Inf Flags")) {
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("0"); ImGui::Text("0");
InsertHelpHoverText("Mostly Kokiri Forest related"); UIWidgets::InsertHelpHoverText("Mostly Kokiri Forest related");
DrawFlagArray16("eci0", gSaveContext.eventChkInf[0]); DrawFlagArray16("eci0", gSaveContext.eventChkInf[0]);
}); });
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("1"); ImGui::Text("1");
InsertHelpHoverText("Mostly Lon Lon Ranch related"); UIWidgets::InsertHelpHoverText("Mostly Lon Lon Ranch related");
DrawFlagArray16("eci1", gSaveContext.eventChkInf[1]); DrawFlagArray16("eci1", gSaveContext.eventChkInf[1]);
}); });
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("2"); ImGui::Text("2");
InsertHelpHoverText("Dodongo Related?"); UIWidgets::InsertHelpHoverText("Dodongo Related?");
DrawFlagArray16("eci2", gSaveContext.eventChkInf[2]); DrawFlagArray16("eci2", gSaveContext.eventChkInf[2]);
}); });
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("3"); ImGui::Text("3");
InsertHelpHoverText("Mostly Zora related"); UIWidgets::InsertHelpHoverText("Mostly Zora related");
DrawFlagArray16("eci3", gSaveContext.eventChkInf[3]); DrawFlagArray16("eci3", gSaveContext.eventChkInf[3]);
}); });
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("4"); ImGui::Text("4");
InsertHelpHoverText("Random"); UIWidgets::InsertHelpHoverText("Random");
DrawFlagArray16("eci4", gSaveContext.eventChkInf[4]); DrawFlagArray16("eci4", gSaveContext.eventChkInf[4]);
}); });
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("5"); ImGui::Text("5");
InsertHelpHoverText("Mostly song learning related"); UIWidgets::InsertHelpHoverText("Mostly song learning related");
DrawFlagArray16("eci5", gSaveContext.eventChkInf[5]); DrawFlagArray16("eci5", gSaveContext.eventChkInf[5]);
}); });
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("6"); ImGui::Text("6");
InsertHelpHoverText("Random"); UIWidgets::InsertHelpHoverText("Random");
DrawFlagArray16("eci6", gSaveContext.eventChkInf[6]); DrawFlagArray16("eci6", gSaveContext.eventChkInf[6]);
}); });
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("7"); ImGui::Text("7");
InsertHelpHoverText("Boss Battle related"); UIWidgets::InsertHelpHoverText("Boss Battle related");
DrawFlagArray16("eci7", gSaveContext.eventChkInf[7]); DrawFlagArray16("eci7", gSaveContext.eventChkInf[7]);
}); });
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("8"); ImGui::Text("8");
InsertHelpHoverText("Mask related?"); UIWidgets::InsertHelpHoverText("Mask related?");
DrawFlagArray16("eci8", gSaveContext.eventChkInf[8]); DrawFlagArray16("eci8", gSaveContext.eventChkInf[8]);
}); });
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("9"); ImGui::Text("9");
InsertHelpHoverText("Mostly carpenter related"); UIWidgets::InsertHelpHoverText("Mostly carpenter related");
DrawFlagArray16("eci9", gSaveContext.eventChkInf[9]); DrawFlagArray16("eci9", gSaveContext.eventChkInf[9]);
}); });
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("A"); ImGui::Text("A");
InsertHelpHoverText("First-time overworld entrance cs related"); UIWidgets::InsertHelpHoverText("First-time overworld entrance cs related");
DrawFlagArray16("eci10", gSaveContext.eventChkInf[10]); DrawFlagArray16("eci10", gSaveContext.eventChkInf[10]);
}); });
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("B"); ImGui::Text("B");
InsertHelpHoverText("First-time dungeon entrance cs/trial cs related"); UIWidgets::InsertHelpHoverText("First-time dungeon entrance cs/trial cs related");
DrawFlagArray16("eci11", gSaveContext.eventChkInf[11]); DrawFlagArray16("eci11", gSaveContext.eventChkInf[11]);
}); });
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("C"); ImGui::Text("C");
InsertHelpHoverText("Random"); UIWidgets::InsertHelpHoverText("Random");
DrawFlagArray16("eci12", gSaveContext.eventChkInf[12]); DrawFlagArray16("eci12", gSaveContext.eventChkInf[12]);
}); });
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("D"); ImGui::Text("D");
InsertHelpHoverText("Frog songs/GS rewards"); UIWidgets::InsertHelpHoverText("Frog songs/GS rewards");
DrawFlagArray16("eci13", gSaveContext.eventChkInf[13]); DrawFlagArray16("eci13", gSaveContext.eventChkInf[13]);
}); });
@ -1061,7 +1060,7 @@ void DrawUpgrade(const std::string& categoryName, int32_t categoryId, const std:
ImGui::EndCombo(); ImGui::EndCombo();
} }
ImGui::PopID(); ImGui::PopID();
SetLastItemHoverText(categoryName.c_str()); UIWidgets::SetLastItemHoverText(categoryName.c_str());
} }
// Draws a combo that lets you choose and upgrade value from a popup grid of icons // Draws a combo that lets you choose and upgrade value from a popup grid of icons
@ -1086,7 +1085,7 @@ void DrawUpgradeIcon(const std::string& categoryName, int32_t categoryId, const
} }
ImGui::PopStyleVar(); ImGui::PopStyleVar();
ImGui::PopStyleColor(); ImGui::PopStyleColor();
SetLastItemHoverText(categoryName.c_str()); UIWidgets::SetLastItemHoverText(categoryName.c_str());
ImGui::PushStyleVar(ImGuiStyleVar_ItemSpacing, ImVec2(0, 0)); ImGui::PushStyleVar(ImGuiStyleVar_ItemSpacing, ImVec2(0, 0));
if (ImGui::BeginPopup(upgradePopupPicker)) { if (ImGui::BeginPopup(upgradePopupPicker)) {
@ -1100,7 +1099,7 @@ void DrawUpgradeIcon(const std::string& categoryName, int32_t categoryId, const
Inventory_ChangeUpgrade(categoryId, pickerIndex); Inventory_ChangeUpgrade(categoryId, pickerIndex);
ImGui::CloseCurrentPopup(); ImGui::CloseCurrentPopup();
} }
SetLastItemHoverText("None"); UIWidgets::SetLastItemHoverText("None");
} else { } else {
const ItemMapEntry& slotEntry = itemMapping[items[pickerIndex]]; const ItemMapEntry& slotEntry = itemMapping[items[pickerIndex]];
if (ImGui::ImageButton(SohImGui::GetTextureByName(slotEntry.name), ImVec2(32.0f, 32.0f), ImVec2(0, 0), if (ImGui::ImageButton(SohImGui::GetTextureByName(slotEntry.name), ImVec2(32.0f, 32.0f), ImVec2(0, 0),
@ -1108,7 +1107,7 @@ void DrawUpgradeIcon(const std::string& categoryName, int32_t categoryId, const
Inventory_ChangeUpgrade(categoryId, pickerIndex); Inventory_ChangeUpgrade(categoryId, pickerIndex);
ImGui::CloseCurrentPopup(); ImGui::CloseCurrentPopup();
} }
SetLastItemHoverText(SohUtils::GetItemName(slotEntry.id)); UIWidgets::SetLastItemHoverText(SohUtils::GetItemName(slotEntry.id));
} }
} }
@ -1150,7 +1149,7 @@ void DrawEquipmentTab() {
} }
ImGui::PopStyleColor(); ImGui::PopStyleColor();
ImGui::PopID(); ImGui::PopID();
SetLastItemHoverText(SohUtils::GetItemName(entry.id)); UIWidgets::SetLastItemHoverText(SohUtils::GetItemName(entry.id));
} }
const std::vector<uint8_t> bulletBagValues = { const std::vector<uint8_t> bulletBagValues = {
@ -1240,7 +1239,7 @@ void DrawQuestItemButton(uint32_t item) {
} }
} }
ImGui::PopStyleColor(); ImGui::PopStyleColor();
SetLastItemHoverText(SohUtils::GetQuestItemName(entry.id)); UIWidgets::SetLastItemHoverText(SohUtils::GetQuestItemName(entry.id));
} }
// Draws a toggleable icon for a dungeon item that is faded when disabled // Draws a toggleable icon for a dungeon item that is faded when disabled
@ -1258,7 +1257,7 @@ void DrawDungeonItemButton(uint32_t item, uint32_t scene) {
} }
} }
ImGui::PopStyleColor(); ImGui::PopStyleColor();
SetLastItemHoverText(SohUtils::GetItemName(entry.id)); UIWidgets::SetLastItemHoverText(SohUtils::GetItemName(entry.id));
} }
void DrawQuestStatusTab() { void DrawQuestStatusTab() {
@ -1305,11 +1304,11 @@ void DrawQuestStatusTab() {
} }
} }
ImGui::PopStyleColor(); ImGui::PopStyleColor();
SetLastItemHoverText(SohUtils::GetQuestItemName(entry.id)); UIWidgets::SetLastItemHoverText(SohUtils::GetQuestItemName(entry.id));
} }
ImGui::InputScalar("GS Count", ImGuiDataType_S16, &gSaveContext.inventory.gsTokens); ImGui::InputScalar("GS Count", ImGuiDataType_S16, &gSaveContext.inventory.gsTokens);
InsertHelpHoverText("Number of gold skulltula tokens aquired"); UIWidgets::InsertHelpHoverText("Number of gold skulltula tokens aquired");
uint32_t bitMask = 1 << QUEST_SKULL_TOKEN; uint32_t bitMask = 1 << QUEST_SKULL_TOKEN;
bool gsUnlocked = (bitMask & gSaveContext.inventory.questItems) != 0; bool gsUnlocked = (bitMask & gSaveContext.inventory.questItems) != 0;
@ -1320,7 +1319,7 @@ void DrawQuestStatusTab() {
gSaveContext.inventory.questItems &= ~bitMask; gSaveContext.inventory.questItems &= ~bitMask;
} }
} }
InsertHelpHoverText("If unlocked, enables showing the gold skulltula count in the quest status menu"); UIWidgets::InsertHelpHoverText("If unlocked, enables showing the gold skulltula count in the quest status menu");
int32_t pohCount = (gSaveContext.inventory.questItems & 0xF0000000) >> 28; int32_t pohCount = (gSaveContext.inventory.questItems & 0xF0000000) >> 28;
if (ImGui::BeginCombo("PoH count", std::to_string(pohCount).c_str())) { if (ImGui::BeginCombo("PoH count", std::to_string(pohCount).c_str())) {
@ -1332,7 +1331,7 @@ void DrawQuestStatusTab() {
} }
ImGui::EndCombo(); ImGui::EndCombo();
} }
InsertHelpHoverText("The number of pieces of heart acquired towards the next heart container"); UIWidgets::InsertHelpHoverText("The number of pieces of heart acquired towards the next heart container");
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("Dungeon Items"); ImGui::Text("Dungeon Items");
@ -1457,7 +1456,7 @@ void DrawPlayerTab() {
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("Link's Rotation"); ImGui::Text("Link's Rotation");
InsertHelpHoverText("For Link's rotation in relation to the world"); UIWidgets::InsertHelpHoverText("For Link's rotation in relation to the world");
ImGui::InputScalar("X Rot", ImGuiDataType_S16, &player->actor.world.rot.x); ImGui::InputScalar("X Rot", ImGuiDataType_S16, &player->actor.world.rot.x);
ImGui::SameLine(); ImGui::SameLine();
ImGui::InputScalar("Y Rot", ImGuiDataType_S16, &player->actor.world.rot.y); ImGui::InputScalar("Y Rot", ImGuiDataType_S16, &player->actor.world.rot.y);
@ -1467,7 +1466,7 @@ void DrawPlayerTab() {
DrawGroupWithBorder([&]() { DrawGroupWithBorder([&]() {
ImGui::Text("Link's Model Rotation"); ImGui::Text("Link's Model Rotation");
InsertHelpHoverText("For Link's actual model"); UIWidgets::InsertHelpHoverText("For Link's actual model");
ImGui::InputScalar("X ModRot", ImGuiDataType_S16, &player->actor.shape.rot.x); ImGui::InputScalar("X ModRot", ImGuiDataType_S16, &player->actor.shape.rot.x);
ImGui::SameLine(); ImGui::SameLine();
ImGui::InputScalar("Y ModRot", ImGuiDataType_S16, &player->actor.shape.rot.y); ImGui::InputScalar("Y ModRot", ImGuiDataType_S16, &player->actor.shape.rot.y);
@ -1476,19 +1475,19 @@ void DrawPlayerTab() {
}); });
ImGui::InputScalar("Linear Velocity", ImGuiDataType_Float, &player->linearVelocity); ImGui::InputScalar("Linear Velocity", ImGuiDataType_Float, &player->linearVelocity);
InsertHelpHoverText("Link's speed along the XZ plane"); UIWidgets::InsertHelpHoverText("Link's speed along the XZ plane");
ImGui::InputScalar("Y Velocity", ImGuiDataType_Float, &player->actor.velocity.y); ImGui::InputScalar("Y Velocity", ImGuiDataType_Float, &player->actor.velocity.y);
InsertHelpHoverText("Link's speed along the Y plane. Caps at -20"); UIWidgets::InsertHelpHoverText("Link's speed along the Y plane. Caps at -20");
ImGui::InputScalar("Wall Height", ImGuiDataType_Float, &player->wallHeight); ImGui::InputScalar("Wall Height", ImGuiDataType_Float, &player->wallHeight);
InsertHelpHoverText("Height used to determine whether Link can climb or grab a ledge at the top"); UIWidgets::InsertHelpHoverText("Height used to determine whether Link can climb or grab a ledge at the top");
ImGui::InputScalar("Invincibility Timer", ImGuiDataType_S8, &player->invincibilityTimer); ImGui::InputScalar("Invincibility Timer", ImGuiDataType_S8, &player->invincibilityTimer);
InsertHelpHoverText("Can't take damage while this is nonzero"); UIWidgets::InsertHelpHoverText("Can't take damage while this is nonzero");
ImGui::InputScalar("Gravity", ImGuiDataType_Float, &player->actor.gravity); ImGui::InputScalar("Gravity", ImGuiDataType_Float, &player->actor.gravity);
InsertHelpHoverText("Rate at which Link falls. Default -4.0f"); UIWidgets::InsertHelpHoverText("Rate at which Link falls. Default -4.0f");
if (ImGui::BeginCombo("Link Age on Load", gGlobalCtx->linkAgeOnLoad == 0 ? "Adult" : "Child")) { if (ImGui::BeginCombo("Link Age on Load", gGlobalCtx->linkAgeOnLoad == 0 ? "Adult" : "Child")) {
if (ImGui::Selectable("Adult")) { if (ImGui::Selectable("Adult")) {
@ -1500,7 +1499,7 @@ void DrawPlayerTab() {
ImGui::EndCombo(); ImGui::EndCombo();
} }
InsertHelpHoverText("This will change Link's age when you load a map"); UIWidgets::InsertHelpHoverText("This will change Link's age when you load a map");
ImGui::Separator(); ImGui::Separator();

View File

@ -3,7 +3,7 @@
#include <ultra64.h> #include <ultra64.h>
#include <z64.h> #include <z64.h>
#include "Cvar.h" #include <libultraship/Cvar.h>
#define MAX_CVARS 2048 #define MAX_CVARS 2048
@ -39,4 +39,4 @@ s32 GameConsole_Split(char* str, char** argv);
} }
#endif #endif
#endif #endif

View File

@ -14,7 +14,7 @@
#include <utility> #include <utility>
#include <set> #include <set>
#include <map> #include <map>
#include <Lib/spdlog/include/spdlog/spdlog.h> #include <spdlog/spdlog.h>
std::list<EntranceOverride> entranceOverrides = {}; std::list<EntranceOverride> entranceOverrides = {};
bool noRandomEntrances = false; bool noRandomEntrances = false;

View File

@ -17,7 +17,7 @@
#include <vector> #include <vector>
#include <list> #include <list>
#include <Lib/spdlog/include/spdlog/spdlog.h> #include <spdlog/spdlog.h>
using namespace CustomMessages; using namespace CustomMessages;
using namespace Logic; using namespace Logic;

View File

@ -12,7 +12,7 @@
#include "trial.hpp" #include "trial.hpp"
#include "entrance.hpp" #include "entrance.hpp"
#include "z64item.h" #include "z64item.h"
#include <Lib/spdlog/include/spdlog/spdlog.h> #include <spdlog/spdlog.h>
using namespace CustomMessages; using namespace CustomMessages;
using namespace Logic; using namespace Logic;

View File

@ -6,7 +6,7 @@
#include "shops.hpp" #include "shops.hpp"
#include "debug.hpp" #include "debug.hpp"
#include "keys.hpp" #include "keys.hpp"
#include <Lib/spdlog/include/spdlog/spdlog.h> #include <spdlog/spdlog.h>
#include "../randomizerTypes.h" #include "../randomizerTypes.h"
//Location definitions //Location definitions
@ -1638,4 +1638,4 @@ void CreateItemOverrides() {
} }
SPDLOG_DEBUG("Overrides Created: "); SPDLOG_DEBUG("Overrides Created: ");
SPDLOG_DEBUG(std::to_string(overrides.size())); SPDLOG_DEBUG(std::to_string(overrides.size()));
} }

View File

@ -9,7 +9,7 @@
#include "settings.hpp" #include "settings.hpp"
#include "spoiler_log.hpp" #include "spoiler_log.hpp"
#include "z64item.h" #include "z64item.h"
#include <Lib/spdlog/include/spdlog/spdlog.h> #include <spdlog/spdlog.h>
using namespace Settings; using namespace Settings;

View File

@ -13,8 +13,8 @@
#include "spoiler_log.hpp" #include "spoiler_log.hpp"
#include "location_access.hpp" #include "location_access.hpp"
#include "debug.hpp" #include "debug.hpp"
#include <Lib/spdlog/include/spdlog/spdlog.h> #include <spdlog/spdlog.h>
#include "soh/Enhancements/randomizer/randomizerTypes.h" #include "../../randomizer/randomizerTypes.h"
namespace { namespace {
bool seedChanged; bool seedChanged;
@ -547,4 +547,4 @@ std::string GenerateRandomizer(std::unordered_map<RandomizerSettingKey, uint8_t>
std::string GetInput(const char* hintText) { std::string GetInput(const char* hintText) {
return std::string(); return std::string();
} }

View File

@ -5,9 +5,9 @@
#include "location_access.hpp" #include "location_access.hpp"
#include "rando_main.hpp" #include "rando_main.hpp"
// #include <soh/Enhancements/randomizer.h> // #include <soh/Enhancements/randomizer.h>
#include <Cvar.h> #include <libultraship/Cvar.h>
#include <Window.h> #include <libultraship/Window.h>
#include <PR/ultra64/types.h> #include <ultra64/types.h>
#define TICKS_PER_SEC 268123480.0 #define TICKS_PER_SEC 268123480.0

View File

@ -11,7 +11,7 @@
#include "utils.hpp" #include "utils.hpp"
#include "shops.hpp" #include "shops.hpp"
#include "hints.hpp" #include "hints.hpp"
#include "Lib/nlohmann/json.hpp" #include <nlohmann/json.hpp>
#include <cstdio> #include <cstdio>
#include <cstdlib> #include <cstdlib>
@ -26,7 +26,7 @@
#include <filesystem> #include <filesystem>
#include <variables.h> #include <variables.h>
#include "Window.h" #include <libultraship/Window.h>
using json = nlohmann::json; using json = nlohmann::json;
@ -780,4 +780,4 @@ bool PlacementLog_Write() {
contentNode->SetCData(true); contentNode->SetCData(true);
return true; return true;
} }

View File

@ -1,21 +1,21 @@
#include "randomizer.h" #include "randomizer.h"
#include "Lib/nlohmann/json.hpp" #include <nlohmann/json.hpp>
#include "3drando/settings.hpp" #include "3drando/settings.hpp"
#include <fstream> #include <fstream>
#include <variables.h> #include <variables.h>
#include <macros.h> #include <macros.h>
#include <objects/gameplay_keep/gameplay_keep.h> #include <objects/gameplay_keep/gameplay_keep.h>
#include <functions.h> #include <functions.h>
#include <Cvar.h> #include <libultraship/Cvar.h>
#include <textures/icon_item_static/icon_item_static.h> #include <textures/icon_item_static/icon_item_static.h>
#include <textures/icon_item_24_static/icon_item_24_static.h> #include <textures/icon_item_24_static/icon_item_24_static.h>
#include "../libultraship/ImGuiImpl.h" #include <libultraship/ImGuiImpl.h>
#include <thread> #include <thread>
#include "3drando/rando_main.hpp" #include "3drando/rando_main.hpp"
#include <soh/Enhancements/debugger/ImGuiHelpers.h> #include "../../UIWidgets.hpp"
#include "Lib/ImGui/imgui_internal.h" #include <ImGui/imgui_internal.h>
#include <soh/Enhancements/custom-message/CustomMessageTypes.h> #include "../custom-message/CustomMessageTypes.h"
#include <soh/Enhancements/item-tables/ItemTableManager.h> #include "../item-tables/ItemTableManager.h"
#include <stdexcept> #include <stdexcept>
#include "randomizer_check_objects.h" #include "randomizer_check_objects.h"
#include <sstream> #include <sstream>

View File

@ -1,14 +1,12 @@
#include "randomizer_item_tracker.h" #include "randomizer_item_tracker.h"
#include "../../util.h" #include "../../util.h"
#include "../libultraship/ImGuiImpl.h" #include <libultraship/ImGuiImpl.h>
#include "../libultraship/Hooks.h" #include "../../UIWidgets.hpp"
#include "../libultraship/UltraController.h"
#include "../debugger/ImGuiHelpers.h"
#include <map> #include <map>
#include <string> #include <string>
#include <vector> #include <vector>
#include <Cvar.h> #include <libultraship/Cvar.h>
extern "C" { extern "C" {
#include <z64.h> #include <z64.h>

View File

@ -1,6 +1,6 @@
#include "savestates.h" #include "savestates.h"
#include "GameVersions.h" #include <libultraship/GameVersions.h>
#include <cstdio> // std::sprintf #include <cstdio> // std::sprintf
@ -9,7 +9,7 @@
#include <soh/OTRGlobals.h> #include <soh/OTRGlobals.h>
#include <soh/OTRAudio.h> #include <soh/OTRAudio.h>
#include <ImGuiImpl.h> #include <libultraship/ImGuiImpl.h>
#include "z64.h" #include "z64.h"
#include "z64save.h" #include "z64save.h"
@ -823,7 +823,7 @@ extern "C" void ProcessSaveStateRequests(void) {
} }
void SaveStateMgr::SetCurrentSlot(unsigned int slot) { void SaveStateMgr::SetCurrentSlot(unsigned int slot) {
SohImGui::overlay->TextDrawNotification(1.0f, true, "slot %u set", slot); SohImGui::GetGameOverlay()->TextDrawNotification(1.0f, true, "slot %u set", slot);
this->currentSlot = slot; this->currentSlot = slot;
} }
@ -841,12 +841,12 @@ void SaveStateMgr::ProcessSaveStateRequests(void) {
this->states[request.slot] = std::make_shared<SaveState>(OTRGlobals::Instance->gSaveStateMgr, request.slot); this->states[request.slot] = std::make_shared<SaveState>(OTRGlobals::Instance->gSaveStateMgr, request.slot);
} }
this->states[request.slot]->Save(); this->states[request.slot]->Save();
SohImGui::overlay->TextDrawNotification(1.0f, true, "saved state %u", request.slot); SohImGui::GetGameOverlay()->TextDrawNotification(1.0f, true, "saved state %u", request.slot);
break; break;
case RequestType::LOAD: case RequestType::LOAD:
if (this->states.contains(request.slot)) { if (this->states.contains(request.slot)) {
this->states[request.slot]->Load(); this->states[request.slot]->Load();
SohImGui::overlay->TextDrawNotification(1.0f, true, "loaded state %u", request.slot); SohImGui::GetGameOverlay()->TextDrawNotification(1.0f, true, "loaded state %u", request.slot);
} else { } else {
SPDLOG_ERROR("Invalid SaveState slot: {}", request.type); SPDLOG_ERROR("Invalid SaveState slot: {}", request.type);
} }
@ -862,7 +862,7 @@ void SaveStateMgr::ProcessSaveStateRequests(void) {
SaveStateReturn SaveStateMgr::AddRequest(const SaveStateRequest request) { SaveStateReturn SaveStateMgr::AddRequest(const SaveStateRequest request) {
if (gGlobalCtx == nullptr) { if (gGlobalCtx == nullptr) {
SPDLOG_ERROR("[SOH] Can not save or load a state outside of \"GamePlay\""); SPDLOG_ERROR("[SOH] Can not save or load a state outside of \"GamePlay\"");
SohImGui::overlay->TextDrawNotification(1.0f, true, "states not available here", request.slot); SohImGui::GetGameOverlay()->TextDrawNotification(1.0f, true, "states not available here", request.slot);
return SaveStateReturn::FAIL_WRONG_GAMESTATE; return SaveStateReturn::FAIL_WRONG_GAMESTATE;
} }
@ -876,7 +876,7 @@ SaveStateReturn SaveStateMgr::AddRequest(const SaveStateRequest request) {
return SaveStateReturn::SUCCESS; return SaveStateReturn::SUCCESS;
} else { } else {
SPDLOG_ERROR("Invalid SaveState slot: {}", request.type); SPDLOG_ERROR("Invalid SaveState slot: {}", request.type);
SohImGui::overlay->TextDrawNotification(1.0f, true, "state slot %u empty", request.slot); SohImGui::GetGameOverlay()->TextDrawNotification(1.0f, true, "state slot %u empty", request.slot);
return SaveStateReturn::FAIL_INVALID_SLOT; return SaveStateReturn::FAIL_INVALID_SLOT;
} }
[[unlikely]] default: [[unlikely]] default:

1367
soh/soh/GameMenuBar.cpp Normal file

File diff suppressed because it is too large Load Diff

27
soh/soh/GameMenuBar.hpp Normal file
View File

@ -0,0 +1,27 @@
//
// GameMenuBar.hpp
// soh
//
// Created by David Chavez on 24.08.22.
//
#ifndef GameMenuBar_hpp
#define GameMenuBar_hpp
#include <stdio.h>
#ifdef __cplusplus
extern "C" {
#endif
void enableBetaQuest();
void disableBetaQuest();
#ifdef __cplusplus
}
#endif
namespace GameMenuBar {
void SetupHooks();
void Draw();
}
#endif /* GameMenuBar_hpp */

View File

@ -5,46 +5,46 @@
#include <filesystem> #include <filesystem>
#include <fstream> #include <fstream>
#include "ResourceMgr.h" #include <libultraship/ResourceMgr.h>
#include "DisplayList.h" #include <libultraship/DisplayList.h>
#include "PlayerAnimation.h" #include <libultraship/PlayerAnimation.h>
#include "Skeleton.h" #include <libultraship/Skeleton.h>
#include "Window.h" #include <libultraship/Window.h>
#include "z64animation.h" #include "z64animation.h"
#include "z64bgcheck.h" #include "z64bgcheck.h"
#include "Enhancements/gameconsole.h" #include "Enhancements/gameconsole.h"
#include <ultra64/gbi.h> #include <ultra64/gbi.h>
#include <Animation.h> #include <libultraship/Animation.h>
#ifdef _WIN32 #ifdef _WIN32
#include <Windows.h> #include <Windows.h>
#else #else
#include <time.h> #include <time.h>
#endif #endif
#include <CollisionHeader.h> #include <libultraship/CollisionHeader.h>
#include <Array.h> #include <libultraship/Array.h>
#include <Cutscene.h> #include <libultraship/Cutscene.h>
#include "Lib/stb/stb_image.h" #include <stb/stb_image.h>
#define DRMP3_IMPLEMENTATION #define DRMP3_IMPLEMENTATION
#include "Lib/dr_libs/mp3.h" #include <dr_libs/mp3.h>
#define DRWAV_IMPLEMENTATION #define DRWAV_IMPLEMENTATION
#include "Lib/dr_libs/wav.h" #include <dr_libs/wav.h>
#include "AudioPlayer.h" #include <libultraship/AudioPlayer.h>
#include "Enhancements/controls/GameControlEditor.h" #include "Enhancements/controls/GameControlEditor.h"
#include "Enhancements/cosmetics/CosmeticsEditor.h" #include "Enhancements/cosmetics/CosmeticsEditor.h"
#include "Enhancements/debugconsole.h" #include "Enhancements/debugconsole.h"
#include "Enhancements/debugger/debugger.h" #include "Enhancements/debugger/debugger.h"
#include <soh/Enhancements/randomizer/randomizer.h> #include "Enhancements/randomizer/randomizer.h"
#include <soh/Enhancements/randomizer/randomizer_item_tracker.h> #include "Enhancements/randomizer/randomizer_item_tracker.h"
#include "Enhancements/n64_weird_frame_data.inc" #include "Enhancements/n64_weird_frame_data.inc"
#include "soh/frame_interpolation.h" #include "frame_interpolation.h"
#include "variables.h" #include "variables.h"
#include "macros.h" #include "macros.h"
#include <Utils/StringHelper.h> #include <Utils/StringHelper.h>
#include "Hooks.h" #include <libultraship/Hooks.h>
#include <soh/Enhancements/custom-message/CustomMessageManager.h> #include "Enhancements/custom-message/CustomMessageManager.h"
#include "Lib/Fast3D/gfx_pc.h" #include <Fast3D/gfx_pc.h>
#include "Lib/Fast3D/gfx_rendering_api.h" #include <Fast3D/gfx_rendering_api.h>
#ifdef __APPLE__ #ifdef __APPLE__
#include <SDL_scancode.h> #include <SDL_scancode.h>
@ -53,15 +53,16 @@
#endif #endif
#ifdef __SWITCH__ #ifdef __SWITCH__
#include "SwitchImpl.h" #include <libultraship/SwitchImpl.h>
#elif defined(__WIIU__) #elif defined(__WIIU__)
#include "WiiUImpl.h" #include <libultraship/WiiUImpl.h>
#endif #endif
#include <Audio.h> #include <libultraship/Audio.h>
#include <soh/Enhancements/custom-message/CustomMessageTypes.h> #include "Enhancements/custom-message/CustomMessageTypes.h"
#include <functions.h> #include <functions.h>
#include <soh/Enhancements/item-tables/ItemTableManager.h> #include "Enhancements/item-tables/ItemTableManager.h"
#include "GameMenuBar.hpp"
OTRGlobals* OTRGlobals::Instance; OTRGlobals* OTRGlobals::Instance;
SaveManager* SaveManager::Instance; SaveManager* SaveManager::Instance;
@ -290,6 +291,7 @@ extern "C" void VanillaItemTable_Init() {
GET_ITEM(ITEM_BULLET_BAG_50, OBJECT_GI_DEKUPOUCH, GID_BULLET_BAG_50, 0x6C, 0x80, CHEST_ANIM_LONG, MOD_NONE, GI_BULLET_BAG_50), GET_ITEM(ITEM_BULLET_BAG_50, OBJECT_GI_DEKUPOUCH, GID_BULLET_BAG_50, 0x6C, 0x80, CHEST_ANIM_LONG, MOD_NONE, GI_BULLET_BAG_50),
GET_ITEM_NONE, GET_ITEM_NONE,
GET_ITEM_NONE, GET_ITEM_NONE,
GET_ITEM_NONE // GI_MAX - if you need to add to this table insert it before this entry.
}; };
ItemTableManager::Instance->AddItemTable(MOD_NONE); ItemTableManager::Instance->AddItemTable(MOD_NONE);
for (uint8_t i = 0; i < ARRAY_COUNT(getItemTable); i++) { for (uint8_t i = 0; i < ARRAY_COUNT(getItemTable); i++) {
@ -321,6 +323,9 @@ extern "C" void InitOTR() {
#elif defined(__WIIU__) #elif defined(__WIIU__)
Ship::WiiU::Init(); Ship::WiiU::Init();
#endif #endif
SohImGui::AddSetupHooksDelegate(GameMenuBar::SetupHooks);
SohImGui::RegisterMenuDrawMethod(GameMenuBar::Draw);
OTRGlobals::Instance = new OTRGlobals(); OTRGlobals::Instance = new OTRGlobals();
SaveManager::Instance = new SaveManager(); SaveManager::Instance = new SaveManager();
CustomMessageManager::Instance = new CustomMessageManager(); CustomMessageManager::Instance = new CustomMessageManager();
@ -1621,7 +1626,7 @@ extern "C" CustomMessageEntry Randomizer_GetHintFromCheck(RandomizerCheck check)
} }
extern "C" GetItemEntry ItemTable_Retrieve(int16_t getItemID) { extern "C" GetItemEntry ItemTable_Retrieve(int16_t getItemID) {
GetItemEntry giEntry = ItemTableManager::Instance->RetrieveItemEntry(OTRGlobals::Instance->getItemModIndex, getItemID); GetItemEntry giEntry = ItemTableManager::Instance->RetrieveItemEntry(MOD_NONE, getItemID);
return giEntry; return giEntry;
} }

View File

@ -7,7 +7,7 @@
#include <soh/Enhancements/item-tables/ItemTableTypes.h> #include <soh/Enhancements/item-tables/ItemTableTypes.h>
#ifdef __cplusplus #ifdef __cplusplus
#include "Window.h" #include <libultraship/Window.h>
#include "Enhancements/savestates.h" #include "Enhancements/savestates.h"
#include "Enhancements/randomizer/randomizer.h" #include "Enhancements/randomizer/randomizer.h"
@ -21,7 +21,6 @@ public:
std::shared_ptr<Ship::Window> context; std::shared_ptr<Ship::Window> context;
std::shared_ptr<SaveStateMgr> gSaveStateMgr; std::shared_ptr<SaveStateMgr> gSaveStateMgr;
std::shared_ptr<Randomizer> gRandomizer; std::shared_ptr<Randomizer> gRandomizer;
uint16_t getItemModIndex;
OTRGlobals(); OTRGlobals();
~OTRGlobals(); ~OTRGlobals();

View File

@ -4,7 +4,7 @@
#include "z64.h" #include "z64.h"
#include "functions.h" #include "functions.h"
#include "macros.h" #include "macros.h"
#include "Cvar.h" #include <libultraship/Cvar.h>
#define NOGDI // avoid various windows defines that conflict with things in z64.h #define NOGDI // avoid various windows defines that conflict with things in z64.h
#include "spdlog/spdlog.h" #include "spdlog/spdlog.h"
@ -1594,4 +1594,4 @@ extern "C" void Save_DeleteFile(int fileNum) {
extern "C" bool Save_Exist(int fileNum) { extern "C" bool Save_Exist(int fileNum) {
return SaveManager::Instance->SaveFile_Exist(fileNum); return SaveManager::Instance->SaveFile_Exist(fileNum);
} }

View File

@ -23,7 +23,7 @@ typedef struct {
#include <vector> #include <vector>
#include <filesystem> #include <filesystem>
#include "Lib/nlohmann/json.hpp" #include <nlohmann/json.hpp>
class SaveManager { class SaveManager {
public: public:

523
soh/soh/UIWidgets.cpp Normal file
View File

@ -0,0 +1,523 @@
//
// UIWidgets.cpp
// soh
//
// Created by David Chavez on 25.08.22.
//
#include "UIWidgets.hpp"
#define IMGUI_DEFINE_MATH_OPERATORS
#include <ImGui/imgui_internal.h>
#include <libultraship/ImGuiImpl.h>
#include <libultraship/Cvar.h>
#include <ultra64/types.h>
namespace UIWidgets {
// MARK: - Layout Helper
// Automatically adds newlines to break up text longer than a specified number of characters
// Manually included newlines will still be respected and reset the line length
// If line is midword when it hits the limit, text should break at the last encountered space
char* WrappedText(const char* text, unsigned int charactersPerLine) {
std::string newText(text);
const size_t tipLength = newText.length();
int lastSpace = -1;
size_t currentLineLength = 0;
for (unsigned int currentCharacter = 0; currentCharacter < tipLength; currentCharacter++) {
if (newText[currentCharacter] == '\n') {
currentLineLength = 0;
lastSpace = -1;
continue;
} else if (newText[currentCharacter] == ' ') {
lastSpace = currentCharacter;
}
if ((currentLineLength >= charactersPerLine) && (lastSpace >= 0)) {
newText[lastSpace] = '\n';
currentLineLength = currentCharacter - lastSpace - 1;
lastSpace = -1;
}
currentLineLength++;
}
return strdup(newText.c_str());
}
char* WrappedText(const std::string& text, unsigned int charactersPerLine) {
return WrappedText(text.c_str(), charactersPerLine);
}
void LoadPickersColors(ImVec4& ColorArray, const char* cvarname, const ImVec4& default_colors, bool has_alpha)
{
Color_RGBA8 defaultColors;
defaultColors.r = default_colors.x;
defaultColors.g = default_colors.y;
defaultColors.b = default_colors.z;
defaultColors.a = default_colors.w;
Color_RGBA8 cvarColor = CVar_GetRGBA(cvarname, defaultColors);
ColorArray.x = cvarColor.r / 255.0;
ColorArray.y = cvarColor.g / 255.0;
ColorArray.z = cvarColor.b / 255.0;
ColorArray.w = cvarColor.a / 255.0;
}
void SetLastItemHoverText(const std::string& text) {
if (ImGui::IsItemHovered()) {
ImGui::BeginTooltip();
ImGui::Text("%s", WrappedText(text, 60));
ImGui::EndTooltip();
}
}
// Adds a "?" next to the previous ImGui item with a custom tooltip
void InsertHelpHoverText(const std::string& text) {
ImGui::SameLine();
ImGui::TextColored(ImVec4(0.7f, 0.7f, 0.7f, 1.0f), "?");
if (ImGui::IsItemHovered()) {
ImGui::BeginTooltip();
ImGui::Text("%s", WrappedText(text, 60));
ImGui::EndTooltip();
}
}
// MARK: - UI Elements
void Tooltip(const char* text) {
if (ImGui::IsItemHovered()) {
ImGui::SetTooltip("%s", WrappedText(text));
}
}
void Spacer(float height) {
ImGui::Dummy(ImVec2(0.0f, height));
}
void PaddedSeparator(bool padTop, bool padBottom, float extraVerticalTopPadding, float extraVerticalBottomPadding) {
if (padTop)
Spacer(0);
ImGui::Separator();
if (padBottom)
Spacer(0);
}
void RenderCross(ImDrawList* draw_list, ImVec2 pos, ImU32 col, float sz) {
float thickness = ImMax(sz / 5.0f, 1.0f);
sz -= thickness * 0.5f;
pos += ImVec2(thickness * 0.25f, thickness * 0.25f);
draw_list->PathLineTo(ImVec2(pos.x, pos.y));
draw_list->PathLineTo(ImVec2(pos.x + sz, pos.y + sz));
draw_list->PathStroke(col, 0, thickness);
draw_list->PathLineTo(ImVec2(pos.x + sz, pos.y));
draw_list->PathLineTo(ImVec2(pos.x, pos.y + sz));
draw_list->PathStroke(col, 0, thickness);
}
bool CustomCheckbox(const char* label, bool* v, bool disabled, CheckboxGraphics disabledGraphic) {
ImGuiWindow* window = ImGui::GetCurrentWindow();
if (window->SkipItems)
return false;
ImGuiContext& g = *GImGui;
const ImGuiStyle& style = g.Style;
const ImGuiID id = window->GetID(label);
const ImVec2 label_size = ImGui::CalcTextSize(label, NULL, true);
const float square_sz = ImGui::GetFrameHeight();
const ImVec2 pos = window->DC.CursorPos;
const ImRect total_bb(pos, pos + ImVec2(square_sz + (label_size.x > 0.0f ? style.ItemInnerSpacing.x + label_size.x : 0.0f), label_size.y + style.FramePadding.y * 2.0f));
ImGui::ItemSize(total_bb, style.FramePadding.y);
if (!ImGui::ItemAdd(total_bb, id)) {
IMGUI_TEST_ENGINE_ITEM_INFO(id, label, g.LastItemData.StatusFlags | ImGuiItemStatusFlags_Checkable | (*v ? ImGuiItemStatusFlags_Checked : 0));
return false;
}
bool hovered, held;
bool pressed = ImGui::ButtonBehavior(total_bb, id, &hovered, &held);
if (pressed) {
*v = !(*v);
ImGui::MarkItemEdited(id);
}
const ImRect check_bb(pos, pos + ImVec2(square_sz, square_sz));
ImGui::RenderNavHighlight(total_bb, id);
ImGui::RenderFrame(check_bb.Min, check_bb.Max, ImGui::GetColorU32((held && hovered) ? ImGuiCol_FrameBgActive : hovered ? ImGuiCol_FrameBgHovered : ImGuiCol_FrameBg), true, style.FrameRounding);
ImU32 check_col = ImGui::GetColorU32(ImGuiCol_CheckMark);
ImU32 cross_col = ImGui::GetColorU32(ImVec4(0.50f, 0.50f, 0.50f, 1.00f));
bool mixed_value = (g.LastItemData.InFlags & ImGuiItemFlags_MixedValue) != 0;
if (mixed_value) {
// Undocumented tristate/mixed/indeterminate checkbox (#2644)
// This may seem awkwardly designed because the aim is to make ImGuiItemFlags_MixedValue supported by all widgets (not just checkbox)
ImVec2 pad(ImMax(1.0f, IM_FLOOR(square_sz / 3.6f)), ImMax(1.0f, IM_FLOOR(square_sz / 3.6f)));
window->DrawList->AddRectFilled(check_bb.Min + pad, check_bb.Max - pad, check_col, style.FrameRounding);
} else if ((!disabled && *v) || (disabled && disabledGraphic == CheckboxGraphics::Checkmark)) {
const float pad = ImMax(1.0f, IM_FLOOR(square_sz / 6.0f));
ImGui::RenderCheckMark(window->DrawList, check_bb.Min + ImVec2(pad, pad), check_col, square_sz - pad * 2.0f);
} else if (disabled && disabledGraphic == CheckboxGraphics::Cross) {
const float pad = ImMax(1.0f, IM_FLOOR(square_sz / 6.0f));
RenderCross(window->DrawList, check_bb.Min + ImVec2(pad, pad), cross_col, square_sz - pad * 2.0f);
}
ImVec2 label_pos = ImVec2(check_bb.Max.x + style.ItemInnerSpacing.x, check_bb.Min.y + style.FramePadding.y);
if (g.LogEnabled)
ImGui::LogRenderedText(&label_pos, mixed_value ? "[~]" : *v ? "[x]" : "[ ]");
if (label_size.x > 0.0f)
ImGui::RenderText(label_pos, label);
IMGUI_TEST_ENGINE_ITEM_INFO(id, label, g.LastItemData.StatusFlags | ImGuiItemStatusFlags_Checkable | (*v ? ImGuiItemStatusFlags_Checked : 0));
return pressed;
}
void EnhancementCheckbox(const char* text, const char* cvarName, bool disabled, const char* disabledTooltipText, CheckboxGraphics disabledGraphic) {
if (disabled) {
ImGui::PushItemFlag(ImGuiItemFlags_Disabled, true);
ImGui::PushStyleVar(ImGuiStyleVar_Alpha, ImGui::GetStyle().Alpha * 0.5f);
}
bool val = (bool)CVar_GetS32(cvarName, 0);
if (CustomCheckbox(text, &val, disabled, disabledGraphic)) {
CVar_SetS32(cvarName, val);
SohImGui::RequestCvarSaveOnNextTick();
}
if (disabled) {
ImGui::PopStyleVar(1);
if (ImGui::IsItemHovered(ImGuiHoveredFlags_AllowWhenDisabled) && strcmp(disabledTooltipText, "") != 0) {
ImGui::SetTooltip("%s", disabledTooltipText);
}
ImGui::PopItemFlag();
}
}
void PaddedEnhancementCheckbox(const char* text, const char* cvarName, bool padTop, bool padBottom, bool disabled, const char* disabledTooltipText, CheckboxGraphics disabledGraphic) {
if (padTop) Spacer(0);
EnhancementCheckbox(text, cvarName, disabled, disabledTooltipText, disabledGraphic);
if (padBottom) Spacer(0);
}
void EnhancementCombo(const std::string& name, const char* cvarName, const std::vector<std::string>& items, int defaultValue) {
if (ImGui::BeginCombo(name.c_str(), items[static_cast<int>(CVar_GetS32(cvarName, defaultValue))].c_str())) {
for (int settingIndex = 0; settingIndex < (int) items.size(); settingIndex++) {
if (ImGui::Selectable(items[settingIndex].c_str())) {
CVar_SetS32(cvarName, settingIndex);
SohImGui::RequestCvarSaveOnNextTick();
}
}
ImGui::EndCombo();
}
}
void EnhancementCombobox(const char* name, const char* ComboArray[], size_t arraySize, uint8_t FirstTimeValue) {
if (FirstTimeValue <= 0) {
FirstTimeValue = 0;
}
uint8_t selected = CVar_GetS32(name, FirstTimeValue);
uint8_t DefaultValue = selected;
std::string comboName = std::string("##") + std::string(name);
if (ImGui::BeginCombo(comboName.c_str(), ComboArray[DefaultValue])) {
for (uint8_t i = 0; i < arraySize; i++) {
if (strlen(ComboArray[i]) > 1) {
if (ImGui::Selectable(ComboArray[i], i == selected)) {
CVar_SetS32(name, i);
selected = i;
SohImGui::RequestCvarSaveOnNextTick();
}
}
}
ImGui::EndCombo();
}
}
void PaddedText(const char* text, bool padTop, bool padBottom) {
if (padTop)
Spacer(0);
ImGui::Text("%s", text);
if (padBottom)
Spacer(0);
}
void EnhancementSliderInt(const char* text, const char* id, const char* cvarName, int min, int max, const char* format, int defaultValue, bool PlusMinusButton) {
int val = CVar_GetS32(cvarName, defaultValue);
ImGui::Text(text, val);
if(PlusMinusButton) {
std::string MinusBTNName = " - ##";
MinusBTNName += cvarName;
if (ImGui::Button(MinusBTNName.c_str())) {
val--;
CVar_SetS32(cvarName, val);
SohImGui::RequestCvarSaveOnNextTick();
}
ImGui::SameLine();
ImGui::SetCursorPosX(ImGui::GetCursorPosX() - 7.0f);
}
if (ImGui::SliderInt(id, &val, min, max, format))
{
CVar_SetS32(cvarName, val);
SohImGui::RequestCvarSaveOnNextTick();
}
if(PlusMinusButton) {
std::string PlusBTNName = " + ##";
PlusBTNName += cvarName;
ImGui::SameLine();
ImGui::SetCursorPosX(ImGui::GetCursorPosX() - 7.0f);
if (ImGui::Button(PlusBTNName.c_str())) {
val++;
CVar_SetS32(cvarName, val);
SohImGui::RequestCvarSaveOnNextTick();
}
}
if (val < min)
{
val = min;
CVar_SetS32(cvarName, val);
SohImGui::RequestCvarSaveOnNextTick();
}
if (val > max)
{
val = max;
CVar_SetS32(cvarName, val);
SohImGui::RequestCvarSaveOnNextTick();
}
}
void EnhancementSliderFloat(const char* text, const char* id, const char* cvarName, float min, float max, const char* format, float defaultValue, bool isPercentage, bool PlusMinusButton) {
float val = CVar_GetFloat(cvarName, defaultValue);
if (!isPercentage)
ImGui::Text(text, val);
else
ImGui::Text(text, static_cast<int>(100 * val));
Spacer(0);
if(PlusMinusButton) {
std::string MinusBTNName = " - ##";
MinusBTNName += cvarName;
if (ImGui::Button(MinusBTNName.c_str())) {
if (!isPercentage)
val -= 0.1f;
else
val -= 0.01f;
CVar_SetFloat(cvarName, val);
SohImGui::RequestCvarSaveOnNextTick();
}
ImGui::SameLine();
ImGui::SetCursorPosX(ImGui::GetCursorPosX() - 7.0f);
}
if (PlusMinusButton) {
#ifdef __WIIU__
ImGui::PushItemWidth(ImGui::GetWindowSize().x - 79.0f * 2);
#else
ImGui::PushItemWidth(ImGui::GetWindowSize().x - 79.0f);
#endif
}
if (ImGui::SliderFloat(id, &val, min, max, format))
{
CVar_SetFloat(cvarName, val);
SohImGui::RequestCvarSaveOnNextTick();
}
if (PlusMinusButton) {
ImGui::PopItemWidth();
}
if(PlusMinusButton) {
std::string PlusBTNName = " + ##";
PlusBTNName += cvarName;
ImGui::SameLine();
ImGui::SetCursorPosX(ImGui::GetCursorPosX() - 7.0f);
if (ImGui::Button(PlusBTNName.c_str())) {
if (!isPercentage)
val += 0.1f;
else
val += 0.01f;
CVar_SetFloat(cvarName, val);
SohImGui::RequestCvarSaveOnNextTick();
}
}
if (val < min)
{
val = min;
CVar_SetFloat(cvarName, val);
SohImGui::RequestCvarSaveOnNextTick();
}
if (val > max)
{
val = max;
CVar_SetFloat(cvarName, val);
SohImGui::RequestCvarSaveOnNextTick();
}
}
void PaddedEnhancementSliderInt(const char* text, const char* id, const char* cvarName, int min, int max, const char* format, int defaultValue, bool PlusMinusButton, bool padTop, bool padBottom) {
if (padTop)
Spacer(0);
EnhancementSliderInt(text, id, cvarName, min, max, format, defaultValue, PlusMinusButton);
if (padBottom)
Spacer(0);
}
void EnhancementRadioButton(const char* text, const char* cvarName, int id) {
/*Usage :
EnhancementRadioButton("My Visible Name","gMyCVarName", MyID);
First arg is the visible name of the Radio button
Second is the cvar name where MyID will be saved.
Note: the CVar name should be the same to each Buddies.
Example :
EnhancementRadioButton("English", "gLanguages", 0);
EnhancementRadioButton("German", "gLanguages", 1);
EnhancementRadioButton("French", "gLanguages", 2);
*/
std::string make_invisible = "##";
make_invisible += text;
make_invisible += cvarName;
int val = CVar_GetS32(cvarName, 0);
if (ImGui::RadioButton(make_invisible.c_str(), id == val)) {
CVar_SetS32(cvarName, id);
SohImGui::RequestCvarSaveOnNextTick();
}
ImGui::SameLine();
ImGui::Text("%s", text);
}
void ResetColor(const char* cvarName, ImVec4* colors, ImVec4 defaultcolors, bool has_alpha) {
std::string Cvar_RBM = cvarName;
Cvar_RBM += "RBM";
std::string MakeInvisible = "Reset";
MakeInvisible += "##";
MakeInvisible += cvarName;
MakeInvisible += "Reset";
if (ImGui::Button(MakeInvisible.c_str())) {
colors->x = defaultcolors.x;
colors->y = defaultcolors.y;
colors->z = defaultcolors.z;
if (has_alpha) { colors->w = defaultcolors.w; };
Color_RGBA8 colorsRGBA;
colorsRGBA.r = defaultcolors.x;
colorsRGBA.g = defaultcolors.y;
colorsRGBA.b = defaultcolors.z;
if (has_alpha) { colorsRGBA.a = defaultcolors.w; };
CVar_SetRGBA(cvarName, colorsRGBA);
CVar_SetS32(Cvar_RBM.c_str(), 0); //On click disable rainbow mode.
SohImGui::RequestCvarSaveOnNextTick();
}
Tooltip("Revert colors to the game's original colors (GameCube version)\nOverwrites previously chosen color");
}
void RandomizeColor(const char* cvarName, ImVec4* colors) {
Color_RGBA8 NewColors = {0,0,0,255};
std::string Cvar_RBM = cvarName;
Cvar_RBM += "RBM";
std::string MakeInvisible = "##";
MakeInvisible += cvarName;
MakeInvisible += "Random";
std::string FullName = "Random";
FullName += MakeInvisible;
if (ImGui::Button(FullName.c_str())) {
s16 RND_R = rand() % (255 - 0);
s16 RND_G = rand() % (255 - 0);
s16 RND_B = rand() % (255 - 0);
colors->x = (float)RND_R / 255;
colors->y = (float)RND_G / 255;
colors->z = (float)RND_B / 255;
NewColors.r = fmin(fmax(colors->x, 0), 255);
NewColors.g = fmin(fmax(colors->y, 0), 255);
NewColors.b = fmin(fmax(colors->z, 0), 255);
CVar_SetRGBA(cvarName, NewColors);
CVar_SetS32(Cvar_RBM.c_str(), 0); // On click disable rainbow mode.
SohImGui::RequestCvarSaveOnNextTick();
}
Tooltip("Chooses a random color\nOverwrites previously chosen color");
}
void RainbowColor(const char* cvarName, ImVec4* colors) {
std::string Cvar_RBM = cvarName;
Cvar_RBM += "RBM";
std::string MakeInvisible = "Rainbow";
MakeInvisible += "##";
MakeInvisible += cvarName;
MakeInvisible += "Rainbow";
EnhancementCheckbox(MakeInvisible.c_str(), Cvar_RBM.c_str());
Tooltip("Cycles through colors on a timer\nOverwrites previously chosen color");
}
void EnhancementColor(const char* text, const char* cvarName, ImVec4 ColorRGBA, ImVec4 default_colors, bool allow_rainbow, bool has_alpha, bool TitleSameLine) {
LoadPickersColors(ColorRGBA, cvarName, default_colors, has_alpha);
ImGuiColorEditFlags flags = ImGuiColorEditFlags_None;
if (!TitleSameLine) {
ImGui::Text("%s", text);
flags = ImGuiColorEditFlags_NoLabel;
}
ImGui::PushID(cvarName);
if (!has_alpha) {
if (ImGui::ColorEdit3(text, (float*)&ColorRGBA, flags))
{
Color_RGBA8 colors;
colors.r = ColorRGBA.x * 255.0;
colors.g = ColorRGBA.y * 255.0;
colors.b = ColorRGBA.z * 255.0;
colors.a = ColorRGBA.w * 255.0;
CVar_SetRGBA(cvarName, colors);
SohImGui::RequestCvarSaveOnNextTick();
}
}
else
{
if (ImGui::ColorEdit4(text, (float*)&ColorRGBA, flags))
{
Color_RGBA8 colors;
colors.r = ColorRGBA.x / 255;
colors.g = ColorRGBA.y / 255;
colors.b = ColorRGBA.z / 255;
colors.a = ColorRGBA.w / 255;
CVar_SetRGBA(cvarName, colors);
SohImGui::RequestCvarSaveOnNextTick();
}
}
ImGui::PopID();
//ImGui::SameLine(); // Removing that one to gain some width spacing on the HUD editor
ImGui::PushItemWidth(-FLT_MIN);
ResetColor(cvarName, &ColorRGBA, default_colors, has_alpha);
ImGui::SameLine();
RandomizeColor(cvarName, &ColorRGBA);
if (allow_rainbow) {
if (ImGui::GetContentRegionAvail().x > 185) {
ImGui::SameLine();
}
RainbowColor(cvarName, &ColorRGBA);
}
ImGui::NewLine();
ImGui::PopItemWidth();
}
}

49
soh/soh/UIWidgets.hpp Normal file
View File

@ -0,0 +1,49 @@
//
// UIWidgets.hpp
// soh
//
// Created by David Chavez on 25.08.22.
//
#ifndef UIWidgets_hpp
#define UIWidgets_hpp
#include <string>
#include <vector>
#include <stdint.h>
#include <ImGui/imgui.h>
namespace UIWidgets {
// MARK: - Enums
enum class CheckboxGraphics {
Cross,
Checkmark,
None
};
char* WrappedText(const char* text, unsigned int charactersPerLine = 60);
char* WrappedText(const std::string& text, unsigned int charactersPerLine);
void SetLastItemHoverText(const std::string& text);
void InsertHelpHoverText(const std::string& text);
void Tooltip(const char* text);
void Spacer(float height);
void PaddedSeparator(bool padTop = true, bool padBottom = true, float extraVerticalTopPadding = 0.0f, float extraVerticalBottomPadding = 0.0f);
void EnhancementCheckbox(const char* text, const char* cvarName, bool disabled = false, const char* disabledTooltipText = "", CheckboxGraphics disabledGraphic = CheckboxGraphics::Cross);
void PaddedEnhancementCheckbox(const char* text, const char* cvarName, bool padTop = true, bool padBottom = true, bool disabled = false, const char* disabledTooltipText = "", CheckboxGraphics disabledGraphic = CheckboxGraphics::Cross);
void EnhancementCombo(const std::string& name, const char* cvarName, const std::vector<std::string>& items, int defaultValue = 0);
void EnhancementCombobox(const char* name, const char* ComboArray[], size_t arraySize, uint8_t FirstTimeValue);
void PaddedText(const char* text, bool padTop = true, bool padBottom = true);
void EnhancementSliderInt(const char* text, const char* id, const char* cvarName, int min, int max, const char* format, int defaultValue = 0, bool PlusMinusButton = false);
void PaddedEnhancementSliderInt(const char* text, const char* id, const char* cvarName, int min, int max, const char* format, int defaultValue = 0, bool PlusMinusButton = false, bool padTop = true, bool padBottom = true);
void EnhancementSliderFloat(const char* text, const char* id, const char* cvarName, float min, float max, const char* format, float defaultValue, bool isPercentage, bool PlusMinusButton = false);
void EnhancementRadioButton(const char* text, const char* cvarName, int id);
void EnhancementColor(const char* text, const char* cvarName, ImVec4 ColorRGBA, ImVec4 default_colors, bool allow_rainbow = true, bool has_alpha=false, bool TitleSameLine=false);
}
#endif /* UIWidgets_hpp */

View File

@ -1,4 +1,4 @@
#include "Cvar.h" #include <libultraship/Cvar.h>
#include <vector> #include <vector>
#include <map> #include <map>

View File

@ -1,13 +1,13 @@
#include "OTRGlobals.h" #include "OTRGlobals.h"
#include "ResourceMgr.h" #include <libultraship/ResourceMgr.h>
#include "Scene.h" #include <libultraship/Scene.h>
#include "Utils/StringHelper.h" #include <Utils/StringHelper.h>
#include "global.h" #include "global.h"
#include "vt.h" #include "vt.h"
#include <Text.h> #include <libultraship/Text.h>
#include <message_data_static.h> #include <message_data_static.h>
#include <soh/Enhancements/custom-message/CustomMessageManager.h> #include "Enhancements/custom-message/CustomMessageManager.h"
#include <soh/Enhancements/custom-message/CustomMessageTypes.h> #include "Enhancements/custom-message/CustomMessageTypes.h"
extern "C" MessageTableEntry* sNesMessageEntryTablePtr; extern "C" MessageTableEntry* sNesMessageEntryTablePtr;
extern "C" MessageTableEntry* sGerMessageEntryTablePtr; extern "C" MessageTableEntry* sGerMessageEntryTablePtr;

View File

@ -1,10 +1,10 @@
#include "OTRGlobals.h" #include "OTRGlobals.h"
#include "ResourceMgr.h" #include <libultraship/ResourceMgr.h>
#include "Scene.h" #include <libultraship/Scene.h>
#include "Utils/StringHelper.h" #include <Utils/StringHelper.h>
#include "global.h" #include "global.h"
#include "vt.h" #include "vt.h"
#include "Vertex.h" #include <libultraship/Vertex.h>
extern "C" void Gameplay_InitScene(GlobalContext * globalCtx, s32 spawn); extern "C" void Gameplay_InitScene(GlobalContext * globalCtx, s32 spawn);
extern "C" void Gameplay_InitEnvironment(GlobalContext * globalCtx, s16 skyboxId); extern "C" void Gameplay_InitEnvironment(GlobalContext * globalCtx, s16 skyboxId);
@ -60,7 +60,6 @@ void OTRGameplay_InitScene(GlobalContext* globalCtx, s32 spawn) {
globalCtx->cUpElfMsgs = nullptr; globalCtx->cUpElfMsgs = nullptr;
globalCtx->setupPathList = nullptr; globalCtx->setupPathList = nullptr;
globalCtx->numSetupActors = 0; globalCtx->numSetupActors = 0;
OTRGlobals::Instance->getItemModIndex = MOD_NONE;
Object_InitBank(globalCtx, &globalCtx->objectCtx); Object_InitBank(globalCtx, &globalCtx->objectCtx);
LightContext_Init(globalCtx, &globalCtx->lightCtx); LightContext_Init(globalCtx, &globalCtx->lightCtx);
TransitionActor_InitContext(&globalCtx->state, &globalCtx->transiActorCtx); TransitionActor_InitContext(&globalCtx->state, &globalCtx->transiActorCtx);
@ -77,4 +76,4 @@ void OTRGameplay_InitScene(GlobalContext* globalCtx, s32 spawn) {
auto data2 = ResourceMgr_LoadVtxByCRC(0x68d4ea06044e228f);*/ auto data2 = ResourceMgr_LoadVtxByCRC(0x68d4ea06044e228f);*/
volatile int a = 0; volatile int a = 0;
} }

View File

@ -1,15 +1,15 @@
#include "OTRGlobals.h" #include "OTRGlobals.h"
#include "ResourceMgr.h" #include <libultraship/ResourceMgr.h>
#include "Scene.h" #include <libultraship/Scene.h>
#include "Utils/StringHelper.h" #include <Utils/StringHelper.h>
#include "global.h" #include "global.h"
#include "vt.h" #include "vt.h"
#include <CollisionHeader.h> #include <libultraship/CollisionHeader.h>
#include <DisplayList.h> #include <libultraship/DisplayList.h>
#include <Cutscene.h> #include <libultraship/Cutscene.h>
#include <Path.h> #include <libultraship/Path.h>
#include <Text.h> #include <libultraship/Text.h>
#include <Blob.h> #include <libultraship/Blob.h>
extern Ship::Resource* OTRGameplay_LoadFile(GlobalContext* globalCtx, const char* fileName); extern Ship::Resource* OTRGameplay_LoadFile(GlobalContext* globalCtx, const char* fileName);
extern "C" s32 Object_Spawn(ObjectContext* objectCtx, s16 objectId); extern "C" s32 Object_Spawn(ObjectContext* objectCtx, s16 objectId);

View File

@ -1,5 +1,5 @@
#include "global.h" #include "global.h"
#include "Cvar.h" #include <libultraship/Cvar.h>
extern bool gUseLegacySD; extern bool gUseLegacySD;

View File

@ -1,6 +1,6 @@
#include "ultra64.h" #include "ultra64.h"
#include "global.h" #include "global.h"
#include "mixer.h" #include <libultraship/mixer.h>
#define DEFAULT_LEN_1CH 0x1A0 #define DEFAULT_LEN_1CH 0x1A0
#define DEFAULT_LEN_2CH 0x340 #define DEFAULT_LEN_2CH 0x340

View File

@ -1,7 +1,7 @@
#include "ultra64.h" #include "ultra64.h"
#include "global.h" #include "global.h"
#include "ultra64/abi.h" #include <ultra64/abi.h>
#include "mixer.h" #include <libultraship/mixer.h>
typedef struct { typedef struct {
u8 unk_0; u8 unk_0;

View File

@ -3,7 +3,7 @@
#include <soh/Enhancements/bootcommands.h> #include <soh/Enhancements/bootcommands.h>
#include "soh/OTRGlobals.h" #include "soh/OTRGlobals.h"
#include "../libultraship/CrashHandler.h" #include <libultraship/CrashHandler.h>
s32 gScreenWidth = SCREEN_WIDTH; s32 gScreenWidth = SCREEN_WIDTH;
@ -42,6 +42,8 @@ int main(int argc, char** argv)
{ {
#ifdef __linux__ #ifdef __linux__
SetupHandlerLinux(); SetupHandlerLinux();
#elif _WIN32
SetUnhandledExceptionFilter(seh_filter);
#endif #endif
GameConsole_Init(); GameConsole_Init();

View File

@ -515,13 +515,13 @@ void EnItem00_Init(Actor* thisx, GlobalContext* globalCtx) {
} }
if (!Actor_HasParent(&this->actor, globalCtx)) { if (!Actor_HasParent(&this->actor, globalCtx)) {
if (!gSaveContext.n64ddFlag) { if (getItemId != GI_NONE) {
if (getItemId != GI_NONE) { if (!gSaveContext.n64ddFlag) {
func_8002F554(&this->actor, globalCtx, getItemId); func_8002F554(&this->actor, globalCtx, getItemId);
} else {
getItem = Randomizer_GetRandomizedItem(getItemId, this->actor.id, this->ogParams, globalCtx->sceneNum);
GiveItemEntryFromActorWithFixedRange(&this->actor, globalCtx, getItem);
} }
} else {
getItem = Randomizer_GetItemFromActor(this->actor.id, globalCtx->sceneNum, this->ogParams, getItemId);
GiveItemEntryFromActorWithFixedRange(&this->actor, globalCtx, getItem);
} }
} }

View File

@ -4,7 +4,7 @@
#include <string.h> #include <string.h>
#include "soh/Enhancements/gameconsole.h" #include "soh/Enhancements/gameconsole.h"
#include "../libultraship/ImGuiImpl.h" #include <libultraship/ImGuiImpl.h>
#include "soh/frame_interpolation.h" #include "soh/frame_interpolation.h"
#include <time.h> #include <time.h>

View File

@ -10,7 +10,7 @@
#include "alloca.h" #include "alloca.h"
#include "textures/nintendo_rogo_static/nintendo_rogo_static.h" #include "textures/nintendo_rogo_static/nintendo_rogo_static.h"
#include <soh/Enhancements/bootcommands.h> #include <soh/Enhancements/bootcommands.h>
#include "GameVersions.h" #include <libultraship/GameVersions.h>
#include <soh/SaveManager.h> #include <soh/SaveManager.h>
const char* GetGameVersionString(); const char* GetGameVersionString();
@ -301,6 +301,9 @@ void Title_Init(GameState* thisx) {
saveloading = true; saveloading = true;
gSaveContext.fileNum = selectedfile; gSaveContext.fileNum = selectedfile;
Sram_OpenSave(); Sram_OpenSave();
Randomizer_LoadSettings("");
Randomizer_LoadHintLocations("");
Randomizer_LoadItemLocations("", true);
gSaveContext.gameMode = 0; gSaveContext.gameMode = 0;
gSaveContext.magic = gSaveContext.magic; gSaveContext.magic = gSaveContext.magic;
SET_NEXT_GAMESTATE(&this->state, Gameplay_Init, GlobalContext); SET_NEXT_GAMESTATE(&this->state, Gameplay_Init, GlobalContext);