1
0
Fork 0
mirror of https://github.com/OpenMW/openmw.git synced 2025-04-01 13:06:40 +00:00

Build the attribute list in the stats window dynamically

This commit is contained in:
Evil Eye 2023-06-18 19:10:29 +02:00
parent bac6777fae
commit ea2cedb5ea
7 changed files with 54 additions and 179 deletions

View file

@ -102,21 +102,11 @@ namespace MWGui
mPlayerSkillValues.emplace(skill.mId, MWMechanics::SkillValue()); mPlayerSkillValues.emplace(skill.mId, MWMechanics::SkillValue());
} }
void CharacterCreation::setValue(std::string_view id, const MWMechanics::AttributeValue& value) void CharacterCreation::setValue(ESM::Attribute::AttributeID id, const MWMechanics::AttributeValue& value)
{ {
std::string_view prefix = "AttribVal"; mPlayerAttributes[id] = value;
if (id.starts_with(prefix) && id.size() == prefix.size() + 1) if (mReviewDialog)
{ mReviewDialog->setAttribute(id, value);
char index = id[prefix.size()];
if (index >= '1' && index <= '8')
{
// Match [AttribVal1-AttribVal8] to the corresponding AttributeID values [0-7]
auto attribute = static_cast<ESM::Attribute::AttributeID>(index - '0' - 1);
mPlayerAttributes[attribute] = value;
if (mReviewDialog)
mReviewDialog->setAttribute(attribute, value);
}
}
} }
void CharacterCreation::setValue(std::string_view id, const MWMechanics::DynamicStat<float>& value) void CharacterCreation::setValue(std::string_view id, const MWMechanics::DynamicStat<float>& value)

View file

@ -44,7 +44,7 @@ namespace MWGui
// Show a dialog // Show a dialog
void spawnDialog(const char id); void spawnDialog(const char id);
void setValue(std::string_view id, const MWMechanics::AttributeValue& value) override; void setValue(ESM::Attribute::AttributeID id, const MWMechanics::AttributeValue& value) override;
void setValue(std::string_view id, const MWMechanics::DynamicStat<float>& value) override; void setValue(std::string_view id, const MWMechanics::DynamicStat<float>& value) override;
void setValue(ESM::RefId id, const MWMechanics::SkillValue& value) override; void setValue(ESM::RefId id, const MWMechanics::SkillValue& value) override;
void configureSkills(const std::vector<ESM::RefId>& major, const std::vector<ESM::RefId>& minor) override; void configureSkills(const std::vector<ESM::RefId>& major, const std::vector<ESM::RefId>& minor) override;

View file

