1
0
Fork 0
mirror of https://github.com/OpenMW/openmw.git synced 2025-10-18 12:46:37 +00:00

Add a tab bar above inventory to show active tab and change tabs with mouse

This commit is contained in:
Andrew Lanzone 2025-05-24 16:00:13 -07:00
parent d759418f01
commit f1c34ea7b1
12 changed files with 177 additions and 21 deletions

View file

@ -44,7 +44,7 @@ add_openmw_dir (mwgui
tradeitemmodel companionitemmodel pickpocketitemmodel controllers savegamedialog tradeitemmodel companionitemmodel pickpocketitemmodel controllers savegamedialog
recharge mode videowidget backgroundimage itemwidget screenfader debugwindow spellmodel spellview recharge mode videowidget backgroundimage itemwidget screenfader debugwindow spellmodel spellview
draganddrop timeadvancer jailscreen itemchargeview keyboardnavigation textcolours statswatcher draganddrop timeadvancer jailscreen itemchargeview keyboardnavigation textcolours statswatcher
postprocessorhud settings controllerbuttonsoverlay postprocessorhud settings controllerbuttonsoverlay inventorytabsoverlay
) )
add_openmw_dir (mwdialogue add_openmw_dir (mwdialogue

View file

@ -389,6 +389,7 @@ namespace MWBase
virtual MWGui::WindowBase* getActiveControllerWindow() = 0; virtual MWGui::WindowBase* getActiveControllerWindow() = 0;
/// Cycle to the next window to receive controller events /// Cycle to the next window to receive controller events
virtual void cycleActiveControllerWindow(bool next) = 0; virtual void cycleActiveControllerWindow(bool next) = 0;
virtual void setActiveControllerWindow(MWGui::GuiMode mode, int activeIndex) = 0;
virtual void updateControllerButtonsOverlay() = 0; virtual void updateControllerButtonsOverlay() = 0;
// Used in Lua bindings // Used in Lua bindings

View file

@ -0,0 +1,49 @@
#include "inventorytabsoverlay.hpp"
#include "../mwbase/environment.hpp"
#include "../mwbase/windowmanager.hpp"
namespace MWGui
{
InventoryTabsOverlay::InventoryTabsOverlay()
: WindowBase("openmw_inventory_tabs.layout")
{
MyGUI::Button* tab;
getWidget(tab, "TabMap");
tab->eventMouseButtonClick += MyGUI::newDelegate(this, &InventoryTabsOverlay::onTabClicked);
mTabs.push_back(tab);
getWidget(tab, "TabInventory");
tab->eventMouseButtonClick += MyGUI::newDelegate(this, &InventoryTabsOverlay::onTabClicked);
mTabs.push_back(tab);
getWidget(tab, "TabSpells");
tab->eventMouseButtonClick += MyGUI::newDelegate(this, &InventoryTabsOverlay::onTabClicked);
mTabs.push_back(tab);
getWidget(tab, "TabStats");
tab->eventMouseButtonClick += MyGUI::newDelegate(this, &InventoryTabsOverlay::onTabClicked);
mTabs.push_back(tab);
}
void InventoryTabsOverlay::onTabClicked(MyGUI::Widget* sender)
{
for (int i = 0; i < mTabs.size(); i++)
{
if (mTabs[i] == sender)
{
Log(Debug::Verbose) << "InventoryTabsOverlay::onTabClicked " << i;
MWBase::Environment::get().getWindowManager()->setActiveControllerWindow(GM_Inventory, i);
//setTab(i);
break;
}
}
}
void InventoryTabsOverlay::setTab(int index)
{
for (int i = 0; i < mTabs.size(); i++)
mTabs[i]->setStateSelected(i == index);
}
}

View file

@ -0,0 +1,24 @@
#ifndef MWGUI_INVENTORYTABSSOVERLAY_H
#define MWGUI_INVENTORYTABSSOVERLAY_H
#include <MyGUI_Button.h>
#include "windowbase.hpp"
namespace MWGui
{
class InventoryTabsOverlay : public WindowBase
{
public:
InventoryTabsOverlay();
void setTab(int index);
private:
std::vector<MyGUI::Button*> mTabs;
void onTabClicked(MyGUI::Widget* sender);
};
}
#endif

View file

@ -1012,7 +1012,7 @@ namespace MWGui
{ {
MyGUI::IntSize viewSize = MyGUI::RenderManager::getInstance().getViewSize(); MyGUI::IntSize viewSize = MyGUI::RenderManager::getInstance().getViewSize();
MyGUI::Window* window = mMainWidget->castType<MyGUI::Window>(); MyGUI::Window* window = mMainWidget->castType<MyGUI::Window>();
window->setCoord(0, active ? 0 : viewSize.height + 1, viewSize.width, viewSize.height - 48); window->setCoord(0, active ? 48 : viewSize.height + 49, viewSize.width, viewSize.height - 48 - 48);
adjustPanes(); adjustPanes();
updatePreviewSize(); updatePreviewSize();

View file

@ -1417,7 +1417,7 @@ namespace MWGui
{ {
MyGUI::IntSize viewSize = MyGUI::RenderManager::getInstance().getViewSize(); MyGUI::IntSize viewSize = MyGUI::RenderManager::getInstance().getViewSize();
MyGUI::Window* window = mMainWidget->castType<MyGUI::Window>(); MyGUI::Window* window = mMainWidget->castType<MyGUI::Window>();
window->setCoord(0, active ? 0 : viewSize.height + 1, viewSize.width, viewSize.height - 48); window->setCoord(0, active ? 48 : viewSize.height + 49, viewSize.width, viewSize.height - 48 - 48);
WindowBase::setActiveControllerWindow(active); WindowBase::setActiveControllerWindow(active);
} }

View file

@ -283,7 +283,7 @@ namespace MWGui
{ {
MyGUI::IntSize viewSize = MyGUI::RenderManager::getInstance().getViewSize(); MyGUI::IntSize viewSize = MyGUI::RenderManager::getInstance().getViewSize();
MyGUI::Window* window = mMainWidget->castType<MyGUI::Window>(); MyGUI::Window* window = mMainWidget->castType<MyGUI::Window>();
window->setCoord(0, active ? 0 : viewSize.height + 1, viewSize.width, viewSize.height - 48); window->setCoord(0, active ? 48 : viewSize.height + 49, viewSize.width, viewSize.height - 48 - 48);
WindowBase::setActiveControllerWindow(active); WindowBase::setActiveControllerWindow(active);
} }

View file

@ -742,7 +742,7 @@ namespace MWGui
{ {
MyGUI::IntSize viewSize = MyGUI::RenderManager::getInstance().getViewSize(); MyGUI::IntSize viewSize = MyGUI::RenderManager::getInstance().getViewSize();
MyGUI::Window* window = mMainWidget->castType<MyGUI::Window>(); MyGUI::Window* window = mMainWidget->castType<MyGUI::Window>();
window->setCoord(0, active ? 0 : viewSize.height + 1, viewSize.width, viewSize.height - 48); window->setCoord(0, active ? 48 : viewSize.height + 49, viewSize.width, viewSize.height - 48 - 48);
onWindowResize(window); onWindowResize(window);

View file

@ -182,6 +182,7 @@ namespace MWGui
, mJailScreen(nullptr) , mJailScreen(nullptr)
, mContainerWindow(nullptr) , mContainerWindow(nullptr)
, mControllerButtonsOverlay(nullptr) , mControllerButtonsOverlay(nullptr)
, mInventoryTabsOverlay(nullptr)
, mTranslationDataStorage(translationDataStorage) , mTranslationDataStorage(translationDataStorage)
, mInputBlocker(nullptr) , mInputBlocker(nullptr)
, mHudEnabled(true) , mHudEnabled(true)
@ -510,6 +511,10 @@ namespace MWGui
mControllerButtonsOverlay = controllerButtonsOverlay.get(); mControllerButtonsOverlay = controllerButtonsOverlay.get();
mWindows.push_back(std::move(controllerButtonsOverlay)); mWindows.push_back(std::move(controllerButtonsOverlay));
auto inventoryTabsOverlay = std::make_unique<InventoryTabsOverlay>();
mInventoryTabsOverlay = inventoryTabsOverlay.get();
mWindows.push_back(std::move(inventoryTabsOverlay));
mInputBlocker = MyGUI::Gui::getInstance().createWidget<MyGUI::Widget>( mInputBlocker = MyGUI::Gui::getInstance().createWidget<MyGUI::Widget>(
{}, 0, 0, w, h, MyGUI::Align::Stretch, "InputBlocker"); {}, 0, 0, w, h, MyGUI::Align::Stretch, "InputBlocker");
@ -668,8 +673,13 @@ namespace MWGui
mSpellWindow->setVisible( mSpellWindow->setVisible(
mSpellWindow->pinned() && !isConsoleMode() && !(mForceHidden & GW_Magic) && (mAllowed & GW_Magic)); mSpellWindow->pinned() && !isConsoleMode() && !(mForceHidden & GW_Magic) && (mAllowed & GW_Magic));
if (Settings::gui().mControllerMenus && mControllerButtonsOverlay) if (Settings::gui().mControllerMenus)
mControllerButtonsOverlay->setVisible(false); {
if (mControllerButtonsOverlay)
mControllerButtonsOverlay->setVisible(false);
if (mInventoryTabsOverlay)
mInventoryTabsOverlay->setVisible(false);
}
return; return;
} }
else if (getMode() != GM_Inventory) else if (getMode() != GM_Inventory)
@ -929,19 +939,27 @@ namespace MWGui
} }
// REMOVEME // REMOVEME
Log(Debug::Error) << "focusNextWindow: mode=" << mode << ", activeIndex=" << activeIndex; Log(Debug::Error) << "cycleActiveControllerWindow: mode=" << mode << ", activeIndex=" << activeIndex;
if (mActiveControllerWindows[mode] != activeIndex) if (mActiveControllerWindows[mode] != activeIndex)
{ setActiveControllerWindow(mode, activeIndex);
mActiveControllerWindows[mode] = activeIndex; }
for (int i = 0; i < winCount; i++)
{ void WindowManager::setActiveControllerWindow(GuiMode mode, int activeIndex)
mGuiModeStates[mode].mWindows[i]->setActiveControllerWindow(i == activeIndex); {
} int winCount = mGuiModeStates[mode].mWindows.size();
updateControllerButtonsOverlay(); if (winCount == 0)
if (winCount > 1) return;
playSound(ESM::RefId::stringRefId("Menu Size"));
} mActiveControllerWindows[mode] = std::clamp(activeIndex, 0, winCount - 1);
for (int i = 0; i < winCount; i++)
mGuiModeStates[mode].mWindows[i]->setActiveControllerWindow(i == activeIndex);
updateControllerButtonsOverlay();
if (winCount > 1)
playSound(ESM::RefId::stringRefId("Menu Size"));
} }
void WindowManager::update(float frameDuration) void WindowManager::update(float frameDuration)
@ -1010,6 +1028,9 @@ namespace MWGui
if (mControllerButtonsOverlay && mControllerButtonsOverlay->isVisible()) if (mControllerButtonsOverlay && mControllerButtonsOverlay->isVisible())
mControllerButtonsOverlay->onFrame(frameDuration); mControllerButtonsOverlay->onFrame(frameDuration);
if (mInventoryTabsOverlay && mInventoryTabsOverlay->isVisible())
mInventoryTabsOverlay->onFrame(frameDuration);
if (!gameRunning) if (!gameRunning)
return; return;
@ -2560,19 +2581,24 @@ namespace MWGui
void WindowManager::updateControllerButtonsOverlay() void WindowManager::updateControllerButtonsOverlay()
{ {
if (!Settings::gui().mControllerMenus ||!mControllerButtonsOverlay) if (!Settings::gui().mControllerMenus || !mControllerButtonsOverlay)
return; return;
WindowBase* topWin = this->getActiveControllerWindow(); WindowBase* topWin = this->getActiveControllerWindow();
if (!topWin || !topWin->isVisible()) if (!topWin || !topWin->isVisible())
{ {
// REMOVEME
Log(Debug::Error) << "WindowManager::updateControllerButtonsOverlay: hiding overlay";
mControllerButtonsOverlay->setVisible(false); mControllerButtonsOverlay->setVisible(false);
mInventoryTabsOverlay->setVisible(false);
return; return;
} }
// setButtons will handle setting visibility based on if any buttons are defined. // setButtons will handle setting visibility based on if any buttons are defined.
mControllerButtonsOverlay->setButtons(topWin->getControllerButtons()); mControllerButtonsOverlay->setButtons(topWin->getControllerButtons());
if (getMode() == GM_Inventory) {
mInventoryTabsOverlay->setVisible(true);
mInventoryTabsOverlay->setTab(mActiveControllerWindows[GM_Inventory]);
}
else
mInventoryTabsOverlay->setVisible(false);
} }
} }

