From 19c946d98a01ce62e51814365e203ed3a4fe5d54 Mon Sep 17 00:00:00 2001 From: etorth Date: Wed, 13 Dec 2023 00:43:14 -0800 Subject: [PATCH] f --- client/src/guimanager.hpp | 4 +- client/src/processrunnet.cpp | 2 +- client/src/runtimeconfigboard.cpp | 374 ++++++++++++++----------- client/src/runtimeconfigboard.hpp | 210 ++------------ client/src/runtimeconfigboardbak.cpp | 356 ++++++++++++++++++++++++ client/src/runtimeconfigboardbak.hpp | 241 ++++++++++++++++ client/src/runtimeconfigextboard.cpp | 402 --------------------------- client/src/runtimeconfigextboard.hpp | 73 ----- 8 files changed, 831 insertions(+), 831 deletions(-) create mode 100644 client/src/runtimeconfigboardbak.cpp create mode 100644 client/src/runtimeconfigboardbak.hpp delete mode 100644 client/src/runtimeconfigextboard.cpp delete mode 100644 client/src/runtimeconfigextboard.hpp diff --git a/client/src/guimanager.hpp b/client/src/guimanager.hpp index d922125f1..f107a638a 100644 --- a/client/src/guimanager.hpp +++ b/client/src/guimanager.hpp @@ -11,7 +11,7 @@ #include "quickaccessboard.hpp" #include "playerstateboard.hpp" #include "inputstringboard.hpp" -#include "runtimeconfigextboard.hpp" +#include "runtimeconfigboard.hpp" #include "secureditemlistboard.hpp" class ProcessRun; @@ -34,7 +34,7 @@ class GUIManager: public Widget QuickAccessBoard m_quickAccessBoard; PlayerStateBoard m_playerStateBoard; InputStringBoard m_inputStringBoard; - RuntimeConfigExtBoard m_runtimeConfigBoard; + RuntimeConfigBoard m_runtimeConfigBoard; SecuredItemListBoard m_securedItemListBoard; public: diff --git a/client/src/processrunnet.cpp b/client/src/processrunnet.cpp index d2973743a..47d6a086a 100644 --- a/client/src/processrunnet.cpp +++ b/client/src/processrunnet.cpp @@ -70,7 +70,7 @@ void ProcessRun::net_STARTGAMESCENE(const uint8_t *buf, size_t bufSize) void ProcessRun::net_PLAYERCONFIG(const uint8_t *buf, size_t bufSize) { const auto sdPC = cerealf::deserialize(buf, bufSize); - dynamic_cast(getWidget("RuntimeConfigBoard"))->setConfig(sdPC.runtimeConfig); + dynamic_cast(getWidget("RuntimeConfigBoard"))->setConfig(sdPC.runtimeConfig); for(const auto &[magicID, key]: sdPC.magicKeyList.keyList){ dynamic_cast(getWidget("SkillBoard"))->getConfig().setMagicKey(magicID, key); diff --git a/client/src/runtimeconfigboard.cpp b/client/src/runtimeconfigboard.cpp index 717c03a73..77e036043 100644 --- a/client/src/runtimeconfigboard.cpp +++ b/client/src/runtimeconfigboard.cpp @@ -6,76 +6,79 @@ #include "soundeffectdb.hpp" #include "processrun.hpp" #include "inventoryboard.hpp" -#include "runtimeconfigboard.hpp" extern Client *g_client; extern IMEBoard *g_imeBoard; extern PNGTexDB *g_progUseDB; extern SDLDevice *g_sdlDevice; -RuntimeConfigBoard::RuntimeConfigBoard(int argX, int argY, ProcessRun *proc, Widget *widgetPtr, bool autoDelete) - : Widget(DIR_UPLEFT, argX, argY, 0, 0, widgetPtr, autoDelete) - , m_closeButton +RuntimeConfigBoard::RuntimeConfigBoard(int argX, int argY, int argW, int argH, ProcessRun *proc, Widget *widgetPtr, bool autoDelete) + : Widget(DIR_UPLEFT, argX, argY, argW, argH, widgetPtr, autoDelete) + , m_frameBoard { DIR_UPLEFT, - 449, - 415, - {SYS_U32NIL, 0X0000001C, 0X0000001D}, - { - SYS_U32NIL, - SYS_U32NIL, - 0X01020000 + 105, - }, - - nullptr, - nullptr, - [this]() - { - setShow(false); - }, - - 0, - 0, 0, 0, + argW, + argH, - true, - true, this, + false, } - , m_musicSwitch + , m_checkLabel { DIR_UPLEFT, - 431, - 85, + 50, + 130, + + colorf::RGBA(231, 231, 189, 128), + 16, + 16, + m_sdRuntimeConfig.ime, - m_sdRuntimeConfig.bgm, + 8, + + u8"拼音输入法", + 1, + 12, 0, - 2, + colorf::WHITE + colorf::A_SHF(255), - [this](int) - { - g_sdlDevice->setBGMVolume(getMusicVolume().value_or(0.0f)); - }, - this + this, + false, } - , m_soundEffectSwitch + , m_texSliderBar { DIR_UPLEFT, - 431, - 145, + 50, + 200, - m_sdRuntimeConfig.soundEff, - 0, - 2, + 100, + true, - [this](int) - { - g_sdlDevice->setSoundEffectVolume(getSoundEffectVolume().value_or(0.0f)); - }, - this + 1, + [](float){}, + + this, + false, + } + + , m_texSliderBarVertical + { + DIR_UPLEFT, + 50, + 250, + + 100, + false, + + 1, + [](float){}, + + this, + false, } , m_musicSlider @@ -84,15 +87,11 @@ RuntimeConfigBoard::RuntimeConfigBoard(int argX, int argY, ProcessRun *proc, Wid 280, 124, 194, - 6, true, 1, - [this](float val) + [this](float) { - m_sdRuntimeConfig.bgmValue = std::lround(val * 100.0); - g_sdlDevice->setBGMVolume(getMusicVolume().value_or(0.0f)); - reportRuntimeConfig(); }, this, } @@ -103,29 +102,126 @@ RuntimeConfigBoard::RuntimeConfigBoard(int argX, int argY, ProcessRun *proc, Wid 280, 184, 194, - 6, true, 1, - [this](float val) + [this](float) { - m_sdRuntimeConfig.soundEffValue = std::lround(val * 100.0); - g_sdlDevice->setSoundEffectVolume(getSoundEffectVolume().value_or(0.0f)); - reportRuntimeConfig(); }, this, } - , m_entryProtoList + , m_item1 + { + DIR_UPLEFT, + 0, + 0, + u8"你好", + } + + , m_item2 { - {{u8"和平攻击", u8"组队攻击", u8"行会攻击", u8"全体攻击"}, std::ref(m_sdRuntimeConfig.attackMode), ATKMODE_BEGIN, [this](int) + DIR_UPLEFT, + 0, + 0, + u8"天气很好", + } + + , m_itemCheckLabel + { + DIR_UPLEFT, + 0, + 0, + + colorf::RGBA(231, 231, 189, 128), + 16, + 16, + m_sdRuntimeConfig.ime, + + 8, + + u8"拼音输入法", + 1, + 12, + 0, + colorf::WHITE + colorf::A_SHF(255), + } + + , m_menuBoard + { + DIR_UPLEFT, + 0, + 0, + + {}, + + 10, + 50, + { - }}, + {&m_item1, false}, + {&m_item2, false}, + {&m_itemCheckLabel, false}, + }, - {{u8"拼音输入法"}, std::ref(m_sdRuntimeConfig.ime), 0, [this](int state) + {10, 10, 10, 10}, + } + + , m_menuButtonGfx + { + DIR_UPLEFT, + 0, + 0, + + u8"点击菜单", + 1, + 12, + 0, + } + + , m_menuButton + { + DIR_UPLEFT, + 200, + 250, + + {&m_menuButtonGfx, false}, + {&m_menuBoard , false}, + + {}, + + this, + false, + } + + , m_selectBoard + { + DIR_UPLEFT, + 20, + 20, + 50, + + false, + {}, + + false, + + 1, + 12, + 0, + colorf::WHITE + colorf::A_SHF(255), + 0, + + LALIGN_LEFT, + 0, + 0, + + [](const std::unordered_map &, int, int) { - g_imeBoard->setActive(state); - }}, + }, + + this, + false, } , m_processRun([proc]() @@ -133,6 +229,16 @@ RuntimeConfigBoard::RuntimeConfigBoard(int argX, int argY, ProcessRun *proc, Wid fflassert(proc); return proc; }()) { + m_selectBoard.loadXML( + R"###( )###""\n" + R"###( 系统 )###""\n" + R"###( 社交 )###""\n" + R"###( 网络 )###""\n" + R"###( 游戏 )###""\n" + R"###( 帮助 )###""\n" + R"###( )###""\n" + ); + // 1.0f -> SDL_MIX_MAXVOLUME // SDL_mixer initial sound/music volume is SDL_MIX_MAXVOLUME @@ -140,82 +246,49 @@ RuntimeConfigBoard::RuntimeConfigBoard(int argX, int argY, ProcessRun *proc, Wid m_soundEffectSlider.setValue(to_f(SDRuntimeConfig().soundEffValue) / 100.0, false); setShow(false); - auto texPtr = g_progUseDB->retrieve(0X0000001B); - - fflassert(texPtr); - std::tie(m_w, m_h) = SDLDeviceHelper::getTextureSize(texPtr); - - m_switchList.reserve(m_entryProtoList.size()); - for(auto &[titleList, valueRef, valueOffset, onSwitch]: m_entryProtoList){ - // can not skip invalid entry - // m_entryProtoList and m_switch shares indices - fflassert(!titleList.empty()); - const auto [infoX, infoY, buttonX, buttonY] = getEntryPLoc(m_switchList.size()); +} - if(titleList.size() == 1){ - m_switchList.push_back(new OnOffButton - { - DIR_UPLEFT, - buttonX, - buttonY, - valueRef, - valueOffset, - 2, - onSwitch, - this, - true, - }); - } - else{ - m_switchList.push_back(new SwitchNextButton - { - DIR_UPLEFT, - buttonX, - buttonY, - valueRef, - valueOffset, - to_d(titleList.size()), - onSwitch, - this, - true, - }); +void RuntimeConfigBoard::drawEx(int dstX, int dstY, int srcX, int srcY, int srcW, int srcH) const +{ + m_frameBoard.drawEx(dstX, dstY, srcX, srcY, srcW, srcH); + for(auto p: + { + static_cast(&m_selectBoard), + static_cast(&m_menuButton), + static_cast(&m_checkLabel), + static_cast(&m_texSliderBar), + static_cast(&m_texSliderBarVertical), + }){ + auto drawSrcX = srcX; + auto drawSrcY = srcY; + auto drawSrcW = srcW; + auto drawSrcH = srcH; + auto drawDstX = dstX; + auto drawDstY = dstY; + + if(mathf::cropChildROI( + &drawSrcX, &drawSrcY, + &drawSrcW, &drawSrcH, + &drawDstX, &drawDstY, + + w(), + h(), + + p->dx(), + p->dy(), + p-> w(), + p-> h())){ + p->drawEx(drawDstX, drawDstY, drawSrcX, drawSrcY, drawSrcW, drawSrcH); } } -} -void RuntimeConfigBoard::drawEx(int dstX, int dstY, int, int, int, int) const -{ - g_sdlDevice->drawTexture(g_progUseDB->retrieve(0X00000100), dstX, dstY); drawEntryTitle(u8"【游戏设置】", 255, 35); - m_closeButton.draw(); drawEntryTitle(u8"背景音乐", 345, 97); drawEntryTitle(u8"音效", 345, 157); - m_musicSwitch.draw(); - m_soundEffectSwitch.draw(); - - if(m_musicSwitch.getValue()){ - m_musicSlider.draw(); - } - - if(m_soundEffectSwitch.getValue()){ - m_soundEffectSlider.draw(); - } - - for(size_t i = 0; i < m_switchList.size(); ++i){ - const auto buttonPtr = m_switchList.at(i); - const auto &titleList = std::get<0>(m_entryProtoList.at(i)); - const auto &[infoX, infoY, buttonX, buttonY] = getEntryPLoc(i); - - if(titleList.size() == 1){ - drawEntryTitle(titleList.front().c_str(), infoX, infoY); - } - else{ - drawEntryTitle(titleList.at(buttonPtr->getValue() - buttonPtr->getValueOffset()).c_str(), infoX, infoY); - } - buttonPtr->draw(); - } + m_musicSlider.draw(); + m_soundEffectSlider.draw(); } bool RuntimeConfigBoard::processEvent(const SDL_Event &event, bool valid) @@ -230,29 +303,26 @@ bool RuntimeConfigBoard::processEvent(const SDL_Event &event, bool valid) for(auto widgetPtr: { - static_cast(&m_closeButton), - static_cast(&m_musicSwitch), - static_cast(&m_soundEffectSwitch), + static_cast(&m_selectBoard), + static_cast(&m_menuButton), + static_cast(&m_checkLabel), + static_cast(&m_frameBoard), + static_cast(&m_texSliderBar), + static_cast(&m_texSliderBarVertical), }){ if(widgetPtr->processEvent(event, valid)){ - return consumeFocus(true); + return true; } } - if(m_musicSwitch.getValue() && m_musicSlider.processEvent(event, valid)){ + if(m_musicSlider.processEvent(event, valid)){ return consumeFocus(true); } - if(m_soundEffectSwitch.getValue() && m_soundEffectSlider.processEvent(event, valid)){ + if(m_soundEffectSlider.processEvent(event, valid)){ return consumeFocus(true); } - for(const auto buttonPtr: m_switchList){ - if(buttonPtr->processEvent(event, valid)){ - return consumeFocus(true); - } - } - switch(event.type){ case SDL_KEYDOWN: { @@ -306,36 +376,12 @@ void RuntimeConfigBoard::drawEntryTitle(const char8_t *info, int dstCenterX, int titleBoard.drawAt(DIR_NONE, x() + dstCenterX, y() + dstCenterY); } -std::tuple RuntimeConfigBoard::getEntryPLoc(size_t entry) -{ - if(entry < 12){ - return {100, 67 + entry * 30, 186, 55 + entry * 30}; - } - else if(entry >= 12 && entry < 19){ - return {345, 67 + (entry - 7) * 30, 431, 55 + (entry - 7) * 30}; - } - else{ - throw fflvalue(entry); - } -} - void RuntimeConfigBoard::setConfig(SDRuntimeConfig config) { m_sdRuntimeConfig = std::move(config); m_musicSlider.setValue(m_sdRuntimeConfig.bgmValue / 100.0, false); - g_sdlDevice->setBGMVolume(getMusicVolume().value_or(0.0f)); - m_soundEffectSlider.setValue(m_sdRuntimeConfig.soundEffValue / 100.0, false); - g_sdlDevice->setSoundEffectVolume(getSoundEffectVolume().value_or(0.0f)); - - for(auto buttonPtr: m_switchList){ - buttonPtr->triggerCallback(); - } - - for(auto buttonPtr: {&m_musicSwitch, &m_soundEffectSwitch}){ - buttonPtr->triggerCallback(); - } } void RuntimeConfigBoard::reportRuntimeConfig() diff --git a/client/src/runtimeconfigboard.hpp b/client/src/runtimeconfigboard.hpp index 2d7991e5c..02c48d58e 100644 --- a/client/src/runtimeconfigboard.hpp +++ b/client/src/runtimeconfigboard.hpp @@ -3,200 +3,52 @@ #include #include "mathf.hpp" #include "widget.hpp" +#include "menuboard.hpp" +#include "menubutton.hpp" +#include "checklabel.hpp" #include "labelboard.hpp" #include "texslider.hpp" #include "tritexbutton.hpp" +#include "texsliderbar.hpp" +#include "resizableframeboard.hpp" class ProcessRun; class RuntimeConfigBoard: public Widget { private: - class BindIntegerRefButton: public TritexButton - { - // each button binds to an integer reference in SDRuntimeConfig - // reference value get udpated when the button is clicked - - // the reference value can be updated outside without let the button know - // need to call triggerCallback() notify this change - - private: - std::tuple m_valueState; - - private: - std::function m_onSwitch; - - public: - BindIntegerRefButton(dir8_t argDir, int argX, int argY, const uint32_t (& texIDList)[3], int &valueRef, int valueOffset, int valueCount, std::function onSwitch, Widget *widgetPtr = nullptr, bool autoDelete = false) - : TritexButton - { - argDir, - argX, - argY, - - texIDList, - { - SYS_U32NIL, - SYS_U32NIL, - 0X01020000 + 105, - }, - - nullptr, - nullptr, - [this]() - { - std::get<0>(m_valueState) = ((getValue() - getValueOffset() + 1) % getValueCount()) + getValueOffset(); - triggerCallback(); - - for(auto parentPtr = parent(); parentPtr; parentPtr = parentPtr->parent()){ - if(auto configBoardPtr = dynamic_cast(parentPtr)){ - configBoardPtr->reportRuntimeConfig(); - break; - } - } - }, - - 0, - 0, - 0, - 0, - - false, - false, - widgetPtr, - autoDelete, - } - - , m_valueState([&valueRef, valueOffset, valueCount]() - { - fflassert(valueOffset >= 0, valueOffset); - fflassert(valueCount > 0, valueCount); - - fflassert(valueRef >= valueOffset, valueRef, valueOffset); - fflassert(valueRef < valueCount, valueRef, valueCount); - - return std::tuple(valueRef, valueOffset, valueCount); - }()) - - , m_onSwitch(std::move(onSwitch)) - {} - - public: - int getValue() const - { - return std::get<0>(m_valueState); - } - - int getValueOffset() const - { - return std::get<1>(m_valueState); - } - - int getValueCount() const - { - return std::get<2>(m_valueState); - } - - public: - void triggerCallback() - { - if(m_onSwitch){ - m_onSwitch(getValue()); - } - } - }; - - class SwitchNextButton: public BindIntegerRefButton - { - public: - SwitchNextButton(dir8_t argDir, int argX, int argY, int &valueRef, int valueOffset, int valueCount, std::function onSwitch, Widget *widgetPtr = nullptr, bool autoDelete = false) - : BindIntegerRefButton - { - argDir, - argX, - argY, - - { - 0X0000130, - 0X0000131, - 0X0000130, - }, - - valueRef, - valueOffset, - valueCount, - std::move(onSwitch), - - widgetPtr, - autoDelete, - } - {} - }; - - class OnOffButton: public BindIntegerRefButton - { - public: - OnOffButton(dir8_t argDir, int argX, int argY, int &valueRef, int valueOffset, int valueCount, std::function onSwitch, Widget *widgetPtr = nullptr, bool autoDelete = false) - : BindIntegerRefButton - { - argDir, - argX, - argY, - - { - to_u32(valueRef ? 0X00000110 : 0X00000120), - to_u32(valueRef ? 0X00000111 : 0X00000121), - to_u32(valueRef ? 0X00000111 : 0X00000121), // click triggers tex switch - }, - - valueRef, - valueOffset, - valueCount, - - [onSwitch = std::move(onSwitch), this](int state) - { - setTexID( - { - to_u32(getValue() ? 0X00000110 : 0X00000120), - to_u32(getValue() ? 0X00000111 : 0X00000121), - to_u32(getValue() ? 0X00000111 : 0X00000121), // click triggers tex switch - }); - - if(onSwitch){ - onSwitch(state); - } - }, - - widgetPtr, - autoDelete, - } - {} - }; + SDRuntimeConfig m_sdRuntimeConfig; private: - TritexButton m_closeButton; + ResizableFrameBoard m_frameBoard; private: - SDRuntimeConfig m_sdRuntimeConfig; + CheckLabel m_checkLabel; + TexSliderBar m_texSliderBar; + TexSliderBar m_texSliderBarVertical; private: - OnOffButton m_musicSwitch; - OnOffButton m_soundEffectSwitch; + TexSliderBar m_musicSlider; + TexSliderBar m_soundEffectSlider; private: - TexSlider m_musicSlider; - TexSlider m_soundEffectSlider; + LabelBoard m_item1; + LabelBoard m_item2; + CheckLabel m_itemCheckLabel; + + MenuBoard m_menuBoard; private: - const std::vector, std::reference_wrapper, int, std::function>> m_entryProtoList; + LabelBoard m_menuButtonGfx; + MenuButton m_menuButton; private: - std::vector m_switchList; + LayoutBoard m_selectBoard; private: ProcessRun *m_processRun; public: - RuntimeConfigBoard(int, int, ProcessRun *, Widget * = nullptr, bool = false); + RuntimeConfigBoard(int, int, int, int, ProcessRun *, Widget * = nullptr, bool = false); public: void drawEx(int, int, int, int, int, int) const override; @@ -207,26 +59,6 @@ class RuntimeConfigBoard: public Widget protected: void drawEntryTitle(const char8_t *, int, int) const; - protected: - static std::tuple getEntryPLoc(size_t); - - public: - std::optional getMusicVolume() const - { - if(m_musicSwitch.getValue()){ - return mathf::bound(m_musicSlider.getValue(), 0.0f, 1.0f); - } - return {}; - } - - std::optional getSoundEffectVolume() const - { - if(m_soundEffectSwitch.getValue()){ - return mathf::bound(m_soundEffectSlider.getValue(), 0.0f, 1.0f); - } - return {}; - } - private: void reportRuntimeConfig(); diff --git a/client/src/runtimeconfigboardbak.cpp b/client/src/runtimeconfigboardbak.cpp new file mode 100644 index 000000000..6fe54a905 --- /dev/null +++ b/client/src/runtimeconfigboardbak.cpp @@ -0,0 +1,356 @@ +#include "luaf.hpp" +#include "client.hpp" +#include "imeboard.hpp" +#include "pngtexdb.hpp" +#include "sdldevice.hpp" +#include "soundeffectdb.hpp" +#include "processrun.hpp" +#include "inventoryboard.hpp" +#include "runtimeconfigboardbak.hpp" + +extern Client *g_client; +extern IMEBoard *g_imeBoard; +extern PNGTexDB *g_progUseDB; +extern SDLDevice *g_sdlDevice; + +RuntimeConfigBoard_bak::RuntimeConfigBoard_bak(int argX, int argY, ProcessRun *proc, Widget *widgetPtr, bool autoDelete) + : Widget(DIR_UPLEFT, argX, argY, 0, 0, widgetPtr, autoDelete) + , m_closeButton + { + DIR_UPLEFT, + 449, + 415, + {SYS_U32NIL, 0X0000001C, 0X0000001D}, + { + SYS_U32NIL, + SYS_U32NIL, + 0X01020000 + 105, + }, + + nullptr, + nullptr, + [this]() + { + setShow(false); + }, + + 0, + 0, + 0, + 0, + + true, + true, + this, + } + + , m_musicSwitch + { + DIR_UPLEFT, + 431, + 85, + + m_sdRuntimeConfig.bgm, + 0, + 2, + + [this](int) + { + g_sdlDevice->setBGMVolume(getMusicVolume().value_or(0.0f)); + }, + this + } + + , m_soundEffectSwitch + { + DIR_UPLEFT, + 431, + 145, + + m_sdRuntimeConfig.soundEff, + 0, + 2, + + [this](int) + { + g_sdlDevice->setSoundEffectVolume(getSoundEffectVolume().value_or(0.0f)); + }, + this + } + + , m_musicSlider + { + DIR_UPLEFT, + 280, + 124, + 194, + 6, + + true, + 1, + [this](float val) + { + m_sdRuntimeConfig.bgmValue = std::lround(val * 100.0); + g_sdlDevice->setBGMVolume(getMusicVolume().value_or(0.0f)); + reportRuntimeConfig(); + }, + this, + } + + , m_soundEffectSlider + { + DIR_UPLEFT, + 280, + 184, + 194, + 6, + + true, + 1, + [this](float val) + { + m_sdRuntimeConfig.soundEffValue = std::lround(val * 100.0); + g_sdlDevice->setSoundEffectVolume(getSoundEffectVolume().value_or(0.0f)); + reportRuntimeConfig(); + }, + this, + } + + , m_entryProtoList + { + {{u8"和平攻击", u8"组队攻击", u8"行会攻击", u8"全体攻击"}, std::ref(m_sdRuntimeConfig.attackMode), ATKMODE_BEGIN, [this](int) + { + }}, + + {{u8"拼音输入法"}, std::ref(m_sdRuntimeConfig.ime), 0, [this](int state) + { + g_imeBoard->setActive(state); + }}, + } + + , m_processRun([proc]() + { + fflassert(proc); return proc; + }()) +{ + // 1.0f -> SDL_MIX_MAXVOLUME + // SDL_mixer initial sound/music volume is SDL_MIX_MAXVOLUME + + m_musicSlider.setValue(to_f(SDRuntimeConfig().bgmValue) / 100.0, false); + m_soundEffectSlider.setValue(to_f(SDRuntimeConfig().soundEffValue) / 100.0, false); + + setShow(false); + auto texPtr = g_progUseDB->retrieve(0X0000001B); + + fflassert(texPtr); + std::tie(m_w, m_h) = SDLDeviceHelper::getTextureSize(texPtr); + + m_switchList.reserve(m_entryProtoList.size()); + for(auto &[titleList, valueRef, valueOffset, onSwitch]: m_entryProtoList){ + // can not skip invalid entry + // m_entryProtoList and m_switch shares indices + fflassert(!titleList.empty()); + const auto [infoX, infoY, buttonX, buttonY] = getEntryPLoc(m_switchList.size()); + + if(titleList.size() == 1){ + m_switchList.push_back(new OnOffButton + { + DIR_UPLEFT, + buttonX, + buttonY, + valueRef, + valueOffset, + 2, + onSwitch, + this, + true, + }); + } + else{ + m_switchList.push_back(new SwitchNextButton + { + DIR_UPLEFT, + buttonX, + buttonY, + valueRef, + valueOffset, + to_d(titleList.size()), + onSwitch, + this, + true, + }); + } + } +} + +void RuntimeConfigBoard_bak::drawEx(int dstX, int dstY, int, int, int, int) const +{ + g_sdlDevice->drawTexture(g_progUseDB->retrieve(0X00000100), dstX, dstY); + drawEntryTitle(u8"【游戏设置】", 255, 35); + m_closeButton.draw(); + + drawEntryTitle(u8"背景音乐", 345, 97); + drawEntryTitle(u8"音效", 345, 157); + + m_musicSwitch.draw(); + m_soundEffectSwitch.draw(); + + if(m_musicSwitch.getValue()){ + m_musicSlider.draw(); + } + + if(m_soundEffectSwitch.getValue()){ + m_soundEffectSlider.draw(); + } + + for(size_t i = 0; i < m_switchList.size(); ++i){ + const auto buttonPtr = m_switchList.at(i); + const auto &titleList = std::get<0>(m_entryProtoList.at(i)); + const auto &[infoX, infoY, buttonX, buttonY] = getEntryPLoc(i); + + if(titleList.size() == 1){ + drawEntryTitle(titleList.front().c_str(), infoX, infoY); + } + else{ + drawEntryTitle(titleList.at(buttonPtr->getValue() - buttonPtr->getValueOffset()).c_str(), infoX, infoY); + } + buttonPtr->draw(); + } +} + +bool RuntimeConfigBoard_bak::processEvent(const SDL_Event &event, bool valid) +{ + if(!valid){ + return consumeFocus(false); + } + + if(!show()){ + return consumeFocus(false); + } + + for(auto widgetPtr: + { + static_cast(&m_closeButton), + static_cast(&m_musicSwitch), + static_cast(&m_soundEffectSwitch), + }){ + if(widgetPtr->processEvent(event, valid)){ + return consumeFocus(true); + } + } + + if(m_musicSwitch.getValue() && m_musicSlider.processEvent(event, valid)){ + return consumeFocus(true); + } + + if(m_soundEffectSwitch.getValue() && m_soundEffectSlider.processEvent(event, valid)){ + return consumeFocus(true); + } + + for(const auto buttonPtr: m_switchList){ + if(buttonPtr->processEvent(event, valid)){ + return consumeFocus(true); + } + } + + switch(event.type){ + case SDL_KEYDOWN: + { + if(event.key.keysym.sym == SDLK_ESCAPE){ + setShow(false); + return consumeFocus(false); + } + return consumeFocus(true); + } + case SDL_MOUSEMOTION: + { + if((event.motion.state & SDL_BUTTON_LMASK) && (in(event.motion.x, event.motion.y) || focus())){ + const auto [rendererW, rendererH] = g_sdlDevice->getRendererSize(); + const int maxX = rendererW - w(); + const int maxY = rendererH - h(); + + const int newX = std::max(0, std::min(maxX, x() + event.motion.xrel)); + const int newY = std::max(0, std::min(maxY, y() + event.motion.yrel)); + moveBy(newX - x(), newY - y()); + return consumeFocus(true); + } + return consumeFocus(false); + } + case SDL_MOUSEBUTTONUP: + case SDL_MOUSEBUTTONDOWN: + { + return consumeFocus(in(event.button.x, event.button.y)); + } + default: + { + return consumeFocus(false); + } + } +} + +void RuntimeConfigBoard_bak::drawEntryTitle(const char8_t *info, int dstCenterX, int dstCenterY) const +{ + const LabelBoard titleBoard + { + DIR_NONE, + 0, // reset by new width + 0, + to_u8cstr(info), + + 1, + 12, + 0, + + colorf::RGBA(0XFF, 0XFF, 0X00, 0XFF), + }; + titleBoard.drawAt(DIR_NONE, x() + dstCenterX, y() + dstCenterY); +} + +std::tuple RuntimeConfigBoard_bak::getEntryPLoc(size_t entry) +{ + if(entry < 12){ + return {100, 67 + entry * 30, 186, 55 + entry * 30}; + } + else if(entry >= 12 && entry < 19){ + return {345, 67 + (entry - 7) * 30, 431, 55 + (entry - 7) * 30}; + } + else{ + throw fflvalue(entry); + } +} + +void RuntimeConfigBoard_bak::setConfig(SDRuntimeConfig config) +{ + m_sdRuntimeConfig = std::move(config); + + m_musicSlider.setValue(m_sdRuntimeConfig.bgmValue / 100.0, false); + g_sdlDevice->setBGMVolume(getMusicVolume().value_or(0.0f)); + + m_soundEffectSlider.setValue(m_sdRuntimeConfig.soundEffValue / 100.0, false); + g_sdlDevice->setSoundEffectVolume(getSoundEffectVolume().value_or(0.0f)); + + for(auto buttonPtr: m_switchList){ + buttonPtr->triggerCallback(); + } + + for(auto buttonPtr: {&m_musicSwitch, &m_soundEffectSwitch}){ + buttonPtr->triggerCallback(); + } +} + +void RuntimeConfigBoard_bak::reportRuntimeConfig() +{ + CMSetRuntimeConfig cmSRC; + std::memset(&cmSRC, 0, sizeof(cmSRC)); + + cmSRC.bgm = getConfig().bgm; + cmSRC.bgmValue = getConfig().bgmValue; + + cmSRC.soundEff = getConfig().soundEff; + cmSRC.soundEffValue = getConfig().soundEffValue; + + cmSRC.ime = getConfig().ime; + cmSRC.attackMode = getConfig().attackMode; + + g_client->send(CM_SETRUNTIMECONFIG, cmSRC); +} diff --git a/client/src/runtimeconfigboardbak.hpp b/client/src/runtimeconfigboardbak.hpp new file mode 100644 index 000000000..102be6bb9 --- /dev/null +++ b/client/src/runtimeconfigboardbak.hpp @@ -0,0 +1,241 @@ +#pragma once +#include +#include +#include "mathf.hpp" +#include "widget.hpp" +#include "labelboard.hpp" +#include "texslider.hpp" +#include "tritexbutton.hpp" + +class ProcessRun; +class RuntimeConfigBoard_bak: public Widget +{ + private: + class BindIntegerRefButton: public TritexButton + { + // each button binds to an integer reference in SDRuntimeConfig + // reference value get udpated when the button is clicked + + // the reference value can be updated outside without let the button know + // need to call triggerCallback() notify this change + + private: + std::tuple m_valueState; + + private: + std::function m_onSwitch; + + public: + BindIntegerRefButton(dir8_t argDir, int argX, int argY, const uint32_t (& texIDList)[3], int &valueRef, int valueOffset, int valueCount, std::function onSwitch, Widget *widgetPtr = nullptr, bool autoDelete = false) + : TritexButton + { + argDir, + argX, + argY, + + texIDList, + { + SYS_U32NIL, + SYS_U32NIL, + 0X01020000 + 105, + }, + + nullptr, + nullptr, + [this]() + { + std::get<0>(m_valueState) = ((getValue() - getValueOffset() + 1) % getValueCount()) + getValueOffset(); + triggerCallback(); + + for(auto parentPtr = parent(); parentPtr; parentPtr = parentPtr->parent()){ + if(auto configBoardPtr = dynamic_cast(parentPtr)){ + configBoardPtr->reportRuntimeConfig(); + break; + } + } + }, + + 0, + 0, + 0, + 0, + + false, + false, + widgetPtr, + autoDelete, + } + + , m_valueState([&valueRef, valueOffset, valueCount]() + { + fflassert(valueOffset >= 0, valueOffset); + fflassert(valueCount > 0, valueCount); + + fflassert(valueRef >= valueOffset, valueRef, valueOffset); + fflassert(valueRef < valueCount, valueRef, valueCount); + + return std::tuple(valueRef, valueOffset, valueCount); + }()) + + , m_onSwitch(std::move(onSwitch)) + {} + + public: + int getValue() const + { + return std::get<0>(m_valueState); + } + + int getValueOffset() const + { + return std::get<1>(m_valueState); + } + + int getValueCount() const + { + return std::get<2>(m_valueState); + } + + public: + void triggerCallback() + { + if(m_onSwitch){ + m_onSwitch(getValue()); + } + } + }; + + class SwitchNextButton: public BindIntegerRefButton + { + public: + SwitchNextButton(dir8_t argDir, int argX, int argY, int &valueRef, int valueOffset, int valueCount, std::function onSwitch, Widget *widgetPtr = nullptr, bool autoDelete = false) + : BindIntegerRefButton + { + argDir, + argX, + argY, + + { + 0X0000130, + 0X0000131, + 0X0000130, + }, + + valueRef, + valueOffset, + valueCount, + std::move(onSwitch), + + widgetPtr, + autoDelete, + } + {} + }; + + class OnOffButton: public BindIntegerRefButton + { + public: + OnOffButton(dir8_t argDir, int argX, int argY, int &valueRef, int valueOffset, int valueCount, std::function onSwitch, Widget *widgetPtr = nullptr, bool autoDelete = false) + : BindIntegerRefButton + { + argDir, + argX, + argY, + + { + to_u32(valueRef ? 0X00000110 : 0X00000120), + to_u32(valueRef ? 0X00000111 : 0X00000121), + to_u32(valueRef ? 0X00000111 : 0X00000121), // click triggers tex switch + }, + + valueRef, + valueOffset, + valueCount, + + [onSwitch = std::move(onSwitch), this](int state) + { + setTexID( + { + to_u32(getValue() ? 0X00000110 : 0X00000120), + to_u32(getValue() ? 0X00000111 : 0X00000121), + to_u32(getValue() ? 0X00000111 : 0X00000121), // click triggers tex switch + }); + + if(onSwitch){ + onSwitch(state); + } + }, + + widgetPtr, + autoDelete, + } + {} + }; + + private: + TritexButton m_closeButton; + + private: + SDRuntimeConfig m_sdRuntimeConfig; + + private: + OnOffButton m_musicSwitch; + OnOffButton m_soundEffectSwitch; + + private: + TexSlider m_musicSlider; + TexSlider m_soundEffectSlider; + + private: + const std::vector, std::reference_wrapper, int, std::function>> m_entryProtoList; + + private: + std::vector m_switchList; + + private: + ProcessRun *m_processRun; + + public: + RuntimeConfigBoard_bak(int, int, ProcessRun *, Widget * = nullptr, bool = false); + + public: + void drawEx(int, int, int, int, int, int) const override; + + public: + bool processEvent(const SDL_Event &, bool) override; + + protected: + void drawEntryTitle(const char8_t *, int, int) const; + + protected: + static std::tuple getEntryPLoc(size_t); + + public: + std::optional getMusicVolume() const + { + if(m_musicSwitch.getValue()){ + return mathf::bound(m_musicSlider.getValue(), 0.0f, 1.0f); + } + return {}; + } + + std::optional getSoundEffectVolume() const + { + if(m_soundEffectSwitch.getValue()){ + return mathf::bound(m_soundEffectSlider.getValue(), 0.0f, 1.0f); + } + return {}; + } + + private: + void reportRuntimeConfig(); + + public: + const SDRuntimeConfig &getConfig() const + { + return m_sdRuntimeConfig; + } + + public: + void setConfig(SDRuntimeConfig); +}; diff --git a/client/src/runtimeconfigextboard.cpp b/client/src/runtimeconfigextboard.cpp deleted file mode 100644 index 61be55d92..000000000 --- a/client/src/runtimeconfigextboard.cpp +++ /dev/null @@ -1,402 +0,0 @@ -#include "luaf.hpp" -#include "client.hpp" -#include "imeboard.hpp" -#include "pngtexdb.hpp" -#include "sdldevice.hpp" -#include "soundeffectdb.hpp" -#include "processrun.hpp" -#include "inventoryboard.hpp" - -extern Client *g_client; -extern IMEBoard *g_imeBoard; -extern PNGTexDB *g_progUseDB; -extern SDLDevice *g_sdlDevice; - -RuntimeConfigExtBoard::RuntimeConfigExtBoard(int argX, int argY, int argW, int argH, ProcessRun *proc, Widget *widgetPtr, bool autoDelete) - : Widget(DIR_UPLEFT, argX, argY, argW, argH, widgetPtr, autoDelete) - , m_frameBoard - { - DIR_UPLEFT, - 0, - 0, - argW, - argH, - - this, - false, - } - - , m_checkLabel - { - DIR_UPLEFT, - 50, - 130, - - colorf::RGBA(231, 231, 189, 128), - 16, - 16, - m_sdRuntimeConfig.ime, - - 8, - - u8"拼音输入法", - 1, - 12, - 0, - colorf::WHITE + colorf::A_SHF(255), - - this, - false, - } - - , m_texSliderBar - { - DIR_UPLEFT, - 50, - 200, - - 100, - true, - - 1, - [](float){}, - - this, - false, - } - - , m_texSliderBarVertical - { - DIR_UPLEFT, - 50, - 250, - - 100, - false, - - 1, - [](float){}, - - this, - false, - } - - , m_musicSlider - { - DIR_UPLEFT, - 280, - 124, - 194, - - true, - 1, - [this](float) - { - }, - this, - } - - , m_soundEffectSlider - { - DIR_UPLEFT, - 280, - 184, - 194, - - true, - 1, - [this](float) - { - }, - this, - } - - , m_item1 - { - DIR_UPLEFT, - 0, - 0, - u8"你好", - } - - , m_item2 - { - DIR_UPLEFT, - 0, - 0, - u8"天气很好", - } - - , m_itemCheckLabel - { - DIR_UPLEFT, - 0, - 0, - - colorf::RGBA(231, 231, 189, 128), - 16, - 16, - m_sdRuntimeConfig.ime, - - 8, - - u8"拼音输入法", - 1, - 12, - 0, - colorf::WHITE + colorf::A_SHF(255), - } - - , m_menuBoard - { - DIR_UPLEFT, - 0, - 0, - - {}, - - 10, - 50, - - { - {&m_item1, false}, - {&m_item2, false}, - {&m_itemCheckLabel, false}, - }, - - {10, 10, 10, 10}, - } - - , m_menuButtonGfx - { - DIR_UPLEFT, - 0, - 0, - - u8"点击菜单", - 1, - 12, - 0, - } - - , m_menuButton - { - DIR_UPLEFT, - 200, - 250, - - {&m_menuButtonGfx, false}, - {&m_menuBoard , false}, - - {}, - - this, - false, - } - - , m_selectBoard - { - DIR_UPLEFT, - 20, - 20, - 50, - - false, - {}, - - false, - - 1, - 12, - 0, - colorf::WHITE + colorf::A_SHF(255), - 0, - - LALIGN_LEFT, - 0, - 0, - - [](const std::unordered_map &, int, int) - { - }, - - this, - false, - } - - , m_processRun([proc]() - { - fflassert(proc); return proc; - }()) -{ - m_selectBoard.loadXML( - R"###( )###""\n" - R"###( 系统 )###""\n" - R"###( 社交 )###""\n" - R"###( 网络 )###""\n" - R"###( 游戏 )###""\n" - R"###( 帮助 )###""\n" - R"###( )###""\n" - ); - - // 1.0f -> SDL_MIX_MAXVOLUME - // SDL_mixer initial sound/music volume is SDL_MIX_MAXVOLUME - - m_musicSlider.setValue(to_f(SDRuntimeConfig().bgmValue) / 100.0, false); - m_soundEffectSlider.setValue(to_f(SDRuntimeConfig().soundEffValue) / 100.0, false); - - setShow(false); -} - -void RuntimeConfigExtBoard::drawEx(int dstX, int dstY, int srcX, int srcY, int srcW, int srcH) const -{ - m_frameBoard.drawEx(dstX, dstY, srcX, srcY, srcW, srcH); - for(auto p: - { - static_cast(&m_selectBoard), - static_cast(&m_menuButton), - static_cast(&m_checkLabel), - static_cast(&m_texSliderBar), - static_cast(&m_texSliderBarVertical), - }){ - auto drawSrcX = srcX; - auto drawSrcY = srcY; - auto drawSrcW = srcW; - auto drawSrcH = srcH; - auto drawDstX = dstX; - auto drawDstY = dstY; - - if(mathf::cropChildROI( - &drawSrcX, &drawSrcY, - &drawSrcW, &drawSrcH, - &drawDstX, &drawDstY, - - w(), - h(), - - p->dx(), - p->dy(), - p-> w(), - p-> h())){ - p->drawEx(drawDstX, drawDstY, drawSrcX, drawSrcY, drawSrcW, drawSrcH); - } - } - - drawEntryTitle(u8"【游戏设置】", 255, 35); - - drawEntryTitle(u8"背景音乐", 345, 97); - drawEntryTitle(u8"音效", 345, 157); - - m_musicSlider.draw(); - m_soundEffectSlider.draw(); -} - -bool RuntimeConfigExtBoard::processEvent(const SDL_Event &event, bool valid) -{ - if(!valid){ - return consumeFocus(false); - } - - if(!show()){ - return consumeFocus(false); - } - - for(auto widgetPtr: - { - static_cast(&m_selectBoard), - static_cast(&m_menuButton), - static_cast(&m_checkLabel), - static_cast(&m_frameBoard), - static_cast(&m_texSliderBar), - static_cast(&m_texSliderBarVertical), - }){ - if(widgetPtr->processEvent(event, valid)){ - return true; - } - } - - if(m_musicSlider.processEvent(event, valid)){ - return consumeFocus(true); - } - - if(m_soundEffectSlider.processEvent(event, valid)){ - return consumeFocus(true); - } - - switch(event.type){ - case SDL_KEYDOWN: - { - if(event.key.keysym.sym == SDLK_ESCAPE){ - setShow(false); - return consumeFocus(false); - } - return consumeFocus(true); - } - case SDL_MOUSEMOTION: - { - if((event.motion.state & SDL_BUTTON_LMASK) && (in(event.motion.x, event.motion.y) || focus())){ - const auto [rendererW, rendererH] = g_sdlDevice->getRendererSize(); - const int maxX = rendererW - w(); - const int maxY = rendererH - h(); - - const int newX = std::max(0, std::min(maxX, x() + event.motion.xrel)); - const int newY = std::max(0, std::min(maxY, y() + event.motion.yrel)); - moveBy(newX - x(), newY - y()); - return consumeFocus(true); - } - return consumeFocus(false); - } - case SDL_MOUSEBUTTONUP: - case SDL_MOUSEBUTTONDOWN: - { - return consumeFocus(in(event.button.x, event.button.y)); - } - default: - { - return consumeFocus(false); - } - } -} - -void RuntimeConfigExtBoard::drawEntryTitle(const char8_t *info, int dstCenterX, int dstCenterY) const -{ - const LabelBoard titleBoard - { - DIR_NONE, - 0, // reset by new width - 0, - to_u8cstr(info), - - 1, - 12, - 0, - - colorf::RGBA(0XFF, 0XFF, 0X00, 0XFF), - }; - titleBoard.drawAt(DIR_NONE, x() + dstCenterX, y() + dstCenterY); -} - -void RuntimeConfigExtBoard::setConfig(SDRuntimeConfig config) -{ - m_sdRuntimeConfig = std::move(config); - - m_musicSlider.setValue(m_sdRuntimeConfig.bgmValue / 100.0, false); - m_soundEffectSlider.setValue(m_sdRuntimeConfig.soundEffValue / 100.0, false); -} - -void RuntimeConfigExtBoard::reportRuntimeConfig() -{ - CMSetRuntimeConfig cmSRC; - std::memset(&cmSRC, 0, sizeof(cmSRC)); - - cmSRC.bgm = getConfig().bgm; - cmSRC.bgmValue = getConfig().bgmValue; - - cmSRC.soundEff = getConfig().soundEff; - cmSRC.soundEffValue = getConfig().soundEffValue; - - cmSRC.ime = getConfig().ime; - cmSRC.attackMode = getConfig().attackMode; - - g_client->send(CM_SETRUNTIMECONFIG, cmSRC); -} diff --git a/client/src/runtimeconfigextboard.hpp b/client/src/runtimeconfigextboard.hpp deleted file mode 100644 index 56dd7b3de..000000000 --- a/client/src/runtimeconfigextboard.hpp +++ /dev/null @@ -1,73 +0,0 @@ -#pragma once -#include -#include -#include "mathf.hpp" -#include "widget.hpp" -#include "menuboard.hpp" -#include "menubutton.hpp" -#include "checklabel.hpp" -#include "labelboard.hpp" -#include "texslider.hpp" -#include "tritexbutton.hpp" -#include "texsliderbar.hpp" -#include "resizableframeboard.hpp" - -class ProcessRun; -class RuntimeConfigExtBoard: public Widget -{ - private: - SDRuntimeConfig m_sdRuntimeConfig; - - private: - ResizableFrameBoard m_frameBoard; - - private: - CheckLabel m_checkLabel; - TexSliderBar m_texSliderBar; - TexSliderBar m_texSliderBarVertical; - - private: - TexSliderBar m_musicSlider; - TexSliderBar m_soundEffectSlider; - - private: - LabelBoard m_item1; - LabelBoard m_item2; - CheckLabel m_itemCheckLabel; - - MenuBoard m_menuBoard; - - private: - LabelBoard m_menuButtonGfx; - MenuButton m_menuButton; - - private: - LayoutBoard m_selectBoard; - - private: - ProcessRun *m_processRun; - - public: - RuntimeConfigExtBoard(int, int, int, int, ProcessRun *, Widget * = nullptr, bool = false); - - public: - void drawEx(int, int, int, int, int, int) const override; - - public: - bool processEvent(const SDL_Event &, bool) override; - - protected: - void drawEntryTitle(const char8_t *, int, int) const; - - private: - void reportRuntimeConfig(); - - public: - const SDRuntimeConfig &getConfig() const - { - return m_sdRuntimeConfig; - } - - public: - void setConfig(SDRuntimeConfig); -};