Index: xbmc/Application.cpp =================================================================== --- xbmc/Application.cpp (revision 31566) +++ xbmc/Application.cpp (working copy) @@ -5008,12 +5008,6 @@ case GUI_MSG_EXECUTE: if (message.GetStringParam().length() > 0) return ExecuteXBMCAction(message.GetStringParam()); - else { - CGUIActionDescriptor action = message.GetAction(); - action.m_sourceWindowId = message.GetControlId(); // set source window id, - return ExecuteAction(action); - } - break; } return false; @@ -5076,22 +5070,6 @@ return true; } -bool CApplication::ExecuteAction(CGUIActionDescriptor action) -{ - if (action.m_lang == CGUIActionDescriptor::LANG_XBMC) - { - return ExecuteXBMCAction(action.m_action); - } - else if (action.m_lang == CGUIActionDescriptor::LANG_PYTHON) - { - // Determine the context of the action, if possible - g_pythonParser.evalString(action.m_action); - - return true; - } - return false; -} - void CApplication::Process() { // check if we need to load a new skin Index: xbmc/Application.h =================================================================== --- xbmc/Application.h (revision 31566) +++ xbmc/Application.h (working copy) @@ -180,7 +180,6 @@ CNetwork& getNetwork(); bool ExecuteXBMCAction(std::string action); - bool ExecuteAction(CGUIActionDescriptor action); CGUIDialogVolumeBar m_guiDialogVolumeBar; CGUIDialogSeekBar m_guiDialogSeekBar; Index: xbmc/GUIInfoManager.cpp =================================================================== --- xbmc/GUIInfoManager.cpp (revision 31566) +++ xbmc/GUIInfoManager.cpp (working copy) @@ -48,7 +48,6 @@ #include "xbox/XKHDD.h" #endif #include "SystemInfo.h" -#include "GUIButtonScroller.h" #include "GUITextBox.h" #include "GUIPassword.h" #include "LangInfo.h" @@ -906,12 +905,6 @@ return AddMultiInfo(GUIInfo(bNegate ? -CONTROL_GROUP_HAS_FOCUS : CONTROL_GROUP_HAS_FOCUS, groupID, controlID)); } } - else if (strTest.Left(24).Equals("buttonscroller.hasfocus(")) - { - int controlID = atoi(strTest.Mid(24, strTest.GetLength() - 24).c_str()); - if (controlID) - return AddMultiInfo(GUIInfo(bNegate ? -BUTTON_SCROLLER_HAS_ICON : BUTTON_SCROLLER_HAS_ICON, controlID, 0)); - } return bNegate ? -ret : ret; } @@ -2395,17 +2388,6 @@ bReturn = (window->GetFocusedControlID() == (int)info.GetData1()); } break; - case BUTTON_SCROLLER_HAS_ICON: - { - CGUIWindow *window = GetWindowWithCondition(contextWindow, 0); - if (window) - { - CGUIControl *pControl = window->GetFocusedControl(); - if (pControl && pControl->GetControlType() == CGUIControl::GUICONTROL_BUTTONBAR) - bReturn = ((CGUIButtonScroller *)pControl)->GetActiveButtonID() == (int)info.GetData1(); - } - } - break; case WINDOW_NEXT: if (info.GetData1()) bReturn = ((int)info.GetData1() == m_nextWindowID); Index: xbmc/GUIInfoManager.h =================================================================== --- xbmc/GUIInfoManager.h (revision 31566) +++ xbmc/GUIInfoManager.h (working copy) @@ -450,7 +450,6 @@ #define CONTROL_IS_VISIBLE 29998 #define CONTROL_GROUP_HAS_FOCUS 29999 #define CONTROL_HAS_FOCUS 30000 -#define BUTTON_SCROLLER_HAS_ICON 30001 // NOTE: Version string MUST NOT contain spaces. It is used in the HTTP request user agent. #ifdef SVN_REV Index: xbmc/guilib/GUIBaseContainer.cpp =================================================================== --- xbmc/guilib/GUIBaseContainer.cpp (revision 31566) +++ xbmc/guilib/GUIBaseContainer.cpp (working copy) @@ -349,7 +349,7 @@ void CGUIBaseContainer::OnUp() { - bool wrapAround = m_controlUp == GetID() || !(m_controlUp || m_upActions.size()); + bool wrapAround = m_actionUp.GetNavigation() == GetID() || !m_actionUp.HasActionsMeetingCondition(); if (m_orientation == VERTICAL && MoveUp(wrapAround)) return; // with horizontal lists it doesn't make much sense to have multiselect labels @@ -358,7 +358,7 @@ void CGUIBaseContainer::OnDown() { - bool wrapAround = m_controlDown == GetID() || !(m_controlDown || m_downActions.size()); + bool wrapAround = m_actionDown.GetNavigation() == GetID() || !m_actionDown.HasActionsMeetingCondition(); if (m_orientation == VERTICAL && MoveDown(wrapAround)) return; // with horizontal lists it doesn't make much sense to have multiselect labels @@ -367,7 +367,7 @@ void CGUIBaseContainer::OnLeft() { - bool wrapAround = m_controlLeft == GetID() || !(m_controlLeft || m_leftActions.size()); + bool wrapAround = m_actionLeft.GetNavigation() == GetID() || !m_actionLeft.HasActionsMeetingCondition(); if (m_orientation == HORIZONTAL && MoveUp(wrapAround)) return; else if (m_orientation == VERTICAL) @@ -381,7 +381,7 @@ void CGUIBaseContainer::OnRight() { - bool wrapAround = m_controlRight == GetID() || !(m_controlRight || m_rightActions.size()); + bool wrapAround = m_actionRight.GetNavigation() == GetID() || !m_actionRight.HasActionsMeetingCondition(); if (m_orientation == HORIZONTAL && MoveDown(wrapAround)) return; else if (m_orientation == VERTICAL) @@ -575,20 +575,8 @@ int selected = GetSelectedItem(); if (selected >= 0 && selected < (int)m_items.size()) { - CFileItemPtr item = boost::static_pointer_cast(m_items[selected]); - // multiple action strings are concat'd together, separated with " , " - int controlID = GetID(); // save as these could go away as we send messages - int parentID = GetParentID(); - vector actions; - StringUtils::SplitString(item->GetPath(), " , ", actions); - for (unsigned int i = 0; i < actions.size(); i++) - { - CStdString action = actions[i]; - action.Replace(",,", ","); - CGUIMessage message(GUI_MSG_EXECUTE, controlID, parentID); - message.SetStringParam(action); - g_windowManager.SendMessage(message); - } + CGUIStaticItemPtr item = boost::static_pointer_cast(m_items[selected]); + item->GetClickActions().Execute(GetID(), GetParentID()); } return true; } Index: xbmc/guilib/GUIButtonControl.cpp =================================================================== --- xbmc/guilib/GUIButtonControl.cpp (revision 31566) +++ xbmc/guilib/GUIButtonControl.cpp (working copy) @@ -275,39 +275,24 @@ // Save values, as the click message may deactivate the window int controlID = GetID(); int parentID = GetParentID(); - vector clickActions = m_clickActions; + CGUIAction clickActions = m_clickActions; // button selected, send a message CGUIMessage msg(GUI_MSG_CLICKED, controlID, parentID, 0); SendWindowMessage(msg); // and execute our actions - for (unsigned int i = 0; i < clickActions.size(); i++) - { - CGUIMessage message(GUI_MSG_EXECUTE, controlID, parentID); - message.SetAction(clickActions[i]); - g_windowManager.SendMessage(message); - } + clickActions.Execute(controlID, parentID); } void CGUIButtonControl::OnFocus() { - for (unsigned int i = 0; i < m_focusActions.size(); i++) - { // send using a thread message to ensure the UI is updated prior to message firing. - CGUIMessage message(GUI_MSG_EXECUTE, m_controlID, m_parentID); - message.SetAction(m_focusActions[i]); - g_windowManager.SendThreadMessage(message); - } + m_focusActions.Execute(GetID(), GetParentID()); } void CGUIButtonControl::OnUnFocus() { - for (unsigned int i = 0; i < m_unfocusActions.size(); i++) - { // send using a thread message to ensure the UI is updated prior to message firing. - CGUIMessage message(GUI_MSG_EXECUTE, m_controlID, m_parentID); - message.SetAction(m_unfocusActions[i]); - g_windowManager.SendThreadMessage(message); - } + m_unfocusActions.Execute(GetID(), GetParentID()); } void CGUIButtonControl::SetSelected(bool bSelected) Index: xbmc/guilib/GUIButtonControl.h =================================================================== --- xbmc/guilib/GUIButtonControl.h (revision 31566) +++ xbmc/guilib/GUIButtonControl.h (working copy) @@ -58,10 +58,10 @@ virtual void SetPosition(float posX, float posY); virtual void SetLabel(const std::string & aLabel); virtual void SetLabel2(const std::string & aLabel2); - void SetClickActions(const std::vector& clickActions) { m_clickActions = clickActions; }; - const std::vector &GetClickActions() const { return m_clickActions; }; - void SetFocusActions(const std::vector& focusActions) { m_focusActions = focusActions; }; - void SetUnFocusActions(const std::vector& unfocusActions) { m_unfocusActions = unfocusActions; }; + void SetClickActions(const CGUIAction& clickActions) { m_clickActions = clickActions; }; + const CGUIAction &GetClickActions() const { return m_clickActions; }; + void SetFocusActions(const CGUIAction& focusActions) { m_focusActions = focusActions; }; + void SetUnFocusActions(const CGUIAction& unfocusActions) { m_unfocusActions = unfocusActions; }; const CLabelInfo& GetLabelInfo() const { return m_label.GetLabelInfo(); }; virtual CStdString GetLabel() const { return GetDescription(); }; virtual CStdString GetLabel2() const; @@ -75,7 +75,7 @@ void SettingsCategorySetTextAlign(uint32_t align); virtual void OnClick(); - bool HasClickActions() { return m_clickActions.size() > 0; }; + bool HasClickActions() { return m_clickActions.HasActionsMeetingCondition(); }; virtual void UpdateColors(); protected: @@ -96,9 +96,9 @@ CGUILabel m_label; CGUILabel m_label2; - std::vector m_clickActions; - std::vector m_focusActions; - std::vector m_unfocusActions; + CGUIAction m_clickActions; + CGUIAction m_focusActions; + CGUIAction m_unfocusActions; bool m_bSelected; }; Index: xbmc/guilib/GUIControl.cpp =================================================================== --- xbmc/guilib/GUIControl.cpp (revision 31566) +++ xbmc/guilib/GUIControl.cpp (working copy) @@ -45,12 +45,6 @@ m_posY = 0; m_width = 0; m_height = 0; - m_controlLeft = 0; - m_controlRight = 0; - m_controlUp = 0; - m_controlDown = 0; - m_controlNext = 0; - m_controlPrev = 0; ControlType = GUICONTROL_UNKNOWN; m_bInvalidated = true; m_bAllocated=false; @@ -77,12 +71,6 @@ m_visibleCondition = 0; m_enableCondition = 0; m_enabled = true; - m_controlLeft = 0; - m_controlRight = 0; - m_controlUp = 0; - m_controlDown = 0; - m_controlNext = 0; - m_controlPrev = 0; ControlType = GUICONTROL_UNKNOWN; m_bInvalidated = true; m_bAllocated=false; @@ -179,6 +167,9 @@ return true; break; + case ACTION_NAV_BACK: + return OnBack(); + case ACTION_NEXT_CONTROL: if (!HasFocus()) return false; OnNextControl(); @@ -198,81 +189,42 @@ void CGUIControl::OnUp() { if (HasFocus()) - { - if (m_upActions.size()) - ExecuteActions(m_upActions); - else if (m_controlID != m_controlUp) - { - // Send a message to the window with the sender set as the window - CGUIMessage msg(GUI_MSG_MOVE, GetParentID(), GetID(), ACTION_MOVE_UP); - SendWindowMessage(msg); - } - } + m_actionUp.Execute(GetID(), GetParentID(), ACTION_MOVE_UP); } void CGUIControl::OnDown() { if (HasFocus()) - { - if (m_downActions.size()) - ExecuteActions(m_downActions); - else if (m_controlID != m_controlDown) - { - // Send a message to the window with the sender set as the window - CGUIMessage msg(GUI_MSG_MOVE, GetParentID(), GetID(), ACTION_MOVE_DOWN); - SendWindowMessage(msg); - } - } + m_actionDown.Execute(GetID(), GetParentID(), ACTION_MOVE_DOWN); } void CGUIControl::OnLeft() { if (HasFocus()) - { - if (m_leftActions.size()) - ExecuteActions(m_leftActions); - else if (m_controlID != m_controlLeft) - { - // Send a message to the window with the sender set as the window - CGUIMessage msg(GUI_MSG_MOVE, GetParentID(), GetID(), ACTION_MOVE_LEFT); - SendWindowMessage(msg); - } - } + m_actionLeft.Execute(GetID(), GetParentID(), ACTION_MOVE_LEFT); } void CGUIControl::OnRight() { if (HasFocus()) - { - if (m_rightActions.size()) - ExecuteActions(m_rightActions); - else if (m_controlID != m_controlRight) - { - // Send a message to the window with the sender set as the window - CGUIMessage msg(GUI_MSG_MOVE, GetParentID(), GetID(), ACTION_MOVE_RIGHT); - SendWindowMessage(msg); - } - } + m_actionRight.Execute(GetID(), GetParentID(), ACTION_MOVE_RIGHT); } +bool CGUIControl::OnBack() +{ + return HasFocus() ? m_actionBack.Execute(GetID(), GetParentID(), ACTION_NAV_BACK) : false; +} + void CGUIControl::OnNextControl() { - if (m_controlID != m_controlNext) - { - // Send a message to the window with the sender set as the window - CGUIMessage msg(GUI_MSG_MOVE, GetParentID(), GetID(), ACTION_NEXT_CONTROL, m_controlNext); - SendWindowMessage(msg); - } + if (HasFocus()) + m_actionNext.Execute(GetID(), GetParentID(), ACTION_NEXT_CONTROL); } void CGUIControl::OnPrevControl() { - if (m_controlID != m_controlPrev) - { - // Send a message to the window with the sender set as the window - CGUIMessage msg(GUI_MSG_MOVE, GetParentID(), GetID(), ACTION_PREV_CONTROL, m_controlPrev); - SendWindowMessage(msg); - } + if (HasFocus()) + m_actionPrev.Execute(GetID(), GetParentID(), ACTION_PREV_CONTROL); } bool CGUIControl::SendWindowMessage(CGUIMessage &message) @@ -440,27 +392,30 @@ return m_height; } -void CGUIControl::SetNavigation(int up, int down, int left, int right) +void CGUIControl::SetNavigation(int up, int down, int left, int right, int back) { - m_controlUp = up; - m_controlDown = down; - m_controlLeft = left; - m_controlRight = right; + m_actionUp.SetNavigation(up); + m_actionDown.SetNavigation(down); + m_actionLeft.SetNavigation(left); + m_actionRight.SetNavigation(right); + m_actionBack.SetNavigation(back); } void CGUIControl::SetTabNavigation(int next, int prev) { - m_controlNext = next; - m_controlPrev = prev; + m_actionNext.SetNavigation(next); + m_actionPrev.SetNavigation(prev); } -void CGUIControl::SetNavigationActions(const vector &up, const vector &down, - const vector &left, const vector &right, bool replace) +void CGUIControl::SetNavigationActions(const CGUIAction &up, const CGUIAction &down, + const CGUIAction &left, const CGUIAction &right, + const CGUIAction &back, bool replace) { - if (m_leftActions.empty() || replace) m_leftActions = left; - if (m_rightActions.empty() || replace) m_rightActions = right; - if (m_upActions.empty() || replace) m_upActions = up; - if (m_downActions.empty() || replace) m_downActions = down; + if (!m_actionLeft.HasAnyActions() || replace) m_actionLeft = left; + if (!m_actionRight.HasAnyActions() || replace) m_actionRight = right; + if (!m_actionUp.HasAnyActions() || replace) m_actionUp = up; + if (!m_actionDown.HasAnyActions() || replace) m_actionDown = down; + if (!m_actionBack.HasAnyActions() || replace) m_actionBack = back; } void CGUIControl::SetWidth(float width) @@ -810,13 +765,15 @@ switch (direction) { case ACTION_MOVE_UP: - return m_controlUp; + return m_actionUp.GetNavigation(); case ACTION_MOVE_DOWN: - return m_controlDown; + return m_actionDown.GetNavigation(); case ACTION_MOVE_LEFT: - return m_controlLeft; + return m_actionLeft.GetNavigation(); case ACTION_MOVE_RIGHT: - return m_controlRight; + return m_actionRight.GetNavigation(); + case ACTION_NAV_BACK: + return m_actionBack.GetNavigation(); default: return -1; } @@ -861,21 +818,6 @@ m_hasCamera = true; } -void CGUIControl::ExecuteActions(const vector &actions) -{ - // we should really save anything we need, as the action may cause the window to close - int savedID = GetID(); - int savedParent = GetParentID(); - vector savedActions = actions; - - for (unsigned int i = 0; i < savedActions.size(); i++) - { - CGUIMessage message(GUI_MSG_EXECUTE, savedID, savedParent); - message.SetAction(savedActions[i]); - g_windowManager.SendMessage(message); - } -} - CPoint CGUIControl::GetRenderPosition() const { float z = 0; Index: xbmc/guilib/GUIControl.h =================================================================== --- xbmc/guilib/GUIControl.h (revision 31566) +++ xbmc/guilib/GUIControl.h (working copy) @@ -8,7 +8,7 @@ #pragma once /* - * Copyright (C) 2005-2012 Team XBMC + * Copyright (C) 2005-2012 2012 XBMC * http://www.xbmc.org * * This Program is free software; you can redistribute it and/or modify @@ -33,7 +33,7 @@ #include "GUIMessage.h" // needed by practically all controls #include "VisibleEffect.h" // needed for the CAnimation members #include "GUIInfoTypes.h" // needed for CGUIInfoColor to handle infolabel'ed colors -#include "GUIActionDescriptor.h" +#include "GUIAction.h" class CGUIListItem; // forward class CMouseEvent; @@ -82,6 +82,7 @@ virtual void OnDown(); virtual void OnLeft(); virtual void OnRight(); + virtual bool OnBack(); virtual void OnNextControl(); virtual void OnPrevControl(); virtual void OnFocus() {}; @@ -137,26 +138,28 @@ virtual float GetYPosition() const; virtual float GetWidth() const; virtual float GetHeight() const; - virtual void SetNavigation(int up, int down, int left, int right); + virtual void SetNavigation(int up, int down, int left, int right, int back = 0); virtual void SetTabNavigation(int next, int prev); /*! \brief Set actions to perform on navigation Navigations are set if replace is true or if there is no previously set action - \param up vector of CGUIActionDescriptors to execute on up - \param down vector of CGUIActionDescriptors to execute on down - \param left vector of CGUIActionDescriptors to execute on left - \param right vector of CGUIActionDescriptors to execute on right + \param up CGUIAction to execute on up + \param down CGUIAction to execute on down + \param left CGUIAction to execute on left + \param right CGUIAction to execute on right + \param back CGUIAction to execute on back \param replace Actions are set only if replace is true or there is no previously set action. Defaults to true - \sa SetNavigation, ExecuteActions + \sa SetNavigation */ - virtual void SetNavigationActions(const std::vector &up, const std::vector &down, - const std::vector &left, const std::vector &right, bool replace = true); - void ExecuteActions(const std::vector &actions); - - int GetControlIdUp() const { return m_controlUp;}; - int GetControlIdDown() const { return m_controlDown;}; - int GetControlIdLeft() const { return m_controlLeft;}; - int GetControlIdRight() const { return m_controlRight;}; + virtual void SetNavigationActions(const CGUIAction &up, const CGUIAction &down, + const CGUIAction &left, const CGUIAction &right, + const CGUIAction &back, bool replace = true); + int GetControlIdUp() const { return m_actionUp.GetNavigation(); }; + int GetControlIdDown() const { return m_actionDown.GetNavigation(); }; + int GetControlIdLeft() const { return m_actionLeft.GetNavigation(); }; + int GetControlIdRight() const { return m_actionRight.GetNavigation(); }; + int GetControlIdBack() const { return m_actionBack.GetNavigation(); }; + virtual int GetNextControl(int direction) const; virtual void SetFocus(bool focus); virtual void SetWidth(float width); @@ -220,7 +223,6 @@ GUICONTROL_VIDEO, GUICONTROL_MOVER, GUICONTROL_RESIZE, - GUICONTROL_BUTTONBAR, GUICONTROL_CONSOLE, GUICONTROL_EDIT, GUICONTROL_VISUALISATION, @@ -275,19 +277,14 @@ void UpdateStates(ANIMATION_TYPE type, ANIMATION_PROCESS currentProcess, ANIMATION_STATE currentState); bool SendWindowMessage(CGUIMessage &message); - // navigation - int m_controlLeft; - int m_controlRight; - int m_controlUp; - int m_controlDown; - int m_controlNext; - int m_controlPrev; - std::vector m_leftActions; - std::vector m_rightActions; - std::vector m_upActions; - std::vector m_downActions; - std::vector m_nextActions; - std::vector m_prevActions; + // navigation and actions + CGUIAction m_actionLeft; + CGUIAction m_actionRight; + CGUIAction m_actionUp; + CGUIAction m_actionDown; + CGUIAction m_actionBack; + CGUIAction m_actionNext; + CGUIAction m_actionPrev; float m_posX; float m_posY; Index: xbmc/guilib/GUIControlFactory.cpp =================================================================== --- xbmc/guilib/GUIControlFactory.cpp (revision 31566) +++ xbmc/guilib/GUIControlFactory.cpp (working copy) @@ -40,7 +40,6 @@ #include "GUISelectButtonControl.h" #include "GUIMoverControl.h" #include "GUIResizeControl.h" -#include "GUIButtonScroller.h" #include "GUISpinControlEx.h" #include "GUIVisualisationControl.h" #include "GUISettingsSliderControl.h" @@ -63,6 +62,7 @@ #include "GUIColorManager.h" #include "SkinInfo.h" #include "settings/Settings.h" +#include "GUIAction.h" using namespace std; @@ -144,25 +144,6 @@ return g_SkinInfo.ResolveConstant(pNode->FirstChild()->Value(), value); } -bool CGUIControlFactory::GetMultipleString(const TiXmlNode* pRootNode, const char* strTag, std::vector& vecStringValue) -{ - const TiXmlNode* pNode = pRootNode->FirstChild(strTag ); - if (!pNode) return false; - vecStringValue.clear(); - bool bFound = false; - while (pNode) - { - CGUIActionDescriptor action; - if (CGUIControlFactory::GetAction((const TiXmlElement*) pNode, action)) - { - vecStringValue.push_back(action); - bFound = true; - } - pNode = pNode->NextSibling(strTag); - } - return bFound; -} - bool CGUIControlFactory::GetPath(const TiXmlNode* pRootNode, const char* strTag, CStdString& strStringPath) { const TiXmlNode* pNode = pRootNode->FirstChild(strTag ); @@ -172,26 +153,6 @@ return true; } -bool CGUIControlFactory::GetAction(const TiXmlElement* pElement, CGUIActionDescriptor &action) -{ - CStdString langStr = pElement->Attribute("lang"); - if (langStr.CompareNoCase("python") == 0 ) - action.m_lang = CGUIActionDescriptor::LANG_PYTHON; - else - action.m_lang = CGUIActionDescriptor::LANG_XBMC; - - if (pElement->FirstChild()) - { - action.m_action = pElement->FirstChild()->Value(); - return true; - } - else - { - action.m_action = ""; - return false; - } -} - bool CGUIControlFactory::GetAspectRatio(const TiXmlNode* pRootNode, const char* strTag, CAspectRatio &aspect) { CStdString ratio; @@ -401,6 +362,24 @@ return ret; } +bool CGUIControlFactory::GetActions(const TiXmlNode* pRootNode, const char* strTag, CGUIAction& action) +{ + action.m_actions.clear(); + const TiXmlElement* pElement = pRootNode->FirstChildElement(strTag); + while (pElement) + { + if (pElement->FirstChild()) + { + CGUIAction::cond_action_pair pair; + pair.condition = pElement->Attribute("condition"); + pair.action = pElement->FirstChild()->Value(); + action.m_actions.push_back(pair); + } + pElement = pElement->NextSiblingElement(strTag); + } + return action.m_actions.size() > 0; +} + bool CGUIControlFactory::GetHitRect(const TiXmlNode *control, CRect &rect) { const TiXmlElement* node = control->FirstChildElement("hitrect"); @@ -445,20 +424,6 @@ return false; } -bool CGUIControlFactory::GetNavigation(const TiXmlElement *node, const char *tag, int &direction, vector &actions) -{ - if (!GetMultipleString(node, tag, actions)) - return false; // no tag specified - if (actions.size() == 1 && StringUtils::IsNaturalNumber(actions[0].m_action)) - { // single numeric tag specified - direction = atol(actions[0].m_action.c_str()); - actions.clear(); - } - else - direction = 0; - return true; -} - void CGUIControlFactory::GetInfoLabel(const TiXmlNode *pControlNode, const CStdString &labelTag, CGUIInfoLabel &infoLabel) { vector labels; @@ -583,9 +548,8 @@ float width = 0, height = 0; float minWidth = 0; - int left = 0, right = 0, up = 0, down = 0, next = 0, prev = 0; - vector leftActions, rightActions, upActions, downActions, nextActions, prevActions; - + CGUIAction leftActions, rightActions, upActions, downActions, backActions, nextActions, prevActions; + int pageControl = 0; CGUIInfoColor colorDiffuse(0xFFFFFFFF); int defaultControl = 0; @@ -637,11 +601,11 @@ float spaceBetweenItems = 2; bool bHasPath = false; - vector clickActions; - vector altclickActions; - vector focusActions; - vector unfocusActions; - vector textChangeActions; + CGUIAction clickActions; + CGUIAction altclickActions; + CGUIAction focusActions; + CGUIAction unfocusActions; + CGUIAction textChangeActions; CStdString strTitle = ""; CStdString strRSSTags = ""; @@ -655,14 +619,8 @@ float thumbWidthBig = 100; float thumbHeightBig = 100; DWORD dwBuddyControlID = 0; - int iNumSlots = 7; float buttonGap = 5; - int iDefaultSlot = 2; int iMovementRange = 0; - bool bHorizontal = false; - int iAlpha = 0; - bool bWrapAround = true; - bool bSmoothScrolling = true; CAspectRatio aspect; #ifdef PRE_SKIN_VERSION_9_10_COMPATIBILITY if (insideContainer) // default for inside containers is keep @@ -752,12 +710,13 @@ hitRect.SetRect(posX, posY, posX + width, posY + height); GetHitRect(pControlNode, hitRect); - if (!GetNavigation(pControlNode, "onup", up, upActions)) up = id - 1; - if (!GetNavigation(pControlNode, "ondown", down, downActions)) down = id + 1; - if (!GetNavigation(pControlNode, "onleft", left, leftActions)) left = id; - if (!GetNavigation(pControlNode, "onright", right, rightActions)) right = id; - if (!GetNavigation(pControlNode, "onnext", next, nextActions)) next = id; - if (!GetNavigation(pControlNode, "onprev", prev, prevActions)) prev = id; + if (!GetActions(pControlNode, "onup", upActions)) upActions.SetNavigation(id); + if (!GetActions(pControlNode, "ondown", downActions)) downActions.SetNavigation(id); + if (!GetActions(pControlNode, "onleft", leftActions)) leftActions.SetNavigation(id); + if (!GetActions(pControlNode, "onright", rightActions)) rightActions.SetNavigation(id); + if (!GetActions(pControlNode, "onnext", nextActions)) nextActions.SetNavigation(id); + if (!GetActions(pControlNode, "onprev", prevActions)) prevActions.SetNavigation(id); + GetActions(pControlNode, "onback", backActions); if (XMLUtils::GetInt(pControlNode, "defaultcontrol", defaultControl)) { @@ -806,11 +765,12 @@ if (XMLUtils::GetString(pControlNode, "font2", strFont)) labelInfo2.font = g_fontManager.GetFont(strFont); - GetMultipleString(pControlNode, "onclick", clickActions); - GetMultipleString(pControlNode, "ontextchange", textChangeActions); - GetMultipleString(pControlNode, "onfocus", focusActions); - GetMultipleString(pControlNode, "onunfocus", unfocusActions); - GetMultipleString(pControlNode, "altclick", altclickActions); + GetActions(pControlNode, "onclick", clickActions); + GetActions(pControlNode, "ontextchange", textChangeActions); + GetActions(pControlNode, "onfocus", focusActions); + GetActions(pControlNode, "onunfocus", unfocusActions); + focusActions.m_sendThreadMessages = unfocusActions.m_sendThreadMessages = true; + GetActions(pControlNode, "altclick", altclickActions); CStdString infoString; if (XMLUtils::GetString(pControlNode, "info", infoString)) @@ -937,23 +897,13 @@ XMLUtils::GetBoolean(pControlNode, "wrapmultiline", wrapMultiLine); XMLUtils::GetInt(pControlNode,"urlset",iUrlSet); - // stuff for button scroller if ( XMLUtils::GetString(pControlNode, "orientation", strTmp) ) { if (strTmp.ToLower() == "horizontal") - { - bHorizontal = true; orientation = HORIZONTAL; - } } - GetFloat(pControlNode, "buttongap", buttonGap); GetFloat(pControlNode, "itemgap", buttonGap); - XMLUtils::GetInt(pControlNode, "numbuttons", iNumSlots); XMLUtils::GetInt(pControlNode, "movement", iMovementRange); - XMLUtils::GetInt(pControlNode, "defaultbutton", iDefaultSlot); - XMLUtils::GetInt(pControlNode, "alpha", iAlpha); - XMLUtils::GetBoolean(pControlNode, "wraparound", bWrapAround); - XMLUtils::GetBoolean(pControlNode, "smoothscrolling", bSmoothScrolling); GetAspectRatio(pControlNode, "aspectratio", aspect); XMLUtils::GetBoolean(pControlNode, "scroll", bScrollLabel); XMLUtils::GetBoolean(pControlNode,"pulseonselect", bPulse); @@ -1340,14 +1290,6 @@ parentID, id, posX, posY, width, height, textureFocus, textureNoFocus); } - else if (strType == "buttonscroller") - { - control = new CGUIButtonScroller( - parentID, id, posX, posY, width, height, buttonGap, iNumSlots, iDefaultSlot, - iMovementRange, bHorizontal, iAlpha, bWrapAround, bSmoothScrolling, - textureFocus, textureNoFocus, labelInfo); - ((CGUIButtonScroller *)control)->LoadButtons(pControlNode); - } else if (strType == "spincontrolex") { control = new CGUISpinControlEx( @@ -1372,9 +1314,7 @@ control->SetEnableCondition(enableCondition); control->SetAnimations(animations); control->SetColorDiffuse(colorDiffuse); - control->SetNavigation(up, down, left, right); - control->SetTabNavigation(next,prev); - control->SetNavigationActions(upActions, downActions, leftActions, rightActions); + control->SetNavigationActions(upActions, downActions, leftActions, rightActions, backActions); control->SetPulseOnSelect(bPulse); if (hasCamera) control->SetCamera(camera); Index: xbmc/guilib/GUIControlFactory.h =================================================================== --- xbmc/guilib/GUIControlFactory.h (revision 31566) +++ xbmc/guilib/GUIControlFactory.h (working copy) @@ -88,12 +88,10 @@ static bool GetInfoColor(const TiXmlNode* pRootNode, const char* strTag, CGUIInfoColor &value); static CStdString FilterLabel(const CStdString &label); static bool GetConditionalVisibility(const TiXmlNode* control, int &condition); - static bool GetMultipleString(const TiXmlNode* pRootNode, const char* strTag, std::vector& vecStringValue); + static bool GetActions(const TiXmlNode* pRootNode, const char* strTag, CGUIAction& actions); static void GetRectFromString(const CStdString &string, FRECT &rect); - static bool GetAction(const TiXmlElement* pElement, CGUIActionDescriptor &action); static bool GetHitRect(const TiXmlNode* pRootNode, CRect &rect); private: - bool GetNavigation(const TiXmlElement *node, const char *tag, int &direction, std::vector &actions); bool GetCondition(const TiXmlNode *control, const char *tag, int &condition); static bool GetConditionalVisibility(const TiXmlNode* control, int &condition, CGUIInfoBool &allowHiddenFocus); bool GetPath(const TiXmlNode* pRootNode, const char* strTag, CStdString& strStringPath); Index: xbmc/guilib/GUIControlGroupList.cpp =================================================================== --- xbmc/guilib/GUIControlGroupList.cpp (revision 31566) +++ xbmc/guilib/GUIControlGroupList.cpp (working copy) @@ -255,29 +255,29 @@ if (m_orientation == VERTICAL) { if (before) // update the DOWN action to point to us - before->SetNavigation(before->GetControlIdUp(), control->GetID(), GetControlIdLeft(), GetControlIdRight()); + before->SetNavigation(before->GetControlIdUp(), control->GetID(), GetControlIdLeft(), GetControlIdRight(), GetControlIdBack()); if (after) // update the UP action to point to us - after->SetNavigation(control->GetID(), after->GetControlIdDown(), GetControlIdLeft(), GetControlIdRight()); + after->SetNavigation(control->GetID(), after->GetControlIdDown(), GetControlIdLeft(), GetControlIdRight(), GetControlIdBack()); } else { if (before) // update the RIGHT action to point to us - before->SetNavigation(GetControlIdUp(), GetControlIdDown(), before->GetControlIdLeft(), control->GetID()); + before->SetNavigation(GetControlIdUp(), GetControlIdDown(), before->GetControlIdLeft(), control->GetID(), GetControlIdBack()); if (after) // update the LEFT action to point to us - after->SetNavigation(GetControlIdUp(), GetControlIdDown(), control->GetID(), after->GetControlIdRight()); + after->SetNavigation(GetControlIdUp(), GetControlIdDown(), control->GetID(), after->GetControlIdRight(), GetControlIdBack()); } } // now the control's nav - std::vector empty; + CGUIAction empty; if (m_orientation == VERTICAL) { - control->SetNavigation(beforeID, afterID, GetControlIdLeft(), GetControlIdRight()); - control->SetNavigationActions(empty, empty, m_leftActions, m_rightActions, false); + control->SetNavigation(beforeID, afterID, GetControlIdLeft(), GetControlIdRight(), GetControlIdBack()); + control->SetNavigationActions(empty, empty, m_actionLeft, m_actionRight, empty, false); } else { - control->SetNavigation(GetControlIdUp(), GetControlIdDown(), beforeID, afterID); - control->SetNavigationActions(m_upActions, m_downActions, empty, empty, false); + control->SetNavigation(GetControlIdUp(), GetControlIdDown(), beforeID, afterID, GetControlIdBack()); + control->SetNavigationActions(m_actionUp, m_actionDown, empty, empty, empty, false); } if (!m_useControlPositions) Index: xbmc/guilib/GUIEditControl.cpp =================================================================== --- xbmc/guilib/GUIEditControl.cpp (revision 31566) +++ xbmc/guilib/GUIEditControl.cpp (working copy) @@ -413,13 +413,7 @@ { SEND_CLICK_MESSAGE(GetID(), GetParentID(), 0); - vector textChangeActions = m_textChangeActions; - for (unsigned int i = 0; i < textChangeActions.size(); i++) - { - CGUIMessage message(GUI_MSG_EXECUTE, GetID(), GetParentID()); - message.SetAction(textChangeActions[i]); - g_windowManager.SendMessage(message); - } + m_textChangeActions.Execute(GetID(), GetParentID()); SetInvalid(); } Index: xbmc/guilib/GUIEditControl.h =================================================================== --- xbmc/guilib/GUIEditControl.h (revision 31566) +++ xbmc/guilib/GUIEditControl.h (working copy) @@ -72,9 +72,9 @@ void SetInputType(INPUT_TYPE type, int heading); - void SetTextChangeActions(const std::vector& textChangeActions) { m_textChangeActions = textChangeActions; }; + void SetTextChangeActions(const CGUIAction& textChangeActions) { m_textChangeActions = textChangeActions; }; - bool HasTextChangeActions() { return m_textChangeActions.size() > 0; }; + bool HasTextChangeActions() { return m_textChangeActions.HasActionsMeetingCondition(); }; protected: virtual void RenderText(); @@ -104,6 +104,6 @@ INPUT_TYPE m_inputType; bool m_isMD5; - std::vector m_textChangeActions; + CGUIAction m_textChangeActions; }; #endif Index: xbmc/guilib/guilib.vcproj =================================================================== --- xbmc/guilib/guilib.vcproj (revision 31566) +++ xbmc/guilib/guilib.vcproj (working copy) @@ -228,7 +228,11 @@ + + + - - + + - - + + - - ¶ms); const CStdString& GetStringParam(size_t param = 0) const; - void SetAction(const CGUIActionDescriptor& action); - const CGUIActionDescriptor& GetAction() const; size_t GetNumStringParams() const; private: std::string m_strLabel; std::vector m_params; - CGUIActionDescriptor m_action; int m_senderID; int m_controlID; int m_message; Index: xbmc/guilib/GUIMultiSelectText.cpp =================================================================== --- xbmc/guilib/GUIMultiSelectText.cpp (revision 31566) +++ xbmc/guilib/GUIMultiSelectText.cpp (working copy) @@ -204,7 +204,7 @@ { if (m_selectedItem > 0) ScrollToItem(m_selectedItem - 1); - else if (GetNumSelectable() && m_controlLeft && m_controlLeft == m_controlID) + else if (GetNumSelectable() && m_actionLeft.GetNavigation() && m_actionLeft.GetNavigation() == m_controlID) ScrollToItem(GetNumSelectable() - 1); else return false; @@ -215,7 +215,7 @@ { if (GetNumSelectable() && m_selectedItem < GetNumSelectable() - 1) ScrollToItem(m_selectedItem + 1); - else if (m_controlRight && m_controlRight == m_controlID) + else if (m_actionRight.GetNavigation() && m_actionRight.GetNavigation() == m_controlID) ScrollToItem(0); else return false; Index: xbmc/guilib/GUIPanelContainer.cpp =================================================================== --- xbmc/guilib/GUIPanelContainer.cpp (revision 31566) +++ xbmc/guilib/GUIPanelContainer.cpp (working copy) @@ -210,7 +210,7 @@ void CGUIPanelContainer::OnLeft() { - bool wrapAround = m_controlLeft == GetID() || !(m_controlLeft || m_leftActions.size()); + bool wrapAround = m_actionLeft.GetNavigation() == GetID() || !m_actionLeft.HasActionsMeetingCondition(); if (m_orientation == VERTICAL && MoveLeft(wrapAround)) return; if (m_orientation == HORIZONTAL && MoveUp(wrapAround)) @@ -220,7 +220,7 @@ void CGUIPanelContainer::OnRight() { - bool wrapAround = m_controlRight == GetID() || !(m_controlRight || m_rightActions.size()); + bool wrapAround = m_actionRight.GetNavigation() == GetID() || !m_actionRight.HasActionsMeetingCondition(); if (m_orientation == VERTICAL && MoveRight(wrapAround)) return; if (m_orientation == HORIZONTAL && MoveDown(wrapAround)) @@ -230,7 +230,7 @@ void CGUIPanelContainer::OnUp() { - bool wrapAround = m_controlUp == GetID() || !(m_controlUp || m_upActions.size()); + bool wrapAround = m_actionUp.GetNavigation() == GetID() || !m_actionUp.HasActionsMeetingCondition(); if (m_orientation == VERTICAL && MoveUp(wrapAround)) return; if (m_orientation == HORIZONTAL && MoveLeft(wrapAround)) @@ -240,7 +240,7 @@ void CGUIPanelContainer::OnDown() { - bool wrapAround = m_controlDown == GetID() || !(m_controlDown || m_downActions.size()); + bool wrapAround = m_actionDown.GetNavigation() == GetID() || !m_actionDown.HasActionsMeetingCondition(); if (m_orientation == VERTICAL && MoveDown(wrapAround)) return; if (m_orientation == HORIZONTAL && MoveRight(wrapAround)) Index: xbmc/guilib/GUIStaticItem.cpp =================================================================== --- xbmc/guilib/GUIStaticItem.cpp (revision 31566) +++ xbmc/guilib/GUIStaticItem.cpp (working copy) @@ -1,5 +1,5 @@ /* - * Copyright (C) 2005-2010 Team XBMC + * Copyright (C) 2005-2012 Team XBMC * http://www.xbmc.org * * This Program is free software; you can redistribute it and/or modify @@ -44,20 +44,8 @@ const char *id = item->Attribute("id"); int visibleCondition = 0; CGUIControlFactory::GetConditionalVisibility(item, visibleCondition); - // multiple action strings are concat'd together, separated with " , " - vector actions; - CGUIControlFactory::GetMultipleString(item, "onclick", actions); - CStdString path; - for (vector::iterator it = actions.begin(); it != actions.end(); ++it) - { - (*it).m_action.Replace(",", ",,"); - if (!path.IsEmpty()) - { - path += " , "; - } - path += (*it).m_action; - } - SetPath(path); + + CGUIControlFactory::GetActions(item, "onclick", m_clickActions); SetLabel(label.GetLabel(parentID)); SetLabel2(label2.GetLabel(parentID)); SetThumbnailImage(thumb.GetLabel(parentID, true)); Index: xbmc/guilib/GUIStaticItem.h =================================================================== --- xbmc/guilib/GUIStaticItem.h (revision 31566) +++ xbmc/guilib/GUIStaticItem.h (working copy) @@ -1,5 +1,5 @@ /* - * Copyright (C) 2005-2010 Team XBMC + * Copyright (C) 2005-2012 Team XBMC * http://www.xbmc.org * * This Program is free software; you can redistribute it and/or modify @@ -28,6 +28,7 @@ #include "GUIInfoTypes.h" #include "FileItem.h" +#include "GUIAction.h" class TiXmlElement; @@ -66,10 +67,13 @@ periodically recomputed \param contextWindow window context to use for any info labels */ + const CGUIAction &GetClickActions() const { return m_clickActions; }; + void UpdateProperties(int contextWindow); private: typedef std::vector< std::pair > InfoVector; InfoVector m_info; + CGUIAction m_clickActions; }; typedef boost::shared_ptr CGUIStaticItemPtr; Index: xbmc/guilib/GUIToggleButtonControl.cpp =================================================================== --- xbmc/guilib/GUIToggleButtonControl.cpp (revision 31566) +++ xbmc/guilib/GUIToggleButtonControl.cpp (working copy) @@ -144,7 +144,7 @@ return CGUIButtonControl::GetLabel(); } -void CGUIToggleButtonControl::SetAltClickActions(const vector &clickActions) +void CGUIToggleButtonControl::SetAltClickActions(const CGUIAction &clickActions) { m_selectButton.SetClickActions(clickActions); } Index: xbmc/guilib/GUIToggleButtonControl.h =================================================================== --- xbmc/guilib/GUIToggleButtonControl.h (revision 31566) +++ xbmc/guilib/GUIToggleButtonControl.h (working copy) @@ -55,7 +55,7 @@ void SetAltLabel(const std::string& label); virtual CStdString GetLabel() const; void SetToggleSelect(int toggleSelect) { m_toggleSelect = toggleSelect; }; - void SetAltClickActions(const std::vector &clickActions); + void SetAltClickActions(const CGUIAction &clickActions); protected: virtual void UpdateColors(); Index: xbmc/guilib/GUIWindow.cpp =================================================================== --- xbmc/guilib/GUIWindow.cpp (revision 31566) +++ xbmc/guilib/GUIWindow.cpp (working copy) @@ -131,10 +131,8 @@ SetDefaults(); CGUIControlFactory::GetInfoColor(pRootElement, "backgroundcolor", m_clearBackground); - - - CGUIControlFactory::GetMultipleString(pRootElement, "onload", m_loadActions); - CGUIControlFactory::GetMultipleString(pRootElement, "onunload", m_unloadActions); + CGUIControlFactory::GetActions(pRootElement, "onload", m_loadActions); + CGUIControlFactory::GetActions(pRootElement, "onunload", m_unloadActions); CGUIControlFactory::GetHitRect(pRootElement, m_hitRect); TiXmlElement *pChild = pRootElement->FirstChildElement(); @@ -909,19 +907,6 @@ g_graphicsContext.Clear(color); } -void CGUIWindow::RunActions(std::vector& actions) -{ - vector tempActions = actions; - - // and execute our actions - for (unsigned int i = 0; i < tempActions.size(); i++) - { - CGUIMessage message(GUI_MSG_EXECUTE, 0, GetID()); - message.SetAction(tempActions[i]); - g_windowManager.SendMessage(message); - } -} - void CGUIWindow::SetRunActionsManually() { m_manualRunActions = true; @@ -929,10 +914,10 @@ void CGUIWindow::RunLoadActions() { - RunActions(m_loadActions); + m_loadActions.Execute(GetID(), GetParentID()); } void CGUIWindow::RunUnloadActions() { - RunActions(m_unloadActions); + m_unloadActions.Execute(GetID(), GetParentID()); } Index: xbmc/guilib/GUIWindow.h =================================================================== --- xbmc/guilib/GUIWindow.h (revision 31566) +++ xbmc/guilib/GUIWindow.h (working copy) @@ -246,8 +246,6 @@ void ChangeButtonToEdit(int id, bool singleLabel = false); //#endif - void RunActions(std::vector& actions); - int m_idRange; bool m_bRelativeCoords; OVERLAY_STATE m_overlayState; @@ -286,8 +284,8 @@ std::map m_mapProperties; - std::vector m_loadActions; - std::vector m_unloadActions; + CGUIAction m_loadActions; + CGUIAction m_unloadActions; bool m_manualRunActions; }; Index: xbmc/guilib/Key.h =================================================================== --- xbmc/guilib/Key.h (revision 31566) +++ xbmc/guilib/Key.h (working copy) @@ -180,6 +180,7 @@ #define ACTION_VOLUME_UP 88 #define ACTION_VOLUME_DOWN 89 #define ACTION_MUTE 91 +#define ACTION_NAV_BACK 92 #define ACTION_MOUSE 90 Index: xbmc/lib/libGoAhead/XBMChttp.cpp =================================================================== --- xbmc/lib/libGoAhead/XBMChttp.cpp (revision 31566) +++ xbmc/lib/libGoAhead/XBMChttp.cpp (working copy) @@ -35,7 +35,6 @@ #include "pictures/GUIWindowSlideShow.h" #include "windows/GUIMediaWindow.h" #include "windows/GUIWindowFileManager.h" -#include "GUIButtonScroller.h" #include "FileSystem/Directory.h" #include "FileSystem/VirtualDirectory.h" #include "utils/UdpClient.h" @@ -1800,17 +1799,9 @@ output += closeTag+openTag+"Type:Button"; if (strTmp!="") output += closeTag+openTag+"Description:" + strTmp; - vector actions = ((CGUIButtonControl *)pControl)->GetClickActions(); - if (actions.size()) - output += closeTag+openTag+"Execution:" + actions[0].m_action; + if (((CGUIButtonControl *)pControl)->HasClickActions()) + output += closeTag+openTag+"Execution:" + ((CGUIButtonControl *)pControl)->GetClickActions().GetFirstAction(); } - else if (pControl->GetControlType() == CGUIControl::GUICONTROL_BUTTONBAR) - { - output += closeTag+openTag+"Type:ButtonBar"+closeTag+openTag+"Description:" + strTmp; - CStdString button; - button.Format("%d",((CGUIButtonScroller *)pControl)->GetActiveButton()); - output += closeTag+openTag+"ActiveButton:" + button; - } else if (pControl->GetControlType() == CGUIControl::GUICONTROL_SPIN) { output += closeTag+openTag+"Type:Spin"+closeTag+openTag+"Description:" + strTmp; Index: xbmc/utils/StringUtils.cpp =================================================================== --- xbmc/utils/StringUtils.cpp (revision 31566) +++ xbmc/utils/StringUtils.cpp (working copy) @@ -290,6 +290,14 @@ return true; } +bool StringUtils::IsInteger(const CStdString& str) +{ + if (str.size() > 0 && str[0] == '-') + return IsNaturalNumber(str.Mid(1)); + else + return IsNaturalNumber(str); +} + void StringUtils::RemoveCRLF(CStdString& strLine) { while ( strLine.size() && (strLine.Right(1) == "\n" || strLine.Right(1) == "\r") ) Index: xbmc/utils/StringUtils.h =================================================================== --- xbmc/utils/StringUtils.h (revision 31566) +++ xbmc/utils/StringUtils.h (working copy) @@ -60,6 +60,7 @@ static CStdString SecondsToTimeString(long seconds, TIME_FORMAT format = TIME_FORMAT_GUESS); static bool IsNaturalNumber(const CStdString& str); + static bool IsInteger(const CStdString& str); static CStdString SizeToString(__int64 size); static const CStdString EmptyString; static size_t FindWords(const char *str, const char *wordLowerCase);