Files
PDModdingCommunity_PD-Loader/source-code/source/plugins/TLAC/Components/Pause.h
T

213 lines
6.1 KiB
C++

#pragma once
#include "../Constants.h"
#include "EmulatorComponent.h"
#include "PlayerData.h"
#include "GameState.h"
#include "../Utilities/Drawing.h"
#include "Input/InputState.h"
#include "Input/TouchSliderState.h"
#include "Input/TouchPanelState.h"
#include <string>
#include <vector>
#include <chrono>
namespace TLAC::Components
{
class Pause : public EmulatorComponent
{
public:
Pause();
~Pause();
virtual const char* GetDisplayName() override;
virtual void Initialize(ComponentsManager*) override;
virtual void Update() override;
virtual void UpdatePostInput() override;
virtual void UpdateDraw2D() override;
virtual void OnFocusLost() override;
static bool pause; // set pause to change pause state
static bool giveUp; // set give up to end current song
static bool autoPause; // pause when window loses focus
private:
// this is a mess of static so that menuItems can work
static bool isPauseKeyTapped();
static bool isInGame();
static std::vector<bool> streamPlayStates;
static void InjectCode(void* address, const std::vector<uint8_t> data);
static bool isPaused; // tracks internal state
static void saveOldPatchOps();
static std::vector<uint8_t> origAetMovOp;
static uint8_t* aetMovPatchAddress;
static std::vector<uint8_t> origFramespeedOp;
static uint8_t* framespeedPatchAddress;
static float_t origDeltaFrameHistory;
static int32_t origDeltaFrameHistoryInt;
static float_t* deltaFrameHistoryAddress;
static int32_t* deltaFrameHistoryIntAddress;
static std::vector<uint8_t> origAgeageHairOp;
static uint8_t* ageageHairPatchAddress;
static bool hookedGiveUpFunc(void* cls);
static void setSEVolume(int amount);
static PlayerData* playerData;
static InputState* inputState;
static TouchSliderState* sliderState;
static TouchPanelState* panelState;
static ComponentsManager* componentsManager;
static const JvsButtons allButtons = (JvsButtons)(JVS_START | JVS_TRIANGLE | JVS_SQUARE | JVS_CROSS | JVS_CIRCLE | JVS_L | JVS_R); // deliberately only has control panel buttons
static JvsButtons filteredButtons;
static int lastTouchType;
static const int menuX = 640;
static const int menuY = 360;
static const int menuItemWidth = 150;
static const int menuItemHeight = 36;
static const int menuItemPadding = 12;
static const int menuItemTotalHeight = menuItemHeight + menuItemPadding;
static const int menuTextSize = 24;
static const uint32_t bgLayer = 0x18;
static const uint32_t contentLayer = 0x19; // same as startup screen
static bool showUI;
static int selResultAet1;
static int selResultAet2;
static int selResultAet3;
static int selResultAet4;
static int triangleAet;
static int squareAet;
static int crossAet;
static int circleAet;
enum menusets
{
MENUSET_MAIN = 0,
MENUSET_SEVOL = 1,
};
struct menuItem
{
std::string name;
void(*callback)();
bool keyRepeat; // unimplemented
menuItem(std::string _name, void(*_callback)(), bool _keyRepeat)
{
name = _name;
callback = _callback;
keyRepeat = _keyRepeat;
}
};
struct menuSet
{
std::string name;
std::vector<menuItem> items;
};
static int curMenuPos;
static std::vector<std::pair<menusets, int>> menuHistory; // used for implementing back button in menus
static menusets curMenuSet;
static std::chrono::time_point<std::chrono::high_resolution_clock> menuItemMoveTime; // used for animation
// static void mainmenu() { setMenuPos(MENUSET_MAIN, 0); menuHistory.resize(0); };
static void menuback()
{
if (menuHistory.size() == 0)
{
// mainmenu();
unpause();
}
else
{
std::pair<menusets, int> menuPos = menuHistory.back();
menuHistory.pop_back();
setMenuPos(menuPos.first, menuPos.second, false);
}
}
static void unpause() { pause = false; };
static void restart()
{
/*
140d0b510+2 = 0, 140d0b510+14 = 8 for restart
also 140cdd8d0+8 (something less than 0x1a but idk what) -- controls a switch statement in FUN_1400fddc0
0x18: PV seems good, audio good, chart and score broken? -- timing resets, notes don't
0x14: PVs a little bugged (not major), chart and scoring fine, life still doesn't reset
0x10: life resets now, but old graphics don't clear
0x15: same as 0x14
0x16: doesn't actually reset????
0x17: crash
0x12: like 0x10 but life isn't cleared
case 0x11 seems to clear life
case 0x15 seems to clear score (maybe note data)
case 0x18 seems to fix timing
patch 0x15 at 1401038cd (was 0x12), 0x18 at 140103b94 (was 0x16)
then call with 0x11
hopefully it'll work
percentage doesn't fully reset by the looks of it????
rip
(actually was hold and slide scores -- fixed by manually clearing them now)
*/
// inject flow overrides to switch cases in FUN_1400fddc0
InjectCode((void*)0x1401038cd, { 0x15 }); InjectCode((void*)0x140103b94, { 0x18 });
// set parameters
*(uint8_t*)PV_STATE_ADDRESS = 0; *(uint8_t*)PV_LOADING_STATE_ADDRESS = 8; *(int*)PV_INNER_LOADING_STATE_ADDRESS = 0x11;
void(*doLoading)(uint64_t) = (void(*)(uint64_t))0x1400fddc0;
// do loading until definitely done
while (*(int*)PV_INNER_LOADING_STATE_ADDRESS < 0x18)
{
doLoading(0x140cdd8d0);
}
// for some reason the above doesn't reset all scoring stuff
*(int*)0x140D0A9BC = 0; // total holds
*(int*)0x140D0A9B8 = 0; // hold + multi
*(int*)0x140D0A9C0 = 0; // slide
*(uint8_t*)0x140D0A50C = 0; // not clear flag
*(char*)0x140D0AA0F = 0; // chance time
// revert patches and unpause
InjectCode((void*)0x1401038cd, { 0x12 }); InjectCode((void*)0x140103b94, { 0x16 });
unpause();
}
static void giveup() { giveUp = true; };
static void sevolmenu() { setMenuPos(MENUSET_SEVOL, 1); };
static void sevolplus() { setSEVolume(10); };
static void sevolminus() { setSEVolume(-10); };
// contents are in Pause.cpp because they can't be inline here for a static (const) array/vec
static std::vector<menuSet> menu;
static void setMenuPos(menusets set, int pos, bool updateHistory = true);
static float getMenuAnimPos();
static TLAC::Utilities::Drawing::Point getMenuItemCoords(menusets set, int pos);
};
}