summaryrefslogtreecommitdiff
path: root/indra/llui
diff options
context:
space:
mode:
authorMerov Linden <merov@lindenlab.com>2012-11-26 15:01:57 -0800
committerMerov Linden <merov@lindenlab.com>2012-11-26 15:01:57 -0800
commit8076f7a33d7f5ee93d4ba8f71a7ba0fed5e364a7 (patch)
tree6a7d0f88666e16948e73d1098c99edc7513b6e49 /indra/llui
parent7ca2508cc2adcdc5201bd53e814246e156bc6013 (diff)
parent890965faf5baa5f6f832e086991d59bb8d33b7bc (diff)
Pull merge from richard/viewer-chui
Diffstat (limited to 'indra/llui')
-rw-r--r--indra/llui/CMakeLists.txt2
-rw-r--r--indra/llui/llbutton.cpp73
-rw-r--r--indra/llui/llbutton.h8
-rw-r--r--indra/llui/llcombobox.cpp3
-rw-r--r--indra/llui/llcommandmanager.cpp2
-rw-r--r--indra/llui/llcommandmanager.h6
-rw-r--r--[-rwxr-xr-x]indra/llui/llcontainerview.cpp0
-rw-r--r--indra/llui/llflashtimer.cpp93
-rw-r--r--indra/llui/llflashtimer.h67
-rw-r--r--indra/llui/llfloater.cpp18
-rw-r--r--indra/llui/llfloater.h2
-rw-r--r--indra/llui/llfloaterreg.cpp2
-rwxr-xr-xindra/llui/llfolderviewitem.cpp46
-rwxr-xr-xindra/llui/llfolderviewitem.h4
-rw-r--r--indra/llui/llnotifications.cpp26
-rw-r--r--indra/llui/llpanel.cpp18
-rw-r--r--indra/llui/llpanel.h2
-rw-r--r--indra/llui/llscrolllistcolumn.cpp3
-rw-r--r--indra/llui/llscrolllistctrl.cpp166
-rw-r--r--indra/llui/llscrolllistctrl.h28
-rw-r--r--indra/llui/lltabcontainer.cpp4
-rw-r--r--indra/llui/lltoolbar.cpp1
-rw-r--r--indra/llui/lltransutil.cpp13
-rw-r--r--indra/llui/llui.cpp87
-rw-r--r--indra/llui/llui.h5
-rw-r--r--indra/llui/lluicolortable.cpp18
-rw-r--r--indra/llui/lluictrlfactory.cpp55
-rw-r--r--indra/llui/lluictrlfactory.h31
-rw-r--r--indra/llui/llview.cpp12
29 files changed, 469 insertions, 326 deletions
diff --git a/indra/llui/CMakeLists.txt b/indra/llui/CMakeLists.txt
index 80cec6c9f3..ccc7aa8cec 100644
--- a/indra/llui/CMakeLists.txt
+++ b/indra/llui/CMakeLists.txt
@@ -47,6 +47,7 @@ set(llui_SOURCE_FILES
lleditmenuhandler.cpp
llf32uictrl.cpp
llfiltereditor.cpp
+ llflashtimer.cpp
llflatlistview.cpp
llfloater.cpp
llfloaterreg.cpp
@@ -153,6 +154,7 @@ set(llui_HEADER_FILES
lleditmenuhandler.h
llf32uictrl.h
llfiltereditor.h
+ llflashtimer.h
llflatlistview.h
llfloater.h
llfloaterreg.h
diff --git a/indra/llui/llbutton.cpp b/indra/llui/llbutton.cpp
index 705fe16559..97547208ec 100644
--- a/indra/llui/llbutton.cpp
+++ b/indra/llui/llbutton.cpp
@@ -105,6 +105,7 @@ LLButton::Params::Params()
badge("badge"),
handle_right_mouse("handle_right_mouse"),
held_down_delay("held_down_delay"),
+ button_flash_enable("button_flash_enable", false),
button_flash_count("button_flash_count"),
button_flash_rate("button_flash_rate")
{
@@ -171,9 +172,24 @@ LLButton::LLButton(const LLButton::Params& p)
mHeldDownSignal(NULL),
mUseDrawContextAlpha(p.use_draw_context_alpha),
mHandleRightMouse(p.handle_right_mouse),
- mButtonFlashCount(p.button_flash_count),
- mButtonFlashRate(p.button_flash_rate)
+ mFlashingTimer(NULL)
{
+ if (p.button_flash_enable)
+ {
+ // If optional parameter "p.button_flash_count" is not provided, LLFlashTimer will be
+ // used instead it a "default" value from gSavedSettings.getS32("FlashCount")).
+ // Likewise, missing "p.button_flash_rate" is replaced by gSavedSettings.getF32("FlashPeriod").
+ // Note: flashing should be allowed in settings.xml (boolean key "EnableButtonFlashing").
+ S32 flash_count = p.button_flash_count.isProvided()? p.button_flash_count : 0;
+ F32 flash_rate = p.button_flash_rate.isProvided()? p.button_flash_rate : 0.0;
+ mFlashingTimer = new LLFlashTimer ((LLFlashTimer::callback_t)NULL, flash_count, flash_rate);
+ }
+ else
+ {
+ mButtonFlashCount = p.button_flash_count;
+ mButtonFlashRate = p.button_flash_rate;
+ }
+
static LLUICachedControl<S32> llbutton_orig_h_pad ("UIButtonOrigHPad", 0);
static Params default_params(LLUICtrlFactory::getDefaultParams<LLButton>());
@@ -267,6 +283,11 @@ LLButton::~LLButton()
delete mMouseDownSignal;
delete mMouseUpSignal;
delete mHeldDownSignal;
+
+ if (mFlashingTimer)
+ {
+ delete mFlashingTimer;
+ }
}
// HACK: Committing a button is the same as instantly clicking it.
@@ -591,20 +612,28 @@ void LLButton::draw()
{
static LLCachedControl<bool> sEnableButtonFlashing(*LLUI::sSettingGroups["config"], "EnableButtonFlashing", true);
F32 alpha = mUseDrawContextAlpha ? getDrawContext().mAlpha : getCurrentTransparency();
- bool flash = FALSE;
- if( mFlashing)
+ bool flash = false;
+ if (mFlashingTimer)
+ {
+ mFlashing = mFlashingTimer->isFlashingInProgress();
+ flash = mFlashing && (!sEnableButtonFlashing || mFlashingTimer->isCurrentlyHighlighted());
+ }
+ else
{
- if ( sEnableButtonFlashing)
+ if(mFlashing)
{
- F32 elapsed = mFlashingTimer.getElapsedTimeF32();
- S32 flash_count = S32(elapsed * mButtonFlashRate * 2.f);
- // flash on or off?
- flash = (flash_count % 2 == 0) || flash_count > S32((F32)mButtonFlashCount * 2.f);
- }
- else
- { // otherwise just highlight button in flash color
- flash = true;
+ if ( sEnableButtonFlashing)
+ {
+ F32 elapsed = mFrameTimer.getElapsedTimeF32();
+ S32 flash_count = S32(elapsed * mButtonFlashRate * 2.f);
+ // flash on or off?
+ flash = (flash_count % 2 == 0) || flash_count > S32((F32)mButtonFlashCount * 2.f);
+ }
+ else
+ { // otherwise just highlight button in flash color
+ flash = true;
+ }
}
}
@@ -949,16 +978,26 @@ void LLButton::setToggleState(BOOL b)
}
}
-void LLButton::setFlashing( BOOL b )
+void LLButton::setFlashing( bool b )
{
- if ((bool)b != mFlashing)
+ if (mFlashingTimer)
+ {
+ if (b)
+ {
+ mFlashingTimer->startFlashing();
+ }
+ else
+ {
+ mFlashingTimer->stopFlashing();
+ }
+ }
+ else if (b != mFlashing)
{
mFlashing = b;
- mFlashingTimer.reset();
+ mFrameTimer.reset();
}
}
-
BOOL LLButton::toggleState()
{
bool flipped = ! getToggleState();
diff --git a/indra/llui/llbutton.h b/indra/llui/llbutton.h
index deaa0823c6..060db59a8a 100644
--- a/indra/llui/llbutton.h
+++ b/indra/llui/llbutton.h
@@ -30,6 +30,7 @@
#include "lluuid.h"
#include "llbadgeowner.h"
#include "llcontrol.h"
+#include "llflashtimer.h"
#include "lluictrl.h"
#include "v4color.h"
#include "llframetimer.h"
@@ -133,6 +134,7 @@ public:
Optional<bool> handle_right_mouse;
+ Optional<bool> button_flash_enable;
Optional<S32> button_flash_count;
Optional<F32> button_flash_rate;
@@ -199,8 +201,9 @@ public:
void setToggleState(BOOL b);
void setHighlight(bool b);
- void setFlashing( BOOL b );
+ void setFlashing( bool b );
BOOL getFlashing() const { return mFlashing; }
+ LLFlashTimer* getFlashTimer() {return mFlashingTimer;}
void setHAlign( LLFontGL::HAlign align ) { mHAlign = align; }
LLFontGL::HAlign getHAlign() const { return mHAlign; }
@@ -373,7 +376,8 @@ protected:
bool mForcePressedState;
bool mDisplayPressedState;
- LLFrameTimer mFlashingTimer;
+ LLFrameTimer mFrameTimer;
+ LLFlashTimer * mFlashingTimer;
bool mHandleRightMouse;
};
diff --git a/indra/llui/llcombobox.cpp b/indra/llui/llcombobox.cpp
index 806d2ef3f6..41e5d74042 100644
--- a/indra/llui/llcombobox.cpp
+++ b/indra/llui/llcombobox.cpp
@@ -563,8 +563,7 @@ void LLComboBox::showList()
S32 min_width = getRect().getWidth();
S32 max_width = llmax(min_width, MAX_COMBO_WIDTH);
// make sure we have up to date content width metrics
- mList->calcColumnWidths();
- S32 list_width = llclamp(mList->getMaxContentWidth(), min_width, max_width);
+ S32 list_width = llclamp(mList->calcMaxContentWidth(), min_width, max_width);
if (mListPosition == BELOW)
{
diff --git a/indra/llui/llcommandmanager.cpp b/indra/llui/llcommandmanager.cpp
index 0e2f3f1961..625fb8e870 100644
--- a/indra/llui/llcommandmanager.cpp
+++ b/indra/llui/llcommandmanager.cpp
@@ -63,6 +63,7 @@ LLCommand::Params::Params()
, is_running_parameters("is_running_parameters")
, is_starting_function("is_starting_function")
, is_starting_parameters("is_starting_parameters")
+ , is_flashing_allowed("is_flashing_allowed", false)
{
}
@@ -83,6 +84,7 @@ LLCommand::LLCommand(const LLCommand::Params& p)
, mIsRunningParameters(p.is_running_parameters)
, mIsStartingFunction(p.is_starting_function)
, mIsStartingParameters(p.is_starting_parameters)
+ , mIsFlashingAllowed(p.is_flashing_allowed)
{
}
diff --git a/indra/llui/llcommandmanager.h b/indra/llui/llcommandmanager.h
index a7276a48aa..ff5a8a3257 100644
--- a/indra/llui/llcommandmanager.h
+++ b/indra/llui/llcommandmanager.h
@@ -111,6 +111,8 @@ public:
Optional<std::string> is_starting_function;
Optional<LLSD> is_starting_parameters;
+ Optional<bool> is_flashing_allowed;
+
Params();
};
@@ -138,6 +140,8 @@ public:
const std::string& isStartingFunctionName() const { return mIsStartingFunction; }
const LLSD& isStartingParameters() const { return mIsStartingParameters; }
+ bool isFlashingAllowed() const { return mIsFlashingAllowed; }
+
private:
LLCommandId mIdentifier;
@@ -161,6 +165,8 @@ private:
std::string mIsStartingFunction;
LLSD mIsStartingParameters;
+
+ bool mIsFlashingAllowed;
};
diff --git a/indra/llui/llcontainerview.cpp b/indra/llui/llcontainerview.cpp
index e08ccb0b78..e08ccb0b78 100755..100644
--- a/indra/llui/llcontainerview.cpp
+++ b/indra/llui/llcontainerview.cpp
diff --git a/indra/llui/llflashtimer.cpp b/indra/llui/llflashtimer.cpp
new file mode 100644
index 0000000000..de7a4ab265
--- /dev/null
+++ b/indra/llui/llflashtimer.cpp
@@ -0,0 +1,93 @@
+/**
+ * @file llflashtimer.cpp
+ * @brief LLFlashTimer class implementation
+ *
+ * $LicenseInfo:firstyear=2002&license=viewerlgpl$
+ * Second Life Viewer Source Code
+ * Copyright (C) 2012, Linden Research, Inc.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation;
+ * version 2.1 of the License only.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
+ *
+ * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA
+ * $/LicenseInfo$
+ */
+#include "../newview/llviewerprecompiledheaders.h"
+
+#include "llflashtimer.h"
+#include "../newview/llviewercontrol.h"
+#include "lleventtimer.h"
+
+LLFlashTimer::LLFlashTimer(callback_t cb, S32 count, F32 period)
+ : LLEventTimer(period)
+ , mCallback(cb)
+ , mCurrentTickCount(0)
+ , mIsFlashingInProgress(false)
+ , mIsCurrentlyHighlighted(false)
+{
+ mEventTimer.stop();
+
+ // By default use settings from settings.xml to be able change them via Debug settings. See EXT-5973.
+ // Due to Timer is implemented as derived class from EventTimer it is impossible to change period
+ // in runtime. So, both settings are made as required restart.
+ mFlashCount = 2 * ((count > 0) ? count : gSavedSettings.getS32("FlashCount"));
+ if (mPeriod <= 0)
+ {
+ mPeriod = gSavedSettings.getF32("FlashPeriod");
+ }
+}
+
+BOOL LLFlashTimer::tick()
+{
+ mIsCurrentlyHighlighted = !mIsCurrentlyHighlighted;
+
+ if (mCallback)
+ {
+ mCallback(mIsCurrentlyHighlighted);
+ }
+
+ if (++mCurrentTickCount >= mFlashCount)
+ {
+ stopFlashing();
+ }
+
+ return FALSE;
+}
+
+void LLFlashTimer::startFlashing()
+{
+ mIsFlashingInProgress = true;
+ mIsCurrentlyHighlighted = true;
+ mEventTimer.start();
+}
+
+void LLFlashTimer::stopFlashing()
+{
+ mEventTimer.stop();
+ mIsFlashingInProgress = false;
+ mIsCurrentlyHighlighted = false;
+ mCurrentTickCount = 0;
+}
+
+bool LLFlashTimer::isFlashingInProgress()
+{
+ return mIsFlashingInProgress;
+}
+
+bool LLFlashTimer::isCurrentlyHighlighted()
+{
+ return mIsCurrentlyHighlighted;
+}
+
+
diff --git a/indra/llui/llflashtimer.h b/indra/llui/llflashtimer.h
new file mode 100644
index 0000000000..5c8860b097
--- /dev/null
+++ b/indra/llui/llflashtimer.h
@@ -0,0 +1,67 @@
+/**
+ * @file llflashtimer.h
+ * @brief LLFlashTimer class implementation
+ *
+ * $LicenseInfo:firstyear=2002&license=viewerlgpl$
+ * Second Life Viewer Source Code
+ * Copyright (C) 2012, Linden Research, Inc.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation;
+ * version 2.1 of the License only.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
+ *
+ * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA
+ * $/LicenseInfo$
+ */
+
+#ifndef LL_FLASHTIMER_H
+#define LL_FLASHTIMER_H
+
+#include "lleventtimer.h"
+
+class LLFlashTimer : public LLEventTimer
+{
+public:
+
+ typedef boost::function<void (bool)> callback_t;
+
+ /**
+ * Constructor.
+ *
+ * @param count - how many times callback should be called (twice to not change original state)
+ * @param period - how frequently callback should be called
+ * @param cb - callback to be called each tick
+ */
+ LLFlashTimer(callback_t cb = NULL, S32 count = 0, F32 period = 0.0);
+ ~LLFlashTimer() {};
+
+ /*virtual*/ BOOL tick();
+
+ void startFlashing();
+ void stopFlashing();
+
+ bool isFlashingInProgress();
+ bool isCurrentlyHighlighted();
+
+private:
+ callback_t mCallback;
+ /**
+ * How many times parent will blink.
+ */
+ S32 mFlashCount;
+ S32 mCurrentTickCount;
+ bool mIsCurrentlyHighlighted;
+ bool mIsFlashingInProgress;
+};
+
+#endif /* LL_FLASHTIMER_H */
diff --git a/indra/llui/llfloater.cpp b/indra/llui/llfloater.cpp
index ada2bde55e..8f9be5285d 100644
--- a/indra/llui/llfloater.cpp
+++ b/indra/llui/llfloater.cpp
@@ -3276,24 +3276,14 @@ bool LLFloater::isVisible(const LLFloater* floater)
static LLFastTimer::DeclareTimer FTM_BUILD_FLOATERS("Build Floaters");
-bool LLFloater::buildFromFile(const std::string& filename, LLXMLNodePtr output_node)
+bool LLFloater::buildFromFile(const std::string& filename)
{
LLFastTimer timer(FTM_BUILD_FLOATERS);
LLXMLNodePtr root;
- //if exporting, only load the language being exported,
- //instead of layering localized version on top of english
- if (output_node)
- {
- if (!LLUICtrlFactory::getLocalizedXMLNode(filename, root))
- {
- llwarns << "Couldn't parse floater from: " << LLUI::getLocalizedSkinPath() + gDirUtilp->getDirDelimiter() + filename << llendl;
- return false;
- }
- }
- else if (!LLUICtrlFactory::getLayeredXMLNode(filename, root))
+ if (!LLUICtrlFactory::getLayeredXMLNode(filename, root))
{
- llwarns << "Couldn't parse floater from: " << LLUI::getSkinPath() + gDirUtilp->getDirDelimiter() + filename << llendl;
+ llwarns << "Couldn't find (or parse) floater from: " << filename << llendl;
return false;
}
@@ -3318,7 +3308,7 @@ bool LLFloater::buildFromFile(const std::string& filename, LLXMLNodePtr output_n
getCommitCallbackRegistrar().pushScope();
getEnableCallbackRegistrar().pushScope();
- res = initFloaterXML(root, getParent(), filename, output_node);
+ res = initFloaterXML(root, getParent(), filename, NULL);
setXMLFilename(filename);
diff --git a/indra/llui/llfloater.h b/indra/llui/llfloater.h
index ca0710cdc1..a657538eb7 100644
--- a/indra/llui/llfloater.h
+++ b/indra/llui/llfloater.h
@@ -202,7 +202,7 @@ public:
// Don't export top/left for rect, only height/width
static void setupParamsForExport(Params& p, LLView* parent);
- bool buildFromFile(const std::string &filename, LLXMLNodePtr output_node = NULL);
+ bool buildFromFile(const std::string &filename);
boost::signals2::connection setMinimizeCallback( const commit_signal_t::slot_type& cb );
boost::signals2::connection setOpenCallback( const commit_signal_t::slot_type& cb );
diff --git a/indra/llui/llfloaterreg.cpp b/indra/llui/llfloaterreg.cpp
index 9115eb7174..306caf2b91 100644
--- a/indra/llui/llfloaterreg.cpp
+++ b/indra/llui/llfloaterreg.cpp
@@ -154,7 +154,7 @@ LLFloater* LLFloaterReg::getInstance(const std::string& name, const LLSD& key)
llwarns << "Failed to build floater type: '" << name << "'." << llendl;
return NULL;
}
- bool success = res->buildFromFile(xui_file, NULL);
+ bool success = res->buildFromFile(xui_file);
if (!success)
{
llwarns << "Failed to build floater type: '" << name << "'." << llendl;
diff --git a/indra/llui/llfolderviewitem.cpp b/indra/llui/llfolderviewitem.cpp
index 822534ffcf..89c7e0d14a 100755
--- a/indra/llui/llfolderviewitem.cpp
+++ b/indra/llui/llfolderviewitem.cpp
@@ -23,9 +23,12 @@
* Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA
* $/LicenseInfo$
*/
+#include "../newview/llviewerprecompiledheaders.h"
+
+#include "llflashtimer.h"
+
#include "linden_common.h"
#include "llfolderviewitem.h"
-
#include "llfolderview.h"
#include "llfolderviewmodel.h"
#include "llpanel.h"
@@ -160,17 +163,18 @@ LLFolderViewItem::LLFolderViewItem(const LLFolderViewItem::Params& p)
}
}
+// Destroys the object
+LLFolderViewItem::~LLFolderViewItem()
+{
+ mViewModelItem = NULL;
+}
+
BOOL LLFolderViewItem::postBuild()
{
refresh();
return TRUE;
}
-// Destroys the object
-LLFolderViewItem::~LLFolderViewItem( void )
-{
- mViewModelItem = NULL;
-}
LLFolderView* LLFolderViewItem::getRoot()
{
@@ -664,6 +668,16 @@ void LLFolderViewItem::drawOpenFolderArrow(const Params& default_params, const L
}
}
+/*virtual*/ bool LLFolderViewItem::isHighlightAllowed()
+{
+ return mIsSelected;
+}
+
+/*virtual*/ bool LLFolderViewItem::isHighlightActive()
+{
+ return mIsCurSelection;
+}
+
void LLFolderViewItem::drawHighlight(const BOOL showContent, const BOOL hasKeyboardFocus, const LLUIColor &bgColor,
const LLUIColor &focusOutlineColor, const LLUIColor &mouseOverColor)
{
@@ -677,11 +691,12 @@ void LLFolderViewItem::drawHighlight(const BOOL showContent, const BOOL hasKeybo
const bool folder_open = (getRect().getHeight() > mItemHeight + 4);
const S32 FOCUS_LEFT = 1;
- if (mIsSelected) // always render "current" item. Only render other selected items if mShowSingleSelection is FALSE
+ if (isHighlightAllowed()) // always render "current" item (only render other selected items if
+ // mShowSingleSelection is FALSE) or flashing item
{
gGL.getTexUnit(0)->unbind(LLTexUnit::TT_TEXTURE);
LLColor4 bg_color = bgColor;
- if (!mIsCurSelection)
+ if (!isHighlightActive())
{
// do time-based fade of extra objects
F32 fade_time = (getRoot() ? getRoot()->getSelectionFadeElapsedTime() : 0.0f);
@@ -696,11 +711,16 @@ void LLFolderViewItem::drawHighlight(const BOOL showContent, const BOOL hasKeybo
bg_color.mV[VALPHA] = clamp_rescale(fade_time, 0.f, 0.4f, 0.f, bg_color.mV[VALPHA]);
}
}
- gl_rect_2d(FOCUS_LEFT,
- focus_top,
- getRect().getWidth() - 2,
- focus_bottom,
- bg_color, hasKeyboardFocus);
+
+ if (!isHighlightAllowed() || isHighlightActive())
+ {
+ gl_rect_2d(FOCUS_LEFT,
+ focus_top,
+ getRect().getWidth() - 2,
+ focus_bottom,
+ bg_color, hasKeyboardFocus);
+ }
+
if (mIsCurSelection)
{
gl_rect_2d(FOCUS_LEFT,
diff --git a/indra/llui/llfolderviewitem.h b/indra/llui/llfolderviewitem.h
index 152ca242e1..c5d6d26e84 100755
--- a/indra/llui/llfolderviewitem.h
+++ b/indra/llui/llfolderviewitem.h
@@ -26,6 +26,7 @@
#ifndef LLFOLDERVIEWITEM_H
#define LLFOLDERVIEWITEM_H
+#include "llflashtimer.h"
#include "llview.h"
#include "lluiimage.h"
@@ -134,6 +135,8 @@ protected:
// no-op at this level, but reimplemented in derived classes.
virtual void addItem(LLFolderViewItem*) { }
virtual void addFolder(LLFolderViewFolder*) { }
+ virtual bool isHighlightAllowed();
+ virtual bool isHighlightActive();
static LLFontGL* getLabelFontForStyle(U8 style);
@@ -272,7 +275,6 @@ public:
private:
static std::map<U8, LLFontGL*> sFonts; // map of styles to fonts
-
};
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
diff --git a/indra/llui/llnotifications.cpp b/indra/llui/llnotifications.cpp
index 9618c002f5..66144671c9 100644
--- a/indra/llui/llnotifications.cpp
+++ b/indra/llui/llnotifications.cpp
@@ -1443,25 +1443,19 @@ void addPathIfExists(const std::string& new_path, std::vector<std::string>& path
bool LLNotifications::loadTemplates()
{
llinfos << "Reading notifications template" << llendl;
- std::vector<std::string> search_paths;
-
- std::string skin_relative_path = gDirUtilp->getDirDelimiter() + LLUI::getSkinPath() + gDirUtilp->getDirDelimiter() + "notifications.xml";
- std::string localized_skin_relative_path = gDirUtilp->getDirDelimiter() + LLUI::getLocalizedSkinPath() + gDirUtilp->getDirDelimiter() + "notifications.xml";
-
- addPathIfExists(gDirUtilp->getDefaultSkinDir() + skin_relative_path, search_paths);
- addPathIfExists(gDirUtilp->getDefaultSkinDir() + localized_skin_relative_path, search_paths);
- addPathIfExists(gDirUtilp->getSkinDir() + skin_relative_path, search_paths);
- addPathIfExists(gDirUtilp->getSkinDir() + localized_skin_relative_path, search_paths);
- addPathIfExists(gDirUtilp->getUserSkinDir() + skin_relative_path, search_paths);
- addPathIfExists(gDirUtilp->getUserSkinDir() + localized_skin_relative_path, search_paths);
+ // Passing findSkinnedFilenames(constraint=LLDir::ALL_SKINS) makes it
+ // output all relevant pathnames instead of just the ones from the most
+ // specific skin.
+ std::vector<std::string> search_paths =
+ gDirUtilp->findSkinnedFilenames(LLDir::XUI, "notifications.xml", LLDir::ALL_SKINS);
std::string base_filename = search_paths.front();
LLXMLNodePtr root;
BOOL success = LLXMLNode::getLayeredXMLNode(root, search_paths);
-
+
if (!success || root.isNull() || !root->hasName( "notifications" ))
{
- llerrs << "Problem reading UI Notifications file: " << base_filename << llendl;
+ llerrs << "Problem reading XML from UI Notifications file: " << base_filename << llendl;
return false;
}
@@ -1471,7 +1465,7 @@ bool LLNotifications::loadTemplates()
if(!params.validateBlock())
{
- llerrs << "Problem reading UI Notifications file: " << base_filename << llendl;
+ llerrs << "Problem reading XUI from UI Notifications file: " << base_filename << llendl;
return false;
}
@@ -1527,7 +1521,9 @@ bool LLNotifications::loadTemplates()
bool LLNotifications::loadVisibilityRules()
{
const std::string xml_filename = "notification_visibility.xml";
- std::string full_filename = gDirUtilp->findSkinnedFilename(LLUI::getXUIPaths().front(), xml_filename);
+ // Note that here we're looking for the "en" version, the default
+ // language, rather than the most localized version of this file.
+ std::string full_filename = gDirUtilp->findSkinnedFilenameBaseLang(LLDir::XUI, xml_filename);
LLNotificationVisibilityRule::Rules params;
LLSimpleXUIParser parser;
diff --git a/indra/llui/llpanel.cpp b/indra/llui/llpanel.cpp
index 00318cec6b..67472ad166 100644
--- a/indra/llui/llpanel.cpp
+++ b/indra/llui/llpanel.cpp
@@ -968,25 +968,15 @@ static LLFastTimer::DeclareTimer FTM_BUILD_PANELS("Build Panels");
//-----------------------------------------------------------------------------
// buildPanel()
//-----------------------------------------------------------------------------
-BOOL LLPanel::buildFromFile(const std::string& filename, LLXMLNodePtr output_node, const LLPanel::Params& default_params)
+BOOL LLPanel::buildFromFile(const std::string& filename, const LLPanel::Params& default_params)
{
LLFastTimer timer(FTM_BUILD_PANELS);
BOOL didPost = FALSE;
LLXMLNodePtr root;
- //if exporting, only load the language being exported,
- //instead of layering localized version on top of english
- if (output_node)
- {
- if (!LLUICtrlFactory::getLocalizedXMLNode(filename, root))
- {
- llwarns << "Couldn't parse panel from: " << LLUI::getLocalizedSkinPath() + gDirUtilp->getDirDelimiter() + filename << llendl;
- return didPost;
- }
- }
- else if (!LLUICtrlFactory::getLayeredXMLNode(filename, root))
+ if (!LLUICtrlFactory::getLayeredXMLNode(filename, root))
{
- llwarns << "Couldn't parse panel from: " << LLUI::getSkinPath() + gDirUtilp->getDirDelimiter() + filename << llendl;
+ llwarns << "Couldn't parse panel from: " << filename << llendl;
return didPost;
}
@@ -1010,7 +1000,7 @@ BOOL LLPanel::buildFromFile(const std::string& filename, LLXMLNodePtr output_nod
getCommitCallbackRegistrar().pushScope();
getEnableCallbackRegistrar().pushScope();
- didPost = initPanelXML(root, NULL, output_node, default_params);
+ didPost = initPanelXML(root, NULL, NULL, default_params);
getCommitCallbackRegistrar().popScope();
getEnableCallbackRegistrar().popScope();
diff --git a/indra/llui/llpanel.h b/indra/llui/llpanel.h
index f620201020..e63b41f97c 100644
--- a/indra/llui/llpanel.h
+++ b/indra/llui/llpanel.h
@@ -105,7 +105,7 @@ protected:
LLPanel(const LLPanel::Params& params = getDefaultParams());
public:
- BOOL buildFromFile(const std::string &filename, LLXMLNodePtr output_node = NULL, const LLPanel::Params&default_params = getDefaultParams());
+ BOOL buildFromFile(const std::string &filename, const LLPanel::Params& default_params = getDefaultParams());
static LLPanel* createFactoryPanel(const std::string& name);
diff --git a/indra/llui/llscrolllistcolumn.cpp b/indra/llui/llscrolllistcolumn.cpp
index 07a6dfaa10..af124d9826 100644
--- a/indra/llui/llscrolllistcolumn.cpp
+++ b/indra/llui/llscrolllistcolumn.cpp
@@ -98,6 +98,7 @@ BOOL LLScrollColumnHeader::handleDoubleClick(S32 x, S32 y, MASK mask)
if (canResize() && mResizeBar->getRect().pointInRect(x, y))
{
// reshape column to max content width
+ mColumn->mParentCtrl->calcMaxContentWidth();
LLRect column_rect = getRect();
column_rect.mRight = column_rect.mLeft + mColumn->mMaxContentWidth;
setShape(column_rect, true);
@@ -127,6 +128,8 @@ LLView* LLScrollColumnHeader::findSnapEdge(S32& new_edge_val, const LLCoordGL& m
LLRect snap_rect = getSnapRect();
+ mColumn->mParentCtrl->calcMaxContentWidth();
+
S32 snap_delta = mColumn->mMaxContentWidth - snap_rect.getWidth();
// x coord growing means column growing, so same signs mean we're going in right direction
diff --git a/indra/llui/llscrolllistctrl.cpp b/indra/llui/llscrolllistctrl.cpp
index b3499693dd..3e0653e9a4 100644
--- a/indra/llui/llscrolllistctrl.cpp
+++ b/indra/llui/llscrolllistctrl.cpp
@@ -35,6 +35,7 @@
#include "llboost.h"
//#include "indra_constants.h"
+#include "llavatarnamecache.h"
#include "llcheckboxctrl.h"
#include "llclipboard.h"
#include "llfocusmgr.h"
@@ -158,15 +159,14 @@ LLScrollListCtrl::LLScrollListCtrl(const LLScrollListCtrl::Params& p)
mMouseWheelOpaque(p.mouse_wheel_opaque),
mPageLines(p.page_lines),
mMaxSelectable(0),
- mAllowKeyboardMovement(TRUE),
+ mAllowKeyboardMovement(true),
mCommitOnKeyboardMovement(p.commit_on_keyboard_movement),
- mCommitOnSelectionChange(FALSE),
- mSelectionChanged(FALSE),
- mNeedsScroll(FALSE),
- mCanSelect(TRUE),
- mColumnsDirty(FALSE),
+ mCommitOnSelectionChange(false),
+ mSelectionChanged(false),
+ mNeedsScroll(false),
+ mCanSelect(true),
+ mColumnsDirty(false),
mMaxItemCount(INT_MAX),
- mMaxContentWidth(0),
mBorderThickness( 2 ),
mOnDoubleClickCallback( NULL ),
mOnMaximumSelectCallback( NULL ),
@@ -180,7 +180,7 @@ LLScrollListCtrl::LLScrollListCtrl(const LLScrollListCtrl::Params& p)
mTotalStaticColumnWidth(0),
mTotalColumnPadding(0),
mSorted(false),
- mDirty(FALSE),
+ mDirty(false),
mOriginalSelection(-1),
mLastSelected(NULL),
mHeadingHeight(p.heading_height),
@@ -356,7 +356,7 @@ void LLScrollListCtrl::clearRows()
mScrollLines = 0;
mLastSelected = NULL;
updateLayout();
- mDirty = FALSE;
+ mDirty = false;
}
@@ -591,13 +591,11 @@ BOOL LLScrollListCtrl::addItem( LLScrollListItem* item, EAddPosition pos, BOOL r
// NOTE: This is *very* expensive for large lists, especially when we are dirtying the list every frame
// while receiving a long list of names.
// *TODO: Use bookkeeping to make this an incramental cost with item additions
-void LLScrollListCtrl::calcColumnWidths()
+S32 LLScrollListCtrl::calcMaxContentWidth()
{
const S32 HEADING_TEXT_PADDING = 25;
const S32 COLUMN_TEXT_PADDING = 10;
- mMaxContentWidth = 0;
-
S32 max_item_width = 0;
ordered_columns_t::iterator column_itor;
@@ -606,6 +604,35 @@ void LLScrollListCtrl::calcColumnWidths()
LLScrollListColumn* column = *column_itor;
if (!column) continue;
+ if (mColumnWidthsDirty)
+ {
+ mColumnWidthsDirty = false;
+ // update max content width for this column, by looking at all items
+ column->mMaxContentWidth = column->mHeader ? LLFontGL::getFontSansSerifSmall()->getWidth(column->mLabel) + mColumnPadding + HEADING_TEXT_PADDING : 0;
+ item_list::iterator iter;
+ for (iter = mItemList.begin(); iter != mItemList.end(); iter++)
+ {
+ LLScrollListCell* cellp = (*iter)->getColumn(column->mIndex);
+ if (!cellp) continue;
+
+ column->mMaxContentWidth = llmax(LLFontGL::getFontSansSerifSmall()->getWidth(cellp->getValue().asString()) + mColumnPadding + COLUMN_TEXT_PADDING, column->mMaxContentWidth);
+ }
+ }
+ max_item_width += column->mMaxContentWidth;
+ }
+
+ return max_item_width;
+}
+
+bool LLScrollListCtrl::updateColumnWidths()
+{
+ bool width_changed = false;
+ ordered_columns_t::iterator column_itor;
+ for (column_itor = mColumnsIndexed.begin(); column_itor != mColumnsIndexed.end(); ++column_itor)
+ {
+ LLScrollListColumn* column = *column_itor;
+ if (!column) continue;
+
// update column width
S32 new_width = column->getWidth();
if (column->mRelWidth >= 0)
@@ -617,23 +644,13 @@ void LLScrollListCtrl::calcColumnWidths()
new_width = (mItemListRect.getWidth() - mTotalStaticColumnWidth - mTotalColumnPadding) / mNumDynamicWidthColumns;
}
- column->setWidth(new_width);
-
- // update max content width for this column, by looking at all items
- column->mMaxContentWidth = column->mHeader ? LLFontGL::getFontSansSerifSmall()->getWidth(column->mLabel) + mColumnPadding + HEADING_TEXT_PADDING : 0;
- item_list::iterator iter;
- for (iter = mItemList.begin(); iter != mItemList.end(); iter++)
+ if (column->getWidth() != new_width)
{
- LLScrollListCell* cellp = (*iter)->getColumn(column->mIndex);
- if (!cellp) continue;
-
- column->mMaxContentWidth = llmax(LLFontGL::getFontSansSerifSmall()->getWidth(cellp->getValue().asString()) + mColumnPadding + COLUMN_TEXT_PADDING, column->mMaxContentWidth);
+ column->setWidth(new_width);
+ width_changed = true;
}
-
- max_item_width += column->mMaxContentWidth;
}
-
- mMaxContentWidth = max_item_width;
+ return width_changed;
}
const S32 SCROLL_LIST_ROW_PAD = 2;
@@ -669,7 +686,12 @@ void LLScrollListCtrl::updateLineHeightInsert(LLScrollListItem* itemp)
void LLScrollListCtrl::updateColumns()
{
- calcColumnWidths();
+ if (!mColumnsDirty)
+ return;
+
+ mColumnsDirty = false;
+
+ bool columns_changed_width = updateColumnWidths();
// update column headers
std::vector<LLScrollListColumn*>::iterator column_ordered_it;
@@ -718,20 +740,22 @@ void LLScrollListCtrl::updateColumns()
}
// propagate column widths to individual cells
- item_list::iterator iter;
- for (iter = mItemList.begin(); iter != mItemList.end(); iter++)
+ if (columns_changed_width)
{
- LLScrollListItem *itemp = *iter;
- S32 num_cols = itemp->getNumColumns();
- S32 i = 0;
- for (LLScrollListCell* cell = itemp->getColumn(i); i < num_cols; cell = itemp->getColumn(++i))
+ item_list::iterator iter;
+ for (iter = mItemList.begin(); iter != mItemList.end(); iter++)
{
- if (i >= (S32)mColumnsIndexed.size()) break;
+ LLScrollListItem *itemp = *iter;
+ S32 num_cols = itemp->getNumColumns();
+ S32 i = 0;
+ for (LLScrollListCell* cell = itemp->getColumn(i); i < num_cols; cell = itemp->getColumn(++i))
+ {
+ if (i >= (S32)mColumnsIndexed.size()) break;
- cell->setWidth(mColumnsIndexed[i]->getWidth());
+ cell->setWidth(mColumnsIndexed[i]->getWidth());
+ }
}
}
-
}
void LLScrollListCtrl::setHeadingHeight(S32 heading_height)
@@ -772,7 +796,7 @@ BOOL LLScrollListCtrl::selectFirstItem()
{
deselectItem(itemp);
}
- first_item = FALSE;
+ first_item = false;
}
if (mCommitOnSelectionChange)
{
@@ -1406,17 +1430,23 @@ void LLScrollListCtrl::drawItems()
S32 cur_y = y;
- S32 line = 0;
S32 max_columns = 0;
LLColor4 highlight_color = LLColor4::white;
static LLUICachedControl<F32> type_ahead_timeout ("TypeAheadTimeout", 0);
highlight_color.mV[VALPHA] = clamp_rescale(mSearchTimer.getElapsedTimeF32(), type_ahead_timeout * 0.7f, type_ahead_timeout, 0.4f, 0.f);
+ S32 first_line = mScrollLines;
+ S32 last_line = llmin((S32)mItemList.size() - 1, mScrollLines + getLinesPerPage());
+
+ if (first_line >= mItemList.size())
+ {
+ return;
+ }
item_list::iterator iter;
- for (iter = mItemList.begin(); iter != mItemList.end(); iter++)
+ for (S32 line = first_line; line <= last_line; line++)
{
- LLScrollListItem* item = *iter;
+ LLScrollListItem* item = mItemList[line];
item_rect.setOriginAndSize(
x,
@@ -1480,7 +1510,6 @@ void LLScrollListCtrl::drawItems()
cur_y -= mLineHeight;
}
- line++;
}
}
}
@@ -1496,7 +1525,7 @@ void LLScrollListCtrl::draw()
if (mNeedsScroll)
{
scrollToShowSelected();
- mNeedsScroll = FALSE;
+ mNeedsScroll = false;
}
LLRect background(0, getRect().getHeight(), getRect().getWidth(), 0);
// Draw background
@@ -1507,11 +1536,7 @@ void LLScrollListCtrl::draw()
gl_rect_2d(background, getEnabled() ? mBgWriteableColor.get() % alpha : mBgReadOnlyColor.get() % alpha );
}
- if (mColumnsDirty)
- {
- updateColumns();
- mColumnsDirty = FALSE;
- }
+ updateColumns();
getChildView("comment_text")->setVisible(mItemList.empty());
@@ -1719,7 +1744,7 @@ BOOL LLScrollListCtrl::handleMouseDown(S32 x, S32 y, MASK mask)
setFocus(TRUE);
// clear selection changed flag because user is starting a selection operation
- mSelectionChanged = FALSE;
+ mSelectionChanged = false;
handleClick(x, y, mask);
}
@@ -1737,15 +1762,15 @@ BOOL LLScrollListCtrl::handleMouseUp(S32 x, S32 y, MASK mask)
if(mask == MASK_NONE)
{
selectItemAt(x, y, mask);
- mNeedsScroll = TRUE;
+ mNeedsScroll = true;
}
}
// always commit when mouse operation is completed inside list
if (mItemListRect.pointInRect(x,y))
{
- mDirty |= mSelectionChanged;
- mSelectionChanged = FALSE;
+ mDirty = mDirty || mSelectionChanged;
+ mSelectionChanged = false;
onCommit();
}
@@ -1805,7 +1830,9 @@ void LLScrollListCtrl::copyNameToClipboard(std::string id, bool is_group)
}
else
{
- gCacheName->getFullName(LLUUID(id), name);
+ LLAvatarName av_name;
+ LLAvatarNameCache::get(LLUUID(id), &av_name);
+ name = av_name.getLegacyName();
}
LLUrlAction::copyURLToClipboard(name);
}
@@ -1859,7 +1886,7 @@ BOOL LLScrollListCtrl::handleClick(S32 x, S32 y, MASK mask)
{
selectItemAt(x, y, mask);
gFocusMgr.setMouseCapture(this);
- mNeedsScroll = TRUE;
+ mNeedsScroll = true;
}
// propagate state of cell to rest of selected column
@@ -1888,7 +1915,7 @@ BOOL LLScrollListCtrl::handleClick(S32 x, S32 y, MASK mask)
// treat this as a normal single item selection
selectItemAt(x, y, mask);
gFocusMgr.setMouseCapture(this);
- mNeedsScroll = TRUE;
+ mNeedsScroll = true;
// do not eat click (allow double click callback)
return FALSE;
}
@@ -1994,7 +2021,7 @@ BOOL LLScrollListCtrl::handleHover(S32 x,S32 y,MASK mask)
if(mask == MASK_NONE)
{
selectItemAt(x, y, mask);
- mNeedsScroll = TRUE;
+ mNeedsScroll = true;
}
}
else
@@ -2041,7 +2068,7 @@ BOOL LLScrollListCtrl::handleKeyHere(KEY key,MASK mask )
{
// commit implicit in call
selectPrevItem(FALSE);
- mNeedsScroll = TRUE;
+ mNeedsScroll = true;
handled = TRUE;
}
break;
@@ -2050,7 +2077,7 @@ BOOL LLScrollListCtrl::handleKeyHere(KEY key,MASK mask )
{
// commit implicit in call
selectNextItem(FALSE);
- mNeedsScroll = TRUE;
+ mNeedsScroll = true;
handled = TRUE;
}
break;
@@ -2058,7 +2085,7 @@ BOOL LLScrollListCtrl::handleKeyHere(KEY key,MASK mask )
if (mAllowKeyboardMovement || hasFocus())
{
selectNthItem(getFirstSelectedIndex() - (mScrollbar->getPageSize() - 1));
- mNeedsScroll = TRUE;
+ mNeedsScroll = true;
if (mCommitOnKeyboardMovement
&& !mCommitOnSelectionChange)
{
@@ -2071,7 +2098,7 @@ BOOL LLScrollListCtrl::handleKeyHere(KEY key,MASK mask )
if (mAllowKeyboardMovement || hasFocus())
{
selectNthItem(getFirstSelectedIndex() + (mScrollbar->getPageSize() - 1));
- mNeedsScroll = TRUE;
+ mNeedsScroll = true;
if (mCommitOnKeyboardMovement
&& !mCommitOnSelectionChange)
{
@@ -2084,7 +2111,7 @@ BOOL LLScrollListCtrl::handleKeyHere(KEY key,MASK mask )
if (mAllowKeyboardMovement || hasFocus())
{
selectFirstItem();
- mNeedsScroll = TRUE;
+ mNeedsScroll = true;
if (mCommitOnKeyboardMovement
&& !mCommitOnSelectionChange)
{
@@ -2097,7 +2124,7 @@ BOOL LLScrollListCtrl::handleKeyHere(KEY key,MASK mask )
if (mAllowKeyboardMovement || hasFocus())
{
selectNthItem(getItemCount() - 1);
- mNeedsScroll = TRUE;
+ mNeedsScroll = true;
if (mCommitOnKeyboardMovement
&& !mCommitOnSelectionChange)
{
@@ -2136,7 +2163,7 @@ BOOL LLScrollListCtrl::handleKeyHere(KEY key,MASK mask )
}
else if (selectItemByPrefix(wstring_to_utf8str(mSearchString), FALSE))
{
- mNeedsScroll = TRUE;
+ mNeedsScroll = true;
// update search string only on successful match
mSearchTimer.reset();
@@ -2177,7 +2204,7 @@ BOOL LLScrollListCtrl::handleUnicodeCharHere(llwchar uni_char)
if (selectItemByPrefix(wstring_to_utf8str(mSearchString + (llwchar)uni_char), FALSE))
{
// update search string only on successful match
- mNeedsScroll = TRUE;
+ mNeedsScroll = true;
mSearchString += uni_char;
mSearchTimer.reset();
@@ -2223,7 +2250,7 @@ BOOL LLScrollListCtrl::handleUnicodeCharHere(llwchar uni_char)
if (item->getEnabled() && LLStringOps::toLower(item_label[0]) == uni_char)
{
selectItem(item);
- mNeedsScroll = TRUE;
+ mNeedsScroll = true;
cellp->highlightText(0, 1);
mSearchTimer.reset();
@@ -2294,7 +2321,7 @@ void LLScrollListCtrl::selectItem(LLScrollListItem* itemp, BOOL select_single_it
}
itemp->setSelected(TRUE);
mLastSelected = itemp;
- mSelectionChanged = TRUE;
+ mSelectionChanged = true;
}
}
@@ -2315,7 +2342,7 @@ void LLScrollListCtrl::deselectItem(LLScrollListItem* itemp)
{
cellp->highlightText(0, 0);
}
- mSelectionChanged = TRUE;
+ mSelectionChanged = true;
}
}
@@ -2323,7 +2350,7 @@ void LLScrollListCtrl::commitIfChanged()
{
if (mSelectionChanged)
{
- mDirty = TRUE;
+ mDirty = true;
mSelectionChanged = FALSE;
onCommit();
}
@@ -2434,7 +2461,8 @@ void LLScrollListCtrl::sortOnce(S32 column, BOOL ascending)
void LLScrollListCtrl::dirtyColumns()
{
- mColumnsDirty = TRUE;
+ mColumnsDirty = true;
+ mColumnWidthsDirty = true;
// need to keep mColumnsIndexed up to date
// just in case someone indexes into it immediately
@@ -3003,7 +3031,7 @@ void LLScrollListCtrl::resetDirty()
void LLScrollListCtrl::onFocusReceived()
{
// forget latent selection changes when getting focus
- mSelectionChanged = FALSE;
+ mSelectionChanged = false;
LLUICtrl::onFocusReceived();
}
diff --git a/indra/llui/llscrolllistctrl.h b/indra/llui/llscrolllistctrl.h
index e83794e173..38450b6313 100644
--- a/indra/llui/llscrolllistctrl.h
+++ b/indra/llui/llscrolllistctrl.h
@@ -343,8 +343,8 @@ public:
static void onClickColumn(void *userdata);
virtual void updateColumns();
- void calcColumnWidths();
- S32 getMaxContentWidth() { return mMaxContentWidth; }
+ S32 calcMaxContentWidth();
+ bool updateColumnWidths();
void setHeadingHeight(S32 heading_height);
/**
@@ -440,16 +440,17 @@ private:
S32 mHeadingHeight; // the height of the column header buttons, if visible
U32 mMaxSelectable;
LLScrollbar* mScrollbar;
- BOOL mAllowMultipleSelection;
- BOOL mAllowKeyboardMovement;
- BOOL mCommitOnKeyboardMovement;
- BOOL mCommitOnSelectionChange;
- BOOL mSelectionChanged;
- BOOL mNeedsScroll;
- BOOL mMouseWheelOpaque;
- BOOL mCanSelect;
- const BOOL mDisplayColumnHeaders;
- BOOL mColumnsDirty;
+ bool mAllowMultipleSelection;
+ bool mAllowKeyboardMovement;
+ bool mCommitOnKeyboardMovement;
+ bool mCommitOnSelectionChange;
+ bool mSelectionChanged;
+ bool mNeedsScroll;
+ bool mMouseWheelOpaque;
+ bool mCanSelect;
+ bool mDisplayColumnHeaders;
+ bool mColumnsDirty;
+ bool mColumnWidthsDirty;
mutable item_list mItemList;
@@ -458,7 +459,6 @@ private:
S32 mMaxItemCount;
LLRect mItemListRect;
- S32 mMaxContentWidth;
S32 mColumnPadding;
BOOL mBackgroundVisible;
@@ -498,7 +498,7 @@ private:
typedef std::map<std::string, LLScrollListColumn*> column_map_t;
column_map_t mColumns;
- BOOL mDirty;
+ bool mDirty;
S32 mOriginalSelection;
ContextMenuType mContextMenuType;
diff --git a/indra/llui/lltabcontainer.cpp b/indra/llui/lltabcontainer.cpp
index c24eb2ee90..3c1dfc1184 100644
--- a/indra/llui/lltabcontainer.cpp
+++ b/indra/llui/lltabcontainer.cpp
@@ -506,8 +506,8 @@ void LLTabContainer::draw()
}
}
- mPrevArrowBtn->setFlashing(FALSE);
- mNextArrowBtn->setFlashing(FALSE);
+ mPrevArrowBtn->setFlashing(false);
+ mNextArrowBtn->setFlashing(false);
}
diff --git a/indra/llui/lltoolbar.cpp b/indra/llui/lltoolbar.cpp
index 81ea0ebf0c..1aa46806c3 100644
--- a/indra/llui/lltoolbar.cpp
+++ b/indra/llui/lltoolbar.cpp
@@ -914,6 +914,7 @@ LLToolBarButton* LLToolBar::createButton(const LLCommandId& id)
button_p.label = LLTrans::getString(commandp->labelRef());
button_p.tool_tip = LLTrans::getString(commandp->tooltipRef());
button_p.image_overlay = LLUI::getUIImage(commandp->icon());
+ button_p.button_flash_enable = commandp->isFlashingAllowed();
button_p.overwriteFrom(mButtonParams[mButtonType]);
LLToolBarButton* button = LLUICtrlFactory::create<LLToolBarButton>(button_p);
diff --git a/indra/llui/lltransutil.cpp b/indra/llui/lltransutil.cpp
index 58fa8a0828..80d079cbc8 100644
--- a/indra/llui/lltransutil.cpp
+++ b/indra/llui/lltransutil.cpp
@@ -31,15 +31,20 @@
#include "lltrans.h"
#include "lluictrlfactory.h"
#include "llxmlnode.h"
-
+#include "lldir.h"
bool LLTransUtil::parseStrings(const std::string& xml_filename, const std::set<std::string>& default_args)
{
LLXMLNodePtr root;
- BOOL success = LLUICtrlFactory::getLayeredXMLNode(xml_filename, root);
+ // Pass LLDir::ALL_SKINS to load a composite of all the individual string
+ // definitions in the default skin and the current skin. This means an
+ // individual skin can provide an xml_filename that overrides only a
+ // subset of the available string definitions; any string definition not
+ // overridden by that skin will be sought in the default skin.
+ bool success = LLUICtrlFactory::getLayeredXMLNode(xml_filename, root, LLDir::ALL_SKINS);
if (!success)
{
- llerrs << "Couldn't load string table" << llendl;
+ llerrs << "Couldn't load string table " << xml_filename << llendl;
return false;
}
@@ -54,7 +59,7 @@ bool LLTransUtil::parseLanguageStrings(const std::string& xml_filename)
if (!success)
{
- llerrs << "Couldn't load string table " << xml_filename << llendl;
+ llerrs << "Couldn't load localization table " << xml_filename << llendl;
return false;
}
diff --git a/indra/llui/llui.cpp b/indra/llui/llui.cpp
index 41a948e545..ee09625890 100644
--- a/indra/llui/llui.cpp
+++ b/indra/llui/llui.cpp
@@ -1824,88 +1824,37 @@ struct Paths : public LLInitParam::Block<Paths>
{}
};
-//static
-void LLUI::setupPaths()
-{
- std::string filename = gDirUtilp->getExpandedFilename(LL_PATH_SKINS, "paths.xml");
-
- LLXMLNodePtr root;
- BOOL success = LLXMLNode::parseFile(filename, root, NULL);
- Paths paths;
-
- if(success)
- {
- LLXUIParser parser;
- parser.readXUI(root, paths, filename);
- }
- sXUIPaths.clear();
-
- if (success && paths.validateBlock())
- {
- LLStringUtil::format_map_t path_args;
- path_args["[LANGUAGE]"] = LLUI::getLanguage();
-
- for (LLInitParam::ParamIterator<Directory>::const_iterator it = paths.directories.begin(),
- end_it = paths.directories.end();
- it != end_it;
- ++it)
- {
- std::string path_val_ui;
- for (LLInitParam::ParamIterator<SubDir>::const_iterator subdir_it = it->subdirs.begin(),
- subdir_end_it = it->subdirs.end();
- subdir_it != subdir_end_it;)
- {
- path_val_ui += subdir_it->value();
- if (++subdir_it != subdir_end_it)
- path_val_ui += gDirUtilp->getDirDelimiter();
- }
- LLStringUtil::format(path_val_ui, path_args);
- if (std::find(sXUIPaths.begin(), sXUIPaths.end(), path_val_ui) == sXUIPaths.end())
- {
- sXUIPaths.push_back(path_val_ui);
- }
-
- }
- }
- else // parsing failed
- {
- std::string slash = gDirUtilp->getDirDelimiter();
- std::string dir = "xui" + slash + "en";
- llwarns << "XUI::config file unable to open: " << filename << llendl;
- sXUIPaths.push_back(dir);
- }
-}
-
//static
std::string LLUI::locateSkin(const std::string& filename)
{
- std::string slash = gDirUtilp->getDirDelimiter();
std::string found_file = filename;
- if (!gDirUtilp->fileExists(found_file))
+ if (gDirUtilp->fileExists(found_file))
{
- found_file = gDirUtilp->getExpandedFilename(LL_PATH_USER_SETTINGS, filename); // Should be CUSTOM_SKINS?
+ return found_file;
}
- if (sSettingGroups["config"] && sSettingGroups["config"]->controlExists("Language"))
+
+ found_file = gDirUtilp->getExpandedFilename(LL_PATH_USER_SETTINGS, filename); // Should be CUSTOM_SKINS?
+ if (gDirUtilp->fileExists(found_file))
{
- if (!gDirUtilp->fileExists(found_file))
- {
- std::string localization = getLanguage();
- std::string local_skin = "xui" + slash + localization + slash + filename;
- found_file = gDirUtilp->findSkinnedFilename(local_skin);
- }
+ return found_file;
}
- if (!gDirUtilp->fileExists(found_file))
+
+ found_file = gDirUtilp->findSkinnedFilename(LLDir::XUI, filename);
+ if (! found_file.empty())
{
- std::string local_skin = "xui" + slash + "en" + slash + filename;
- found_file = gDirUtilp->findSkinnedFilename(local_skin);
+ return found_file;
}
- if (!gDirUtilp->fileExists(found_file))
+
+ found_file = gDirUtilp->getExpandedFilename(LL_PATH_APP_SETTINGS, filename);
+ if (gDirUtilp->fileExists(found_file))
{
- found_file = gDirUtilp->getExpandedFilename(LL_PATH_APP_SETTINGS, filename);
+ return found_file;
}
- return found_file;
-}
+ LL_WARNS("LLUI") << "Can't find '" << filename
+ << "' in user settings, any skin directory or app_settings" << LL_ENDL;
+ return "";
+}
//static
LLVector2 LLUI::getWindowSize()
diff --git a/indra/llui/llui.h b/indra/llui/llui.h
index 1fbfbd7a07..e54cae1d78 100644
--- a/indra/llui/llui.h
+++ b/indra/llui/llui.h
@@ -291,11 +291,6 @@ public:
// Return the ISO639 language name ("en", "ko", etc.) for the viewer UI.
// http://www.loc.gov/standards/iso639-2/php/code_list.php
static std::string getLanguage();
-
- static void setupPaths();
- static const std::vector<std::string>& getXUIPaths() { return sXUIPaths; }
- static std::string getSkinPath() { return sXUIPaths.front(); }
- static std::string getLocalizedSkinPath() { return sXUIPaths.back(); } //all files may not exist at the localized path
//helper functions (should probably move free standing rendering helper functions here)
static LLView* getRootView() { return sRootView; }
diff --git a/indra/llui/lluicolortable.cpp b/indra/llui/lluicolortable.cpp
index 9455d09cc0..ffeff15968 100644
--- a/indra/llui/lluicolortable.cpp
+++ b/indra/llui/lluicolortable.cpp
@@ -32,6 +32,7 @@
#include "llui.h"
#include "lluicolortable.h"
#include "lluictrlfactory.h"
+#include <boost/foreach.hpp>
LLUIColorTable::ColorParams::ColorParams()
: value("value"),
@@ -206,19 +207,12 @@ bool LLUIColorTable::loadFromSettings()
{
bool result = false;
- std::string default_filename = gDirUtilp->getExpandedFilename(LL_PATH_DEFAULT_SKIN, "colors.xml");
- result |= loadFromFilename(default_filename, mLoadedColors);
-
- std::string current_filename = gDirUtilp->getExpandedFilename(LL_PATH_TOP_SKIN, "colors.xml");
- if(current_filename != default_filename)
- {
- result |= loadFromFilename(current_filename, mLoadedColors);
- }
-
- current_filename = gDirUtilp->getExpandedFilename(LL_PATH_USER_SKIN, "colors.xml");
- if(current_filename != default_filename)
+ // pass constraint=LLDir::ALL_SKINS because we want colors.xml from every
+ // skin dir
+ BOOST_FOREACH(std::string colors_path,
+ gDirUtilp->findSkinnedFilenames(LLDir::SKINBASE, "colors.xml", LLDir::ALL_SKINS))
{
- result |= loadFromFilename(current_filename, mLoadedColors);
+ result |= loadFromFilename(colors_path, mLoadedColors);
}
std::string user_filename = gDirUtilp->getExpandedFilename(LL_PATH_USER_SETTINGS, "colors.xml");
diff --git a/indra/llui/lluictrlfactory.cpp b/indra/llui/lluictrlfactory.cpp
index 91a6b3259c..60fee47ae0 100644
--- a/indra/llui/lluictrlfactory.cpp
+++ b/indra/llui/lluictrlfactory.cpp
@@ -90,10 +90,12 @@ LLUICtrlFactory::~LLUICtrlFactory()
void LLUICtrlFactory::loadWidgetTemplate(const std::string& widget_tag, LLInitParam::BaseBlock& block)
{
- std::string filename = std::string("widgets") + gDirUtilp->getDirDelimiter() + widget_tag + ".xml";
+ std::string filename = gDirUtilp->add("widgets", widget_tag + ".xml");
LLXMLNodePtr root_node;
- std::string full_filename = gDirUtilp->findSkinnedFilename(LLUI::getXUIPaths().front(), filename);
+ // Here we're looking for the "en" version, the default-language version
+ // of the file, rather than the localized version.
+ std::string full_filename = gDirUtilp->findSkinnedFilenameBaseLang(LLDir::XUI, filename);
if (!full_filename.empty())
{
LLUICtrlFactory::instance().pushFileName(full_filename);
@@ -149,22 +151,12 @@ static LLFastTimer::DeclareTimer FTM_XML_PARSE("XML Reading/Parsing");
//-----------------------------------------------------------------------------
// getLayeredXMLNode()
//-----------------------------------------------------------------------------
-bool LLUICtrlFactory::getLayeredXMLNode(const std::string &xui_filename, LLXMLNodePtr& root)
+bool LLUICtrlFactory::getLayeredXMLNode(const std::string &xui_filename, LLXMLNodePtr& root,
+ LLDir::ESkinConstraint constraint)
{
LLFastTimer timer(FTM_XML_PARSE);
-
- std::vector<std::string> paths;
- std::string path = gDirUtilp->findSkinnedFilename(LLUI::getSkinPath(), xui_filename);
- if (!path.empty())
- {
- paths.push_back(path);
- }
-
- std::string localize_path = gDirUtilp->findSkinnedFilename(LLUI::getLocalizedSkinPath(), xui_filename);
- if (!localize_path.empty() && localize_path != path)
- {
- paths.push_back(localize_path);
- }
+ std::vector<std::string> paths =
+ gDirUtilp->findSkinnedFilenames(LLDir::XUI, xui_filename, constraint);
if (paths.empty())
{
@@ -177,23 +169,6 @@ bool LLUICtrlFactory::getLayeredXMLNode(const std::string &xui_filename, LLXMLNo
//-----------------------------------------------------------------------------
-// getLocalizedXMLNode()
-//-----------------------------------------------------------------------------
-bool LLUICtrlFactory::getLocalizedXMLNode(const std::string &xui_filename, LLXMLNodePtr& root)
-{
- LLFastTimer timer(FTM_XML_PARSE);
- std::string full_filename = gDirUtilp->findSkinnedFilename(LLUI::getLocalizedSkinPath(), xui_filename);
- if (!LLXMLNode::parseFile(full_filename, root, NULL))
- {
- return false;
- }
- else
- {
- return true;
- }
-}
-
-//-----------------------------------------------------------------------------
// saveToXML()
//-----------------------------------------------------------------------------
S32 LLUICtrlFactory::saveToXML(LLView* viewp, const std::string& filename)
@@ -239,8 +214,10 @@ std::string LLUICtrlFactory::getCurFileName()
void LLUICtrlFactory::pushFileName(const std::string& name)
-{
- mFileNames.push_back(gDirUtilp->findSkinnedFilename(LLUI::getSkinPath(), name));
+{
+ // Here we seem to be looking for the default language file ("en") rather
+ // than the localized one, if any.
+ mFileNames.push_back(gDirUtilp->findSkinnedFilenameBaseLang(LLDir::XUI, name));
}
void LLUICtrlFactory::popFileName()
@@ -255,14 +232,6 @@ void LLUICtrlFactory::setCtrlParent(LLView* view, LLView* parent, S32 tab_group)
parent->addChild(view, tab_group);
}
-
-// Avoid directly using LLUI and LLDir in the template code
-//static
-std::string LLUICtrlFactory::findSkinnedFilename(const std::string& filename)
-{
- return gDirUtilp->findSkinnedFilename(LLUI::getSkinPath(), filename);
-}
-
//static
void LLUICtrlFactory::copyName(LLXMLNodePtr src, LLXMLNodePtr dest)
{
diff --git a/indra/llui/lluictrlfactory.h b/indra/llui/lluictrlfactory.h
index 4ce1aeac76..876bb5ef46 100644
--- a/indra/llui/lluictrlfactory.h
+++ b/indra/llui/lluictrlfactory.h
@@ -32,6 +32,7 @@
#include "llregistry.h"
#include "llxuiparser.h"
#include "llstl.h"
+#include "lldir.h"
class LLView;
@@ -160,32 +161,21 @@ public:
LLView* createFromXML(LLXMLNodePtr node, LLView* parent, const std::string& filename, const widget_registry_t&, LLXMLNodePtr output_node );
template<typename T>
- static T* createFromFile(const std::string &filename, LLView *parent, const widget_registry_t& registry, LLXMLNodePtr output_node = NULL)
+ static T* createFromFile(const std::string &filename, LLView *parent, const widget_registry_t& registry)
{
T* widget = NULL;
-
- std::string skinned_filename = findSkinnedFilename(filename);
+
instance().pushFileName(filename);
{
LLXMLNodePtr root_node;
- //if exporting, only load the language being exported,
- //instead of layering localized version on top of english
- if (output_node)
- {
- if (!LLUICtrlFactory::getLocalizedXMLNode(filename, root_node))
- {
- llwarns << "Couldn't parse XUI file: " << filename << llendl;
- goto fail;
- }
- }
- else if (!LLUICtrlFactory::getLayeredXMLNode(filename, root_node))
+ if (!LLUICtrlFactory::getLayeredXMLNode(filename, root_node))
{
- llwarns << "Couldn't parse XUI file: " << skinned_filename << llendl;
+ llwarns << "Couldn't parse XUI file: " << instance().getCurFileName() << llendl;
goto fail;
}
-
- LLView* view = getInstance()->createFromXML(root_node, parent, filename, registry, output_node);
+
+ LLView* view = getInstance()->createFromXML(root_node, parent, filename, registry, NULL);
if (view)
{
widget = dynamic_cast<T*>(view);
@@ -213,8 +203,8 @@ fail:
static void createChildren(LLView* viewp, LLXMLNodePtr node, const widget_registry_t&, LLXMLNodePtr output_node = NULL);
- static bool getLayeredXMLNode(const std::string &filename, LLXMLNodePtr& root);
- static bool getLocalizedXMLNode(const std::string &xui_filename, LLXMLNodePtr& root);
+ static bool getLayeredXMLNode(const std::string &filename, LLXMLNodePtr& root,
+ LLDir::ESkinConstraint constraint=LLDir::CURRENT_SKIN);
private:
//NOTE: both friend declarations are necessary to keep both gcc and msvc happy
@@ -297,9 +287,6 @@ private:
// this exists to get around dependency on llview
static void setCtrlParent(LLView* view, LLView* parent, S32 tab_group);
- // Avoid directly using LLUI and LLDir in the template code
- static std::string findSkinnedFilename(const std::string& filename);
-
class LLPanel* mDummyPanel;
std::vector<std::string> mFileNames;
};
diff --git a/indra/llui/llview.cpp b/indra/llui/llview.cpp
index 8323bfc12f..5bcdae921d 100644
--- a/indra/llui/llview.cpp
+++ b/indra/llui/llview.cpp
@@ -1548,16 +1548,18 @@ void LLView::screenPointToLocal(S32 screen_x, S32 screen_y, S32* local_x, S32* l
void LLView::localPointToScreen(S32 local_x, S32 local_y, S32* screen_x, S32* screen_y) const
{
- *screen_x = local_x + getRect().mLeft;
- *screen_y = local_y + getRect().mBottom;
+ *screen_x = local_x;
+ *screen_y = local_y;
const LLView* cur = this;
- while( cur->mParentView )
+ do
{
+ LLRect cur_rect = cur->getRect();
+ *screen_x += cur_rect.mLeft;
+ *screen_y += cur_rect.mBottom;
cur = cur->mParentView;
- *screen_x += cur->getRect().mLeft;
- *screen_y += cur->getRect().mBottom;
}
+ while( cur );
}
void LLView::screenRectToLocal(const LLRect& screen, LLRect* local) const