diff options
Diffstat (limited to 'indra/llui')
-rw-r--r-- | indra/llui/llchatentry.cpp | 9 | ||||
-rw-r--r-- | indra/llui/llfloater.cpp | 2 | ||||
-rw-r--r-- | indra/llui/llfloater.h | 2 | ||||
-rw-r--r-- | indra/llui/llfloaterreg.cpp | 10 | ||||
-rw-r--r-- | indra/llui/lllineeditor.cpp | 8 | ||||
-rw-r--r-- | indra/llui/llscrolllistctrl.cpp | 27 | ||||
-rw-r--r-- | indra/llui/llscrolllistctrl.h | 3 | ||||
-rw-r--r-- | indra/llui/lltabcontainer.cpp | 27 | ||||
-rw-r--r-- | indra/llui/lltextbase.cpp | 30 | ||||
-rw-r--r-- | indra/llui/lltexteditor.cpp | 1 | ||||
-rw-r--r-- | indra/llui/lltoolbar.cpp | 5 | ||||
-rw-r--r-- | indra/llui/llurlaction.cpp | 31 | ||||
-rw-r--r-- | indra/llui/llurlaction.h | 2 |
13 files changed, 123 insertions, 34 deletions
diff --git a/indra/llui/llchatentry.cpp b/indra/llui/llchatentry.cpp index 8e9c6555c3..9e48dcde7e 100644 --- a/indra/llui/llchatentry.cpp +++ b/indra/llui/llchatentry.cpp @@ -169,6 +169,15 @@ BOOL LLChatEntry::handleSpecialKey(const KEY key, const MASK mask) { BOOL handled = FALSE; + // In the case of a chat entry, pressing RETURN when something is selected + // should NOT erase the selection (unlike a notecard, for example) + if (key == KEY_RETURN) + { + endOfDoc(); + startSelection(); + endSelection(); + } + LLTextEditor::handleSpecialKey(key, mask); switch(key) diff --git a/indra/llui/llfloater.cpp b/indra/llui/llfloater.cpp index 27dd7f5b32..09e27a264a 100644 --- a/indra/llui/llfloater.cpp +++ b/indra/llui/llfloater.cpp @@ -1621,7 +1621,7 @@ void LLFloater::bringToFront( S32 x, S32 y ) // virtual -void LLFloater::setVisibleAndFrontmost(BOOL take_focus) +void LLFloater::setVisibleAndFrontmost(BOOL take_focus, const LLSD& key) { LLMultiFloater* hostp = getHost(); if (hostp) diff --git a/indra/llui/llfloater.h b/indra/llui/llfloater.h index cb5bf28db3..4dba1e645f 100644 --- a/indra/llui/llfloater.h +++ b/indra/llui/llfloater.h @@ -305,7 +305,7 @@ public: /*virtual*/ void handleVisibilityChange ( BOOL new_visibility ); // do not override void setFrontmost(BOOL take_focus = TRUE); - virtual void setVisibleAndFrontmost(BOOL take_focus=TRUE); + virtual void setVisibleAndFrontmost(BOOL take_focus=TRUE, const LLSD& key = LLSD()); // Defaults to false. virtual BOOL canSaveAs() const { return FALSE; } diff --git a/indra/llui/llfloaterreg.cpp b/indra/llui/llfloaterreg.cpp index c20d863612..1cdddf0d5b 100644 --- a/indra/llui/llfloaterreg.cpp +++ b/indra/llui/llfloaterreg.cpp @@ -488,12 +488,12 @@ void LLFloaterReg::toggleInstanceOrBringToFront(const LLSD& sdname, const LLSD& { host->setMinimized(FALSE); instance->openFloater(key); - instance->setVisibleAndFrontmost(); + instance->setVisibleAndFrontmost(true, key); } else if (!instance->getVisible()) { instance->openFloater(key); - instance->setVisibleAndFrontmost(); + instance->setVisibleAndFrontmost(true, key); instance->setFocus(TRUE); } else @@ -506,16 +506,16 @@ void LLFloaterReg::toggleInstanceOrBringToFront(const LLSD& sdname, const LLSD& if (instance->isMinimized()) { instance->setMinimized(FALSE); - instance->setVisibleAndFrontmost(); + instance->setVisibleAndFrontmost(true, key); } else if (!instance->isShown()) { instance->openFloater(key); - instance->setVisibleAndFrontmost(); + instance->setVisibleAndFrontmost(true, key); } else if (!instance->isFrontmost()) { - instance->setVisibleAndFrontmost(); + instance->setVisibleAndFrontmost(true, key); } else { diff --git a/indra/llui/lllineeditor.cpp b/indra/llui/lllineeditor.cpp index 2e64be89fa..6976b06a92 100644 --- a/indra/llui/lllineeditor.cpp +++ b/indra/llui/lllineeditor.cpp @@ -202,6 +202,14 @@ LLLineEditor::LLLineEditor(const LLLineEditor::Params& p) LLLineEditor::~LLLineEditor() { mCommitOnFocusLost = FALSE; + + // Make sure no context menu linger around once the widget is deleted + LLContextMenu* menu = static_cast<LLContextMenu*>(mContextMenuHandle.get()); + if (menu) + { + menu->hide(); + } + setContextMenu(NULL); // calls onCommit() while LLLineEditor still valid gFocusMgr.releaseFocusIfNeeded( this ); diff --git a/indra/llui/llscrolllistctrl.cpp b/indra/llui/llscrolllistctrl.cpp index 8b9fb47d5c..7f04c92b27 100644 --- a/indra/llui/llscrolllistctrl.cpp +++ b/indra/llui/llscrolllistctrl.cpp @@ -1801,6 +1801,9 @@ BOOL LLScrollListCtrl::handleRightMouseDown(S32 x, S32 y, MASK mask) // (N.B. callbacks don't take const refs as id is local scope) bool is_group = (mContextMenuType == MENU_GROUP); LLUICtrl::CommitCallbackRegistry::ScopedRegistrar registrar; + registrar.add("Url.ShowProfile", boost::bind(&LLScrollListCtrl::showProfile, id, is_group)); + registrar.add("Url.SendIM", boost::bind(&LLScrollListCtrl::sendIM, id)); + registrar.add("Url.AddFriend", boost::bind(&LLScrollListCtrl::addFriend, id)); registrar.add("Url.Execute", boost::bind(&LLScrollListCtrl::showNameDetails, id, is_group)); registrar.add("Url.CopyLabel", boost::bind(&LLScrollListCtrl::copyNameToClipboard, id, is_group)); registrar.add("Url.CopyUrl", boost::bind(&LLScrollListCtrl::copySLURLToClipboard, id, is_group)); @@ -1821,11 +1824,33 @@ BOOL LLScrollListCtrl::handleRightMouseDown(S32 x, S32 y, MASK mask) return FALSE; } -void LLScrollListCtrl::showNameDetails(std::string id, bool is_group) +void LLScrollListCtrl::showProfile(std::string id, bool is_group) { // show the resident's profile or the group profile std::string sltype = is_group ? "group" : "agent"; std::string slurl = "secondlife:///app/" + sltype + "/" + id + "/about"; + LLUrlAction::showProfile(slurl); +} + +void LLScrollListCtrl::sendIM(std::string id) +{ + // send im to the resident + std::string slurl = "secondlife:///app/agent/" + id + "/about"; + LLUrlAction::sendIM(slurl); +} + +void LLScrollListCtrl::addFriend(std::string id) +{ + // add resident to friends list + std::string slurl = "secondlife:///app/agent/" + id + "/about"; + LLUrlAction::addFriend(slurl); +} + +void LLScrollListCtrl::showNameDetails(std::string id, bool is_group) +{ + // open the resident's details or the group details + std::string sltype = is_group ? "group" : "agent"; + std::string slurl = "secondlife:///app/" + sltype + "/" + id + "/about"; LLUrlAction::clickAction(slurl); } diff --git a/indra/llui/llscrolllistctrl.h b/indra/llui/llscrolllistctrl.h index 38450b6313..8fa06cc499 100644 --- a/indra/llui/llscrolllistctrl.h +++ b/indra/llui/llscrolllistctrl.h @@ -430,6 +430,9 @@ private: BOOL setSort(S32 column, BOOL ascending); S32 getLinesPerPage(); + static void showProfile(std::string id, bool is_group); + static void sendIM(std::string id); + static void addFriend(std::string id); static void showNameDetails(std::string id, bool is_group); static void copyNameToClipboard(std::string id, bool is_group); static void copySLURLToClipboard(std::string id, bool is_group); diff --git a/indra/llui/lltabcontainer.cpp b/indra/llui/lltabcontainer.cpp index 0c43a571b8..6f895ed939 100644 --- a/indra/llui/lltabcontainer.cpp +++ b/indra/llui/lltabcontainer.cpp @@ -1483,16 +1483,22 @@ BOOL LLTabContainer::setTab(S32 which) for(tuple_list_t::iterator iter = mTabList.begin(); iter != mTabList.end(); ++iter) { LLTabTuple* tuple = *iter; - if (!tuple) - continue; BOOL is_selected = ( tuple == selected_tuple ); - tuple->mButton->setUseEllipses(mUseTabEllipses); - tuple->mButton->setHAlign(mFontHalign); - tuple->mTabPanel->setVisible( is_selected ); -// tuple->mTabPanel->setFocus(is_selected); // not clear that we want to do this here. - tuple->mButton->setToggleState( is_selected ); - // RN: this limits tab-stops to active button only, which would require arrow keys to switch tabs - tuple->mButton->setTabStop( is_selected ); + + // Although the selected tab must be complete, we may have hollow LLTabTuple tucked in the list + if (tuple->mButton) + { + tuple->mButton->setUseEllipses(mUseTabEllipses); + tuple->mButton->setHAlign(mFontHalign); + tuple->mButton->setToggleState( is_selected ); + // RN: this limits tab-stops to active button only, which would require arrow keys to switch tabs + tuple->mButton->setTabStop( is_selected ); + } + if (tuple->mTabPanel) + { + tuple->mTabPanel->setVisible( is_selected ); + //tuple->mTabPanel->setFocus(is_selected); // not clear that we want to do this here. + } if (is_selected) { @@ -1563,8 +1569,7 @@ BOOL LLTabContainer::selectTabByName(const std::string& name) LLPanel* panel = getPanelByName(name); if (!panel) { - llwarns << "LLTabContainer::selectTabByName(" - << name << ") failed" << llendl; + llwarns << "LLTabContainer::selectTabByName(" << name << ") failed" << llendl; return FALSE; } diff --git a/indra/llui/lltextbase.cpp b/indra/llui/lltextbase.cpp index 4bb819a7f6..270d5294f9 100644 --- a/indra/llui/lltextbase.cpp +++ b/indra/llui/lltextbase.cpp @@ -359,7 +359,6 @@ void LLTextBase::drawSelectionBackground() S32 selection_left = llmin( mSelectionStart, mSelectionEnd ); S32 selection_right = llmax( mSelectionStart, mSelectionEnd ); - LLRect selection_rect = mVisibleTextRect; // Skip through the lines we aren't drawing. LLRect content_display_rect = getVisibleDocumentRect(); @@ -1086,7 +1085,14 @@ BOOL LLTextBase::handleRightMouseUp(S32 x, S32 y, MASK mask) BOOL LLTextBase::handleDoubleClick(S32 x, S32 y, MASK mask) { - mTripleClickTimer.setTimerExpirySec(TRIPLE_CLICK_INTERVAL); + //Don't start triple click timer if user have clicked on scrollbar + mVisibleTextRect = mScroller ? mScroller->getContentWindowRect() : getLocalRect(); + if (x >= mVisibleTextRect.mLeft && x <= mVisibleTextRect.mRight + && y >= mVisibleTextRect.mBottom && y <= mVisibleTextRect.mTop) + { + mTripleClickTimer.setTimerExpirySec(TRIPLE_CLICK_INTERVAL); + } + LLTextSegmentPtr cur_segment = getSegmentAtLocalPos(x, y); if (cur_segment && cur_segment->handleDoubleClick(x, y, mask)) { @@ -1912,6 +1918,7 @@ void LLTextBase::createUrlContextMenu(S32 x, S32 y, const std::string &in_url) registrar.add("Url.Teleport", boost::bind(&LLUrlAction::teleportToLocation, url)); registrar.add("Url.ShowProfile", boost::bind(&LLUrlAction::showProfile, url)); registrar.add("Url.SendIM", boost::bind(&LLUrlAction::sendIM, url)); + registrar.add("Url.AddFriend", boost::bind(&LLUrlAction::addFriend, url)); registrar.add("Url.ShowOnMap", boost::bind(&LLUrlAction::showLocationOnMap, url)); registrar.add("Url.CopyLabel", boost::bind(&LLUrlAction::copyLabelToClipboard, url)); registrar.add("Url.CopyUrl", boost::bind(&LLUrlAction::copyURLToClipboard, url)); @@ -2330,7 +2337,6 @@ const LLWString& LLTextBase::getWText() const S32 LLTextBase::getDocIndexFromLocalCoord( S32 local_x, S32 local_y, BOOL round, bool hit_past_end_of_line) const { // Figure out which line we're nearest to. - LLRect visible_region = getVisibleDocumentRect(); LLRect doc_rect = mDocumentView->getRect(); S32 doc_y = local_y - doc_rect.mBottom; @@ -3195,7 +3201,23 @@ S32 LLNormalTextSegment::getNumChars(S32 num_pixels, S32 segment_offset, S32 lin LLFontGL::EWordWrapStyle word_wrap_style = (line_offset == 0) ? LLFontGL::WORD_BOUNDARY_IF_POSSIBLE : LLFontGL::ONLY_WORD_BOUNDARIES; - S32 num_chars = mStyle->getFont()->maxDrawableChars(text.c_str() + segment_offset + mStart, + + + LLWString offsetString(text.c_str() + segment_offset + mStart); + + if(getLength() < segment_offset + mStart) + { + llerrs << "getLength() < segment_offset + mStart\t getLength()\t" << getLength() << "\tsegment_offset:\t" + << segment_offset << "\tmStart:\t" << mStart << "\tsegments\t" << mEditor.mSegments.size() << "\tmax_chars\t" << max_chars << llendl; + } + + if(offsetString.length() + 1 < max_chars) + { + llerrs << "offsetString.length() + 1 < max_chars\t max_chars:\t" << max_chars << "\toffsetString.length():\t" << offsetString.length() + << getLength() << "\tsegment_offset:\t" << segment_offset << "\tmStart:\t" << mStart << "\tsegments\t" << mEditor.mSegments.size() << llendl; + } + + S32 num_chars = mStyle->getFont()->maxDrawableChars(offsetString.c_str(), (F32)num_pixels, max_chars, word_wrap_style); diff --git a/indra/llui/lltexteditor.cpp b/indra/llui/lltexteditor.cpp index 2f120479d9..d5e08fa29b 100644 --- a/indra/llui/lltexteditor.cpp +++ b/indra/llui/lltexteditor.cpp @@ -2515,7 +2515,6 @@ void LLTextEditor::updateSegments() mKeywords.findSegments(&segment_list, getWText(), mDefaultColor.get(), *this); clearSegments(); - segment_set_t::iterator insert_it = mSegments.begin(); for (segment_vec_t::iterator list_it = segment_list.begin(); list_it != segment_list.end(); ++list_it) { insertSegment(*list_it); diff --git a/indra/llui/lltoolbar.cpp b/indra/llui/lltoolbar.cpp index b9256dd890..1c74395c66 100644 --- a/indra/llui/lltoolbar.cpp +++ b/indra/llui/lltoolbar.cpp @@ -1059,10 +1059,9 @@ BOOL LLToolBar::handleDragAndDrop(S32 x, S32 y, MASK mask, BOOL drop, // Convert drag position into insert position and rank if (!isReadOnly() && handled && !drop) { - LLInventoryItem* inv_item = (LLInventoryItem*)cargo_data; - LLAssetType::EType type = inv_item->getType(); - if (type == LLAssetType::AT_WIDGET) + if (cargo_type == DAD_WIDGET) { + LLInventoryItem* inv_item = (LLInventoryItem*)cargo_data; LLCommandId dragged_command(inv_item->getUUID()); int orig_rank = getRankFromPosition(dragged_command); mDragRank = getRankFromPosition(x, y); diff --git a/indra/llui/llurlaction.cpp b/indra/llui/llurlaction.cpp index fd872eca4b..f51aeaec13 100644 --- a/indra/llui/llurlaction.cpp +++ b/indra/llui/llurlaction.cpp @@ -24,7 +24,6 @@ * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA * $/LicenseInfo$ */ - #include "linden_common.h" #include "llurlaction.h" @@ -32,6 +31,7 @@ #include "llwindow.h" #include "llurlregistry.h" + // global state for the callback functions LLUrlAction::url_callback_t LLUrlAction::sOpenURLCallback; LLUrlAction::url_callback_t LLUrlAction::sOpenURLInternalCallback; @@ -158,16 +158,33 @@ void LLUrlAction::showProfile(std::string url) } } -void LLUrlAction::sendIM(std::string url) +std::string LLUrlAction::getUserID(std::string url) { LLURI uri(url); LLSD path_array = uri.pathArray(); + std::string id_str; if (path_array.size() == 4) { - std::string id_str = path_array.get(2).asString(); - if (LLUUID::validate(id_str)) - { - executeSLURL("secondlife:///app/agent/" + id_str + "/im"); - } + id_str = path_array.get(2).asString(); } + return id_str; } + +void LLUrlAction::sendIM(std::string url) +{ + std::string id_str = getUserID(url); + if (LLUUID::validate(id_str)) + { + executeSLURL("secondlife:///app/agent/" + id_str + "/im"); + } +} + +void LLUrlAction::addFriend(std::string url) +{ + std::string id_str = getUserID(url); + if (LLUUID::validate(id_str)) + { + executeSLURL("secondlife:///app/agent/" + id_str + "/requestfriend"); + } +} + diff --git a/indra/llui/llurlaction.h b/indra/llui/llurlaction.h index f5f2ceba72..e31cd71a20 100644 --- a/indra/llui/llurlaction.h +++ b/indra/llui/llurlaction.h @@ -76,7 +76,9 @@ public: /// if the Url specifies an SL command in the form like 'app/{cmd}/{id}/*', show its profile static void showProfile(std::string url); + static std::string getUserID(std::string url); static void sendIM(std::string url); + static void addFriend(std::string url); /// specify the callbacks to enable this class's functionality typedef boost::function<void (const std::string&)> url_callback_t; |