Index: ps/trunk/source/gui/CGUI.h =================================================================== --- ps/trunk/source/gui/CGUI.h +++ ps/trunk/source/gui/CGUI.h @@ -148,6 +148,12 @@ void LoadXmlFile(const VfsPath& Filename, boost::unordered_set& Paths); /** + * Allows the JS side to modify the hotkey setting assigned to a GUI object. + */ + void SetObjectHotkey(IGUIObject* pObject, const CStr& hotkeyTag); + void UnsetObjectHotkey(IGUIObject* pObject, const CStr& hotkeyTag); + + /** * Return the object which is an ancestor of every other GUI object. */ IGUIObject* GetBaseObject() const { return m_BaseObject; }; @@ -625,8 +631,6 @@ * Map from hotkey names to objects that listen to the hotkey. * (This is an optimisation to avoid recursing over the whole GUI * tree every time a hotkey is pressed). - * Currently this is only set at load time - dynamic changes to an - * object's hotkey property will be ignored. */ std::map > m_HotkeyObjects; Index: ps/trunk/source/gui/CGUI.cpp =================================================================== --- ps/trunk/source/gui/CGUI.cpp +++ ps/trunk/source/gui/CGUI.cpp @@ -466,6 +466,28 @@ } } +void CGUI::SetObjectHotkey(IGUIObject* pObject, const CStr& hotkeyTag) +{ + if (!hotkeyTag.empty()) + m_HotkeyObjects[hotkeyTag].push_back(pObject); +} + +void CGUI::UnsetObjectHotkey(IGUIObject* pObject, const CStr& hotkeyTag) +{ + if (hotkeyTag.empty()) + return; + + std::vector& assignment = m_HotkeyObjects[hotkeyTag]; + + assignment.erase( + std::remove_if( + assignment.begin(), + assignment.end(), + [&pObject](const IGUIObject* hotkeyObject) + { return pObject == hotkeyObject; }), + assignment.end()); +} + const SGUIScrollBarStyle* CGUI::GetScrollBarStyle(const CStr& style) const { std::map::const_iterator it = m_ScrollBarStyles.find(style); @@ -603,7 +625,6 @@ ATTR(style); ATTR(type); ATTR(name); - ATTR(hotkey); ATTR(z); ATTR(on); ATTR(file); @@ -635,7 +656,6 @@ bool ManuallySetZ = false; CStrW inclusionPath; - CStr hotkeyTag; for (XMBAttribute attr : attributes) { @@ -659,9 +679,6 @@ continue; } - if (attr.Name == attr_hotkey) - hotkeyTag = attr.Value; - if (attr.Name == attr_z) ManuallySetZ = true; @@ -679,9 +696,6 @@ ++m_InternalNameNumber; } - if (!hotkeyTag.empty()) - m_HotkeyObjects[hotkeyTag].push_back(object); - CStrW caption(Element.GetText().FromUTF8()); if (!caption.empty()) object->SetSettingFromString("caption", caption, false); Index: ps/trunk/source/gui/IGUIObject.h =================================================================== --- ps/trunk/source/gui/IGUIObject.h +++ ps/trunk/source/gui/IGUIObject.h @@ -428,6 +428,7 @@ /** * Updates some internal data depending on the setting changed. */ + void PreSettingChange(const CStr& Setting); void SettingChanged(const CStr& Setting, const bool SendMessage); /** Index: ps/trunk/source/gui/IGUIObject.cpp =================================================================== --- ps/trunk/source/gui/IGUIObject.cpp +++ ps/trunk/source/gui/IGUIObject.cpp @@ -154,6 +154,7 @@ template void IGUIObject::SetSetting(const CStr& Setting, T& Value, const bool SendMessage) { + PreSettingChange(Setting); static_cast* >(m_Settings[Setting])->m_pSetting = std::move(Value); SettingChanged(Setting, SendMessage); } @@ -161,10 +162,17 @@ template void IGUIObject::SetSetting(const CStr& Setting, const T& Value, const bool SendMessage) { + PreSettingChange(Setting); static_cast* >(m_Settings[Setting])->m_pSetting = Value; SettingChanged(Setting, SendMessage); } +void IGUIObject::PreSettingChange(const CStr& Setting) +{ + if (Setting == "hotkey") + m_pGUI.UnsetObjectHotkey(this, GetSetting(Setting)); +} + void IGUIObject::SettingChanged(const CStr& Setting, const bool SendMessage) { if (Setting == "size") @@ -178,6 +186,8 @@ if (GetSetting(Setting)) RecurseObject(nullptr, &IGUIObject::ResetStates); } + else if (Setting == "hotkey") + m_pGUI.SetObjectHotkey(this, GetSetting(Setting)); if (SendMessage) {