@ -35,14 +35,16 @@ namespace MWGui
if (mWatched.isEmpty()) if (mWatched.isEmpty())
return; return;
const auto& store = MWBase::Environment::get().getESMStore();
MWBase::WindowManager* winMgr = MWBase::Environment::get().getWindowManager(); MWBase::WindowManager* winMgr = MWBase::Environment::get().getWindowManager();
const MWMechanics::NpcStats& stats = mWatched.getClass().getNpcStats(mWatched); const MWMechanics::NpcStats& stats = mWatched.getClass().getNpcStats(mWatched);
for (int i = 0; i < ESM::Attribute::Length; ++i) for (const ESM::Attribute& attribute : store->get<ESM::Attribute>())
{ {
if (stats.getAttribute(i) != mWatchedAttributes[i] || mWatchedStatsEmpty) const auto& value = stats.getAttribute(attribute.mId);
if (value != mWatchedAttributes[attribute.mId] || mWatchedStatsEmpty)
{ {
mWatchedAttributes[i] = stats.getAttribute(i); mWatchedAttributes[attribute.mId] = value;
setValue("AttribVal" + std::to_string(i + 1), stats.getAttribute(i)); setValue(attribute.mId, value);
} }
} }
@ -83,7 +85,7 @@ namespace MWGui
} }
} }
for (const ESM::Skill& skill : MWBase::Environment::get().getESMStore()->get<ESM::Skill>()) for (const ESM::Skill& skill : store->get<ESM::Skill>())
{ {
const auto& value = stats.getSkill(skill.mId); const auto& value = stats.getSkill(skill.mId);
if (value != mWatchedSkills[skill.mId] || mWatchedStatsEmpty) if (value != mWatchedSkills[skill.mId] || mWatchedStatsEmpty)
@ -112,16 +114,14 @@ namespace MWGui
if (watchedRecord->mRace != mWatchedRace || mWatchedStatsEmpty) if (watchedRecord->mRace != mWatchedRace || mWatchedStatsEmpty)
{ {
mWatchedRace = watchedRecord->mRace; mWatchedRace = watchedRecord->mRace;
const ESM::Race* race const ESM::Race* race = store->get<ESM::Race>().find(watchedRecord->mRace);
= MWBase::Environment::get().getESMStore()->get<ESM::Race>().find(watchedRecord->mRace);
setValue("race", race->mName); setValue("race", race->mName);
} }
if (watchedRecord->mClass != mWatchedClass || mWatchedStatsEmpty) if (watchedRecord->mClass != mWatchedClass || mWatchedStatsEmpty)
{ {
mWatchedClass = watchedRecord->mClass; mWatchedClass = watchedRecord->mClass;
const ESM::Class* cls const ESM::Class* cls = store->get<ESM::Class>().find(watchedRecord->mClass);
= MWBase::Environment::get().getESMStore()->get<ESM::Class>().find(watchedRecord->mClass);
setValue("class", cls->mName); setValue("class", cls->mName);
size_t size = cls->mData.mSkills.size(); size_t size = cls->mData.mSkills.size();
@ -151,7 +151,7 @@ namespace MWGui
mListeners.erase(listener); mListeners.erase(listener);
} }
void StatsWatcher::setValue(std::string_view id, const MWMechanics::AttributeValue& value) void StatsWatcher::setValue(ESM::Attribute::AttributeID id, const MWMechanics::AttributeValue& value)
{ {
for (StatsListener* listener : mListeners) for (StatsListener* listener : mListeners)
listener->setValue(id, value); listener->setValue(id, value);

View file

@ -19,7 +19,7 @@ namespace MWGui
virtual ~StatsListener() = default; virtual ~StatsListener() = default;
/// Set value for the given ID. /// Set value for the given ID.
virtual void setValue(std::string_view id, const MWMechanics::AttributeValue& value) {} virtual void setValue(ESM::Attribute::AttributeID id, const MWMechanics::AttributeValue& value) {}
virtual void setValue(std::string_view id, const MWMechanics::DynamicStat<float>& value) {} virtual void setValue(std::string_view id, const MWMechanics::DynamicStat<float>& value) {}
virtual void setValue(std::string_view, const std::string& value) {} virtual void setValue(std::string_view, const std::string& value) {}
virtual void setValue(std::string_view, int value) {} virtual void setValue(std::string_view, int value) {}
@ -50,7 +50,7 @@ namespace MWGui
std::set<StatsListener*> mListeners; std::set<StatsListener*> mListeners;
void setValue(std::string_view id, const MWMechanics::AttributeValue& value); void setValue(ESM::Attribute::AttributeID id, const MWMechanics::AttributeValue& value);
void setValue(std::string_view id, const MWMechanics::DynamicStat<float>& value); void setValue(std::string_view id, const MWMechanics::DynamicStat<float>& value);
void setValue(std::string_view id, const std::string& value); void setValue(std::string_view id, const std::string& value);
void setValue(std::string_view id, int value); void setValue(std::string_view id, int value);

View file

@ -1,5 +1,6 @@
#include "statswindow.hpp" #include "statswindow.hpp"
#include <MyGUI_Button.h>
#include <MyGUI_Gui.h> #include <MyGUI_Gui.h>
#include <MyGUI_ImageBox.h> #include <MyGUI_ImageBox.h>
#include <MyGUI_InputManager.h> #include <MyGUI_InputManager.h>
@ -43,15 +44,26 @@ namespace MWGui
, mMinFullWidth(mMainWidget->getSize().width) , mMinFullWidth(mMainWidget->getSize().width)
{ {
const char* names[][2] = { { "Attrib1", "sAttributeStrength" }, { "Attrib2", "sAttributeIntelligence" },
{ "Attrib3", "sAttributeWillpower" }, { "Attrib4", "sAttributeAgility" }, { "Attrib5", "sAttributeSpeed" },
{ "Attrib6", "sAttributeEndurance" }, { "Attrib7", "sAttributePersonality" },
{ "Attrib8", "sAttributeLuck" }, { 0, 0 } };
const MWWorld::ESMStore& store = *MWBase::Environment::get().getESMStore(); const MWWorld::ESMStore& store = *MWBase::Environment::get().getESMStore();
for (int i = 0; names[i][0]; ++i) MyGUI::Widget* attributeView = getWidget("AttributeView");
MyGUI::IntCoord coord{ 0, 0, 204, 144 };
const MyGUI::Align align = MyGUI::Align::Left | MyGUI::Align::Top | MyGUI::Align::HStretch;
for (const ESM::Attribute& attribute : store.get<ESM::Attribute>())
{ {
setText(names[i][0], store.get<ESM::GameSetting>().find(names[i][1])->mValue.getString()); auto* box = attributeView->createWidget<MyGUI::Button>({}, coord, align);
box->setUserString("ToolTipType", "Layout");
box->setUserString("ToolTipLayout", "AttributeToolTip");
box->setUserString("Caption_AttributeName", attribute.mName);
box->setUserString("Caption_AttributeDescription", attribute.mDescription);
box->setUserString("ImageTexture_AttributeImage", attribute.mIcon);
coord.top += 18;
auto* name = box->createWidget<MyGUI::TextBox>("SandText", { 0, 0, 160, 18 }, align);
name->setNeedMouseFocus(false);
name->setCaption(attribute.mName);
auto* value = box->createWidget<MyGUI::TextBox>(
"SandTextRight", { 160, 0, 44, 18 }, MyGUI::Align::Right | MyGUI::Align::Top);
value->setNeedMouseFocus(false);
mAttributeWidgets.emplace(attribute.mId, value);
} }
getWidget(mSkillView, "SkillView"); getWidget(mSkillView, "SkillView");
@ -143,37 +155,20 @@ namespace MWGui
mMainWidget->castType<MyGUI::Window>()->setCaption(playerName); mMainWidget->castType<MyGUI::Window>()->setCaption(playerName);
} }
void StatsWindow::setValue(std::string_view id, const MWMechanics::AttributeValue& value) void StatsWindow::setValue(ESM::Attribute::AttributeID id, const MWMechanics::AttributeValue& value)
{ {
static const char* ids[] = { auto it = mAttributeWidgets.find(id);
"AttribVal1", if (it != mAttributeWidgets.end())
"AttribVal2", {
"AttribVal3", MyGUI::TextBox* box = it->second;
"AttribVal4", box->setCaption(std::to_string(static_cast<int>(value.getModified())));
"AttribVal5", if (value.getModified() > value.getBase())
"AttribVal6", box->_setWidgetState("increased");
"AttribVal7", else if (value.getModified() < value.getBase())
"AttribVal8", box->_setWidgetState("decreased");
nullptr, else
}; box->_setWidgetState("normal");
}
for (int i = 0; ids[i]; ++i)
if (ids[i] == id)
{
setText(id, std::to_string(static_cast<int>(value.getModified())));
MyGUI::TextBox* box;
getWidget(box, id);
if (value.getModified() > value.getBase())
box->_setWidgetState("increased");
else if (value.getModified() < value.getBase())
box->_setWidgetState("decreased");
else
box->_setWidgetState("normal");
break;
}
} }
void StatsWindow::setValue(std::string_view id, const MWMechanics::DynamicStat<float>& value) void StatsWindow::setValue(std::string_view id, const MWMechanics::DynamicStat<float>& value)

View file

@ -3,6 +3,7 @@
#include "statswatcher.hpp" #include "statswatcher.hpp"
#include "windowpinnablebase.hpp" #include "windowpinnablebase.hpp"
#include <components/esm/attr.hpp>
#include <components/esm/refid.hpp> #include <components/esm/refid.hpp>
namespace MWGui namespace MWGui
@ -21,7 +22,7 @@ namespace MWGui
void setPlayerName(const std::string& playerName); void setPlayerName(const std::string& playerName);
/// Set value for the given ID. /// Set value for the given ID.
void setValue(std::string_view id, const MWMechanics::AttributeValue& value) override; void setValue(ESM::Attribute::AttributeID id, const MWMechanics::AttributeValue& value) override;
void setValue(std::string_view id, const MWMechanics::DynamicStat<float>& value) override; void setValue(std::string_view id, const MWMechanics::DynamicStat<float>& value) override;
void setValue(std::string_view id, const std::string& value) override; void setValue(std::string_view id, const std::string& value) override;
void setValue(std::string_view id, int value) override; void setValue(std::string_view id, int value) override;
@ -67,6 +68,7 @@ namespace MWGui
std::vector<ESM::RefId> mMajorSkills, mMinorSkills, mMiscSkills; std::vector<ESM::RefId> mMajorSkills, mMinorSkills, mMiscSkills;
std::map<ESM::RefId, MWMechanics::SkillValue> mSkillValues; std::map<ESM::RefId, MWMechanics::SkillValue> mSkillValues;
std::map<ESM::Attribute::AttributeID, MyGUI::TextBox*> mAttributeWidgets;
std::map<ESM::RefId, std::pair<MyGUI::TextBox*, MyGUI::TextBox*>> mSkillWidgetMap; std::map<ESM::RefId, std::pair<MyGUI::TextBox*, MyGUI::TextBox*>> mSkillWidgetMap;
std::map<std::string, MyGUI::Widget*> mFactionWidgetMap; std::map<std::string, MyGUI::Widget*> mFactionWidgetMap;
FactionList mFactions; ///< Stores a list of factions and the current rank FactionList mFactions; ///< Stores a list of factions and the current rank

View file

@ -113,120 +113,8 @@
</Widget> </Widget>
<Widget type="Widget" skin="MW_Box" position="8 148 212 152" align="Left Top Stretch"> <Widget type="Widget" skin="MW_Box" position="8 148 212 152" align="Left Top Stretch">
<!-- TODO: this should be a scroll view --> <!-- TODO: this should be a scroll view -->
<Widget type="Widget" skin="" position="4 4 204 144" align="Left Top Stretch"> <Widget type="Widget" skin="" position="4 4 204 144" align="Left Top Stretch" name="AttributeView" />
<Widget type="Button" skin="" position="0 0 204 18" name="Attrib1Box" align="Left Top HStretch">
<UserString key="ToolTipType" value="Layout"/>
<UserString key="ToolTipLayout" value="AttributeToolTip"/>
<UserString key="Caption_AttributeName" value="#{sAttributeStrength}"/>
<UserString key="Caption_AttributeDescription" value="#{sStrDesc}"/>
<UserString key="ImageTexture_AttributeImage" value="icons\k\attribute_strength.dds"/>
<Widget type="TextBox" skin="SandText" position="0 0 160 18" name="Attrib1" align="Left Top HStretch">
<Property key="NeedMouse" value="false"/>
</Widget>
<Widget type="TextBox" skin="SandTextRight" position="160 0 44 18" name="AttribVal1" align="Right Top">
<Property key="NeedMouse" value="false"/>
</Widget>
</Widget>
<Widget type="Button" skin="" position="0 18 204 18" name="Attrib2Box" align="Left Top HStretch">
<UserString key="ToolTipType" value="Layout"/>
<UserString key="ToolTipLayout" value="AttributeToolTip"/>
<UserString key="Caption_AttributeName" value="#{sAttributeIntelligence}"/>
<UserString key="Caption_AttributeDescription" value="#{sIntDesc}"/>
<UserString key="ImageTexture_AttributeImage" value="icons\k\attribute_int.dds"/>
<Widget type="TextBox" skin="SandText" position="0 0 160 18" name="Attrib2" align="Left Top HStretch">
<Property key="NeedMouse" value="false"/>
</Widget>
<Widget type="TextBox" skin="SandTextRight" position="160 0 44 18" name="AttribVal2" align="Right Top">
<Property key="NeedMouse" value="false"/>
</Widget>
</Widget>
<Widget type="Button" skin="" position="0 36 204 18" name="Attrib3Box" align="Left Top HStretch">
<UserString key="ToolTipType" value="Layout"/>
<UserString key="ToolTipLayout" value="AttributeToolTip"/>
<UserString key="Caption_AttributeName" value="#{sAttributeWillpower}"/>
<UserString key="Caption_AttributeDescription" value="#{sWilDesc}"/>
<UserString key="ImageTexture_AttributeImage" value="icons\k\attribute_wilpower.dds"/>
<Widget type="TextBox" skin="SandText" position="0 0 160 18" name="Attrib3" align="Left Top HStretch">
<Property key="NeedMouse" value="false"/>
</Widget>
<Widget type="TextBox" skin="SandTextRight" position="160 0 44 18" name="AttribVal3" align="Right Top">
<Property key="NeedMouse" value="false"/>
</Widget>
</Widget>
<Widget type="Button" skin="" position="0 54 204 18" name="Attrib4Box" align="Left Top HStretch">
<UserString key="ToolTipType" value="Layout"/>
<UserString key="ToolTipLayout" value="AttributeToolTip"/>
<UserString key="Caption_AttributeName" value="#{sAttributeAgility}"/>
<UserString key="Caption_AttributeDescription" value="#{sAgiDesc}"/>
<UserString key="ImageTexture_AttributeImage" value="icons\k\attribute_agility.dds"/>
<Widget type="TextBox" skin="SandText" position="0 0 160 18" name="Attrib4" align="Left Top HStretch">
<Property key="NeedMouse" value="false"/>
</Widget>
<Widget type="TextBox" skin="SandTextRight" position="160 0 44 18" name="AttribVal4" align="Right Top">
<Property key="NeedMouse" value="false"/>
</Widget>
</Widget>
<Widget type="Button" skin="" position="0 72 204 18" name="Attrib5Box" align="Left Top HStretch">
<UserString key="ToolTipType" value="Layout"/>
<UserString key="ToolTipLayout" value="AttributeToolTip"/>
<UserString key="Caption_AttributeName" value="#{sAttributeSpeed}"/>
<UserString key="Caption_AttributeDescription" value="#{sSpdDesc}"/>
<UserString key="ImageTexture_AttributeImage" value="icons\k\attribute_speed.dds"/>
<Widget type="TextBox" skin="SandText" position="0 0 160 18" name="Attrib5" align="Left Top HStretch">
<Property key="NeedMouse" value="false"/>
</Widget>
<Widget type="TextBox" skin="SandTextRight" position="160 0 44 18" name="AttribVal5" align="Right Top">
<Property key="NeedMouse" value="false"/>
</Widget>
</Widget>
<Widget type="Button" skin="" position="0 90 204 18" name="Attrib6Box" align="Left Top HStretch">
<UserString key="ToolTipType" value="Layout"/>
<UserString key="ToolTipLayout" value="AttributeToolTip"/>
<UserString key="Caption_AttributeName" value="#{sAttributeEndurance}"/>
<UserString key="Caption_AttributeDescription" value="#{sEndDesc}"/>
<UserString key="ImageTexture_AttributeImage" value="icons\k\attribute_endurance.dds"/>
<Widget type="TextBox" skin="SandText" position="0 0 160 18" name="Attrib6" align="Left Top HStretch">
<Property key="NeedMouse" value="false"/>
</Widget>
<Widget type="TextBox" skin="SandTextRight" position="160 0 44 18" name="AttribVal6" align="Right Top">
<Property key="NeedMouse" value="false"/>
</Widget>
</Widget>
<Widget type="Button" skin="" position="0 108 204 18" name="Attrib7Box" align="Left Top HStretch">
<UserString key="ToolTipType" value="Layout"/>
<UserString key="ToolTipLayout" value="AttributeToolTip"/>
<UserString key="Caption_AttributeName" value="#{sAttributePersonality}"/>
<UserString key="Caption_AttributeDescription" value="#{sPerDesc}"/>
<UserString key="ImageTexture_AttributeImage" value="icons\k\attribute_personality.dds"/>
<Widget type="TextBox" skin="SandText" position="0 0 160 18" name="Attrib7" align="Left Top HStretch">
<Property key="NeedMouse" value="false"/>
</Widget>
<Widget type="TextBox" skin="SandTextRight" position="160 0 44 18" name="AttribVal7" align="Right Top">
<Property key="NeedMouse" value="false"/>
</Widget>
</Widget>
<Widget type="Button" skin="" position="0 126 204 18" name="Attrib8Box" align="Left Top HStretch">
<UserString key="ToolTipType" value="Layout"/>
<UserString key="ToolTipLayout" value="AttributeToolTip"/>
<UserString key="Caption_AttributeName" value="#{sAttributeLuck}"/>
<UserString key="Caption_AttributeDescription" value="#{sLucDesc}"/>
<UserString key="ImageTexture_AttributeImage" value="icons\k\attribute_luck.dds"/>
<Widget type="TextBox" skin="SandText" position="0 0 160 18" name="Attrib8" align="Left Top HStretch">
<Property key="NeedMouse" value="false"/>
</Widget>
<Widget type="TextBox" skin="SandTextRight" position="160 0 44 18" name="AttribVal8" align="Right Top">
<Property key="NeedMouse" value="false"/>
</Widget>
</Widget>
</Widget>
</Widget> </Widget>
</Widget> </Widget>