1
0
Fork 0
mirror of https://github.com/OpenMW/openmw.git synced 2025-10-17 02:46:34 +00:00

Add controller support to repair and recharge menus

This commit is contained in:
Andrew Lanzone 2025-05-31 18:58:30 -07:00
parent d3c7904e64
commit cbe74cdab4
10 changed files with 113 additions and 2 deletions

View file

@ -1,5 +1,6 @@
#include "itemchargeview.hpp"
#include <SDL.h>
#include <set>
#include <MyGUI_FactoryManager.h>
@ -9,8 +10,11 @@
#include <MyGUI_UString.h>
#include <components/esm3/loadench.hpp>
#include <components/settings/values.hpp>
#include "../mwbase/environment.hpp"
#include "../mwbase/inputmanager.hpp"
#include "../mwbase/windowmanager.hpp"
#include "../mwmechanics/spellutil.hpp"
@ -19,6 +23,7 @@
#include "itemmodel.hpp"
#include "itemwidget.hpp"
#include "textcolours.hpp"
namespace MWGui
{
@ -156,11 +161,20 @@ namespace MWGui
mScrollView->setCanvasSize(
MyGUI::IntSize(mScrollView->getWidth(), std::max(mScrollView->getHeight(), currentY)));
mScrollView->setVisibleVScroll(true);
if (Settings::gui().mControllerMenus)
updateControllerFocus(-1, mControllerFocus);
}
void ItemChargeView::resetScrollbars()
{
mScrollView->setViewOffset(MyGUI::IntPoint(0, 0));
if (Settings::gui().mControllerMenus)
{
updateControllerFocus(mControllerFocus, 0);
mControllerFocus = 0;
}
}
void ItemChargeView::setSize(const MyGUI::IntSize& value)
@ -224,4 +238,52 @@ namespace MWGui
mScrollView->setViewOffset(
MyGUI::IntPoint(0, static_cast<int>(mScrollView->getViewOffset().top + rel * 0.3f)));
}
void ItemChargeView::onControllerButton(const unsigned char button)
{
if (mLines.empty())
return;
int prevFocus = mControllerFocus;
if (button == SDL_CONTROLLER_BUTTON_A)
{
// Select the focused item, if any.
if (mControllerFocus >= 0 && mControllerFocus < mLines.size())
onIconClicked(mLines[mControllerFocus].mIcon);
}
else if (button == SDL_CONTROLLER_BUTTON_DPAD_UP)
mControllerFocus = wrap(mControllerFocus - 1, mLines.size());
else if (button == SDL_CONTROLLER_BUTTON_DPAD_DOWN)
mControllerFocus = wrap(mControllerFocus + 1, mLines.size());
if (prevFocus != mControllerFocus)
updateControllerFocus(prevFocus, mControllerFocus);
}
void ItemChargeView::updateControllerFocus(int prevFocus, int newFocus)
{
if (mLines.empty())
return;
const TextColours& textColours{ MWBase::Environment::get().getWindowManager()->getTextColours() };
if (prevFocus >= 0 && prevFocus < mLines.size())
{
mLines[prevFocus].mText->setTextColour(textColours.normal);
mLines[prevFocus].mIcon->setControllerFocus(false);
}
if (newFocus >= 0 && newFocus < mLines.size())
{
mLines[newFocus].mText->setTextColour(textColours.link);
mLines[newFocus].mIcon->setControllerFocus(true);
// Scroll the list to keep the active item in view
if (mControllerFocus <= 3)
mScrollView->setViewOffset(MyGUI::IntPoint(0, 0));
else
mScrollView->setViewOffset(MyGUI::IntPoint(-55 * (mControllerFocus - 3), 0));
}
}
}

View file

@ -52,6 +52,8 @@ namespace MWGui
MyGUI::delegates::MultiDelegate<MyGUI::Widget*, const MWWorld::Ptr&> eventItemClicked;
void onControllerButton(const unsigned char button);
private:
struct Line
{
@ -72,6 +74,9 @@ namespace MWGui
std::unique_ptr<ItemModel> mModel;
MyGUI::ScrollView* mScrollView;
DisplayMode mDisplayMode;
int mControllerFocus;
void updateControllerFocus(int prevFocus, int newFocus);
};
}

View file

@ -31,6 +31,7 @@ namespace MWGui
mControllerButtons.a = "#{sSelect}";
mControllerButtons.b = "#{sBack}";
mControllerButtons.r3 = "#{sInfo}";
}
bool ItemSelectionDialog::exit()

View file

