aboutsummaryrefslogtreecommitdiff
path: root/mp/src/vgui2/vgui_controls/Label.cpp
diff options
context:
space:
mode:
authorJørgen P. Tjernø <[email protected]>2013-12-02 19:31:46 -0800
committerJørgen P. Tjernø <[email protected]>2013-12-02 19:46:31 -0800
commitf56bb35301836e56582a575a75864392a0177875 (patch)
treede61ddd39de3e7df52759711950b4c288592f0dc /mp/src/vgui2/vgui_controls/Label.cpp
parentMark some more files as text. (diff)
downloadsource-sdk-2013-f56bb35301836e56582a575a75864392a0177875.tar.xz
source-sdk-2013-f56bb35301836e56582a575a75864392a0177875.zip
Fix line endings. WHAMMY.
Diffstat (limited to 'mp/src/vgui2/vgui_controls/Label.cpp')
-rw-r--r--mp/src/vgui2/vgui_controls/Label.cpp2772
1 files changed, 1386 insertions, 1386 deletions
diff --git a/mp/src/vgui2/vgui_controls/Label.cpp b/mp/src/vgui2/vgui_controls/Label.cpp
index 26199308..776c8c6e 100644
--- a/mp/src/vgui2/vgui_controls/Label.cpp
+++ b/mp/src/vgui2/vgui_controls/Label.cpp
@@ -1,1386 +1,1386 @@
-//========= Copyright Valve Corporation, All rights reserved. ============//
-//
-// Purpose:
-//
-// $NoKeywords: $
-//=============================================================================//
-
-#include <assert.h>
-#include <stdarg.h>
-#include <stdio.h>
-#include <ctype.h>
-
-#include <vgui/IInput.h>
-#include <vgui/ILocalize.h>
-#include <vgui/IPanel.h>
-#include <vgui/ISurface.h>
-#include <vgui/IScheme.h>
-#include <KeyValues.h>
-
-#include <vgui_controls/Label.h>
-#include <vgui_controls/Image.h>
-#include <vgui_controls/TextImage.h>
-#include <vgui_controls/Controls.h>
-
-// memdbgon must be the last include file in a .cpp file!!!
-#include <tier0/memdbgon.h>
-
-using namespace vgui;
-
-#ifndef max
-#define max(a,b) (((a) > (b)) ? (a) : (b))
-#endif
-
-DECLARE_BUILD_FACTORY_DEFAULT_TEXT( Label, Label );
-
-//-----------------------------------------------------------------------------
-// Purpose: Constructor
-//-----------------------------------------------------------------------------
-Label::Label(Panel *parent, const char *panelName, const char *text) : BaseClass(parent, panelName)
-{
- Init();
-
- _textImage = new TextImage(text);
- _textImage->SetColor(Color(0, 0, 0, 0));
- SetText(text);
- _textImageIndex = AddImage(_textImage, 0);
-
- REGISTER_COLOR_AS_OVERRIDABLE( _disabledFgColor2, "disabledfgcolor2_override" );
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Constructor
-//-----------------------------------------------------------------------------
-Label::Label(Panel *parent, const char *panelName, const wchar_t *wszText) : BaseClass(parent, panelName)
-{
- Init();
-
- _textImage = new TextImage(wszText);
- _textImage->SetColor(Color(0, 0, 0, 0));
- SetText(wszText);
- _textImageIndex = AddImage(_textImage, 0);
-
- REGISTER_COLOR_AS_OVERRIDABLE( _disabledFgColor2, "disabledfgcolor2_override" );
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Destructor
-//-----------------------------------------------------------------------------
-Label::~Label()
-{
- delete _textImage;
- delete [] _associateName;
- delete [] _fontOverrideName;
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Construct the label
-//-----------------------------------------------------------------------------
-void Label::Init()
-{
- _contentAlignment = a_west;
- _textColorState = CS_NORMAL;
- _textInset[0] = 0;
- _textInset[1] = 0;
- _hotkey = 0;
- _associate = NULL;
- _associateName = NULL;
- _fontOverrideName = NULL;
- m_bWrap = false;
- m_bCenterWrap = false;
- m_bAutoWideToContents = false;
- m_bUseProportionalInsets = false;
- m_bAutoWideDirty = false;
-
-// SetPaintBackgroundEnabled(false);
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Set whether the text is displayed bright or dull
-//-----------------------------------------------------------------------------
-void Label::SetTextColorState(EColorState state)
-{
- if (_textColorState != state)
- {
- _textColorState = state;
- InvalidateLayout();
- }
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Return the full size of the contained content
-//-----------------------------------------------------------------------------
-void Label::GetContentSize(int &wide, int &tall)
-{
- if( GetFont() == INVALID_FONT ) // we haven't loaded our font yet, so load it now
- {
- IScheme *pScheme = scheme()->GetIScheme( GetScheme() );
- if ( pScheme )
- {
- SetFont( pScheme->GetFont( "Default", IsProportional() ) );
- }
- }
-
-
- int tx0, ty0, tx1, ty1;
- ComputeAlignment(tx0, ty0, tx1, ty1);
-
- // the +8 is padding to the content size
- // the code which uses it should really set that itself;
- // however a lot of existing code relies on this
- wide = (tx1 - tx0) + _textInset[0];
-
- // get the size of the text image and remove it
- int iWide, iTall;
- _textImage->GetSize(iWide, iTall);
- wide -= iWide;
- // get the full, untruncated (no elipsis) size of the text image.
- _textImage->GetContentSize(iWide, iTall);
- wide += iWide;
-
- // addin the image offsets as well
- for (int i=0; i < _imageDar.Size(); i++)
- wide += _imageDar[i].offset;
-
- tall = max((ty1 - ty0) + _textInset[1], iTall);
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Calculate the keyboard key that is a hotkey
-//-----------------------------------------------------------------------------
-wchar_t Label::CalculateHotkey(const char *text)
-{
- for (const char *ch = text; *ch != 0; ch++)
- {
- if (*ch == '&')
- {
- // get the next character
- ch++;
-
- if (*ch == '&')
- {
- // just an &
- continue;
- }
- else if (*ch == 0)
- {
- break;
- }
- else if (V_isalnum(*ch))
- {
- // found the hotkey
- return (wchar_t)tolower(*ch);
- }
- }
- }
-
- return '\0';
-}
-
-wchar_t Label::CalculateHotkey(const wchar_t *text)
-{
- if( text )
- {
- for (const wchar_t *ch = text; *ch != 0; ch++)
- {
- if (*ch == '&')
- {
- // get the next character
- ch++;
-
- if (*ch == '&')
- {
- // just an &
- continue;
- }
- else if (*ch == 0)
- {
- break;
- }
- else if (iswalnum(*ch))
- {
- // found the hotkey
- return (wchar_t)towlower(*ch);
- }
- }
- }
- }
-
- return '\0';
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Check if this label has a hotkey that is the key passed in.
-//-----------------------------------------------------------------------------
-Panel *Label::HasHotkey(wchar_t key)
-{
-#ifdef VGUI_HOTKEYS_ENABLED
- if ( iswalnum( key ) )
- key = towlower( key );
-
- if (_hotkey == key)
- return this;
-#endif
-
- return NULL;
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Set the hotkey for this label
-//-----------------------------------------------------------------------------
-void Label::SetHotkey(wchar_t ch)
-{
- _hotkey = ch;
-}
-
-wchar_t Label::GetHotKey()
-{
- return _hotkey;
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Handle a hotkey by passing on focus to associate
-//-----------------------------------------------------------------------------
-void Label::OnHotkeyPressed()
-{
- // we can't accept focus, but if we are associated to a control give it to that
- if (_associate.Get() && !IsBuildModeActive())
- {
- _associate->RequestFocus();
- }
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Redirect mouse pressed to giving focus to associate
-//-----------------------------------------------------------------------------
-void Label::OnMousePressed(MouseCode code)
-{
- if (_associate.Get() && !IsBuildModeActive())
- {
- _associate->RequestFocus();
- }
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Return the text in the label
-//-----------------------------------------------------------------------------
-void Label::GetText(char *textOut, int bufferLen)
-{
- _textImage->GetText(textOut, bufferLen);
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Return the text in the label
-//-----------------------------------------------------------------------------
-void Label::GetText(wchar_t *textOut, int bufLenInBytes)
-{
- _textImage->GetText(textOut, bufLenInBytes);
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Take the string and looks it up in the localization file
-// to convert it to unicode
-// Setting the text will not set the size of the label.
-// Set the size explicitly or use setToContent()
-//-----------------------------------------------------------------------------
-void Label::SetText(const char *text)
-{
- // if set to null, just make blank
- if (!text)
- {
- text = "";
- }
-
- // let the text image do the translation itself
- _textImage->SetText(text);
-
- if( text[0] == '#' )
- {
- SetHotkey(CalculateHotkey(g_pVGuiLocalize->Find(text)));
- }
- else
- {
- SetHotkey(CalculateHotkey(text));
- }
-
- m_bAutoWideDirty = m_bAutoWideToContents;
-
- InvalidateLayout();
- Repaint();
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Set unicode text directly
-//-----------------------------------------------------------------------------
-void Label::SetText(const wchar_t *unicodeString, bool bClearUnlocalizedSymbol)
-{
- m_bAutoWideDirty = m_bAutoWideToContents;
-
- if ( unicodeString && _textImage->GetUText() && !Q_wcscmp(unicodeString,_textImage->GetUText()) )
- return;
-
- _textImage->SetText(unicodeString, bClearUnlocalizedSymbol);
-
-//!! need to calculate hotkey from translated string
- SetHotkey(CalculateHotkey(unicodeString));
-
- InvalidateLayout(); // possible that the textimage needs to expand
- Repaint();
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: updates localized text
-//-----------------------------------------------------------------------------
-void Label::OnDialogVariablesChanged(KeyValues *dialogVariables )
-{
- StringIndex_t index = _textImage->GetUnlocalizedTextSymbol();
- if (index != INVALID_LOCALIZE_STRING_INDEX)
- {
- // reconstruct the string from the variables
- wchar_t buf[1024];
- g_pVGuiLocalize->ConstructString(buf, sizeof(buf), index, dialogVariables);
- SetText(buf);
- }
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Additional offset at the Start of the text (from whichever side it is aligned)
-//-----------------------------------------------------------------------------
-void Label::SetTextInset(int xInset, int yInset)
-{
- _textInset[0] = xInset;
- _textInset[1] = yInset;
-
- int wide, tall;
- GetSize( wide, tall);
- _textImage->SetDrawWidth(wide - _textInset[0]);
-}
-
-//-----------------------------------------------------------------------------
-// Purpose:
-//-----------------------------------------------------------------------------
-void Label::GetTextInset(int *xInset, int *yInset )
-{
- *xInset = _textInset[0];
- *yInset = _textInset[1];
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Set the enabled state
-//-----------------------------------------------------------------------------
-void Label::SetEnabled(bool state)
-{
- Panel::SetEnabled(state);
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Calculates where in the panel the content resides
-// Input : &tx0 - [out] position of the content
-// &ty0 -
-// &tx1 -
-// &ty1 -
-// Note: horizontal alignment is west if the image dar has
-// more than one image in it, this is because we use image sizes
-// to determine layout in classes for example, Menu.
-//-----------------------------------------------------------------------------
-void Label::ComputeAlignment(int &tx0, int &ty0, int &tx1, int &ty1)
-{
- int wide, tall;
- GetPaintSize(wide, tall);
- int tWide,tTall;
-
- // text bounding box
- tx0 = 0;
- ty0 = 0;
-
- // loop through all the images and calculate the complete bounds
- int maxX = 0, maxY = 0;
-
- int actualXAlignment = _contentAlignment;
- for (int i = 0; i < _imageDar.Count(); i++)
- {
- TImageInfo &imageInfo = _imageDar[i];
- IImage *image = imageInfo.image;
- if (!image)
- continue; // skip over null images
-
- // add up the bounds
- int iWide, iTall;
- image->GetSize(iWide, iTall);
- if (iWide > wide) // if the image is larger than the label just do a west alignment
- actualXAlignment = Label::a_west;
-
- // get the max height
- maxY = max(maxY, iTall);
- maxX += iWide;
-
- // add the offset to x
- maxX += imageInfo.offset;
- }
-
- tWide = maxX;
- tTall = maxY;
-
- // x align text
- switch (actualXAlignment)
- {
- // left
- case Label::a_northwest:
- case Label::a_west:
- case Label::a_southwest:
- {
- tx0 = 0;
- break;
- }
- // center
- case Label::a_north:
- case Label::a_center:
- case Label::a_south:
- {
- tx0 = (wide - tWide) / 2;
- break;
- }
- // right
- case Label::a_northeast:
- case Label::a_east:
- case Label::a_southeast:
- {
- tx0 = wide - tWide;
- break;
- }
- }
-
- // y align text
- switch (_contentAlignment)
- {
- //top
- case Label::a_northwest:
- case Label::a_north:
- case Label::a_northeast:
- {
- ty0 = 0;
- break;
- }
- // center
- case Label::a_west:
- case Label::a_center:
- case Label::a_east:
- {
- ty0 = (tall - tTall) / 2;
- break;
- }
- // south
- case Label::a_southwest:
- case Label::a_south:
- case Label::a_southeast:
- {
- ty0 = tall - tTall;
- break;
- }
- }
-
- tx1 = tx0 + tWide;
- ty1 = ty0 + tTall;
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: overridden main drawing function for the panel
-//-----------------------------------------------------------------------------
-void Label::Paint()
-{
- int tx0, ty0, tx1, ty1;
- ComputeAlignment(tx0, ty0, tx1, ty1);
-
- // calculate who our associate is if we haven't already
- if (_associateName)
- {
- SetAssociatedControl(FindSiblingByName(_associateName));
- delete [] _associateName;
- _associateName = NULL;
- }
-
- int labelWide, labelTall;
- GetSize(labelWide, labelTall);
- int x = tx0, y = _textInset[1] + ty0;
- int imageYPos = 0; // a place to save the y offset for when we draw the disable version of the image
-
- // draw the set of images
- for (int i = 0; i < _imageDar.Count(); i++)
- {
- TImageInfo &imageInfo = _imageDar[i];
- IImage *image = imageInfo.image;
- if (!image)
- continue; // skip over null images
-
- // add the offset to x
- x += imageInfo.offset;
-
- // if this is the text image then add its inset to the left or from the right
- if (i == _textImageIndex)
- {
- switch ( _contentAlignment )
- {
- // left
- case Label::a_northwest:
- case Label::a_west:
- case Label::a_southwest:
- {
- x += _textInset[0];
- break;
- }
- // right
- case Label::a_northeast:
- case Label::a_east:
- case Label::a_southeast:
- {
- x -= _textInset[0];
- break;
- }
- }
- }
-
- // see if the image is in a fixed position
- if (imageInfo.xpos >= 0)
- {
- x = imageInfo.xpos;
- }
-
- // draw
- imageYPos = y;
- image->SetPos(x, y);
-
- // fix up y for center-aligned text
- if (_contentAlignment == Label::a_west || _contentAlignment == Label::a_center || _contentAlignment == Label::a_east)
- {
- int iw, it;
- image->GetSize(iw, it);
- if (it < (ty1 - ty0))
- {
- imageYPos = ((ty1 - ty0) - it) / 2 + y;
- image->SetPos(x, ((ty1 - ty0) - it) / 2 + y);
- }
- }
-
- // don't resize the image unless its too big
- if (imageInfo.width >= 0)
- {
- int w, t;
- image->GetSize(w, t);
- if (w > imageInfo.width)
- {
- image->SetSize(imageInfo.width, t);
- }
- }
-
- // if it's the basic text image then draw specially
- if (image == _textImage)
- {
- if (IsEnabled())
- {
- if (_associate.Get() && ipanel()->HasParent(input()->GetFocus(), _associate->GetVPanel()))
- {
- _textImage->SetColor(_associateColor);
- }
- else
- {
- _textImage->SetColor(GetFgColor());
- }
-
- _textImage->Paint();
- }
- else
- {
- // draw disabled version, with embossed look
- // offset image
- _textImage->SetPos(x + 1, imageYPos + 1);
- _textImage->SetColor(_disabledFgColor1);
- _textImage->Paint();
-
- surface()->DrawFlushText();
-
- // overlayed image
- _textImage->SetPos(x, imageYPos);
- _textImage->SetColor(_disabledFgColor2);
- _textImage->Paint();
- }
- }
- else
- {
- image->Paint();
- }
-
- // add the image size to x
- int wide, tall;
- image->GetSize(wide, tall);
- x += wide;
- }
-}
-
-
-//-----------------------------------------------------------------------------
-// Purpose: Helper function, draws a simple line with dashing parameters
-//-----------------------------------------------------------------------------
-void Label::DrawDashedLine(int x0, int y0, int x1, int y1, int dashLen, int gapLen)
-{
- // work out which way the line goes
- if ((x1 - x0) > (y1 - y0))
- {
- // x direction line
- while (1)
- {
- if (x0 + dashLen > x1)
- {
- // draw partial
- surface()->DrawFilledRect(x0, y0, x1, y1);
- }
- else
- {
- surface()->DrawFilledRect(x0, y0, x0 + dashLen, y1);
- }
-
- x0 += dashLen;
-
- if (x0 + gapLen > x1)
- break;
-
- x0 += gapLen;
- }
- }
- else
- {
- // y direction
- while (1)
- {
- if (y0 + dashLen > y1)
- {
- // draw partial
- surface()->DrawFilledRect(x0, y0, x1, y1);
- }
- else
- {
- surface()->DrawFilledRect(x0, y0, x1, y0 + dashLen);
- }
-
- y0 += dashLen;
-
- if (y0 + gapLen > y1)
- break;
-
- y0 += gapLen;
- }
- }
-}
-
-void Label::SetContentAlignment(Alignment alignment)
-{
- _contentAlignment=alignment;
- Repaint();
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Size the width of the label to its contents - only works from in ApplySchemeSettings or PerformLayout()
-//-----------------------------------------------------------------------------
-void Label::SizeToContents()
-{
- int wide, tall;
- GetContentSize(wide, tall);
-
- SetSize(wide, tall);
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Set the font the text is drawn in
-//-----------------------------------------------------------------------------
-void Label::SetFont(HFont font)
-{
- _textImage->SetFont(font);
- Repaint();
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Resond to resizing of the panel
-//-----------------------------------------------------------------------------
-void Label::OnSizeChanged(int wide, int tall)
-{
- InvalidateLayout();
- Panel::OnSizeChanged(wide, tall);
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Get the font the textImage is drawn in.
-//-----------------------------------------------------------------------------
-HFont Label::GetFont()
-{
- return _textImage->GetFont();
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Set the foreground color of the Label
-//-----------------------------------------------------------------------------
-void Label::SetFgColor(Color color)
-{
- if (!(GetFgColor() == color))
- {
- BaseClass::SetFgColor(color);
- _textImage->SetColor(color);
- Repaint();
- }
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Get the foreground color of the Label
-//-----------------------------------------------------------------------------
-Color Label::GetFgColor()
-{
- Color clr = Panel::GetFgColor();
- return clr;
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Set the foreground color 1 color of the Label
-//-----------------------------------------------------------------------------
-void Label::SetDisabledFgColor1(Color color)
-{
- _disabledFgColor1 = color;
-}
-
-//-----------------------------------------------------------------------------
-// Purpose:
-//-----------------------------------------------------------------------------
-void Label::SetDisabledFgColor2(Color color)
-{
- _disabledFgColor2 = color;
-}
-
-//-----------------------------------------------------------------------------
-// Purpose:
-//-----------------------------------------------------------------------------
-Color Label::GetDisabledFgColor1()
-{
- return _disabledFgColor1;
-}
-
-//-----------------------------------------------------------------------------
-// Purpose:
-//-----------------------------------------------------------------------------
-Color Label::GetDisabledFgColor2()
-{
- return _disabledFgColor2;
-}
-
-//-----------------------------------------------------------------------------
-// Purpose:
-//-----------------------------------------------------------------------------
-TextImage *Label::GetTextImage()
-{
- return _textImage;
-}
-
-
-//-----------------------------------------------------------------------------
-// Purpose:
-//-----------------------------------------------------------------------------
-bool Label::RequestInfo(KeyValues *outputData)
-{
- if (!stricmp(outputData->GetName(), "GetText"))
- {
- wchar_t wbuf[256];
- _textImage->GetText(wbuf, 255);
- outputData->SetWString("text", wbuf);
- return true;
- }
-
- return Panel::RequestInfo(outputData);
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Sets the text from the message
-//-----------------------------------------------------------------------------
-void Label::OnSetText(KeyValues *params)
-{
- KeyValues *pkvText = params->FindKey("text", false);
- if (!pkvText)
- return;
-
- if (pkvText->GetDataType() == KeyValues::TYPE_STRING)
- {
- SetText(pkvText->GetString());
- }
- else if (pkvText->GetDataType() == KeyValues::TYPE_WSTRING)
- {
- SetText(pkvText->GetWString());
- }
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Add an image to the list
-// returns the index the image was placed in
-//-----------------------------------------------------------------------------
-int Label::AddImage(IImage *image, int offset)
-{
- int newImage = _imageDar.AddToTail();
- _imageDar[newImage].image = image;
- _imageDar[newImage].offset = (short)offset;
- _imageDar[newImage].xpos = -1;
- _imageDar[newImage].width = -1;
- InvalidateLayout();
- return newImage;
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: removes all images from the list
-// user is responsible for the memory
-//-----------------------------------------------------------------------------
-void Label::ClearImages()
-{
- _imageDar.RemoveAll();
- _textImageIndex = -1;
-}
-
-void Label::ResetToSimpleTextImage()
-{
- ClearImages();
- _textImageIndex = AddImage(_textImage, 0);
-}
-
-
-//-----------------------------------------------------------------------------
-// Purpose: Multiple image handling
-// Images are drawn from left to right across the label, ordered by index
-// By default there is a TextImage in position 0
-// Set the contents of an IImage in the IImage array.
-//-----------------------------------------------------------------------------
-void Label::SetImageAtIndex(int index, IImage *image, int offset)
-{
- EnsureImageCapacity(index);
-// Assert( image );
-
- if ( _imageDar[index].image != image || _imageDar[index].offset != offset)
- {
- _imageDar[index].image = image;
- _imageDar[index].offset = (short)offset;
- InvalidateLayout();
- }
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Get an IImage in the IImage array.
-//-----------------------------------------------------------------------------
-IImage *Label::GetImageAtIndex(int index)
-{
- if ( _imageDar.IsValidIndex( index ) )
- return _imageDar[index].image;
- return NULL;
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Get the number of images in the array.
-//-----------------------------------------------------------------------------
-int Label::GetImageCount()
-{
- return _imageDar.Count();
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Move where the default text image is within the image array
-// (it starts in position 0)
-// Input : newIndex -
-// Output : int - the index the default text image was previously in
-//-----------------------------------------------------------------------------
-int Label::SetTextImageIndex(int newIndex)
-{
- if (newIndex == _textImageIndex)
- return _textImageIndex;
-
- EnsureImageCapacity(newIndex);
-
- int oldIndex = _textImageIndex;
- if ( _textImageIndex >= 0 )
- {
- _imageDar[_textImageIndex].image = NULL;
- }
- if (newIndex > -1)
- {
- _imageDar[newIndex].image = _textImage;
- }
- _textImageIndex = newIndex;
- return oldIndex;
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Ensure that the maxIndex will be a valid index
-//-----------------------------------------------------------------------------
-void Label::EnsureImageCapacity(int maxIndex)
-{
- while (_imageDar.Size() <= maxIndex)
- {
- AddImage(NULL, 0);
- }
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Set the offset in pixels before the image
-//-----------------------------------------------------------------------------
-void Label::SetImagePreOffset(int index, int preOffset)
-{
- if (_imageDar.IsValidIndex(index) && _imageDar[index].offset != preOffset)
- {
- _imageDar[index].offset = (short)preOffset;
- InvalidateLayout();
- }
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: fixes the layout bounds of the image within the label
-//-----------------------------------------------------------------------------
-void Label::SetImageBounds(int index, int x, int width)
-{
- _imageDar[index].xpos = (short)x;
- _imageDar[index].width = (short)width;
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Labels can be associated with controls, and alter behaviour based on the associates behaviour
-// If the associate is disabled, so are we
-// If the associate has focus, we may alter how we draw
-// If we get a hotkey press or focus message, we forward the focus to the associate
-//-----------------------------------------------------------------------------
-void Label::SetAssociatedControl(Panel *control)
-{
- if (control != this)
- {
- _associate = control;
- }
- else
- {
- // don't let the associate ever be set to be ourself
- _associate = NULL;
- }
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Called after a panel requests focus to fix up the whole chain
-//-----------------------------------------------------------------------------
-void Label::OnRequestFocus(VPANEL subFocus, VPANEL defaultPanel)
-{
- if (_associate.Get() && subFocus == GetVPanel() && !IsBuildModeActive())
- {
- // we've received focus; pass the focus onto the associate instead
- _associate->RequestFocus();
- }
- else
- {
- BaseClass::OnRequestFocus(subFocus, defaultPanel);
- }
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: sets custom settings from the scheme file
-//-----------------------------------------------------------------------------
-void Label::ApplySchemeSettings(IScheme *pScheme)
-{
- BaseClass::ApplySchemeSettings(pScheme);
-
- if (_fontOverrideName)
- {
- // use the custom specified font since we have one set
- SetFont(pScheme->GetFont(_fontOverrideName, IsProportional()));
- }
- if ( GetFont() == INVALID_FONT )
- {
- SetFont( pScheme->GetFont( "Default", IsProportional() ) );
- }
-
- if ( m_bWrap || m_bCenterWrap )
- {
- //tell it how big it is
- int wide, tall;
- Panel::GetSize(wide, tall);
- wide -= _textInset[0]; // take inset into account
- _textImage->SetSize(wide, tall);
-
- _textImage->RecalculateNewLinePositions();
- }
- else
- {
- // if you don't set the size of the image, many, many buttons will break - we might want to look into fixing this all over the place later
- int wide, tall;
- _textImage->GetContentSize(wide, tall);
- _textImage->SetSize(wide, tall);
- }
-
- if ( m_bAutoWideToContents )
- {
- m_bAutoWideDirty = true;
- HandleAutoSizing();
- }
-
- // clear out any the images, since they will have been invalidated
- for (int i = 0; i < _imageDar.Count(); i++)
- {
- IImage *image = _imageDar[i].image;
- if (!image)
- continue; // skip over null images
-
- if (i == _textImageIndex)
- continue;
-
- _imageDar[i].image = NULL;
- }
-
- SetDisabledFgColor1(GetSchemeColor("Label.DisabledFgColor1", pScheme));
- SetDisabledFgColor2(GetSchemeColor("Label.DisabledFgColor2", pScheme));
- SetBgColor(GetSchemeColor("Label.BgColor", pScheme));
-
- switch (_textColorState)
- {
- case CS_DULL:
- SetFgColor(GetSchemeColor("Label.TextDullColor", pScheme));
- break;
- case CS_BRIGHT:
- SetFgColor(GetSchemeColor("Label.TextBrightColor", pScheme));
- break;
- case CS_NORMAL:
- default:
- SetFgColor(GetSchemeColor("Label.TextColor", pScheme));
- break;
- }
-
- _associateColor = GetSchemeColor("Label.SelectedTextColor", pScheme);
-}
-
-//-----------------------------------------------------------------------------
-// Purpose:
-//-----------------------------------------------------------------------------
-void Label::GetSettings( KeyValues *outResourceData )
-{
- // panel settings
- Panel::GetSettings( outResourceData );
-
- // label settings
- char buf[256];
- _textImage->GetUnlocalizedText( buf, 255 );
- if (!strnicmp(buf, "#var_", 5))
- {
- // strip off the variable prepender on save
- outResourceData->SetString( "labelText", buf + 5 );
- }
- else
- {
- outResourceData->SetString( "labelText", buf );
- }
-
- const char *alignmentString = "";
- switch ( _contentAlignment )
- {
- case a_northwest: alignmentString = "north-west"; break;
- case a_north: alignmentString = "north"; break;
- case a_northeast: alignmentString = "north-east"; break;
- case a_center: alignmentString = "center"; break;
- case a_east: alignmentString = "east"; break;
- case a_southwest: alignmentString = "south-west"; break;
- case a_south: alignmentString = "south"; break;
- case a_southeast: alignmentString = "south-east"; break;
- case a_west:
- default: alignmentString = "west"; break;
- }
-
- outResourceData->SetString( "textAlignment", alignmentString );
-
- if (_associate)
- {
- outResourceData->SetString("associate", _associate->GetName());
- }
-
- outResourceData->SetInt("dulltext", (int)(_textColorState == CS_DULL));
- outResourceData->SetInt("brighttext", (int)(_textColorState == CS_BRIGHT));
-
- if (_fontOverrideName)
- {
- outResourceData->SetString("font", _fontOverrideName);
- }
-
- outResourceData->SetInt("wrap", ( m_bWrap ? 1 : 0 ));
- outResourceData->SetInt("centerwrap", ( m_bCenterWrap ? 1 : 0 ));
-
- if ( m_bUseProportionalInsets )
- {
- outResourceData->SetInt("textinsetx", scheme()->GetProportionalNormalizedValueEx( GetScheme(), _textInset[0] ) );
- outResourceData->SetInt("textinsety", _textInset[1]);
- }
- else
- {
- outResourceData->SetInt("textinsetx", _textInset[0]);
- outResourceData->SetInt("textinsety", _textInset[1]);
- }
- outResourceData->SetInt("auto_wide_tocontents", ( m_bAutoWideToContents ? 1 : 0 ));
- outResourceData->SetInt("use_proportional_insets", ( m_bUseProportionalInsets ? 1 : 0 ));
-}
-
-//-----------------------------------------------------------------------------
-// Purpose:
-//-----------------------------------------------------------------------------
-void Label::ApplySettings( KeyValues *inResourceData )
-{
- BaseClass::ApplySettings( inResourceData );
-
- // label settings
- const char *labelText = inResourceData->GetString( "labelText", NULL );
- if ( labelText )
- {
- if (labelText[0] == '%' && labelText[strlen(labelText) - 1] == '%')
- {
- // it's a variable, set it to be a special variable localized string
- wchar_t unicodeVar[256];
- g_pVGuiLocalize->ConvertANSIToUnicode(labelText, unicodeVar, sizeof(unicodeVar));
-
- char var[256];
- _snprintf(var, sizeof(var), "#var_%s", labelText);
- g_pVGuiLocalize->AddString(var + 1, unicodeVar, "");
- SetText(var);
- }
- else
- {
- SetText(labelText);
- }
- }
-
- // text alignment
- const char *alignmentString = inResourceData->GetString( "textAlignment", "" );
- int align = -1;
-
- if ( !stricmp(alignmentString, "north-west") )
- {
- align = a_northwest;
- }
- else if ( !stricmp(alignmentString, "north") )
- {
- align = a_north;
- }
- else if ( !stricmp(alignmentString, "north-east") )
- {
- align = a_northeast;
- }
- else if ( !stricmp(alignmentString, "west") )
- {
- align = a_west;
- }
- else if ( !stricmp(alignmentString, "center") )
- {
- align = a_center;
- }
- else if ( !stricmp(alignmentString, "east") )
- {
- align = a_east;
- }
- else if ( !stricmp(alignmentString, "south-west") )
- {
- align = a_southwest;
- }
- else if ( !stricmp(alignmentString, "south") )
- {
- align = a_south;
- }
- else if ( !stricmp(alignmentString, "south-east") )
- {
- align = a_southeast;
- }
-
- if ( align != -1 )
- {
- SetContentAlignment( (Alignment)align );
- }
-
- // the control we are to be associated with may not have been created yet,
- // so keep a pointer to it's name and calculate it when we can
- const char *associateName = inResourceData->GetString("associate", "");
- if (associateName[0] != 0)
- {
- int len = Q_strlen(associateName) + 1;
- _associateName = new char[ len ];
- Q_strncpy( _associateName, associateName, len );
- }
-
- if (inResourceData->GetInt("dulltext", 0) == 1)
- {
- SetTextColorState(CS_DULL);
- }
- else if (inResourceData->GetInt("brighttext", 0) == 1)
- {
- SetTextColorState(CS_BRIGHT);
- }
- else
- {
- SetTextColorState(CS_NORMAL);
- }
-
- // font settings
- const char *overrideFont = inResourceData->GetString("font", "");
- IScheme *pScheme = scheme()->GetIScheme( GetScheme() );
-
- if (*overrideFont)
- {
- delete [] _fontOverrideName;
- int len = Q_strlen(overrideFont) + 1;
- _fontOverrideName = new char[ len ];
- Q_strncpy(_fontOverrideName, overrideFont, len );
- SetFont(pScheme->GetFont(_fontOverrideName, IsProportional()));
- }
- else if (_fontOverrideName)
- {
- delete [] _fontOverrideName;
- _fontOverrideName = NULL;
- SetFont(pScheme->GetFont("Default", IsProportional()));
- }
-
- bool bWrapText = inResourceData->GetInt("centerwrap", 0) > 0;
- SetCenterWrap( bWrapText );
-
- m_bAutoWideToContents = inResourceData->GetInt("auto_wide_tocontents", 0) > 0;
-
- bWrapText = inResourceData->GetInt("wrap", 0) > 0;
- SetWrap( bWrapText );
-
- int inset_x = inResourceData->GetInt("textinsetx", _textInset[0]);
- int inset_y = inResourceData->GetInt("textinsety", _textInset[1]);
- // Had to play it safe and add a new key for backwards compatibility
- m_bUseProportionalInsets = inResourceData->GetInt("use_proportional_insets", 0) > 0;
- if ( m_bUseProportionalInsets )
- {
- inset_x = scheme()->GetProportionalScaledValueEx( GetScheme(), inset_x );
- }
-
- SetTextInset( inset_x, inset_y );
-
- bool bAllCaps = inResourceData->GetInt("allcaps", 0) > 0;
- SetAllCaps( bAllCaps );
-
- InvalidateLayout(true);
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: Returns a description of the label string
-//-----------------------------------------------------------------------------
-const char *Label::GetDescription( void )
-{
- static char buf[1024];
- Q_snprintf(buf, sizeof(buf), "%s, string labelText, string associate, alignment textAlignment, int wrap, int dulltext, int brighttext, string font", BaseClass::GetDescription());
- return buf;
-}
-
-//-----------------------------------------------------------------------------
-// Purpose: If a label has images in _imageDar, the size
-// must take those into account as well as the textImage part
-// Textimage part will shrink ONLY if there is not enough room.
-//-----------------------------------------------------------------------------
-void Label::PerformLayout()
-{
- int wide, tall;
- Panel::GetSize(wide, tall);
- wide -= _textInset[0]; // take inset into account
-
- // if we just have a textImage, this is trivial.
- if (_imageDar.Count() == 1 && _textImageIndex == 0)
- {
- if ( m_bWrap || m_bCenterWrap )
- {
- int twide, ttall;
- _textImage->GetContentSize(twide, ttall);
- _textImage->SetSize(wide, ttall);
- }
- else
- {
- int twide, ttall;
- _textImage->GetContentSize(twide, ttall);
-
- // tell the textImage how much space we have to draw in
- if ( wide < twide)
- _textImage->SetSize(wide, ttall);
- else
- _textImage->SetSize(twide, ttall);
- }
-
- HandleAutoSizing();
-
- HandleAutoSizing();
-
- return;
- }
-
- // assume the images in the dar cannot be resized, and if
- // the images + the textimage are too wide we shring the textimage part
- if (_textImageIndex < 0)
- return;
-
- // get the size of the images
- int widthOfImages = 0;
- for (int i = 0; i < _imageDar.Count(); i++)
- {
- TImageInfo &imageInfo = _imageDar[i];
- IImage *image = imageInfo.image;
- if (!image)
- continue; // skip over null images
-
- if (i == _textImageIndex)
- continue;
-
- // add up the bounds
- int iWide, iTall;
- image->GetSize(iWide, iTall);
- widthOfImages += iWide;
- }
-
- // so this is how much room we have to draw the textimage part
- int spaceAvail = wide - widthOfImages;
-
- // if we have no space at all just leave everything as is.
- if (spaceAvail < 0)
- return;
-
- int twide, ttall;
- _textImage->GetSize (twide, ttall);
- // tell the textImage how much space we have to draw in
- _textImage->SetSize(spaceAvail, ttall);
-
- HandleAutoSizing();
-}
-
-void Label::SetWrap( bool bWrap )
-{
- m_bWrap = bWrap;
- _textImage->SetWrap( m_bWrap );
-
- InvalidateLayout();
-}
-
-void Label::SetCenterWrap( bool bWrap )
-{
- m_bCenterWrap = bWrap;
- _textImage->SetCenterWrap( m_bCenterWrap );
-
- InvalidateLayout();
-}
-
-void Label::SetAllCaps( bool bAllCaps )
-{
- m_bAllCaps = bAllCaps;
- _textImage->SetAllCaps( m_bAllCaps );
-
- InvalidateLayout();
-}
-
-void Label::HandleAutoSizing( void )
-{
- if ( m_bAutoWideDirty )
- {
- m_bAutoWideDirty = false;
-
- // Only change our width to match our content
- int wide, tall;
- GetContentSize(wide, tall);
- SetSize(wide, GetTall());
- }
-}
-
-
-
+//========= Copyright Valve Corporation, All rights reserved. ============//
+//
+// Purpose:
+//
+// $NoKeywords: $
+//=============================================================================//
+
+#include <assert.h>
+#include <stdarg.h>
+#include <stdio.h>
+#include <ctype.h>
+
+#include <vgui/IInput.h>
+#include <vgui/ILocalize.h>
+#include <vgui/IPanel.h>
+#include <vgui/ISurface.h>
+#include <vgui/IScheme.h>
+#include <KeyValues.h>
+
+#include <vgui_controls/Label.h>
+#include <vgui_controls/Image.h>
+#include <vgui_controls/TextImage.h>
+#include <vgui_controls/Controls.h>
+
+// memdbgon must be the last include file in a .cpp file!!!
+#include <tier0/memdbgon.h>
+
+using namespace vgui;
+
+#ifndef max
+#define max(a,b) (((a) > (b)) ? (a) : (b))
+#endif
+
+DECLARE_BUILD_FACTORY_DEFAULT_TEXT( Label, Label );
+
+//-----------------------------------------------------------------------------
+// Purpose: Constructor
+//-----------------------------------------------------------------------------
+Label::Label(Panel *parent, const char *panelName, const char *text) : BaseClass(parent, panelName)
+{
+ Init();
+
+ _textImage = new TextImage(text);
+ _textImage->SetColor(Color(0, 0, 0, 0));
+ SetText(text);
+ _textImageIndex = AddImage(_textImage, 0);
+
+ REGISTER_COLOR_AS_OVERRIDABLE( _disabledFgColor2, "disabledfgcolor2_override" );
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Constructor
+//-----------------------------------------------------------------------------
+Label::Label(Panel *parent, const char *panelName, const wchar_t *wszText) : BaseClass(parent, panelName)
+{
+ Init();
+
+ _textImage = new TextImage(wszText);
+ _textImage->SetColor(Color(0, 0, 0, 0));
+ SetText(wszText);
+ _textImageIndex = AddImage(_textImage, 0);
+
+ REGISTER_COLOR_AS_OVERRIDABLE( _disabledFgColor2, "disabledfgcolor2_override" );
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Destructor
+//-----------------------------------------------------------------------------
+Label::~Label()
+{
+ delete _textImage;
+ delete [] _associateName;
+ delete [] _fontOverrideName;
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Construct the label
+//-----------------------------------------------------------------------------
+void Label::Init()
+{
+ _contentAlignment = a_west;
+ _textColorState = CS_NORMAL;
+ _textInset[0] = 0;
+ _textInset[1] = 0;
+ _hotkey = 0;
+ _associate = NULL;
+ _associateName = NULL;
+ _fontOverrideName = NULL;
+ m_bWrap = false;
+ m_bCenterWrap = false;
+ m_bAutoWideToContents = false;
+ m_bUseProportionalInsets = false;
+ m_bAutoWideDirty = false;
+
+// SetPaintBackgroundEnabled(false);
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Set whether the text is displayed bright or dull
+//-----------------------------------------------------------------------------
+void Label::SetTextColorState(EColorState state)
+{
+ if (_textColorState != state)
+ {
+ _textColorState = state;
+ InvalidateLayout();
+ }
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Return the full size of the contained content
+//-----------------------------------------------------------------------------
+void Label::GetContentSize(int &wide, int &tall)
+{
+ if( GetFont() == INVALID_FONT ) // we haven't loaded our font yet, so load it now
+ {
+ IScheme *pScheme = scheme()->GetIScheme( GetScheme() );
+ if ( pScheme )
+ {
+ SetFont( pScheme->GetFont( "Default", IsProportional() ) );
+ }
+ }
+
+
+ int tx0, ty0, tx1, ty1;
+ ComputeAlignment(tx0, ty0, tx1, ty1);
+
+ // the +8 is padding to the content size
+ // the code which uses it should really set that itself;
+ // however a lot of existing code relies on this
+ wide = (tx1 - tx0) + _textInset[0];
+
+ // get the size of the text image and remove it
+ int iWide, iTall;
+ _textImage->GetSize(iWide, iTall);
+ wide -= iWide;
+ // get the full, untruncated (no elipsis) size of the text image.
+ _textImage->GetContentSize(iWide, iTall);
+ wide += iWide;
+
+ // addin the image offsets as well
+ for (int i=0; i < _imageDar.Size(); i++)
+ wide += _imageDar[i].offset;
+
+ tall = max((ty1 - ty0) + _textInset[1], iTall);
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Calculate the keyboard key that is a hotkey
+//-----------------------------------------------------------------------------
+wchar_t Label::CalculateHotkey(const char *text)
+{
+ for (const char *ch = text; *ch != 0; ch++)
+ {
+ if (*ch == '&')
+ {
+ // get the next character
+ ch++;
+
+ if (*ch == '&')
+ {
+ // just an &
+ continue;
+ }
+ else if (*ch == 0)
+ {
+ break;
+ }
+ else if (V_isalnum(*ch))
+ {
+ // found the hotkey
+ return (wchar_t)tolower(*ch);
+ }
+ }
+ }
+
+ return '\0';
+}
+
+wchar_t Label::CalculateHotkey(const wchar_t *text)
+{
+ if( text )
+ {
+ for (const wchar_t *ch = text; *ch != 0; ch++)
+ {
+ if (*ch == '&')
+ {
+ // get the next character
+ ch++;
+
+ if (*ch == '&')
+ {
+ // just an &
+ continue;
+ }
+ else if (*ch == 0)
+ {
+ break;
+ }
+ else if (iswalnum(*ch))
+ {
+ // found the hotkey
+ return (wchar_t)towlower(*ch);
+ }
+ }
+ }
+ }
+
+ return '\0';
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Check if this label has a hotkey that is the key passed in.
+//-----------------------------------------------------------------------------
+Panel *Label::HasHotkey(wchar_t key)
+{
+#ifdef VGUI_HOTKEYS_ENABLED
+ if ( iswalnum( key ) )
+ key = towlower( key );
+
+ if (_hotkey == key)
+ return this;
+#endif
+
+ return NULL;
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Set the hotkey for this label
+//-----------------------------------------------------------------------------
+void Label::SetHotkey(wchar_t ch)
+{
+ _hotkey = ch;
+}
+
+wchar_t Label::GetHotKey()
+{
+ return _hotkey;
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Handle a hotkey by passing on focus to associate
+//-----------------------------------------------------------------------------
+void Label::OnHotkeyPressed()
+{
+ // we can't accept focus, but if we are associated to a control give it to that
+ if (_associate.Get() && !IsBuildModeActive())
+ {
+ _associate->RequestFocus();
+ }
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Redirect mouse pressed to giving focus to associate
+//-----------------------------------------------------------------------------
+void Label::OnMousePressed(MouseCode code)
+{
+ if (_associate.Get() && !IsBuildModeActive())
+ {
+ _associate->RequestFocus();
+ }
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Return the text in the label
+//-----------------------------------------------------------------------------
+void Label::GetText(char *textOut, int bufferLen)
+{
+ _textImage->GetText(textOut, bufferLen);
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Return the text in the label
+//-----------------------------------------------------------------------------
+void Label::GetText(wchar_t *textOut, int bufLenInBytes)
+{
+ _textImage->GetText(textOut, bufLenInBytes);
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Take the string and looks it up in the localization file
+// to convert it to unicode
+// Setting the text will not set the size of the label.
+// Set the size explicitly or use setToContent()
+//-----------------------------------------------------------------------------
+void Label::SetText(const char *text)
+{
+ // if set to null, just make blank
+ if (!text)
+ {
+ text = "";
+ }
+
+ // let the text image do the translation itself
+ _textImage->SetText(text);
+
+ if( text[0] == '#' )
+ {
+ SetHotkey(CalculateHotkey(g_pVGuiLocalize->Find(text)));
+ }
+ else
+ {
+ SetHotkey(CalculateHotkey(text));
+ }
+
+ m_bAutoWideDirty = m_bAutoWideToContents;
+
+ InvalidateLayout();
+ Repaint();
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Set unicode text directly
+//-----------------------------------------------------------------------------
+void Label::SetText(const wchar_t *unicodeString, bool bClearUnlocalizedSymbol)
+{
+ m_bAutoWideDirty = m_bAutoWideToContents;
+
+ if ( unicodeString && _textImage->GetUText() && !Q_wcscmp(unicodeString,_textImage->GetUText()) )
+ return;
+
+ _textImage->SetText(unicodeString, bClearUnlocalizedSymbol);
+
+//!! need to calculate hotkey from translated string
+ SetHotkey(CalculateHotkey(unicodeString));
+
+ InvalidateLayout(); // possible that the textimage needs to expand
+ Repaint();
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: updates localized text
+//-----------------------------------------------------------------------------
+void Label::OnDialogVariablesChanged(KeyValues *dialogVariables )
+{
+ StringIndex_t index = _textImage->GetUnlocalizedTextSymbol();
+ if (index != INVALID_LOCALIZE_STRING_INDEX)
+ {
+ // reconstruct the string from the variables
+ wchar_t buf[1024];
+ g_pVGuiLocalize->ConstructString(buf, sizeof(buf), index, dialogVariables);
+ SetText(buf);
+ }
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Additional offset at the Start of the text (from whichever side it is aligned)
+//-----------------------------------------------------------------------------
+void Label::SetTextInset(int xInset, int yInset)
+{
+ _textInset[0] = xInset;
+ _textInset[1] = yInset;
+
+ int wide, tall;
+ GetSize( wide, tall);
+ _textImage->SetDrawWidth(wide - _textInset[0]);
+}
+
+//-----------------------------------------------------------------------------
+// Purpose:
+//-----------------------------------------------------------------------------
+void Label::GetTextInset(int *xInset, int *yInset )
+{
+ *xInset = _textInset[0];
+ *yInset = _textInset[1];
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Set the enabled state
+//-----------------------------------------------------------------------------
+void Label::SetEnabled(bool state)
+{
+ Panel::SetEnabled(state);
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Calculates where in the panel the content resides
+// Input : &tx0 - [out] position of the content
+// &ty0 -
+// &tx1 -
+// &ty1 -
+// Note: horizontal alignment is west if the image dar has
+// more than one image in it, this is because we use image sizes
+// to determine layout in classes for example, Menu.
+//-----------------------------------------------------------------------------
+void Label::ComputeAlignment(int &tx0, int &ty0, int &tx1, int &ty1)
+{
+ int wide, tall;
+ GetPaintSize(wide, tall);
+ int tWide,tTall;
+
+ // text bounding box
+ tx0 = 0;
+ ty0 = 0;
+
+ // loop through all the images and calculate the complete bounds
+ int maxX = 0, maxY = 0;
+
+ int actualXAlignment = _contentAlignment;
+ for (int i = 0; i < _imageDar.Count(); i++)
+ {
+ TImageInfo &imageInfo = _imageDar[i];
+ IImage *image = imageInfo.image;
+ if (!image)
+ continue; // skip over null images
+
+ // add up the bounds
+ int iWide, iTall;
+ image->GetSize(iWide, iTall);
+ if (iWide > wide) // if the image is larger than the label just do a west alignment
+ actualXAlignment = Label::a_west;
+
+ // get the max height
+ maxY = max(maxY, iTall);
+ maxX += iWide;
+
+ // add the offset to x
+ maxX += imageInfo.offset;
+ }
+
+ tWide = maxX;
+ tTall = maxY;
+
+ // x align text
+ switch (actualXAlignment)
+ {
+ // left
+ case Label::a_northwest:
+ case Label::a_west:
+ case Label::a_southwest:
+ {
+ tx0 = 0;
+ break;
+ }
+ // center
+ case Label::a_north:
+ case Label::a_center:
+ case Label::a_south:
+ {
+ tx0 = (wide - tWide) / 2;
+ break;
+ }
+ // right
+ case Label::a_northeast:
+ case Label::a_east:
+ case Label::a_southeast:
+ {
+ tx0 = wide - tWide;
+ break;
+ }
+ }
+
+ // y align text
+ switch (_contentAlignment)
+ {
+ //top
+ case Label::a_northwest:
+ case Label::a_north:
+ case Label::a_northeast:
+ {
+ ty0 = 0;
+ break;
+ }
+ // center
+ case Label::a_west:
+ case Label::a_center:
+ case Label::a_east:
+ {
+ ty0 = (tall - tTall) / 2;
+ break;
+ }
+ // south
+ case Label::a_southwest:
+ case Label::a_south:
+ case Label::a_southeast:
+ {
+ ty0 = tall - tTall;
+ break;
+ }
+ }
+
+ tx1 = tx0 + tWide;
+ ty1 = ty0 + tTall;
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: overridden main drawing function for the panel
+//-----------------------------------------------------------------------------
+void Label::Paint()
+{
+ int tx0, ty0, tx1, ty1;
+ ComputeAlignment(tx0, ty0, tx1, ty1);
+
+ // calculate who our associate is if we haven't already
+ if (_associateName)
+ {
+ SetAssociatedControl(FindSiblingByName(_associateName));
+ delete [] _associateName;
+ _associateName = NULL;
+ }
+
+ int labelWide, labelTall;
+ GetSize(labelWide, labelTall);
+ int x = tx0, y = _textInset[1] + ty0;
+ int imageYPos = 0; // a place to save the y offset for when we draw the disable version of the image
+
+ // draw the set of images
+ for (int i = 0; i < _imageDar.Count(); i++)
+ {
+ TImageInfo &imageInfo = _imageDar[i];
+ IImage *image = imageInfo.image;
+ if (!image)
+ continue; // skip over null images
+
+ // add the offset to x
+ x += imageInfo.offset;
+
+ // if this is the text image then add its inset to the left or from the right
+ if (i == _textImageIndex)
+ {
+ switch ( _contentAlignment )
+ {
+ // left
+ case Label::a_northwest:
+ case Label::a_west:
+ case Label::a_southwest:
+ {
+ x += _textInset[0];
+ break;
+ }
+ // right
+ case Label::a_northeast:
+ case Label::a_east:
+ case Label::a_southeast:
+ {
+ x -= _textInset[0];
+ break;
+ }
+ }
+ }
+
+ // see if the image is in a fixed position
+ if (imageInfo.xpos >= 0)
+ {
+ x = imageInfo.xpos;
+ }
+
+ // draw
+ imageYPos = y;
+ image->SetPos(x, y);
+
+ // fix up y for center-aligned text
+ if (_contentAlignment == Label::a_west || _contentAlignment == Label::a_center || _contentAlignment == Label::a_east)
+ {
+ int iw, it;
+ image->GetSize(iw, it);
+ if (it < (ty1 - ty0))
+ {
+ imageYPos = ((ty1 - ty0) - it) / 2 + y;
+ image->SetPos(x, ((ty1 - ty0) - it) / 2 + y);
+ }
+ }
+
+ // don't resize the image unless its too big
+ if (imageInfo.width >= 0)
+ {
+ int w, t;
+ image->GetSize(w, t);
+ if (w > imageInfo.width)
+ {
+ image->SetSize(imageInfo.width, t);
+ }
+ }
+
+ // if it's the basic text image then draw specially
+ if (image == _textImage)
+ {
+ if (IsEnabled())
+ {
+ if (_associate.Get() && ipanel()->HasParent(input()->GetFocus(), _associate->GetVPanel()))
+ {
+ _textImage->SetColor(_associateColor);
+ }
+ else
+ {
+ _textImage->SetColor(GetFgColor());
+ }
+
+ _textImage->Paint();
+ }
+ else
+ {
+ // draw disabled version, with embossed look
+ // offset image
+ _textImage->SetPos(x + 1, imageYPos + 1);
+ _textImage->SetColor(_disabledFgColor1);
+ _textImage->Paint();
+
+ surface()->DrawFlushText();
+
+ // overlayed image
+ _textImage->SetPos(x, imageYPos);
+ _textImage->SetColor(_disabledFgColor2);
+ _textImage->Paint();
+ }
+ }
+ else
+ {
+ image->Paint();
+ }
+
+ // add the image size to x
+ int wide, tall;
+ image->GetSize(wide, tall);
+ x += wide;
+ }
+}
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Helper function, draws a simple line with dashing parameters
+//-----------------------------------------------------------------------------
+void Label::DrawDashedLine(int x0, int y0, int x1, int y1, int dashLen, int gapLen)
+{
+ // work out which way the line goes
+ if ((x1 - x0) > (y1 - y0))
+ {
+ // x direction line
+ while (1)
+ {
+ if (x0 + dashLen > x1)
+ {
+ // draw partial
+ surface()->DrawFilledRect(x0, y0, x1, y1);
+ }
+ else
+ {
+ surface()->DrawFilledRect(x0, y0, x0 + dashLen, y1);
+ }
+
+ x0 += dashLen;
+
+ if (x0 + gapLen > x1)
+ break;
+
+ x0 += gapLen;
+ }
+ }
+ else
+ {
+ // y direction
+ while (1)
+ {
+ if (y0 + dashLen > y1)
+ {
+ // draw partial
+ surface()->DrawFilledRect(x0, y0, x1, y1);
+ }
+ else
+ {
+ surface()->DrawFilledRect(x0, y0, x1, y0 + dashLen);
+ }
+
+ y0 += dashLen;
+
+ if (y0 + gapLen > y1)
+ break;
+
+ y0 += gapLen;
+ }
+ }
+}
+
+void Label::SetContentAlignment(Alignment alignment)
+{
+ _contentAlignment=alignment;
+ Repaint();
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Size the width of the label to its contents - only works from in ApplySchemeSettings or PerformLayout()
+//-----------------------------------------------------------------------------
+void Label::SizeToContents()
+{
+ int wide, tall;
+ GetContentSize(wide, tall);
+
+ SetSize(wide, tall);
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Set the font the text is drawn in
+//-----------------------------------------------------------------------------
+void Label::SetFont(HFont font)
+{
+ _textImage->SetFont(font);
+ Repaint();
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Resond to resizing of the panel
+//-----------------------------------------------------------------------------
+void Label::OnSizeChanged(int wide, int tall)
+{
+ InvalidateLayout();
+ Panel::OnSizeChanged(wide, tall);
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Get the font the textImage is drawn in.
+//-----------------------------------------------------------------------------
+HFont Label::GetFont()
+{
+ return _textImage->GetFont();
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Set the foreground color of the Label
+//-----------------------------------------------------------------------------
+void Label::SetFgColor(Color color)
+{
+ if (!(GetFgColor() == color))
+ {
+ BaseClass::SetFgColor(color);
+ _textImage->SetColor(color);
+ Repaint();
+ }
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Get the foreground color of the Label
+//-----------------------------------------------------------------------------
+Color Label::GetFgColor()
+{
+ Color clr = Panel::GetFgColor();
+ return clr;
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Set the foreground color 1 color of the Label
+//-----------------------------------------------------------------------------
+void Label::SetDisabledFgColor1(Color color)
+{
+ _disabledFgColor1 = color;
+}
+
+//-----------------------------------------------------------------------------
+// Purpose:
+//-----------------------------------------------------------------------------
+void Label::SetDisabledFgColor2(Color color)
+{
+ _disabledFgColor2 = color;
+}
+
+//-----------------------------------------------------------------------------
+// Purpose:
+//-----------------------------------------------------------------------------
+Color Label::GetDisabledFgColor1()
+{
+ return _disabledFgColor1;
+}
+
+//-----------------------------------------------------------------------------
+// Purpose:
+//-----------------------------------------------------------------------------
+Color Label::GetDisabledFgColor2()
+{
+ return _disabledFgColor2;
+}
+
+//-----------------------------------------------------------------------------
+// Purpose:
+//-----------------------------------------------------------------------------
+TextImage *Label::GetTextImage()
+{
+ return _textImage;
+}
+
+
+//-----------------------------------------------------------------------------
+// Purpose:
+//-----------------------------------------------------------------------------
+bool Label::RequestInfo(KeyValues *outputData)
+{
+ if (!stricmp(outputData->GetName(), "GetText"))
+ {
+ wchar_t wbuf[256];
+ _textImage->GetText(wbuf, 255);
+ outputData->SetWString("text", wbuf);
+ return true;
+ }
+
+ return Panel::RequestInfo(outputData);
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Sets the text from the message
+//-----------------------------------------------------------------------------
+void Label::OnSetText(KeyValues *params)
+{
+ KeyValues *pkvText = params->FindKey("text", false);
+ if (!pkvText)
+ return;
+
+ if (pkvText->GetDataType() == KeyValues::TYPE_STRING)
+ {
+ SetText(pkvText->GetString());
+ }
+ else if (pkvText->GetDataType() == KeyValues::TYPE_WSTRING)
+ {
+ SetText(pkvText->GetWString());
+ }
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Add an image to the list
+// returns the index the image was placed in
+//-----------------------------------------------------------------------------
+int Label::AddImage(IImage *image, int offset)
+{
+ int newImage = _imageDar.AddToTail();
+ _imageDar[newImage].image = image;
+ _imageDar[newImage].offset = (short)offset;
+ _imageDar[newImage].xpos = -1;
+ _imageDar[newImage].width = -1;
+ InvalidateLayout();
+ return newImage;
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: removes all images from the list
+// user is responsible for the memory
+//-----------------------------------------------------------------------------
+void Label::ClearImages()
+{
+ _imageDar.RemoveAll();
+ _textImageIndex = -1;
+}
+
+void Label::ResetToSimpleTextImage()
+{
+ ClearImages();
+ _textImageIndex = AddImage(_textImage, 0);
+}
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Multiple image handling
+// Images are drawn from left to right across the label, ordered by index
+// By default there is a TextImage in position 0
+// Set the contents of an IImage in the IImage array.
+//-----------------------------------------------------------------------------
+void Label::SetImageAtIndex(int index, IImage *image, int offset)
+{
+ EnsureImageCapacity(index);
+// Assert( image );
+
+ if ( _imageDar[index].image != image || _imageDar[index].offset != offset)
+ {
+ _imageDar[index].image = image;
+ _imageDar[index].offset = (short)offset;
+ InvalidateLayout();
+ }
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Get an IImage in the IImage array.
+//-----------------------------------------------------------------------------
+IImage *Label::GetImageAtIndex(int index)
+{
+ if ( _imageDar.IsValidIndex( index ) )
+ return _imageDar[index].image;
+ return NULL;
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Get the number of images in the array.
+//-----------------------------------------------------------------------------
+int Label::GetImageCount()
+{
+ return _imageDar.Count();
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Move where the default text image is within the image array
+// (it starts in position 0)
+// Input : newIndex -
+// Output : int - the index the default text image was previously in
+//-----------------------------------------------------------------------------
+int Label::SetTextImageIndex(int newIndex)
+{
+ if (newIndex == _textImageIndex)
+ return _textImageIndex;
+
+ EnsureImageCapacity(newIndex);
+
+ int oldIndex = _textImageIndex;
+ if ( _textImageIndex >= 0 )
+ {
+ _imageDar[_textImageIndex].image = NULL;
+ }
+ if (newIndex > -1)
+ {
+ _imageDar[newIndex].image = _textImage;
+ }
+ _textImageIndex = newIndex;
+ return oldIndex;
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Ensure that the maxIndex will be a valid index
+//-----------------------------------------------------------------------------
+void Label::EnsureImageCapacity(int maxIndex)
+{
+ while (_imageDar.Size() <= maxIndex)
+ {
+ AddImage(NULL, 0);
+ }
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Set the offset in pixels before the image
+//-----------------------------------------------------------------------------
+void Label::SetImagePreOffset(int index, int preOffset)
+{
+ if (_imageDar.IsValidIndex(index) && _imageDar[index].offset != preOffset)
+ {
+ _imageDar[index].offset = (short)preOffset;
+ InvalidateLayout();
+ }
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: fixes the layout bounds of the image within the label
+//-----------------------------------------------------------------------------
+void Label::SetImageBounds(int index, int x, int width)
+{
+ _imageDar[index].xpos = (short)x;
+ _imageDar[index].width = (short)width;
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Labels can be associated with controls, and alter behaviour based on the associates behaviour
+// If the associate is disabled, so are we
+// If the associate has focus, we may alter how we draw
+// If we get a hotkey press or focus message, we forward the focus to the associate
+//-----------------------------------------------------------------------------
+void Label::SetAssociatedControl(Panel *control)
+{
+ if (control != this)
+ {
+ _associate = control;
+ }
+ else
+ {
+ // don't let the associate ever be set to be ourself
+ _associate = NULL;
+ }
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Called after a panel requests focus to fix up the whole chain
+//-----------------------------------------------------------------------------
+void Label::OnRequestFocus(VPANEL subFocus, VPANEL defaultPanel)
+{
+ if (_associate.Get() && subFocus == GetVPanel() && !IsBuildModeActive())
+ {
+ // we've received focus; pass the focus onto the associate instead
+ _associate->RequestFocus();
+ }
+ else
+ {
+ BaseClass::OnRequestFocus(subFocus, defaultPanel);
+ }
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: sets custom settings from the scheme file
+//-----------------------------------------------------------------------------
+void Label::ApplySchemeSettings(IScheme *pScheme)
+{
+ BaseClass::ApplySchemeSettings(pScheme);
+
+ if (_fontOverrideName)
+ {
+ // use the custom specified font since we have one set
+ SetFont(pScheme->GetFont(_fontOverrideName, IsProportional()));
+ }
+ if ( GetFont() == INVALID_FONT )
+ {
+ SetFont( pScheme->GetFont( "Default", IsProportional() ) );
+ }
+
+ if ( m_bWrap || m_bCenterWrap )
+ {
+ //tell it how big it is
+ int wide, tall;
+ Panel::GetSize(wide, tall);
+ wide -= _textInset[0]; // take inset into account
+ _textImage->SetSize(wide, tall);
+
+ _textImage->RecalculateNewLinePositions();
+ }
+ else
+ {
+ // if you don't set the size of the image, many, many buttons will break - we might want to look into fixing this all over the place later
+ int wide, tall;
+ _textImage->GetContentSize(wide, tall);
+ _textImage->SetSize(wide, tall);
+ }
+
+ if ( m_bAutoWideToContents )
+ {
+ m_bAutoWideDirty = true;
+ HandleAutoSizing();
+ }
+
+ // clear out any the images, since they will have been invalidated
+ for (int i = 0; i < _imageDar.Count(); i++)
+ {
+ IImage *image = _imageDar[i].image;
+ if (!image)
+ continue; // skip over null images
+
+ if (i == _textImageIndex)
+ continue;
+
+ _imageDar[i].image = NULL;
+ }
+
+ SetDisabledFgColor1(GetSchemeColor("Label.DisabledFgColor1", pScheme));
+ SetDisabledFgColor2(GetSchemeColor("Label.DisabledFgColor2", pScheme));
+ SetBgColor(GetSchemeColor("Label.BgColor", pScheme));
+
+ switch (_textColorState)
+ {
+ case CS_DULL:
+ SetFgColor(GetSchemeColor("Label.TextDullColor", pScheme));
+ break;
+ case CS_BRIGHT:
+ SetFgColor(GetSchemeColor("Label.TextBrightColor", pScheme));
+ break;
+ case CS_NORMAL:
+ default:
+ SetFgColor(GetSchemeColor("Label.TextColor", pScheme));
+ break;
+ }
+
+ _associateColor = GetSchemeColor("Label.SelectedTextColor", pScheme);
+}
+
+//-----------------------------------------------------------------------------
+// Purpose:
+//-----------------------------------------------------------------------------
+void Label::GetSettings( KeyValues *outResourceData )
+{
+ // panel settings
+ Panel::GetSettings( outResourceData );
+
+ // label settings
+ char buf[256];
+ _textImage->GetUnlocalizedText( buf, 255 );
+ if (!strnicmp(buf, "#var_", 5))
+ {
+ // strip off the variable prepender on save
+ outResourceData->SetString( "labelText", buf + 5 );
+ }
+ else
+ {
+ outResourceData->SetString( "labelText", buf );
+ }
+
+ const char *alignmentString = "";
+ switch ( _contentAlignment )
+ {
+ case a_northwest: alignmentString = "north-west"; break;
+ case a_north: alignmentString = "north"; break;
+ case a_northeast: alignmentString = "north-east"; break;
+ case a_center: alignmentString = "center"; break;
+ case a_east: alignmentString = "east"; break;
+ case a_southwest: alignmentString = "south-west"; break;
+ case a_south: alignmentString = "south"; break;
+ case a_southeast: alignmentString = "south-east"; break;
+ case a_west:
+ default: alignmentString = "west"; break;
+ }
+
+ outResourceData->SetString( "textAlignment", alignmentString );
+
+ if (_associate)
+ {
+ outResourceData->SetString("associate", _associate->GetName());
+ }
+
+ outResourceData->SetInt("dulltext", (int)(_textColorState == CS_DULL));
+ outResourceData->SetInt("brighttext", (int)(_textColorState == CS_BRIGHT));
+
+ if (_fontOverrideName)
+ {
+ outResourceData->SetString("font", _fontOverrideName);
+ }
+
+ outResourceData->SetInt("wrap", ( m_bWrap ? 1 : 0 ));
+ outResourceData->SetInt("centerwrap", ( m_bCenterWrap ? 1 : 0 ));
+
+ if ( m_bUseProportionalInsets )
+ {
+ outResourceData->SetInt("textinsetx", scheme()->GetProportionalNormalizedValueEx( GetScheme(), _textInset[0] ) );
+ outResourceData->SetInt("textinsety", _textInset[1]);
+ }
+ else
+ {
+ outResourceData->SetInt("textinsetx", _textInset[0]);
+ outResourceData->SetInt("textinsety", _textInset[1]);
+ }
+ outResourceData->SetInt("auto_wide_tocontents", ( m_bAutoWideToContents ? 1 : 0 ));
+ outResourceData->SetInt("use_proportional_insets", ( m_bUseProportionalInsets ? 1 : 0 ));
+}
+
+//-----------------------------------------------------------------------------
+// Purpose:
+//-----------------------------------------------------------------------------
+void Label::ApplySettings( KeyValues *inResourceData )
+{
+ BaseClass::ApplySettings( inResourceData );
+
+ // label settings
+ const char *labelText = inResourceData->GetString( "labelText", NULL );
+ if ( labelText )
+ {
+ if (labelText[0] == '%' && labelText[strlen(labelText) - 1] == '%')
+ {
+ // it's a variable, set it to be a special variable localized string
+ wchar_t unicodeVar[256];
+ g_pVGuiLocalize->ConvertANSIToUnicode(labelText, unicodeVar, sizeof(unicodeVar));
+
+ char var[256];
+ _snprintf(var, sizeof(var), "#var_%s", labelText);
+ g_pVGuiLocalize->AddString(var + 1, unicodeVar, "");
+ SetText(var);
+ }
+ else
+ {
+ SetText(labelText);
+ }
+ }
+
+ // text alignment
+ const char *alignmentString = inResourceData->GetString( "textAlignment", "" );
+ int align = -1;
+
+ if ( !stricmp(alignmentString, "north-west") )
+ {
+ align = a_northwest;
+ }
+ else if ( !stricmp(alignmentString, "north") )
+ {
+ align = a_north;
+ }
+ else if ( !stricmp(alignmentString, "north-east") )
+ {
+ align = a_northeast;
+ }
+ else if ( !stricmp(alignmentString, "west") )
+ {
+ align = a_west;
+ }
+ else if ( !stricmp(alignmentString, "center") )
+ {
+ align = a_center;
+ }
+ else if ( !stricmp(alignmentString, "east") )
+ {
+ align = a_east;
+ }
+ else if ( !stricmp(alignmentString, "south-west") )
+ {
+ align = a_southwest;
+ }
+ else if ( !stricmp(alignmentString, "south") )
+ {
+ align = a_south;
+ }
+ else if ( !stricmp(alignmentString, "south-east") )
+ {
+ align = a_southeast;
+ }
+
+ if ( align != -1 )
+ {
+ SetContentAlignment( (Alignment)align );
+ }
+
+ // the control we are to be associated with may not have been created yet,
+ // so keep a pointer to it's name and calculate it when we can
+ const char *associateName = inResourceData->GetString("associate", "");
+ if (associateName[0] != 0)
+ {
+ int len = Q_strlen(associateName) + 1;
+ _associateName = new char[ len ];
+ Q_strncpy( _associateName, associateName, len );
+ }
+
+ if (inResourceData->GetInt("dulltext", 0) == 1)
+ {
+ SetTextColorState(CS_DULL);
+ }
+ else if (inResourceData->GetInt("brighttext", 0) == 1)
+ {
+ SetTextColorState(CS_BRIGHT);
+ }
+ else
+ {
+ SetTextColorState(CS_NORMAL);
+ }
+
+ // font settings
+ const char *overrideFont = inResourceData->GetString("font", "");
+ IScheme *pScheme = scheme()->GetIScheme( GetScheme() );
+
+ if (*overrideFont)
+ {
+ delete [] _fontOverrideName;
+ int len = Q_strlen(overrideFont) + 1;
+ _fontOverrideName = new char[ len ];
+ Q_strncpy(_fontOverrideName, overrideFont, len );
+ SetFont(pScheme->GetFont(_fontOverrideName, IsProportional()));
+ }
+ else if (_fontOverrideName)
+ {
+ delete [] _fontOverrideName;
+ _fontOverrideName = NULL;
+ SetFont(pScheme->GetFont("Default", IsProportional()));
+ }
+
+ bool bWrapText = inResourceData->GetInt("centerwrap", 0) > 0;
+ SetCenterWrap( bWrapText );
+
+ m_bAutoWideToContents = inResourceData->GetInt("auto_wide_tocontents", 0) > 0;
+
+ bWrapText = inResourceData->GetInt("wrap", 0) > 0;
+ SetWrap( bWrapText );
+
+ int inset_x = inResourceData->GetInt("textinsetx", _textInset[0]);
+ int inset_y = inResourceData->GetInt("textinsety", _textInset[1]);
+ // Had to play it safe and add a new key for backwards compatibility
+ m_bUseProportionalInsets = inResourceData->GetInt("use_proportional_insets", 0) > 0;
+ if ( m_bUseProportionalInsets )
+ {
+ inset_x = scheme()->GetProportionalScaledValueEx( GetScheme(), inset_x );
+ }
+
+ SetTextInset( inset_x, inset_y );
+
+ bool bAllCaps = inResourceData->GetInt("allcaps", 0) > 0;
+ SetAllCaps( bAllCaps );
+
+ InvalidateLayout(true);
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Returns a description of the label string
+//-----------------------------------------------------------------------------
+const char *Label::GetDescription( void )
+{
+ static char buf[1024];
+ Q_snprintf(buf, sizeof(buf), "%s, string labelText, string associate, alignment textAlignment, int wrap, int dulltext, int brighttext, string font", BaseClass::GetDescription());
+ return buf;
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: If a label has images in _imageDar, the size
+// must take those into account as well as the textImage part
+// Textimage part will shrink ONLY if there is not enough room.
+//-----------------------------------------------------------------------------
+void Label::PerformLayout()
+{
+ int wide, tall;
+ Panel::GetSize(wide, tall);
+ wide -= _textInset[0]; // take inset into account
+
+ // if we just have a textImage, this is trivial.
+ if (_imageDar.Count() == 1 && _textImageIndex == 0)
+ {
+ if ( m_bWrap || m_bCenterWrap )
+ {
+ int twide, ttall;
+ _textImage->GetContentSize(twide, ttall);
+ _textImage->SetSize(wide, ttall);
+ }
+ else
+ {
+ int twide, ttall;
+ _textImage->GetContentSize(twide, ttall);
+
+ // tell the textImage how much space we have to draw in
+ if ( wide < twide)
+ _textImage->SetSize(wide, ttall);
+ else
+ _textImage->SetSize(twide, ttall);
+ }
+
+ HandleAutoSizing();
+
+ HandleAutoSizing();
+
+ return;
+ }
+
+ // assume the images in the dar cannot be resized, and if
+ // the images + the textimage are too wide we shring the textimage part
+ if (_textImageIndex < 0)
+ return;
+
+ // get the size of the images
+ int widthOfImages = 0;
+ for (int i = 0; i < _imageDar.Count(); i++)
+ {
+ TImageInfo &imageInfo = _imageDar[i];
+ IImage *image = imageInfo.image;
+ if (!image)
+ continue; // skip over null images
+
+ if (i == _textImageIndex)
+ continue;
+
+ // add up the bounds
+ int iWide, iTall;
+ image->GetSize(iWide, iTall);
+ widthOfImages += iWide;
+ }
+
+ // so this is how much room we have to draw the textimage part
+ int spaceAvail = wide - widthOfImages;
+
+ // if we have no space at all just leave everything as is.
+ if (spaceAvail < 0)
+ return;
+
+ int twide, ttall;
+ _textImage->GetSize (twide, ttall);
+ // tell the textImage how much space we have to draw in
+ _textImage->SetSize(spaceAvail, ttall);
+
+ HandleAutoSizing();
+}
+
+void Label::SetWrap( bool bWrap )
+{
+ m_bWrap = bWrap;
+ _textImage->SetWrap( m_bWrap );
+
+ InvalidateLayout();
+}
+
+void Label::SetCenterWrap( bool bWrap )
+{
+ m_bCenterWrap = bWrap;
+ _textImage->SetCenterWrap( m_bCenterWrap );
+
+ InvalidateLayout();
+}
+
+void Label::SetAllCaps( bool bAllCaps )
+{
+ m_bAllCaps = bAllCaps;
+ _textImage->SetAllCaps( m_bAllCaps );
+
+ InvalidateLayout();
+}
+
+void Label::HandleAutoSizing( void )
+{
+ if ( m_bAutoWideDirty )
+ {
+ m_bAutoWideDirty = false;
+
+ // Only change our width to match our content
+ int wide, tall;
+ GetContentSize(wide, tall);
+ SetSize(wide, GetTall());
+ }
+}
+
+
+