diff options
| author | Jørgen P. Tjernø <[email protected]> | 2013-12-02 19:31:46 -0800 |
|---|---|---|
| committer | Jørgen P. Tjernø <[email protected]> | 2013-12-02 19:46:31 -0800 |
| commit | f56bb35301836e56582a575a75864392a0177875 (patch) | |
| tree | de61ddd39de3e7df52759711950b4c288592f0dc /mp/src/vgui2/vgui_controls/ComboBox.cpp | |
| parent | Mark some more files as text. (diff) | |
| download | source-sdk-2013-f56bb35301836e56582a575a75864392a0177875.tar.xz source-sdk-2013-f56bb35301836e56582a575a75864392a0177875.zip | |
Fix line endings. WHAMMY.
Diffstat (limited to 'mp/src/vgui2/vgui_controls/ComboBox.cpp')
| -rw-r--r-- | mp/src/vgui2/vgui_controls/ComboBox.cpp | 2082 |
1 files changed, 1041 insertions, 1041 deletions
diff --git a/mp/src/vgui2/vgui_controls/ComboBox.cpp b/mp/src/vgui2/vgui_controls/ComboBox.cpp index 4949bf19..f8be274b 100644 --- a/mp/src/vgui2/vgui_controls/ComboBox.cpp +++ b/mp/src/vgui2/vgui_controls/ComboBox.cpp @@ -1,1041 +1,1041 @@ -//========= Copyright Valve Corporation, All rights reserved. ============//
-//
-// Purpose:
-//
-// $NoKeywords: $
-//=============================================================================//
-
-#define PROTECTED_THINGS_DISABLE
-
-#include "vgui/Cursor.h"
-#include "vgui/IInput.h"
-#include "vgui/ILocalize.h"
-#include "vgui/IScheme.h"
-#include "vgui/ISurface.h"
-#include "vgui/IPanel.h"
-#include "KeyValues.h"
-
-#include "vgui_controls/ComboBox.h"
-#include "vgui_controls/Menu.h"
-#include "vgui_controls/MenuItem.h"
-#include "vgui_controls/TextImage.h"
-
-#include <ctype.h>
-
-// memdbgon must be the last include file in a .cpp file!!!
-#include "tier0/memdbgon.h"
-
-using namespace vgui;
-
-namespace vgui
-{
-ComboBoxButton::ComboBoxButton(ComboBox *parent, const char *panelName, const char *text) : Button(parent, panelName, text)
-{
- SetButtonActivationType(ACTIVATE_ONPRESSED);
-}
-
-void ComboBoxButton::ApplySchemeSettings(IScheme *pScheme)
-{
- Button::ApplySchemeSettings(pScheme);
-
- SetFont(pScheme->GetFont("Marlett", IsProportional()));
- SetContentAlignment(Label::a_west);
-#ifdef OSX
- SetTextInset(-3, 0);
-#else
- SetTextInset(3, 0);
-#endif
- SetDefaultBorder(pScheme->GetBorder("ScrollBarButtonBorder"));
-
- // arrow changes color but the background doesnt.
- SetDefaultColor(GetSchemeColor("ComboBoxButton.ArrowColor", pScheme), GetSchemeColor("ComboBoxButton.BgColor", pScheme));
- SetArmedColor(GetSchemeColor("ComboBoxButton.ArmedArrowColor", pScheme), GetSchemeColor("ComboBoxButton.BgColor", pScheme));
- SetDepressedColor(GetSchemeColor("ComboBoxButton.ArmedArrowColor", pScheme), GetSchemeColor("ComboBoxButton.BgColor", pScheme));
- m_DisabledBgColor = GetSchemeColor("ComboBoxButton.DisabledBgColor", pScheme);
-}
-
-IBorder * ComboBoxButton::GetBorder(bool depressed, bool armed, bool selected, bool keyfocus)
-{
- return NULL;
- // return Button::GetBorder(depressed, armed, selected, keyfocus);
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Dim the arrow on the button when exiting the box
-// only if the menu is closed, so let the parent handle this.
-//-----------------------------------------------------------------------------
-void ComboBoxButton::OnCursorExited()
-{
- // want the arrow to go grey when we exit the box if the menu is not open
- CallParentFunction(new KeyValues("CursorExited"));
-}
-
-} // namespace vgui
-
-vgui::Panel *ComboBox_Factory()
-{
- return new ComboBox( NULL, NULL, 5, true );
-}
-DECLARE_BUILD_FACTORY_CUSTOM( ComboBox, ComboBox_Factory );
-
-//-----------------------------------------------------------------------------
-// Purpose: Constructor
-// Input : parent - parent class
-// panelName
-// numLines - number of lines in dropdown menu
-// allowEdit - whether combobox is editable or not
-//-----------------------------------------------------------------------------
-ComboBox::ComboBox(Panel *parent, const char *panelName, int numLines, bool allowEdit ) : TextEntry(parent, panelName)
-{
- SetEditable(allowEdit);
- SetHorizontalScrolling(false); // do not scroll, always Start at the beginning of the text.
-
- // create the drop-down menu
- m_pDropDown = new Menu(this, NULL);
- m_pDropDown->AddActionSignalTarget(this);
- m_pDropDown->SetTypeAheadMode( Menu::TYPE_AHEAD_MODE );
-
- // button to Activate menu
- m_pButton = new ComboBoxButton(this, "Button", "u");
- m_pButton->SetCommand("ButtonClicked");
- m_pButton->AddActionSignalTarget(this);
-
- SetNumberOfEditLines(numLines);
-
- m_bHighlight = false;
- m_iDirection = Menu::DOWN;
- m_iOpenOffsetY = 0;
- m_bPreventTextChangeMessage = false;
- m_szBorderOverride[0] = '\0';
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Destructor
-//-----------------------------------------------------------------------------
-ComboBox::~ComboBox()
-{
- m_pDropDown->DeletePanel();
- m_pButton->DeletePanel();
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Set the number of items in the dropdown menu.
-// Input : numLines - number of items in dropdown menu
-//-----------------------------------------------------------------------------
-void ComboBox::SetNumberOfEditLines( int numLines )
-{
- m_pDropDown->SetNumberOfVisibleItems( numLines );
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Add an item to the drop down
-// Input : char *itemText - name of dropdown menu item
-//-----------------------------------------------------------------------------
-int ComboBox::AddItem(const char *itemText, const KeyValues *userData)
-{
- // when the menu item is selected it will send the custom message "SetText"
- return m_pDropDown->AddMenuItem( itemText, new KeyValues("SetText", "text", itemText), this, userData );
-}
-
-
-//-----------------------------------------------------------------------------
-// Purpose: Add an item to the drop down
-// Input : char *itemText - name of dropdown menu item
-//-----------------------------------------------------------------------------
-int ComboBox::AddItem(const wchar_t *itemText, const KeyValues *userData)
-{
- // add the element to the menu
- // when the menu item is selected it will send the custom message "SetText"
- KeyValues *kv = new KeyValues("SetText");
- kv->SetWString("text", itemText);
- // get an ansi version for the menuitem name
- char ansi[128];
- g_pVGuiLocalize->ConvertUnicodeToANSI(itemText, ansi, sizeof(ansi));
- return m_pDropDown->AddMenuItem(ansi, kv, this, userData);
-}
-
-
-//-----------------------------------------------------------------------------
-// Removes a single item
-//-----------------------------------------------------------------------------
-void ComboBox::DeleteItem( int itemID )
-{
- if ( !m_pDropDown->IsValidMenuID(itemID))
- return;
-
- m_pDropDown->DeleteItem( itemID );
-}
-
-
-//-----------------------------------------------------------------------------
-// Purpose: Updates a current item to the drop down
-// Input : char *itemText - name of dropdown menu item
-//-----------------------------------------------------------------------------
-bool ComboBox::UpdateItem(int itemID, const char *itemText, const KeyValues *userData)
-{
- if ( !m_pDropDown->IsValidMenuID(itemID))
- return false;
-
- // when the menu item is selected it will send the custom message "SetText"
- m_pDropDown->UpdateMenuItem(itemID, itemText, new KeyValues("SetText", "text", itemText), userData);
- InvalidateLayout();
- return true;
-}
-//-----------------------------------------------------------------------------
-// Purpose: Updates a current item to the drop down
-// Input : wchar_t *itemText - name of dropdown menu item
-//-----------------------------------------------------------------------------
-bool ComboBox::UpdateItem(int itemID, const wchar_t *itemText, const KeyValues *userData)
-{
- if ( !m_pDropDown->IsValidMenuID(itemID))
- return false;
-
- // when the menu item is selected it will send the custom message "SetText"
- KeyValues *kv = new KeyValues("SetText");
- kv->SetWString("text", itemText);
- m_pDropDown->UpdateMenuItem(itemID, itemText, kv, userData);
- InvalidateLayout();
- return true;
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Updates a current item to the drop down
-// Input : wchar_t *itemText - name of dropdown menu item
-//-----------------------------------------------------------------------------
-bool ComboBox::IsItemIDValid( int itemID )
-{
- return m_pDropDown->IsValidMenuID(itemID);
-}
-
-//-----------------------------------------------------------------------------
-// Purpose:
-//-----------------------------------------------------------------------------
-void ComboBox::SetItemEnabled(const char *itemText, bool state)
-{
- m_pDropDown->SetItemEnabled(itemText, state);
-}
-
-//-----------------------------------------------------------------------------
-// Purpose:
-//-----------------------------------------------------------------------------
-void ComboBox::SetItemEnabled(int itemID, bool state)
-{
- m_pDropDown->SetItemEnabled(itemID, state);
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Remove all items from the drop down menu
-//-----------------------------------------------------------------------------
-void ComboBox::RemoveAll()
-{
- m_pDropDown->DeleteAllItems();
-}
-
-//-----------------------------------------------------------------------------
-// Purpose:
-//-----------------------------------------------------------------------------
-int ComboBox::GetItemCount()
-{
- return m_pDropDown->GetItemCount();
-}
-
-int ComboBox::GetItemIDFromRow( int row )
-{
- // valid from [0, GetItemCount)
- return m_pDropDown->GetMenuID( row );
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Activate the item in the menu list, as if that menu item had been selected by the user
-// Input : itemID - itemID from AddItem in list of dropdown items
-//-----------------------------------------------------------------------------
-void ComboBox::ActivateItem(int itemID)
-{
- m_pDropDown->ActivateItem(itemID);
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Activate the item in the menu list, as if that menu item had been selected by the user
-// Input : itemID - itemID from AddItem in list of dropdown items
-//-----------------------------------------------------------------------------
-void ComboBox::ActivateItemByRow(int row)
-{
- m_pDropDown->ActivateItemByRow(row);
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Activate the item in the menu list, without sending a TextChanged message
-// Input : row - row to activate
-//-----------------------------------------------------------------------------
-void ComboBox::SilentActivateItemByRow(int row)
-{
- int itemID = GetItemIDFromRow( row );
- if ( itemID >= 0 )
- {
- SilentActivateItem( itemID );
- }
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Activate the item in the menu list, without sending a TextChanged message
-// Input : itemID - itemID from AddItem in list of dropdown items
-//-----------------------------------------------------------------------------
-void ComboBox::SilentActivateItem(int itemID)
-{
- m_pDropDown->SilentActivateItem(itemID);
-
- // Now manually call our set text, with a wrapper to ensure we don't send the Text Changed message
- wchar_t name[ 256 ];
- GetItemText( itemID, name, sizeof( name ) );
-
- m_bPreventTextChangeMessage = true;
- OnSetText( name );
- m_bPreventTextChangeMessage = false;
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Allows a custom menu to be used with the combo box
-//-----------------------------------------------------------------------------
-void ComboBox::SetMenu( Menu *menu )
-{
- if ( m_pDropDown )
- {
- m_pDropDown->MarkForDeletion();
- }
-
- m_pDropDown = menu;
- if ( m_pDropDown )
- {
- m_pDropDown->SetParent( this );
- }
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Layout the format of the combo box for drawing on screen
-//-----------------------------------------------------------------------------
-void ComboBox::PerformLayout()
-{
- int wide, tall;
- GetPaintSize(wide, tall);
-
- BaseClass::PerformLayout();
-
- HFont buttonFont = m_pButton->GetFont();
- int fontTall = surface()->GetFontTall( buttonFont );
-
- int buttonSize = min( tall, fontTall );
-
- int buttonY = ( ( tall - 1 ) - buttonSize ) / 2;
-
- // Some dropdown button icons in our games are wider than they are taller. We need to factor that in.
- int button_wide, button_tall;
- m_pButton->GetContentSize(button_wide, button_tall);
- button_wide = max( buttonSize, button_wide );
-
- m_pButton->SetBounds( wide - button_wide, buttonY, button_wide, buttonSize );
- if ( IsEditable() )
- {
- SetCursor(dc_ibeam);
- }
- else
- {
- SetCursor(dc_arrow);
- }
-
- m_pButton->SetEnabled(IsEnabled());
-
- DoMenuLayout();
-}
-
-//-----------------------------------------------------------------------------
-// Purpose:
-//-----------------------------------------------------------------------------
-void ComboBox::DoMenuLayout()
-{
- m_pDropDown->PositionRelativeToPanel( this, m_iDirection, m_iOpenOffsetY );
-
- // reset the width of the drop down menu to be the width of the combo box
- m_pDropDown->SetFixedWidth(GetWide());
- m_pDropDown->ForceCalculateWidth();
-
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Sorts the items in the list
-//-----------------------------------------------------------------------------
-void ComboBox::SortItems( void )
-{
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: return the index of the last selected item
-//-----------------------------------------------------------------------------
-int ComboBox::GetActiveItem()
-{
- return m_pDropDown->GetActiveItem();
-}
-
-//-----------------------------------------------------------------------------
-// Purpose:
-//-----------------------------------------------------------------------------
-KeyValues *ComboBox::GetActiveItemUserData()
-{
- return m_pDropDown->GetItemUserData(GetActiveItem());
-}
-
-
-//-----------------------------------------------------------------------------
-// Purpose:
-//-----------------------------------------------------------------------------
-KeyValues *ComboBox::GetItemUserData(int itemID)
-{
- return m_pDropDown->GetItemUserData(itemID);
-}
-
-
-//-----------------------------------------------------------------------------
-// Purpose: data accessor
-//-----------------------------------------------------------------------------
-void ComboBox::GetItemText( int itemID, wchar_t *text, int bufLenInBytes )
-{
- m_pDropDown->GetItemText( itemID, text, bufLenInBytes );
-}
-
-void ComboBox::GetItemText( int itemID, char *text, int bufLenInBytes )
-{
- m_pDropDown->GetItemText( itemID, text, bufLenInBytes );
-}
-
-
-//-----------------------------------------------------------------------------
-// Purpose:
-// Output : Returns true on success, false on failure.
-//-----------------------------------------------------------------------------
-bool ComboBox::IsDropdownVisible()
-{
- return m_pDropDown->IsVisible();
-}
-
-//-----------------------------------------------------------------------------
-// Purpose:
-// Input : *inResourceData -
-//-----------------------------------------------------------------------------
-void ComboBox::ApplySchemeSettings(IScheme *pScheme)
-{
- BaseClass::ApplySchemeSettings(pScheme);
-
- SetBorder( pScheme->GetBorder( m_szBorderOverride[0] ? m_szBorderOverride : "ComboBoxBorder" ) );
-}
-
-void ComboBox::ApplySettings( KeyValues *pInResourceData )
-{
- BaseClass::ApplySettings( pInResourceData );
-
- const char *pBorderOverride = pInResourceData->GetString( "border_override", NULL );
- if ( pBorderOverride )
- {
- V_strncpy( m_szBorderOverride, pBorderOverride, sizeof( m_szBorderOverride ) );
- }
-
- KeyValues *pKVButton = pInResourceData->FindKey( "Button" );
- if ( pKVButton && m_pButton )
- {
- m_pButton->ApplySettings( pKVButton );
- }
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Set the visiblity of the drop down menu button.
-//-----------------------------------------------------------------------------
-void ComboBox::SetDropdownButtonVisible(bool state)
-{
- m_pButton->SetVisible(state);
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: overloads TextEntry MousePressed
-//-----------------------------------------------------------------------------
-void ComboBox::OnMousePressed(MouseCode code)
-{
- if ( !m_pDropDown )
- return;
-
- if ( !IsEnabled() )
- return;
-
- // make sure it's getting pressed over us (it may not be due to mouse capture)
- if ( !IsCursorOver() )
- {
- HideMenu();
- return;
- }
-
- if ( IsEditable() )
- {
- BaseClass::OnMousePressed(code);
- HideMenu();
- }
- else
- {
- // clicking on a non-editable text box just activates the drop down menu
- RequestFocus();
- DoClick();
- }
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Double-click acts the same as a single-click
-//-----------------------------------------------------------------------------
-void ComboBox::OnMouseDoublePressed(MouseCode code)
-{
- if (IsEditable())
- {
- BaseClass::OnMouseDoublePressed(code);
- }
- else
- {
- OnMousePressed(code);
- }
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Called when a command is received from the menu
-// Changes the label text to be that of the command
-// Input : char *command -
-//-----------------------------------------------------------------------------
-void ComboBox::OnCommand( const char *command )
-{
- if (!stricmp(command, "ButtonClicked"))
- {
- // hide / show the menu underneath
- DoClick();
- }
-
- Panel::OnCommand(command);
-}
-
-//-----------------------------------------------------------------------------
-// Purpose:
-//-----------------------------------------------------------------------------
-void ComboBox::OnSetText(const wchar_t *newtext)
-{
- // see if the combobox text has changed, and if so, post a message detailing the new text
- const wchar_t *text = newtext;
-
- // check if the new text is a localized string, if so undo it
- if (*text == '#')
- {
- char cbuf[255];
- g_pVGuiLocalize->ConvertUnicodeToANSI(text, cbuf, 255);
-
- // try lookup in localization tables
- StringIndex_t unlocalizedTextSymbol = g_pVGuiLocalize->FindIndex(cbuf + 1);
-
- if (unlocalizedTextSymbol != INVALID_LOCALIZE_STRING_INDEX)
- {
- // we have a new text value
- text = g_pVGuiLocalize->GetValueByIndex(unlocalizedTextSymbol);
- }
- }
-
- wchar_t wbuf[255];
- GetText(wbuf, 254);
-
- if ( wcscmp(wbuf, text) )
- {
- // text has changed
- SetText(text);
-
- // fire off that things have changed
- if ( !m_bPreventTextChangeMessage )
- {
- PostActionSignal(new KeyValues("TextChanged", "text", text));
- }
- Repaint();
- }
-
- // close the box
- HideMenu();
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: hides the menu
-//-----------------------------------------------------------------------------
-void ComboBox::HideMenu(void)
-{
- if ( !m_pDropDown )
- return;
-
- // hide the menu
- m_pDropDown->SetVisible(false);
- Repaint();
- OnHideMenu(m_pDropDown);
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: shows the menu
-//-----------------------------------------------------------------------------
-void ComboBox::ShowMenu(void)
-{
- if ( !m_pDropDown )
- return;
-
- // hide the menu
- m_pDropDown->SetVisible(false);
- DoClick();
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Called when the window loses focus; hides the menu
-//-----------------------------------------------------------------------------
-void ComboBox::OnKillFocus()
-{
- SelectNoText();
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Called when the menu is closed
-//-----------------------------------------------------------------------------
-void ComboBox::OnMenuClose()
-{
- HideMenu();
-
- if ( HasFocus() )
- {
- SelectAllText(false);
- }
- else if ( m_bHighlight )
- {
- m_bHighlight = false;
- // we want the text to be highlighted when we request the focus
-// SelectAllOnFirstFocus(true);
- RequestFocus();
- }
- // if cursor is in this box or the arrow box
- else if ( IsCursorOver() )// make sure it's getting pressed over us (it may not be due to mouse capture)
- {
- SelectAllText(false);
- OnCursorEntered();
- // Get focus so the box will unhighlight if we click somewhere else.
- RequestFocus();
- }
- else
- {
- m_pButton->SetArmed(false);
- }
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Handles hotkey accesses
-// FIXME: make this open different directions as necessary see menubutton.
-//-----------------------------------------------------------------------------
-void ComboBox::DoClick()
-{
- // menu is already visible, hide the menu
- if ( m_pDropDown->IsVisible() )
- {
- HideMenu();
- return;
- }
-
- // do nothing if menu is not enabled
- if ( !m_pDropDown->IsEnabled() )
- {
- return;
- }
- // force the menu to Think
- m_pDropDown->PerformLayout();
-
- // make sure we're at the top of the draw order (and therefore our children as well)
- // RequestFocus();
-
- // We want the item that is shown in the combo box to show as selected
- int itemToSelect = -1;
- int i;
- wchar_t comboBoxContents[255];
- GetText(comboBoxContents, 255);
- for ( i = 0 ; i < m_pDropDown->GetItemCount() ; i++ )
- {
- wchar_t menuItemName[255];
- int menuID = m_pDropDown->GetMenuID(i);
- m_pDropDown->GetMenuItem(menuID)->GetText(menuItemName, 255);
- if (!wcscmp(menuItemName, comboBoxContents))
- {
- itemToSelect = i;
- break;
- }
- }
- // if we found a match, highlight it on opening the menu
- if ( itemToSelect >= 0 )
- {
- m_pDropDown->SetCurrentlyHighlightedItem( m_pDropDown->GetMenuID(itemToSelect) );
- }
-
- // reset the dropdown's position
- DoMenuLayout();
-
-
- // make sure we're at the top of the draw order (and therefore our children as well)
- // this important to make sure the menu will be drawn in the foreground
- MoveToFront();
-
- // !KLUDGE! Force alpha to solid. Otherwise,
- // we run into weird VGUI problems with pops
- // and the stencil test
- Color c = m_pDropDown->GetBgColor();
- c[3] = 255;
- m_pDropDown->SetBgColor( c );
-
- // notify
- OnShowMenu(m_pDropDown);
-
- // show the menu
- m_pDropDown->SetVisible(true);
-
- // bring to focus
- m_pDropDown->RequestFocus();
-
- // no text is highlighted when the menu is opened
- SelectNoText();
-
- // highlight the arrow while menu is open
- m_pButton->SetArmed(true);
-
- Repaint();
-}
-
-
-//-----------------------------------------------------------------------------
-// Purpose: Brighten the arrow on the button when entering the box
-//-----------------------------------------------------------------------------
-void ComboBox::OnCursorEntered()
-{
- // want the arrow to go white when we enter the box
- m_pButton->OnCursorEntered();
- TextEntry::OnCursorEntered();
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Dim the arrow on the button when exiting the box
-//-----------------------------------------------------------------------------
-void ComboBox::OnCursorExited()
-{
- // want the arrow to go grey when we exit the box if the menu is not open
- if ( !m_pDropDown->IsVisible() )
- {
- m_pButton->SetArmed(false);
- TextEntry::OnCursorExited();
- }
-}
-
-//-----------------------------------------------------------------------------
-// Purpose:
-//-----------------------------------------------------------------------------
-#ifdef _X360
-void ComboBox::OnMenuItemSelected()
-{
- m_bHighlight = true;
- // For editable cbs, fill in the text field from whatever is chosen from the dropdown...
-
- //=============================================================================
- // HPE_BEGIN:
- // [pfreese] The text for the combo box should be updated regardless of its
- // editable state, and in any case, the member variable below was never
- // correctly initialized.
- //=============================================================================
-
- // if ( m_bAllowEdit )
-
- //=============================================================================
- // HPE_END
- //=============================================================================
- {
- int idx = GetActiveItem();
- if ( idx >= 0 )
- {
- wchar_t name[ 256 ];
- GetItemText( idx, name, sizeof( name ) );
-
- OnSetText( name );
- }
- }
-
- Repaint();
-
- // go to the next control
- if(!NavigateDown())
- {
- NavigateUp();
- }
-}
-#else
-void ComboBox::OnMenuItemSelected()
-{
- m_bHighlight = true;
- // For editable cbs, fill in the text field from whatever is chosen from the dropdown...
- //if ( m_bAllowEdit )
- {
- int idx = GetActiveItem();
- if ( idx >= 0 )
- {
- wchar_t name[ 256 ];
- GetItemText( idx, name, sizeof( name ) );
-
- OnSetText( name );
- }
- }
-
- Repaint();
-}
-#endif
-
-//-----------------------------------------------------------------------------
-// Purpose:
-//-----------------------------------------------------------------------------
-void ComboBox::OnSizeChanged(int wide, int tall)
-{
- BaseClass::OnSizeChanged( wide, tall);
-
- // set the drawwidth.
- int bwide, btall;
- PerformLayout();
- m_pButton->GetSize( bwide, btall);
- SetDrawWidth( wide - bwide );
-}
-
-//-----------------------------------------------------------------------------
-// Purpose:
-//-----------------------------------------------------------------------------
-#ifdef _X360
-void ComboBox::OnSetFocus()
-{
- BaseClass::OnSetFocus();
-
- GotoTextEnd();
- SelectAllText(true);
-}
-#else
-void ComboBox::OnSetFocus()
-{
- BaseClass::OnSetFocus();
-
- GotoTextEnd();
- SelectAllText(false);
-}
-#endif
-
-//-----------------------------------------------------------------------------
-// Purpose:
-//-----------------------------------------------------------------------------
-#ifdef _X360
-void ComboBox::OnKeyCodePressed(KeyCode code)
-{
- switch ( GetBaseButtonCode( code ) )
- {
- case KEY_XBUTTON_A:
- DoClick();
- break;
- case KEY_XBUTTON_UP:
- case KEY_XSTICK1_UP:
- case KEY_XSTICK2_UP:
- if(m_pDropDown->IsVisible())
- {
- MoveAlongMenuItemList(-1);
- }
- else
- {
- BaseClass::OnKeyCodePressed(code);
- }
- break;
- case KEY_XBUTTON_DOWN:
- case KEY_XSTICK1_DOWN:
- case KEY_XSTICK2_DOWN:
- if(m_pDropDown->IsVisible())
- {
- MoveAlongMenuItemList(1);
- }
- else
- {
- BaseClass::OnKeyCodePressed(code);
- }
- break;
- default:
- BaseClass::OnKeyCodePressed(code);
- break;
- }
-}
-#endif
-
-//-----------------------------------------------------------------------------
-// Purpose: Handles up/down arrows
-//-----------------------------------------------------------------------------
-void ComboBox::OnKeyCodeTyped(KeyCode code)
-{
- bool alt = (input()->IsKeyDown(KEY_LALT) || input()->IsKeyDown(KEY_RALT));
-
- if (alt)
- {
- switch (code)
- {
- case KEY_UP:
- case KEY_DOWN:
- {
- DoClick();
- break;
- }
- default:
- {
- BaseClass::OnKeyCodeTyped(code);
- break;
- }
- }
- }
- else
- {
- switch (code)
- {
- case KEY_HOME:
- case KEY_END:
- case KEY_PAGEUP:
- case KEY_PAGEDOWN:
- case KEY_UP:
- case KEY_DOWN:
- {
- int itemSelected = m_pDropDown->GetCurrentlyHighlightedItem();
- m_pDropDown->OnKeyCodeTyped(code);
- int itemToSelect = m_pDropDown->GetCurrentlyHighlightedItem();
-
- if ( itemToSelect != itemSelected )
- {
- SelectMenuItem(itemToSelect);
- }
- break;
- }
-
- case KEY_ENTER:
- {
- int itemToSelect = m_pDropDown->GetCurrentlyHighlightedItem();
- m_pDropDown->ActivateItem(itemToSelect);
- break;
- }
-
- default:
- {
- BaseClass::OnKeyCodeTyped(code);
- break;
- }
- }
- }
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: handles key input
-//-----------------------------------------------------------------------------
-void ComboBox::OnKeyTyped(wchar_t unichar)
-{
- if ( IsEditable() || unichar == '\t') // don't play with key presses in edit mode
- {
- BaseClass::OnKeyTyped( unichar );
- return;
- }
-
- int itemSelected = m_pDropDown->GetCurrentlyHighlightedItem();
- m_pDropDown->OnKeyTyped(unichar);
- int itemToSelect = m_pDropDown->GetCurrentlyHighlightedItem();
-
- if ( itemToSelect != itemSelected )
- {
- SelectMenuItem(itemToSelect);
- }
- else
- {
- BaseClass::OnKeyTyped( unichar );
- }
-}
-
-void ComboBox::SelectMenuItem(int itemToSelect)
-{
- // if we found this item, then we scroll up or down
- if ( itemToSelect >= 0 && itemToSelect < m_pDropDown->GetItemCount() )
- {
- wchar_t menuItemName[255];
-
- int menuID = m_pDropDown->GetMenuID(itemToSelect);
- m_pDropDown->GetMenuItem(menuID)->GetText(menuItemName, 254);
- OnSetText(menuItemName);
- SelectAllText(false);
- }
-}
-
-//-----------------------------------------------------------------------------
-// Purpose:
-//-----------------------------------------------------------------------------
-void ComboBox::MoveAlongMenuItemList(int direction)
-{
- // We want the item that is shown in the combo box to show as selected
- int itemToSelect = -1;
- wchar_t menuItemName[255];
- int i;
-
- wchar_t comboBoxContents[255];
- GetText(comboBoxContents, 254);
- for ( i = 0 ; i < m_pDropDown->GetItemCount() ; i++ )
- {
- int menuID = m_pDropDown->GetMenuID(i);
- m_pDropDown->GetMenuItem(menuID)->GetText(menuItemName, 254);
-
- if ( !wcscmp(menuItemName, comboBoxContents) )
- {
- itemToSelect = i;
- break;
- }
- }
-
- if ( itemToSelect >= 0 )
- {
- int newItem = itemToSelect + direction;
- if ( newItem < 0 )
- {
- newItem = 0;
- }
- else if ( newItem >= m_pDropDown->GetItemCount() )
- {
- newItem = m_pDropDown->GetItemCount() - 1;
- }
- SelectMenuItem(newItem);
- }
-
-}
-
-void ComboBox::MoveToFirstMenuItem()
-{
- SelectMenuItem(0);
-}
-
-void ComboBox::MoveToLastMenuItem()
-{
- SelectMenuItem(m_pDropDown->GetItemCount() - 1);
-}
-
-
-//-----------------------------------------------------------------------------
-// Purpose: Sets the direction from the menu button the menu should open
-//-----------------------------------------------------------------------------
-void ComboBox::SetOpenDirection(Menu::MenuDirection_e direction)
-{
- m_iDirection = direction;
-}
-
-void ComboBox::SetFont( HFont font )
-{
- BaseClass::SetFont( font );
-
- m_pDropDown->SetFont( font );
-}
-
-
-void ComboBox::SetUseFallbackFont( bool bState, HFont hFallback )
-{
- BaseClass::SetUseFallbackFont( bState, hFallback );
- m_pDropDown->SetUseFallbackFont( bState, hFallback );
-}
+//========= Copyright Valve Corporation, All rights reserved. ============// +// +// Purpose: +// +// $NoKeywords: $ +//=============================================================================// + +#define PROTECTED_THINGS_DISABLE + +#include "vgui/Cursor.h" +#include "vgui/IInput.h" +#include "vgui/ILocalize.h" +#include "vgui/IScheme.h" +#include "vgui/ISurface.h" +#include "vgui/IPanel.h" +#include "KeyValues.h" + +#include "vgui_controls/ComboBox.h" +#include "vgui_controls/Menu.h" +#include "vgui_controls/MenuItem.h" +#include "vgui_controls/TextImage.h" + +#include <ctype.h> + +// memdbgon must be the last include file in a .cpp file!!! +#include "tier0/memdbgon.h" + +using namespace vgui; + +namespace vgui +{ +ComboBoxButton::ComboBoxButton(ComboBox *parent, const char *panelName, const char *text) : Button(parent, panelName, text) +{ + SetButtonActivationType(ACTIVATE_ONPRESSED); +} + +void ComboBoxButton::ApplySchemeSettings(IScheme *pScheme) +{ + Button::ApplySchemeSettings(pScheme); + + SetFont(pScheme->GetFont("Marlett", IsProportional())); + SetContentAlignment(Label::a_west); +#ifdef OSX + SetTextInset(-3, 0); +#else + SetTextInset(3, 0); +#endif + SetDefaultBorder(pScheme->GetBorder("ScrollBarButtonBorder")); + + // arrow changes color but the background doesnt. + SetDefaultColor(GetSchemeColor("ComboBoxButton.ArrowColor", pScheme), GetSchemeColor("ComboBoxButton.BgColor", pScheme)); + SetArmedColor(GetSchemeColor("ComboBoxButton.ArmedArrowColor", pScheme), GetSchemeColor("ComboBoxButton.BgColor", pScheme)); + SetDepressedColor(GetSchemeColor("ComboBoxButton.ArmedArrowColor", pScheme), GetSchemeColor("ComboBoxButton.BgColor", pScheme)); + m_DisabledBgColor = GetSchemeColor("ComboBoxButton.DisabledBgColor", pScheme); +} + +IBorder * ComboBoxButton::GetBorder(bool depressed, bool armed, bool selected, bool keyfocus) +{ + return NULL; + // return Button::GetBorder(depressed, armed, selected, keyfocus); +} + +//----------------------------------------------------------------------------- +// Purpose: Dim the arrow on the button when exiting the box +// only if the menu is closed, so let the parent handle this. +//----------------------------------------------------------------------------- +void ComboBoxButton::OnCursorExited() +{ + // want the arrow to go grey when we exit the box if the menu is not open + CallParentFunction(new KeyValues("CursorExited")); +} + +} // namespace vgui + +vgui::Panel *ComboBox_Factory() +{ + return new ComboBox( NULL, NULL, 5, true ); +} +DECLARE_BUILD_FACTORY_CUSTOM( ComboBox, ComboBox_Factory ); + +//----------------------------------------------------------------------------- +// Purpose: Constructor +// Input : parent - parent class +// panelName +// numLines - number of lines in dropdown menu +// allowEdit - whether combobox is editable or not +//----------------------------------------------------------------------------- +ComboBox::ComboBox(Panel *parent, const char *panelName, int numLines, bool allowEdit ) : TextEntry(parent, panelName) +{ + SetEditable(allowEdit); + SetHorizontalScrolling(false); // do not scroll, always Start at the beginning of the text. + + // create the drop-down menu + m_pDropDown = new Menu(this, NULL); + m_pDropDown->AddActionSignalTarget(this); + m_pDropDown->SetTypeAheadMode( Menu::TYPE_AHEAD_MODE ); + + // button to Activate menu + m_pButton = new ComboBoxButton(this, "Button", "u"); + m_pButton->SetCommand("ButtonClicked"); + m_pButton->AddActionSignalTarget(this); + + SetNumberOfEditLines(numLines); + + m_bHighlight = false; + m_iDirection = Menu::DOWN; + m_iOpenOffsetY = 0; + m_bPreventTextChangeMessage = false; + m_szBorderOverride[0] = '\0'; +} + +//----------------------------------------------------------------------------- +// Purpose: Destructor +//----------------------------------------------------------------------------- +ComboBox::~ComboBox() +{ + m_pDropDown->DeletePanel(); + m_pButton->DeletePanel(); +} + +//----------------------------------------------------------------------------- +// Purpose: Set the number of items in the dropdown menu. +// Input : numLines - number of items in dropdown menu +//----------------------------------------------------------------------------- +void ComboBox::SetNumberOfEditLines( int numLines ) +{ + m_pDropDown->SetNumberOfVisibleItems( numLines ); +} + +//----------------------------------------------------------------------------- +// Purpose: Add an item to the drop down +// Input : char *itemText - name of dropdown menu item +//----------------------------------------------------------------------------- +int ComboBox::AddItem(const char *itemText, const KeyValues *userData) +{ + // when the menu item is selected it will send the custom message "SetText" + return m_pDropDown->AddMenuItem( itemText, new KeyValues("SetText", "text", itemText), this, userData ); +} + + +//----------------------------------------------------------------------------- +// Purpose: Add an item to the drop down +// Input : char *itemText - name of dropdown menu item +//----------------------------------------------------------------------------- +int ComboBox::AddItem(const wchar_t *itemText, const KeyValues *userData) +{ + // add the element to the menu + // when the menu item is selected it will send the custom message "SetText" + KeyValues *kv = new KeyValues("SetText"); + kv->SetWString("text", itemText); + // get an ansi version for the menuitem name + char ansi[128]; + g_pVGuiLocalize->ConvertUnicodeToANSI(itemText, ansi, sizeof(ansi)); + return m_pDropDown->AddMenuItem(ansi, kv, this, userData); +} + + +//----------------------------------------------------------------------------- +// Removes a single item +//----------------------------------------------------------------------------- +void ComboBox::DeleteItem( int itemID ) +{ + if ( !m_pDropDown->IsValidMenuID(itemID)) + return; + + m_pDropDown->DeleteItem( itemID ); +} + + +//----------------------------------------------------------------------------- +// Purpose: Updates a current item to the drop down +// Input : char *itemText - name of dropdown menu item +//----------------------------------------------------------------------------- +bool ComboBox::UpdateItem(int itemID, const char *itemText, const KeyValues *userData) +{ + if ( !m_pDropDown->IsValidMenuID(itemID)) + return false; + + // when the menu item is selected it will send the custom message "SetText" + m_pDropDown->UpdateMenuItem(itemID, itemText, new KeyValues("SetText", "text", itemText), userData); + InvalidateLayout(); + return true; +} +//----------------------------------------------------------------------------- +// Purpose: Updates a current item to the drop down +// Input : wchar_t *itemText - name of dropdown menu item +//----------------------------------------------------------------------------- +bool ComboBox::UpdateItem(int itemID, const wchar_t *itemText, const KeyValues *userData) +{ + if ( !m_pDropDown->IsValidMenuID(itemID)) + return false; + + // when the menu item is selected it will send the custom message "SetText" + KeyValues *kv = new KeyValues("SetText"); + kv->SetWString("text", itemText); + m_pDropDown->UpdateMenuItem(itemID, itemText, kv, userData); + InvalidateLayout(); + return true; +} + +//----------------------------------------------------------------------------- +// Purpose: Updates a current item to the drop down +// Input : wchar_t *itemText - name of dropdown menu item +//----------------------------------------------------------------------------- +bool ComboBox::IsItemIDValid( int itemID ) +{ + return m_pDropDown->IsValidMenuID(itemID); +} + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +void ComboBox::SetItemEnabled(const char *itemText, bool state) +{ + m_pDropDown->SetItemEnabled(itemText, state); +} + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +void ComboBox::SetItemEnabled(int itemID, bool state) +{ + m_pDropDown->SetItemEnabled(itemID, state); +} + +//----------------------------------------------------------------------------- +// Purpose: Remove all items from the drop down menu +//----------------------------------------------------------------------------- +void ComboBox::RemoveAll() +{ + m_pDropDown->DeleteAllItems(); +} + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +int ComboBox::GetItemCount() +{ + return m_pDropDown->GetItemCount(); +} + +int ComboBox::GetItemIDFromRow( int row ) +{ + // valid from [0, GetItemCount) + return m_pDropDown->GetMenuID( row ); +} + +//----------------------------------------------------------------------------- +// Purpose: Activate the item in the menu list, as if that menu item had been selected by the user +// Input : itemID - itemID from AddItem in list of dropdown items +//----------------------------------------------------------------------------- +void ComboBox::ActivateItem(int itemID) +{ + m_pDropDown->ActivateItem(itemID); +} + +//----------------------------------------------------------------------------- +// Purpose: Activate the item in the menu list, as if that menu item had been selected by the user +// Input : itemID - itemID from AddItem in list of dropdown items +//----------------------------------------------------------------------------- +void ComboBox::ActivateItemByRow(int row) +{ + m_pDropDown->ActivateItemByRow(row); +} + +//----------------------------------------------------------------------------- +// Purpose: Activate the item in the menu list, without sending a TextChanged message +// Input : row - row to activate +//----------------------------------------------------------------------------- +void ComboBox::SilentActivateItemByRow(int row) +{ + int itemID = GetItemIDFromRow( row ); + if ( itemID >= 0 ) + { + SilentActivateItem( itemID ); + } +} + +//----------------------------------------------------------------------------- +// Purpose: Activate the item in the menu list, without sending a TextChanged message +// Input : itemID - itemID from AddItem in list of dropdown items +//----------------------------------------------------------------------------- +void ComboBox::SilentActivateItem(int itemID) +{ + m_pDropDown->SilentActivateItem(itemID); + + // Now manually call our set text, with a wrapper to ensure we don't send the Text Changed message + wchar_t name[ 256 ]; + GetItemText( itemID, name, sizeof( name ) ); + + m_bPreventTextChangeMessage = true; + OnSetText( name ); + m_bPreventTextChangeMessage = false; +} + +//----------------------------------------------------------------------------- +// Purpose: Allows a custom menu to be used with the combo box +//----------------------------------------------------------------------------- +void ComboBox::SetMenu( Menu *menu ) +{ + if ( m_pDropDown ) + { + m_pDropDown->MarkForDeletion(); + } + + m_pDropDown = menu; + if ( m_pDropDown ) + { + m_pDropDown->SetParent( this ); + } +} + +//----------------------------------------------------------------------------- +// Purpose: Layout the format of the combo box for drawing on screen +//----------------------------------------------------------------------------- +void ComboBox::PerformLayout() +{ + int wide, tall; + GetPaintSize(wide, tall); + + BaseClass::PerformLayout(); + + HFont buttonFont = m_pButton->GetFont(); + int fontTall = surface()->GetFontTall( buttonFont ); + + int buttonSize = min( tall, fontTall ); + + int buttonY = ( ( tall - 1 ) - buttonSize ) / 2; + + // Some dropdown button icons in our games are wider than they are taller. We need to factor that in. + int button_wide, button_tall; + m_pButton->GetContentSize(button_wide, button_tall); + button_wide = max( buttonSize, button_wide ); + + m_pButton->SetBounds( wide - button_wide, buttonY, button_wide, buttonSize ); + if ( IsEditable() ) + { + SetCursor(dc_ibeam); + } + else + { + SetCursor(dc_arrow); + } + + m_pButton->SetEnabled(IsEnabled()); + + DoMenuLayout(); +} + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +void ComboBox::DoMenuLayout() +{ + m_pDropDown->PositionRelativeToPanel( this, m_iDirection, m_iOpenOffsetY ); + + // reset the width of the drop down menu to be the width of the combo box + m_pDropDown->SetFixedWidth(GetWide()); + m_pDropDown->ForceCalculateWidth(); + +} + +//----------------------------------------------------------------------------- +// Purpose: Sorts the items in the list +//----------------------------------------------------------------------------- +void ComboBox::SortItems( void ) +{ +} + +//----------------------------------------------------------------------------- +// Purpose: return the index of the last selected item +//----------------------------------------------------------------------------- +int ComboBox::GetActiveItem() +{ + return m_pDropDown->GetActiveItem(); +} + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +KeyValues *ComboBox::GetActiveItemUserData() +{ + return m_pDropDown->GetItemUserData(GetActiveItem()); +} + + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +KeyValues *ComboBox::GetItemUserData(int itemID) +{ + return m_pDropDown->GetItemUserData(itemID); +} + + +//----------------------------------------------------------------------------- +// Purpose: data accessor +//----------------------------------------------------------------------------- +void ComboBox::GetItemText( int itemID, wchar_t *text, int bufLenInBytes ) +{ + m_pDropDown->GetItemText( itemID, text, bufLenInBytes ); +} + +void ComboBox::GetItemText( int itemID, char *text, int bufLenInBytes ) +{ + m_pDropDown->GetItemText( itemID, text, bufLenInBytes ); +} + + +//----------------------------------------------------------------------------- +// Purpose: +// Output : Returns true on success, false on failure. +//----------------------------------------------------------------------------- +bool ComboBox::IsDropdownVisible() +{ + return m_pDropDown->IsVisible(); +} + +//----------------------------------------------------------------------------- +// Purpose: +// Input : *inResourceData - +//----------------------------------------------------------------------------- +void ComboBox::ApplySchemeSettings(IScheme *pScheme) +{ + BaseClass::ApplySchemeSettings(pScheme); + + SetBorder( pScheme->GetBorder( m_szBorderOverride[0] ? m_szBorderOverride : "ComboBoxBorder" ) ); +} + +void ComboBox::ApplySettings( KeyValues *pInResourceData ) +{ + BaseClass::ApplySettings( pInResourceData ); + + const char *pBorderOverride = pInResourceData->GetString( "border_override", NULL ); + if ( pBorderOverride ) + { + V_strncpy( m_szBorderOverride, pBorderOverride, sizeof( m_szBorderOverride ) ); + } + + KeyValues *pKVButton = pInResourceData->FindKey( "Button" ); + if ( pKVButton && m_pButton ) + { + m_pButton->ApplySettings( pKVButton ); + } +} + +//----------------------------------------------------------------------------- +// Purpose: Set the visiblity of the drop down menu button. +//----------------------------------------------------------------------------- +void ComboBox::SetDropdownButtonVisible(bool state) +{ + m_pButton->SetVisible(state); +} + +//----------------------------------------------------------------------------- +// Purpose: overloads TextEntry MousePressed +//----------------------------------------------------------------------------- +void ComboBox::OnMousePressed(MouseCode code) +{ + if ( !m_pDropDown ) + return; + + if ( !IsEnabled() ) + return; + + // make sure it's getting pressed over us (it may not be due to mouse capture) + if ( !IsCursorOver() ) + { + HideMenu(); + return; + } + + if ( IsEditable() ) + { + BaseClass::OnMousePressed(code); + HideMenu(); + } + else + { + // clicking on a non-editable text box just activates the drop down menu + RequestFocus(); + DoClick(); + } +} + +//----------------------------------------------------------------------------- +// Purpose: Double-click acts the same as a single-click +//----------------------------------------------------------------------------- +void ComboBox::OnMouseDoublePressed(MouseCode code) +{ + if (IsEditable()) + { + BaseClass::OnMouseDoublePressed(code); + } + else + { + OnMousePressed(code); + } +} + +//----------------------------------------------------------------------------- +// Purpose: Called when a command is received from the menu +// Changes the label text to be that of the command +// Input : char *command - +//----------------------------------------------------------------------------- +void ComboBox::OnCommand( const char *command ) +{ + if (!stricmp(command, "ButtonClicked")) + { + // hide / show the menu underneath + DoClick(); + } + + Panel::OnCommand(command); +} + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +void ComboBox::OnSetText(const wchar_t *newtext) +{ + // see if the combobox text has changed, and if so, post a message detailing the new text + const wchar_t *text = newtext; + + // check if the new text is a localized string, if so undo it + if (*text == '#') + { + char cbuf[255]; + g_pVGuiLocalize->ConvertUnicodeToANSI(text, cbuf, 255); + + // try lookup in localization tables + StringIndex_t unlocalizedTextSymbol = g_pVGuiLocalize->FindIndex(cbuf + 1); + + if (unlocalizedTextSymbol != INVALID_LOCALIZE_STRING_INDEX) + { + // we have a new text value + text = g_pVGuiLocalize->GetValueByIndex(unlocalizedTextSymbol); + } + } + + wchar_t wbuf[255]; + GetText(wbuf, 254); + + if ( wcscmp(wbuf, text) ) + { + // text has changed + SetText(text); + + // fire off that things have changed + if ( !m_bPreventTextChangeMessage ) + { + PostActionSignal(new KeyValues("TextChanged", "text", text)); + } + Repaint(); + } + + // close the box + HideMenu(); +} + +//----------------------------------------------------------------------------- +// Purpose: hides the menu +//----------------------------------------------------------------------------- +void ComboBox::HideMenu(void) +{ + if ( !m_pDropDown ) + return; + + // hide the menu + m_pDropDown->SetVisible(false); + Repaint(); + OnHideMenu(m_pDropDown); +} + +//----------------------------------------------------------------------------- +// Purpose: shows the menu +//----------------------------------------------------------------------------- +void ComboBox::ShowMenu(void) +{ + if ( !m_pDropDown ) + return; + + // hide the menu + m_pDropDown->SetVisible(false); + DoClick(); +} + +//----------------------------------------------------------------------------- +// Purpose: Called when the window loses focus; hides the menu +//----------------------------------------------------------------------------- +void ComboBox::OnKillFocus() +{ + SelectNoText(); +} + +//----------------------------------------------------------------------------- +// Purpose: Called when the menu is closed +//----------------------------------------------------------------------------- +void ComboBox::OnMenuClose() +{ + HideMenu(); + + if ( HasFocus() ) + { + SelectAllText(false); + } + else if ( m_bHighlight ) + { + m_bHighlight = false; + // we want the text to be highlighted when we request the focus +// SelectAllOnFirstFocus(true); + RequestFocus(); + } + // if cursor is in this box or the arrow box + else if ( IsCursorOver() )// make sure it's getting pressed over us (it may not be due to mouse capture) + { + SelectAllText(false); + OnCursorEntered(); + // Get focus so the box will unhighlight if we click somewhere else. + RequestFocus(); + } + else + { + m_pButton->SetArmed(false); + } +} + +//----------------------------------------------------------------------------- +// Purpose: Handles hotkey accesses +// FIXME: make this open different directions as necessary see menubutton. +//----------------------------------------------------------------------------- +void ComboBox::DoClick() +{ + // menu is already visible, hide the menu + if ( m_pDropDown->IsVisible() ) + { + HideMenu(); + return; + } + + // do nothing if menu is not enabled + if ( !m_pDropDown->IsEnabled() ) + { + return; + } + // force the menu to Think + m_pDropDown->PerformLayout(); + + // make sure we're at the top of the draw order (and therefore our children as well) + // RequestFocus(); + + // We want the item that is shown in the combo box to show as selected + int itemToSelect = -1; + int i; + wchar_t comboBoxContents[255]; + GetText(comboBoxContents, 255); + for ( i = 0 ; i < m_pDropDown->GetItemCount() ; i++ ) + { + wchar_t menuItemName[255]; + int menuID = m_pDropDown->GetMenuID(i); + m_pDropDown->GetMenuItem(menuID)->GetText(menuItemName, 255); + if (!wcscmp(menuItemName, comboBoxContents)) + { + itemToSelect = i; + break; + } + } + // if we found a match, highlight it on opening the menu + if ( itemToSelect >= 0 ) + { + m_pDropDown->SetCurrentlyHighlightedItem( m_pDropDown->GetMenuID(itemToSelect) ); + } + + // reset the dropdown's position + DoMenuLayout(); + + + // make sure we're at the top of the draw order (and therefore our children as well) + // this important to make sure the menu will be drawn in the foreground + MoveToFront(); + + // !KLUDGE! Force alpha to solid. Otherwise, + // we run into weird VGUI problems with pops + // and the stencil test + Color c = m_pDropDown->GetBgColor(); + c[3] = 255; + m_pDropDown->SetBgColor( c ); + + // notify + OnShowMenu(m_pDropDown); + + // show the menu + m_pDropDown->SetVisible(true); + + // bring to focus + m_pDropDown->RequestFocus(); + + // no text is highlighted when the menu is opened + SelectNoText(); + + // highlight the arrow while menu is open + m_pButton->SetArmed(true); + + Repaint(); +} + + +//----------------------------------------------------------------------------- +// Purpose: Brighten the arrow on the button when entering the box +//----------------------------------------------------------------------------- +void ComboBox::OnCursorEntered() +{ + // want the arrow to go white when we enter the box + m_pButton->OnCursorEntered(); + TextEntry::OnCursorEntered(); +} + +//----------------------------------------------------------------------------- +// Purpose: Dim the arrow on the button when exiting the box +//----------------------------------------------------------------------------- +void ComboBox::OnCursorExited() +{ + // want the arrow to go grey when we exit the box if the menu is not open + if ( !m_pDropDown->IsVisible() ) + { + m_pButton->SetArmed(false); + TextEntry::OnCursorExited(); + } +} + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +#ifdef _X360 +void ComboBox::OnMenuItemSelected() +{ + m_bHighlight = true; + // For editable cbs, fill in the text field from whatever is chosen from the dropdown... + + //============================================================================= + // HPE_BEGIN: + // [pfreese] The text for the combo box should be updated regardless of its + // editable state, and in any case, the member variable below was never + // correctly initialized. + //============================================================================= + + // if ( m_bAllowEdit ) + + //============================================================================= + // HPE_END + //============================================================================= + { + int idx = GetActiveItem(); + if ( idx >= 0 ) + { + wchar_t name[ 256 ]; + GetItemText( idx, name, sizeof( name ) ); + + OnSetText( name ); + } + } + + Repaint(); + + // go to the next control + if(!NavigateDown()) + { + NavigateUp(); + } +} +#else +void ComboBox::OnMenuItemSelected() +{ + m_bHighlight = true; + // For editable cbs, fill in the text field from whatever is chosen from the dropdown... + //if ( m_bAllowEdit ) + { + int idx = GetActiveItem(); + if ( idx >= 0 ) + { + wchar_t name[ 256 ]; + GetItemText( idx, name, sizeof( name ) ); + + OnSetText( name ); + } + } + + Repaint(); +} +#endif + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +void ComboBox::OnSizeChanged(int wide, int tall) +{ + BaseClass::OnSizeChanged( wide, tall); + + // set the drawwidth. + int bwide, btall; + PerformLayout(); + m_pButton->GetSize( bwide, btall); + SetDrawWidth( wide - bwide ); +} + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +#ifdef _X360 +void ComboBox::OnSetFocus() +{ + BaseClass::OnSetFocus(); + + GotoTextEnd(); + SelectAllText(true); +} +#else +void ComboBox::OnSetFocus() +{ + BaseClass::OnSetFocus(); + + GotoTextEnd(); + SelectAllText(false); +} +#endif + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +#ifdef _X360 +void ComboBox::OnKeyCodePressed(KeyCode code) +{ + switch ( GetBaseButtonCode( code ) ) + { + case KEY_XBUTTON_A: + DoClick(); + break; + case KEY_XBUTTON_UP: + case KEY_XSTICK1_UP: + case KEY_XSTICK2_UP: + if(m_pDropDown->IsVisible()) + { + MoveAlongMenuItemList(-1); + } + else + { + BaseClass::OnKeyCodePressed(code); + } + break; + case KEY_XBUTTON_DOWN: + case KEY_XSTICK1_DOWN: + case KEY_XSTICK2_DOWN: + if(m_pDropDown->IsVisible()) + { + MoveAlongMenuItemList(1); + } + else + { + BaseClass::OnKeyCodePressed(code); + } + break; + default: + BaseClass::OnKeyCodePressed(code); + break; + } +} +#endif + +//----------------------------------------------------------------------------- +// Purpose: Handles up/down arrows +//----------------------------------------------------------------------------- +void ComboBox::OnKeyCodeTyped(KeyCode code) +{ + bool alt = (input()->IsKeyDown(KEY_LALT) || input()->IsKeyDown(KEY_RALT)); + + if (alt) + { + switch (code) + { + case KEY_UP: + case KEY_DOWN: + { + DoClick(); + break; + } + default: + { + BaseClass::OnKeyCodeTyped(code); + break; + } + } + } + else + { + switch (code) + { + case KEY_HOME: + case KEY_END: + case KEY_PAGEUP: + case KEY_PAGEDOWN: + case KEY_UP: + case KEY_DOWN: + { + int itemSelected = m_pDropDown->GetCurrentlyHighlightedItem(); + m_pDropDown->OnKeyCodeTyped(code); + int itemToSelect = m_pDropDown->GetCurrentlyHighlightedItem(); + + if ( itemToSelect != itemSelected ) + { + SelectMenuItem(itemToSelect); + } + break; + } + + case KEY_ENTER: + { + int itemToSelect = m_pDropDown->GetCurrentlyHighlightedItem(); + m_pDropDown->ActivateItem(itemToSelect); + break; + } + + default: + { + BaseClass::OnKeyCodeTyped(code); + break; + } + } + } +} + +//----------------------------------------------------------------------------- +// Purpose: handles key input +//----------------------------------------------------------------------------- +void ComboBox::OnKeyTyped(wchar_t unichar) +{ + if ( IsEditable() || unichar == '\t') // don't play with key presses in edit mode + { + BaseClass::OnKeyTyped( unichar ); + return; + } + + int itemSelected = m_pDropDown->GetCurrentlyHighlightedItem(); + m_pDropDown->OnKeyTyped(unichar); + int itemToSelect = m_pDropDown->GetCurrentlyHighlightedItem(); + + if ( itemToSelect != itemSelected ) + { + SelectMenuItem(itemToSelect); + } + else + { + BaseClass::OnKeyTyped( unichar ); + } +} + +void ComboBox::SelectMenuItem(int itemToSelect) +{ + // if we found this item, then we scroll up or down + if ( itemToSelect >= 0 && itemToSelect < m_pDropDown->GetItemCount() ) + { + wchar_t menuItemName[255]; + + int menuID = m_pDropDown->GetMenuID(itemToSelect); + m_pDropDown->GetMenuItem(menuID)->GetText(menuItemName, 254); + OnSetText(menuItemName); + SelectAllText(false); + } +} + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +void ComboBox::MoveAlongMenuItemList(int direction) +{ + // We want the item that is shown in the combo box to show as selected + int itemToSelect = -1; + wchar_t menuItemName[255]; + int i; + + wchar_t comboBoxContents[255]; + GetText(comboBoxContents, 254); + for ( i = 0 ; i < m_pDropDown->GetItemCount() ; i++ ) + { + int menuID = m_pDropDown->GetMenuID(i); + m_pDropDown->GetMenuItem(menuID)->GetText(menuItemName, 254); + + if ( !wcscmp(menuItemName, comboBoxContents) ) + { + itemToSelect = i; + break; + } + } + + if ( itemToSelect >= 0 ) + { + int newItem = itemToSelect + direction; + if ( newItem < 0 ) + { + newItem = 0; + } + else if ( newItem >= m_pDropDown->GetItemCount() ) + { + newItem = m_pDropDown->GetItemCount() - 1; + } + SelectMenuItem(newItem); + } + +} + +void ComboBox::MoveToFirstMenuItem() +{ + SelectMenuItem(0); +} + +void ComboBox::MoveToLastMenuItem() +{ + SelectMenuItem(m_pDropDown->GetItemCount() - 1); +} + + +//----------------------------------------------------------------------------- +// Purpose: Sets the direction from the menu button the menu should open +//----------------------------------------------------------------------------- +void ComboBox::SetOpenDirection(Menu::MenuDirection_e direction) +{ + m_iDirection = direction; +} + +void ComboBox::SetFont( HFont font ) +{ + BaseClass::SetFont( font ); + + m_pDropDown->SetFont( font ); +} + + +void ComboBox::SetUseFallbackFont( bool bState, HFont hFallback ) +{ + BaseClass::SetUseFallbackFont( bState, hFallback ); + m_pDropDown->SetUseFallbackFont( bState, hFallback ); +} |