@ -454,7 +454,7 @@ namespace MWGui
if (mButtons.size() == 1)
buttonActivated(mButtons[0]);
}
else if (arg.button == SDL_CONTROLLER_BUTTON_DPAD_LEFT)
else if (arg.button == SDL_CONTROLLER_BUTTON_DPAD_UP || arg.button == SDL_CONTROLLER_BUTTON_DPAD_LEFT)
{
if (mButtons.size() <= 1)
return true;
@ -465,7 +465,7 @@ namespace MWGui
mControllerFocus = wrap(mControllerFocus - 1, mButtons.size());
mButtons[mControllerFocus]->setStateSelected(true);
}
else if (arg.button == SDL_CONTROLLER_BUTTON_DPAD_RIGHT)
else if (arg.button == SDL_CONTROLLER_BUTTON_DPAD_DOWN || arg.button == SDL_CONTROLLER_BUTTON_DPAD_RIGHT)
{
if (mButtons.size() <= 1)
return true;

View file

@ -39,6 +39,10 @@ namespace MWGui
mBox->setDisplayMode(ItemChargeView::DisplayMode_EnchantmentCharge);
mGemIcon->eventMouseButtonClick += MyGUI::newDelegate(this, &Recharge::onSelectItem);
mControllerButtons.a = "Recharge";
mControllerButtons.b = "#{sBack}";
mControllerButtons.y = "#{sSoulGem}";
}
void Recharge::onOpen()
@ -136,4 +140,16 @@ namespace MWGui
updateView();
}
bool Recharge::onControllerButtonEvent(const SDL_ControllerButtonEvent& arg)
{
if ((arg.button == SDL_CONTROLLER_BUTTON_A && !mGemBox->getVisible())
|| arg.button == SDL_CONTROLLER_BUTTON_Y)
onSelectItem(mGemIcon);
else if (arg.button == SDL_CONTROLLER_BUTTON_B)
onCancel(mCancelButton);
else
mBox->onControllerButton(arg.button);
return true;
}
}

View file

@ -51,6 +51,8 @@ namespace MWGui
void onItemClicked(MyGUI::Widget* sender, const MWWorld::Ptr& item);
void onCancel(MyGUI::Widget* sender);
void onMouseWheel(MyGUI::Widget* _sender, int _rel);
bool onControllerButtonEvent(const SDL_ControllerButtonEvent& arg) override;
};
}

View file

@ -39,6 +39,10 @@ namespace MWGui
mRepairBox->setDisplayMode(ItemChargeView::DisplayMode_Health);
mToolIcon->eventMouseButtonClick += MyGUI::newDelegate(this, &Repair::onSelectItem);
mControllerButtons.a = "#{sRepair}";
mControllerButtons.b = "#{sBack}";
mControllerButtons.y = "Tool";
}
void Repair::onOpen()
@ -150,4 +154,16 @@ namespace MWGui
updateRepairView();
}
bool Repair::onControllerButtonEvent(const SDL_ControllerButtonEvent& arg)
{
if ((arg.button == SDL_CONTROLLER_BUTTON_A && !mToolBox->getVisible())
|| arg.button == SDL_CONTROLLER_BUTTON_Y)
onSelectItem(mToolIcon);
else if (arg.button == SDL_CONTROLLER_BUTTON_B)
onCancel(mCancelButton);
else
mRepairBox->onControllerButton(arg.button);
return true;
}
}

View file

@ -50,6 +50,8 @@ namespace MWGui
void onRepairItem(MyGUI::Widget* sender, const MWWorld::Ptr& ptr);
void onCancel(MyGUI::Widget* sender);
bool onControllerButtonEvent(const SDL_ControllerButtonEvent& arg) override;
};
}

View file

@ -952,6 +952,9 @@ namespace MWGui
for (int i = 0; i < winCount; i++)
mGuiModeStates[mode].mWindows[i]->setActiveControllerWindow(i == activeIndex);
MWBase::Environment::get().getInputManager()->setGamepadGuiCursorEnabled(
mGuiModeStates[mode].mWindows[activeIndex]->isGamepadCursorAllowed());
updateControllerButtonsOverlay();
setCursorActive(false);

View file

@ -172,6 +172,10 @@
<Property key="Alpha" value="0.5"/>
</Widget>
</Widget>
<Widget type="ImageBox" skin="ImageBox" position="0 0 32 32" align="Stretch" name="ControllerBorder">
<Property key="ImageTexture" value="textures\omw_menu_icon_active.dds"/>
<Property key="Visible" value="false"/>
</Widget>
</Widget>
</Resource>