summaryrefslogtreecommitdiff
path: root/indra/llui
diff options
context:
space:
mode:
authorAaron Brashears <aaronb@lindenlab.com>2007-06-13 18:02:37 +0000
committerAaron Brashears <aaronb@lindenlab.com>2007-06-13 18:02:37 +0000
commitf118e7c80b95d8c0a0c8abb14ff379b6697e01b6 (patch)
treedb55a74f8d18b3c366608a537e2a32f6d089d56f /indra/llui
parent680667d4bdca7e2a6df15cd6f16f34c12c97da8e (diff)
result of merge manually performed through diff and patch. svn diff svn+ssh://svn/svn/linden/release@63615 svn+ssh://svn/svn/linden/branches/release-candidate@63637 | patch -p0 in release
Diffstat (limited to 'indra/llui')
-rw-r--r--indra/llui/llbutton.cpp78
-rw-r--r--indra/llui/llbutton.h7
-rw-r--r--indra/llui/llfloater.cpp73
-rw-r--r--indra/llui/llfloater.h10
-rw-r--r--indra/llui/llscrolllistctrl.cpp51
-rw-r--r--indra/llui/llscrolllistctrl.h8
-rw-r--r--indra/llui/lltabcontainer.cpp54
-rw-r--r--indra/llui/lltabcontainer.h7
-rw-r--r--indra/llui/lltexteditor.cpp32
-rw-r--r--indra/llui/lltexteditor.h2
-rw-r--r--indra/llui/llui.h91
11 files changed, 360 insertions, 53 deletions
diff --git a/indra/llui/llbutton.cpp b/indra/llui/llbutton.cpp
index ddd81e77b3..d28cf96fa0 100644
--- a/indra/llui/llbutton.cpp
+++ b/indra/llui/llbutton.cpp
@@ -595,6 +595,56 @@ void LLButton::draw()
gl_rect_2d(0, mRect.getHeight(), mRect.getWidth(), 0, LLColor4::pink1, FALSE);
}
+ // draw overlay image
+ if (mImageOverlay.notNull())
+ {
+ const S32 IMG_PAD = 4;
+ // get max width and height (discard level 0)
+ S32 overlay_width = mImageOverlay->getWidth(0);
+ S32 overlay_height = mImageOverlay->getHeight(0);
+
+ F32 scale_factor = llmin((F32)mRect.getWidth() / (F32)overlay_width, (F32)mRect.getHeight() / (F32)overlay_height, 1.f);
+ overlay_width = llround((F32)overlay_width * scale_factor);
+ overlay_height = llround((F32)overlay_height * scale_factor);
+
+ S32 center_x = getLocalRect().getCenterX();
+ S32 center_y = getLocalRect().getCenterY();
+
+ switch(mImageOverlayAlignment)
+ {
+ case LLFontGL::LEFT:
+ gl_draw_scaled_image(
+ IMG_PAD,
+ center_y - (overlay_height / 2),
+ overlay_width,
+ overlay_height,
+ mImageOverlay,
+ LLColor4::white);
+ break;
+ case LLFontGL::HCENTER:
+ gl_draw_scaled_image(
+ center_x - (overlay_width / 2),
+ center_y - (overlay_height / 2),
+ overlay_width,
+ overlay_height,
+ mImageOverlay,
+ LLColor4::white);
+ break;
+ case LLFontGL::RIGHT:
+ gl_draw_scaled_image(
+ mRect.getWidth() - IMG_PAD - overlay_width,
+ center_y - (overlay_height / 2),
+ overlay_width,
+ overlay_height,
+ mImageOverlay,
+ LLColor4::white);
+ break;
+ default:
+ // draw nothing
+ break;
+ }
+ }
+
// Draw label
if( !label.empty() )
{
@@ -806,6 +856,21 @@ void LLButton::setHoverImages( const LLString& image_name, const LLString& selec
setImageHoverSelected(selected_name);
}
+void LLButton::setImageOverlay(const LLString &image_name, LLFontGL::HAlign alignment)
+{
+ if (image_name.empty())
+ {
+ mImageOverlay = NULL;
+ }
+ else
+ {
+ LLUUID overlay_image_id = LLUI::findAssetUUIDByName(image_name);
+ mImageOverlay = LLUI::sImageProvider->getUIImageByID(overlay_image_id);
+ mImageOverlayAlignment = alignment;
+ }
+}
+
+
void LLButton::onMouseCaptureLost()
{
mMouseDownTimer.stop();
@@ -978,6 +1043,18 @@ LLView* LLButton::fromXML(LLXMLNodePtr node, LLView *parent, LLUICtrlFactory *fa
LLString image_disabled;
if (node->hasAttribute("image_disabled")) node->getAttributeString("image_disabled",image_disabled);
+ LLString image_overlay;
+ node->getAttributeString("image_overlay", image_overlay);
+
+ LLFontGL::HAlign image_overlay_alignment = LLFontGL::HCENTER;
+ LLString image_overlay_alignment_string;
+ if (node->hasAttribute("image_overlay_alignment"))
+ {
+ node->getAttributeString("image_overlay_alignment", image_overlay_alignment_string);
+ image_overlay_alignment = LLFontGL::hAlignFromName(image_overlay_alignment_string);
+ }
+
+
LLButton *button = new LLButton(name,
LLRect(),
image_unselected,
@@ -1000,6 +1077,7 @@ LLView* LLButton::fromXML(LLXMLNodePtr node, LLView *parent, LLUICtrlFactory *fa
if(image_disabled != LLString::null) button->setImageDisabled(image_disabled);
+ if(image_overlay != LLString::null) button->setImageOverlay(image_overlay, image_overlay_alignment);
if (node->hasAttribute("halign"))
{
diff --git a/indra/llui/llbutton.h b/indra/llui/llbutton.h
index 9048358bd8..470c34fb64 100644
--- a/indra/llui/llbutton.h
+++ b/indra/llui/llbutton.h
@@ -122,6 +122,10 @@ public:
void setDisabledSelectedLabelColor( const LLColor4& c ) { mDisabledSelectedLabelColor = c; }
+ void setImageOverlay(const LLString &image_name, LLFontGL::HAlign alignment = LLFontGL::HCENTER);
+ LLPointer<LLImageGL> getImageOverlay() { return mImageOverlay; }
+
+
virtual void setValue(const LLSD& value );
virtual LLSD getValue() const;
@@ -182,6 +186,9 @@ protected:
F32 mHeldDownDelay; // seconds, after which held-down callbacks get called
S32 mHeldDownFrameDelay; // frames, after which held-down callbacks get called
+ LLPointer<LLImageGL> mImageOverlay;
+ LLFontGL::HAlign mImageOverlayAlignment;
+
LLPointer<LLImageGL> mImageUnselected;
LLUIString mUnselectedLabel;
LLColor4 mUnselectedLabelColor;
diff --git a/indra/llui/llfloater.cpp b/indra/llui/llfloater.cpp
index fd8947c594..66642d8f34 100644
--- a/indra/llui/llfloater.cpp
+++ b/indra/llui/llfloater.cpp
@@ -555,17 +555,20 @@ void LLFloater::close(bool app_quitting)
cleanupHandles();
gFocusMgr.clearLastFocusForGroup(this);
- // Do this early, so UI controls will commit before the
- // window is taken down.
- releaseFocus();
-
- // give focus to dependee floater if it exists, and we had focus first
- if (isDependent())
+ if (hasFocus())
{
- LLFloater* dependee = LLFloater::getFloaterByHandle(mDependeeHandle);
- if (dependee && !dependee->isDead())
+ // Do this early, so UI controls will commit before the
+ // window is taken down.
+ releaseFocus();
+
+ // give focus to dependee floater if it exists, and we had focus first
+ if (isDependent())
{
- dependee->setFocus(TRUE);
+ LLFloater* dependee = LLFloater::getFloaterByHandle(mDependeeHandle);
+ if (dependee && !dependee->isDead())
+ {
+ dependee->setFocus(TRUE);
+ }
}
}
@@ -1150,6 +1153,28 @@ BOOL LLFloater::getEditModeEnabled()
return sEditModeEnabled;
}
+//static
+void LLFloater::show(LLFloater* floaterp)
+{
+ if (floaterp) floaterp->open();
+}
+
+//static
+void LLFloater::hide(LLFloater* floaterp)
+{
+ if (floaterp) floaterp->close();
+}
+
+//static
+BOOL LLFloater::visible(LLFloater* floaterp)
+{
+ if (floaterp)
+ {
+ return floaterp->isInVisibleChain();
+ }
+ return FALSE;
+}
+
// static
void LLFloater::onClickMinimize(void *userdata)
{
@@ -2352,7 +2377,7 @@ void LLFloaterView::popVisibleAll(const skip_list_t& skip_list)
LLMultiFloater::LLMultiFloater() :
mTabContainer(NULL),
mTabPos(LLTabContainerCommon::TOP),
- mAutoResize(FALSE)
+ mAutoResize(TRUE)
{
}
@@ -2360,7 +2385,7 @@ LLMultiFloater::LLMultiFloater() :
LLMultiFloater::LLMultiFloater(LLTabContainerCommon::TabPosition tab_pos) :
mTabContainer(NULL),
mTabPos(tab_pos),
- mAutoResize(FALSE)
+ mAutoResize(TRUE)
{
}
@@ -2574,15 +2599,12 @@ void LLMultiFloater::addFloater(LLFloater* floaterp, BOOL select_added_floater,
floaterp->setCanResize(FALSE);
floaterp->setCanDrag(FALSE);
- S32 new_width = llmax(mRect.getWidth(), floaterp->getRect().getWidth());
- S32 new_height = llmax(mRect.getHeight(), floaterp->getRect().getHeight() + LLFLOATER_HEADER_SIZE + TABCNTR_HEADER_HEIGHT);
-
- reshape(new_width, new_height);
-
//add the panel, add it to proper maps
mTabContainer->addTabPanel(floaterp, floaterp->getTitle(), FALSE, onTabSelected, this, 0, FALSE, insertion_point);
mFloaterDataMap[floaterp->getHandle()] = floater_data;
+ resizeToContents();
+
if ( select_added_floater )
{
mTabContainer->selectLastTab();
@@ -2656,10 +2678,7 @@ void LLMultiFloater::removeFloater(LLFloater* floaterp)
floaterp->setBackgroundVisible(TRUE);
floaterp->setHost(NULL);
- if (mAutoResize)
- {
- resizeToContents();
- }
+ resizeToContents();
tabOpen((LLFloater*)mTabContainer->getCurrentPanel(), false);
}
@@ -2709,7 +2728,8 @@ BOOL LLMultiFloater::handleKeyHere(KEY key, MASK mask, BOOL called_from_parent)
if (key == 'W')
{
LLFloater* floater = getActiveFloater();
- if (floater && floater->canClose())
+ // is user closeable and is system closeable
+ if (floater && floater->canClose() && floater->isCloseable())
{
floater->close();
}
@@ -2828,10 +2848,17 @@ void LLMultiFloater::resizeToContents()
S32 cur_height = mRect.getHeight();
- reshape(new_width, new_height);
+ if (mAutoResize)
+ {
+ reshape(new_width, new_height);
+ }
+ else
+ {
+ reshape(llmax(new_min_width, mRect.getWidth()), llmax(new_min_height, mRect.getHeight()));
+ }
// make sure upper left corner doesn't move
- translate(0, cur_height - new_height);
+ translate(0, cur_height - mRect.getHeight());
// Try to keep whole view onscreen, don't allow partial offscreen.
gFloaterView->adjustToFitScreen(this, FALSE);
diff --git a/indra/llui/llfloater.h b/indra/llui/llfloater.h
index 90063108f5..c71f3df3e8 100644
--- a/indra/llui/llfloater.h
+++ b/indra/llui/llfloater.h
@@ -192,6 +192,10 @@ public:
static BOOL getEditModeEnabled();
static LLMultiFloater* getFloaterHost() {return sHostp; }
+ static void show(LLFloater* floaterp);
+ static void hide(LLFloater* floaterp);
+ static BOOL visible(LLFloater* floaterp);
+
static LLFloater* getFloaterByHandle(LLViewHandle handle);
protected:
@@ -259,7 +263,6 @@ protected:
std::vector<LLView*> mMinimizedHiddenChildren;
};
-
/////////////////////////////////////////////////////////////
// LLFloaterView
// Parent of all floating panels
@@ -334,8 +337,8 @@ public:
LLMultiFloater();
LLMultiFloater(LLTabContainerCommon::TabPosition tab_pos);
LLMultiFloater(const LLString& name);
- LLMultiFloater(const LLString& name, const LLRect& rect, LLTabContainer::TabPosition tab_pos = LLTabContainer::TOP, BOOL auto_resize = FALSE);
- LLMultiFloater(const LLString& name, const LLString& rect_control, LLTabContainer::TabPosition tab_pos = LLTabContainer::TOP, BOOL auto_resize = FALSE);
+ LLMultiFloater(const LLString& name, const LLRect& rect, LLTabContainer::TabPosition tab_pos = LLTabContainer::TOP, BOOL auto_resize = TRUE);
+ LLMultiFloater(const LLString& name, const LLString& rect_control, LLTabContainer::TabPosition tab_pos = LLTabContainer::TOP, BOOL auto_resize = TRUE);
virtual ~LLMultiFloater();
virtual BOOL postBuild();
@@ -396,3 +399,4 @@ extern LLFloaterView* gFloaterView;
#endif // LL_FLOATER_H
+
diff --git a/indra/llui/llscrolllistctrl.cpp b/indra/llui/llscrolllistctrl.cpp
index 94d5d7ae75..4c01387941 100644
--- a/indra/llui/llscrolllistctrl.cpp
+++ b/indra/llui/llscrolllistctrl.cpp
@@ -79,7 +79,7 @@ protected:
// LLScrollListIcon
//
LLScrollListIcon::LLScrollListIcon(LLImageGL* icon, S32 width, LLUUID image_id) :
-mIcon(icon), mImageUUID(image_id.asString())
+mIcon(icon), mColor(LLColor4::white), mImageUUID(image_id.asString())
{
if (width)
{
@@ -95,6 +95,16 @@ LLScrollListIcon::~LLScrollListIcon()
{
}
+void LLScrollListIcon::setColor(const LLColor4& color)
+{
+ mColor = color;
+}
+
+void LLScrollListIcon::drawToWidth(S32 width, const LLColor4& color, const LLColor4& highlight_color) const
+{
+ gl_draw_image(0, 0, mIcon, mColor);
+}
+
//
// LLScrollListCheck
//
@@ -188,6 +198,15 @@ LLScrollListText::~LLScrollListText()
delete mColor;
}
+void LLScrollListText::setColor(const LLColor4& color)
+{
+ if (!mColor)
+ {
+ mColor = new LLColor4();
+ }
+ *mColor = color;
+}
+
void LLScrollListText::setText(const LLString& text)
{
mText = text;
@@ -2789,6 +2808,8 @@ LLScrollListItem* LLScrollListCtrl::addElement(const LLSD& value, EAddPosition p
LLString fontname = (*itor)["font"].asString();
LLString fontstyle = (*itor)["font-style"].asString();
LLString type = (*itor)["type"].asString();
+ BOOL has_color = (*itor).has("color");
+ LLColor4 color = ((*itor)["color"]);
const LLFontGL *font = gResMgr->getRes(fontname);
if (!font)
@@ -2801,21 +2822,41 @@ LLScrollListItem* LLScrollListCtrl::addElement(const LLSD& value, EAddPosition p
{
LLUUID image_id = value.asUUID();
LLImageGL* icon = LLUI::sImageProvider->getUIImageByID(image_id);
- new_item->setColumn(index, new LLScrollListIcon(icon, width, image_id));
+ LLScrollListIcon* cell = new LLScrollListIcon(icon, width, image_id);
+ if (has_color)
+ {
+ cell->setColor(color);
+ }
+ new_item->setColumn(index, cell);
}
else if (type == "checkbox")
{
LLCheckBoxCtrl* ctrl = new LLCheckBoxCtrl(value.asString(),
LLRect(0, 0, width, width), "label");
- new_item->setColumn(index, new LLScrollListCheck(ctrl,width));
+ LLScrollListCheck* cell = new LLScrollListCheck(ctrl,width);
+ if (has_color)
+ {
+ cell->setColor(color);
+ }
+ new_item->setColumn(index, cell);
}
else if (type == "separator")
{
- new_item->setColumn(index, new LLScrollListSeparator(width));
+ LLScrollListSeparator* cell = new LLScrollListSeparator(width);
+ if (has_color)
+ {
+ cell->setColor(color);
+ }
+ new_item->setColumn(index, cell);
}
else
{
- new_item->setColumn(index, new LLScrollListText(value.asString(), font, width, font_style, font_alignment));
+ LLScrollListText* cell = new LLScrollListText(value.asString(), font, width, font_style, font_alignment);
+ if (has_color)
+ {
+ cell->setColor(color);
+ }
+ new_item->setColumn(index, cell);
if (columnp->mHeader && !value.asString().empty())
{
columnp->mHeader->setHasResizableElement(TRUE);
diff --git a/indra/llui/llscrolllistctrl.h b/indra/llui/llscrolllistctrl.h
index de9b58bd1e..dff522bc0b 100644
--- a/indra/llui/llscrolllistctrl.h
+++ b/indra/llui/llscrolllistctrl.h
@@ -43,6 +43,7 @@ public:
virtual void setWidth(S32 width) = 0;
virtual void highlightText(S32 offset, S32 num_chars) {}
virtual BOOL isText() = 0;
+ virtual void setColor(const LLColor4&) = 0;
virtual BOOL handleClick() { return FALSE; }
virtual void setEnabled(BOOL enable) { }
@@ -57,6 +58,7 @@ public:
virtual S32 getWidth() const {return mWidth;}
virtual S32 getHeight() const { return 5; };
virtual void setWidth(S32 width) {mWidth = width; }
+ virtual void setColor(const LLColor4&) {};
virtual BOOL isText() { return FALSE; }
protected:
@@ -77,6 +79,7 @@ public:
virtual const BOOL getVisible() const { return mVisible; }
virtual void highlightText(S32 offset, S32 num_chars) {mHighlightOffset = offset; mHighlightCount = num_chars;}
void setText(const LLString& text);
+ virtual void setColor(const LLColor4&);
virtual BOOL isText() { return TRUE; }
private:
@@ -100,18 +103,20 @@ class LLScrollListIcon : public LLScrollListCell
public:
LLScrollListIcon( LLImageGL* icon, S32 width = 0, LLUUID image_id = LLUUID::null);
/*virtual*/ ~LLScrollListIcon();
- virtual void drawToWidth(S32 width, const LLColor4& color, const LLColor4& highlight_color) const { gl_draw_image(0, 0, mIcon); }
+ virtual void drawToWidth(S32 width, const LLColor4& color, const LLColor4& highlight_color) const;
virtual S32 getWidth() const { return mWidth; }
virtual S32 getHeight() const { return mIcon->getHeight(); }
virtual const LLString& getText() const { return mImageUUID; }
virtual const LLString& getTextLower() const { return mImageUUID; }
virtual void setWidth(S32 width) { mWidth = width; }
+ virtual void setColor(const LLColor4&);
virtual BOOL isText() { return FALSE; }
private:
LLPointer<LLImageGL> mIcon;
LLString mImageUUID;
S32 mWidth;
+ LLColor4 mColor;
};
class LLScrollListCheck : public LLScrollListCell
@@ -126,6 +131,7 @@ public:
virtual BOOL handleClick();
virtual void setEnabled(BOOL enable) { if (mCheckBox) mCheckBox->setEnabled(enable); }
+ virtual void setColor(const LLColor4& color) {};
LLCheckBoxCtrl* getCheckBox() { return mCheckBox; }
virtual BOOL isText() { return FALSE; }
diff --git a/indra/llui/lltabcontainer.cpp b/indra/llui/lltabcontainer.cpp
index a5bad91670..2844640291 100644
--- a/indra/llui/lltabcontainer.cpp
+++ b/indra/llui/lltabcontainer.cpp
@@ -57,7 +57,8 @@ LLTabContainerCommon::LLTabContainerCommon(
mCallbackUserdata( callback_userdata ),
mTitleBox(NULL),
mTopBorderHeight(LLPANEL_BORDER_WIDTH),
- mTabPosition(pos)
+ mTabPosition(pos),
+ mLockedTabCount(0)
{
setMouseOpaque(FALSE);
}
@@ -122,6 +123,13 @@ void LLTabContainerCommon::addPlaceholder(LLPanel* child, const LLString& label)
addTabPanel(child, label, FALSE, NULL, NULL, 0, TRUE);
}
+void LLTabContainerCommon::lockTabs()
+{
+ // count current tabs and ensure no new tabs get
+ // inserted between them
+ mLockedTabCount = getTabCount();
+}
+
void LLTabContainerCommon::removeTabPanel(LLPanel* child)
{
BOOL has_focus = gFocusMgr.childHasKeyboardFocus(this);
@@ -144,6 +152,10 @@ void LLTabContainerCommon::removeTabPanel(LLPanel* child)
break;
}
}
+
+ // make sure we don't have more locked tabs than we have tabs
+ mLockedTabCount = llmin(getTabCount(), mLockedTabCount);
+
if (mCurrentTabIdx >= (S32)mTabList.size())
{
mCurrentTabIdx = mTabList.size()-1;
@@ -506,6 +518,15 @@ void LLTabContainerCommon::setTabPanelFlashing(LLPanel* child, BOOL state )
}
}
+void LLTabContainerCommon::setTabImage(LLPanel* child, std::string img_name)
+{
+ LLTabTuple* tuple = getTabByPanel(child);
+ if( tuple )
+ {
+ tuple->mButton->setImageOverlay(img_name, LLFontGL::RIGHT);
+ }
+}
+
void LLTabContainerCommon::setTitle(const LLString& title)
{
if (mTitleBox)
@@ -667,12 +688,12 @@ void LLTabContainerCommon::insertTuple(LLTabTuple * tuple, eInsertionPoint inser
{
case START:
// insert the new tab in the front of the list
- mTabList.insert(mTabList.begin(), tuple);
+ mTabList.insert(mTabList.begin() + mLockedTabCount, tuple);
break;
case RIGHT_OF_CURRENT:
- // insert the new tab after the current tab
+ // insert the new tab after the current tab (but not before mLockedTabCount)
{
- tuple_list_t::iterator current_iter = mTabList.begin() + mCurrentTabIdx + 1;
+ tuple_list_t::iterator current_iter = mTabList.begin() + llmax(mLockedTabCount, mCurrentTabIdx + 1);
mTabList.insert(current_iter, tuple);
}
break;
@@ -1229,6 +1250,7 @@ void LLTabContainer::draw()
for(tuple_list_t::iterator iter = mTabList.begin(); iter != mTabList.end(); ++iter)
{
LLTabTuple* tuple = *iter;
+
tuple->mButton->translate( left - tuple->mButton->getRect().mLeft, 0 );
left += tuple->mButton->getRect().getWidth();
@@ -1576,3 +1598,27 @@ BOOL LLTabContainer::handleDragAndDrop(S32 x, S32 y, MASK mask, BOOL drop, EDrag
return LLView::handleDragAndDrop(x, y, mask, drop, type, cargo_data, accept, tooltip);
}
+
+void LLTabContainer::setTabImage(LLPanel* child, std::string image_name)
+{
+ LLTabTuple* tuple = getTabByPanel(child);
+ if( tuple )
+ {
+ tuple->mButton->setImageOverlay(image_name, LLFontGL::RIGHT);
+
+ const LLFontGL* fontp = gResMgr->getRes( LLFONT_SANSSERIF_SMALL );
+ // remove current width from total tab strip width
+ mTotalTabWidth -= tuple->mButton->getRect().getWidth();
+
+ S32 image_overlay_width = tuple->mButton->getImageOverlay().notNull() ?
+ tuple->mButton->getImageOverlay()->getWidth(0) :
+ 0;
+ tuple->mButton->reshape(llclamp(fontp->getWidth(tuple->mButton->getLabelSelected()) + TAB_PADDING + image_overlay_width, mMinTabWidth, mMaxTabWidth),
+ tuple->mButton->getRect().getHeight());
+ // add back in button width to total tab strip width
+ mTotalTabWidth += tuple->mButton->getRect().getWidth();
+
+ // tabs have changed size, might need to scroll to see current tab
+ updateMaxScrollPos();
+ }
+} \ No newline at end of file
diff --git a/indra/llui/lltabcontainer.h b/indra/llui/lltabcontainer.h
index aa4c1c608a..fbb73b951b 100644
--- a/indra/llui/lltabcontainer.h
+++ b/indra/llui/lltabcontainer.h
@@ -67,7 +67,8 @@ public:
BOOL placeholder = FALSE,
eInsertionPoint insertion_point = END) = 0;
virtual void addPlaceholder(LLPanel* child, const LLString& label);
-
+ virtual void lockTabs();
+
virtual void enableTabButton(S32 which, BOOL enable);
virtual void removeTabPanel( LLPanel* child );
@@ -93,6 +94,7 @@ public:
BOOL getTabPanelFlashing(LLPanel* child);
void setTabPanelFlashing(LLPanel* child, BOOL state);
+ virtual void setTabImage(LLPanel* child, std::string img_name);
void setTitle( const LLString& title );
const LLString getPanelTitle(S32 index);
@@ -160,6 +162,7 @@ protected:
S32 mTopBorderHeight;
TabPosition mTabPosition;
+ S32 mLockedTabCount;
protected:
void scrollPrev();
@@ -201,7 +204,7 @@ public:
/*virtual*/ void removeTabPanel( LLPanel* child );
/*virtual*/ void setPanelTitle(S32 index, const LLString& title);
-
+ /*virtual*/ void setTabImage(LLPanel* child, std::string img_name);
/*virtual*/ void setRightTabBtnOffset( S32 offset );
/*virtual*/ void setMinTabWidth(S32 width);
diff --git a/indra/llui/lltexteditor.cpp b/indra/llui/lltexteditor.cpp
index 9363415dc2..f8e1e33cad 100644
--- a/indra/llui/lltexteditor.cpp
+++ b/indra/llui/lltexteditor.cpp
@@ -331,7 +331,7 @@ LLTextEditor::LLTextEditor(
mBorder = new LLViewBorder( "text ed border", LLRect(0, mRect.getHeight(), mRect.getWidth(), 0), LLViewBorder::BEVEL_IN, LLViewBorder::STYLE_LINE, UI_TEXTEDITOR_BORDER );
addChild( mBorder );
- setText(default_text);
+ appendText(default_text, FALSE, FALSE);
mParseHTML=FALSE;
mHTML="";
@@ -2630,7 +2630,8 @@ void LLTextEditor::drawSelectionBackground()
{
LLGLSNoTexture no_texture;
const LLColor4& color = mReadOnly ? mReadOnlyBgColor : mWriteableBgColor;
- glColor3f( 1.f - color.mV[0], 1.f - color.mV[1], 1.f - color.mV[2] );
+ F32 alpha = hasFocus() ? 1.f : 0.5f;
+ glColor4f( 1.f - color.mV[0], 1.f - color.mV[1], 1.f - color.mV[2], alpha );
if( selection_left_y == selection_right_y )
{
@@ -3357,6 +3358,14 @@ void LLTextEditor::appendColoredText(const LLString &new_text,
style.setVisible(true);
style.setColor(color);
style.setFontName(font_name);
+ appendStyledText(new_text, allow_undo, prepend_newline, &style);
+}
+
+void LLTextEditor::appendStyledText(const LLString &new_text,
+ bool allow_undo,
+ bool prepend_newline,
+ const LLStyle* style)
+{
if(mParseHTML)
{
@@ -3367,10 +3376,13 @@ void LLTextEditor::appendColoredText(const LLString &new_text,
LLStyle html;
html.setVisible(true);
html.setColor(mLinkColor);
- html.setFontName(font_name);
+ if (style)
+ {
+ html.setFontName(style->getFontString());
+ }
html.mUnderline = TRUE;
- if (start > 0) appendText(text.substr(0,start),allow_undo, prepend_newline, &style);
+ if (start > 0) appendText(text.substr(0,start),allow_undo, prepend_newline, style);
html.setLinkHREF(text.substr(start,end-start));
appendText(text.substr(start, end-start),allow_undo, prepend_newline, &html);
if (end < (S32)text.length())
@@ -3383,22 +3395,14 @@ void LLTextEditor::appendColoredText(const LLString &new_text,
break;
}
}
- if (end < (S32)text.length()) appendText(text,allow_undo, prepend_newline, &style);
+ if (end < (S32)text.length()) appendText(text,allow_undo, prepend_newline, style);
}
else
{
- appendText(new_text, allow_undo, prepend_newline, &style);
+ appendText(new_text, allow_undo, prepend_newline, style);
}
}
-void LLTextEditor::appendStyledText(const LLString &new_text,
- bool allow_undo,
- bool prepend_newline,
- const LLStyle &style)
-{
- appendText(new_text, allow_undo, prepend_newline, &style);
-}
-
// Appends new text to end of document
void LLTextEditor::appendText(const LLString &new_text, bool allow_undo, bool prepend_newline,
const LLStyle* segment_style)
diff --git a/indra/llui/lltexteditor.h b/indra/llui/lltexteditor.h
index 7454b192fd..1a82d3e8c8 100644
--- a/indra/llui/lltexteditor.h
+++ b/indra/llui/lltexteditor.h
@@ -139,7 +139,7 @@ public:
// if styled text starts a line, you need to prepend a newline.
void appendStyledText(const LLString &new_text, bool allow_undo,
bool prepend_newline,
- const LLStyle &style);
+ const LLStyle* style);
// Removes text from the end of document
// Does not change highlight or cursor position.
diff --git a/indra/llui/llui.h b/indra/llui/llui.h
index c8c244072e..dbe79338e5 100644
--- a/indra/llui/llui.h
+++ b/indra/llui/llui.h
@@ -255,4 +255,95 @@ typedef enum e_widget_type
WIDGET_TYPE_COUNT
} EWidgetType;
+// Manages generation of UI elements by LLSD, such that there is
+// only one instance per uniquely identified LLSD parameter
+// Class T is the instance type being managed, and INSTANCE_ADDAPTOR
+// wraps an instance of the class with handlers for show/hide semantics, etc.
+template <class T, class INSTANCE_ADAPTOR = T>
+class LLUIInstanceMgr
+{
+public:
+ LLUIInstanceMgr()
+ {
+ }
+
+ virtual ~LLUIInstanceMgr()
+ {
+ }
+
+ // default show and hide methods
+ static T* showInstance(const LLSD& seed)
+ {
+ T* instance = INSTANCE_ADAPTOR::getInstance(seed);
+ INSTANCE_ADAPTOR::show(instance);
+ return instance;
+ }
+
+ static void hideInstance(const LLSD& seed)
+ {
+ T* instance = INSTANCE_ADAPTOR::getInstance(seed);
+ INSTANCE_ADAPTOR::hide(instance);
+ }
+
+ static void toggleInstance(const LLSD& seed)
+ {
+ if (!INSTANCE_ADAPTOR::instanceVisible(seed))
+ {
+ INSTANCE_ADAPTOR::showInstance(seed);
+ }
+ else
+ {
+ INSTANCE_ADAPTOR::hideInstance(seed);
+ }
+ }
+
+ static BOOL instanceVisible(const LLSD& seed)
+ {
+ T* instance = INSTANCE_ADAPTOR::findInstance(seed);
+ return instance != NULL && INSTANCE_ADAPTOR::visible(instance);
+ }
+
+ static T* getInstance(const LLSD& seed)
+ {
+ T* instance = INSTANCE_ADAPTOR::findInstance(seed);
+ if (instance == NULL)
+ {
+ instance = INSTANCE_ADAPTOR::createInstance(seed);
+ }
+ return instance;
+ }
+};
+
+// Creates a UI singleton by ignoring the identifying parameter
+// and always generating the same instance via the LLUIInstanceMgr interface.
+// Note that since UI elements can be destroyed by their hierarchy, this singleton
+// pattern uses a static pointer to an instance that will be re-created as needed.
+template <class T, class INSTANCE_ADAPTOR = T>
+class LLUISingleton: public LLUIInstanceMgr<T, INSTANCE_ADAPTOR>
+{
+public:
+ // default constructor assumes T is derived from LLUISingleton (a true singleton)
+ LLUISingleton() : LLUIInstanceMgr<T, INSTANCE_ADAPTOR>() { sInstance = (T*)this; }
+ ~LLUISingleton() { sInstance = NULL; }
+
+ static T* findInstance(const LLSD& seed)
+ {
+ return sInstance;
+ }
+
+ static T* createInstance(const LLSD& seed)
+ {
+ if (sInstance == NULL)
+ {
+ sInstance = new T(seed);
+ }
+ return sInstance;
+ }
+
+protected:
+ static T* sInstance;
+};
+
+template <class T, class U> T* LLUISingleton<T,U>::sInstance = NULL;
+
#endif