View file

@ -27,6 +27,7 @@
#include "charactercreation.hpp" #include "charactercreation.hpp"
#include "controllerbuttonsoverlay.hpp" #include "controllerbuttonsoverlay.hpp"
#include "draganddrop.hpp" #include "draganddrop.hpp"
#include "inventorytabsoverlay.hpp"
#include "mapwindow.hpp" #include "mapwindow.hpp"
#include "messagebox.hpp" #include "messagebox.hpp"
#include "settings.hpp" #include "settings.hpp"
@ -120,6 +121,7 @@ namespace MWGui
class JailScreen; class JailScreen;
class KeyboardNavigation; class KeyboardNavigation;
class ControllerButtonsOverlay; class ControllerButtonsOverlay;
class InventoryTabsOverlay;
class WindowManager : public MWBase::WindowManager class WindowManager : public MWBase::WindowManager
{ {
@ -393,6 +395,7 @@ namespace MWGui
WindowBase* getActiveControllerWindow() override; WindowBase* getActiveControllerWindow() override;
void cycleActiveControllerWindow(bool next) override; void cycleActiveControllerWindow(bool next) override;
void setActiveControllerWindow(GuiMode mode, int activeIndex) override;
void updateControllerButtonsOverlay() override; void updateControllerButtonsOverlay() override;
// Used in Lua bindings // Used in Lua bindings
@ -463,6 +466,7 @@ namespace MWGui
JailScreen* mJailScreen; JailScreen* mJailScreen;
ContainerWindow* mContainerWindow; ContainerWindow* mContainerWindow;
ControllerButtonsOverlay* mControllerButtonsOverlay; ControllerButtonsOverlay* mControllerButtonsOverlay;
InventoryTabsOverlay* mInventoryTabsOverlay;
std::vector<std::unique_ptr<WindowBase>> mWindows; std::vector<std::unique_ptr<WindowBase>> mWindows;

View file

@ -172,6 +172,7 @@ set(BUILTIN_DATA_FILES
mygui/openmw_infobox.layout mygui/openmw_infobox.layout
mygui/openmw_interactive_messagebox.layout mygui/openmw_interactive_messagebox.layout
mygui/openmw_interactive_messagebox_notransp.layout mygui/openmw_interactive_messagebox_notransp.layout
mygui/openmw_inventory_tabs.layout
mygui/openmw_inventory_window.layout mygui/openmw_inventory_window.layout
mygui/openmw_journal.layout mygui/openmw_journal.layout
mygui/openmw_journal.skin.xml mygui/openmw_journal.skin.xml

View file

@ -0,0 +1,51 @@
<?xml version="1.0" encoding="UTF-8"?>
<MyGUI type="Layout">
<Widget type="Window" skin="MW_Dialog" layer="Windows" position="0 0 800 48" align="HStretch Top" name="_Main">
<Property key="Visible" value="true"/>
<Widget type="HBox" position="0 0 800 48" align="Center Center" name="TabBox">
<Property key="Padding" value="0"/>
<Property key="Spacing" value="0"/>
<Widget type="Spacer"/>
<Widget type="ImageBox" skin="ImageBox" align="Stretch" position="0 0 24 24">
<Property key="ImageTexture" value="textures\omw_steam_button_l2.dds"/>
<Property key="Colour" value="#ccb589"/>
<Property key="Alpha" value="0.7"/>
</Widget>
<Widget type="Button" skin="SandTextButton" align="Center" position="0 0 100 48" name="TabMap">
<Property key="Caption" value="#{sMap}"/>
<Property key="TextAlign" value="Center"/>
<Property key="TextShadow" value="true"/>
<Property key="TextShadowColour" value="0 0 0"/>
</Widget>
<Widget type="Button" skin="SandTextButton" align="Center" position="0 0 100 48" name="TabInventory">
<Property key="Caption" value="#{sInventory}"/>
<Property key="TextAlign" value="Center"/>
<Property key="TextShadow" value="true"/>
<Property key="TextShadowColour" value="0 0 0"/>
</Widget>
<Widget type="Button" skin="SandTextButton" align="Center" position="0 0 100 48" name="TabSpells">
<Property key="Caption" value="#{sMagicMenu}"/>
<Property key="TextAlign" value="Center"/>
<Property key="TextShadow" value="true"/>
<Property key="TextShadowColour" value="0 0 0"/>
</Widget>
<Widget type="Button" skin="SandTextButton" align="Center" position="0 0 100 48" name="TabStats">
<Property key="Caption" value="#{sStats}"/>
<Property key="TextAlign" value="Center"/>
<Property key="TextShadow" value="true"/>
<Property key="TextShadowColour" value="0 0 0"/>
</Widget>
<Widget type="ImageBox" skin="ImageBox" align="Stretch" position="0 0 24 24">
<Property key="ImageTexture" value="textures\omw_steam_button_r2.dds"/>
<Property key="Colour" value="#ccb589"/>
<Property key="Alpha" value="0.7"/>
</Widget>
<Widget type="Spacer"/>
</Widget>
</Widget>
</MyGUI>