diff options
Diffstat (limited to 'indra/newview')
-rw-r--r-- | indra/newview/llbottomtray.cpp | 121 | ||||
-rw-r--r-- | indra/newview/llbottomtray.h | 2 | ||||
-rw-r--r-- | indra/newview/llchatbar.cpp | 5 | ||||
-rw-r--r-- | indra/newview/llchathistory.cpp | 4 | ||||
-rw-r--r-- | indra/newview/llchiclet.cpp | 11 | ||||
-rw-r--r-- | indra/newview/llfloatergesture.cpp | 255 | ||||
-rw-r--r-- | indra/newview/llfloatergesture.h | 12 | ||||
-rw-r--r-- | indra/newview/llfriendcard.cpp | 265 | ||||
-rw-r--r-- | indra/newview/llfriendcard.h | 47 | ||||
-rw-r--r-- | indra/newview/llgesturemgr.cpp | 31 | ||||
-rw-r--r-- | indra/newview/llgesturemgr.h | 30 | ||||
-rw-r--r-- | indra/newview/llimfloater.cpp | 6 | ||||
-rw-r--r-- | indra/newview/llnearbychatbar.cpp | 5 | ||||
-rw-r--r-- | indra/newview/llnearbychathandler.cpp | 3 | ||||
-rw-r--r-- | indra/newview/llscreenchannel.cpp | 2 | ||||
-rw-r--r-- | indra/newview/llstartup.cpp | 7 | ||||
-rw-r--r-- | indra/newview/skins/default/xui/en/floater_gesture.xml | 10 | ||||
-rw-r--r-- | indra/newview/skins/default/xui/en/panel_bottomtray.xml | 2 | ||||
-rw-r--r-- | indra/newview/skins/default/xui/en/panel_group_notify.xml | 194 | ||||
-rw-r--r-- | indra/newview/skins/default/xui/en/panel_nearby_chat_bar.xml | 2 |
20 files changed, 610 insertions, 404 deletions
diff --git a/indra/newview/llbottomtray.cpp b/indra/newview/llbottomtray.cpp index 8d57c68cf2..76cb31e2a6 100644 --- a/indra/newview/llbottomtray.cpp +++ b/indra/newview/llbottomtray.cpp @@ -367,74 +367,87 @@ void LLBottomTray::verifyChildControlsSizes() mNearbyChatBar->setRect(rect); } } -#define __FEATURE_EXT_991 + void LLBottomTray::reshape(S32 width, S32 height, BOOL called_from_parent) { - lldebugs << "****************************************" << llendl; + static S32 debug_calling_number = 0; + lldebugs << "**************************************** " << ++debug_calling_number << llendl; S32 current_width = getRect().getWidth(); + S32 delta_width = width - current_width; lldebugs << "Reshaping: " << ", width: " << width - << ", height: " << height - << ", called_from_parent: " << called_from_parent << ", cur width: " << current_width - << ", cur height: " << getRect().getHeight() + << ", delta_width: " << delta_width + << ", called_from_parent: " << called_from_parent << llendl; if (mNearbyChatBar) log(mNearbyChatBar, "before"); if (mChicletPanel) log(mChicletPanel, "before"); + // stores width size on which bottom tray is less than width required by its children. EXT-991 + static S32 extra_shrink_width = 0; + bool should_be_reshaped = true; + if (mChicletPanel && mToolbarStack && mNearbyChatBar) { mToolbarStack->updatePanelAutoResize(PANEL_CHICLET_NAME, TRUE); verifyChildControlsSizes(); - updateResizeState(width, current_width); - } - - LLPanel::reshape(width, height, called_from_parent); - - - if (mNearbyChatBar) log(mNearbyChatBar, "after"); - if (mChicletPanel) log(mChicletPanel, "after"); -} - -void LLBottomTray::updateResizeState(S32 new_width, S32 cur_width) -{ - mResizeState = RS_NORESIZE; - - S32 delta_width = new_width - cur_width; -// if (delta_width == 0) return; - bool shrink = new_width < cur_width; - - const S32 chiclet_panel_width = mChicletPanel->getParent()->getRect().getWidth(); - const S32 chiclet_panel_min_width = mChicletPanel->getMinWidth(); - - const S32 chatbar_panel_width = mNearbyChatBar->getRect().getWidth(); - const S32 chatbar_panel_min_width = mNearbyChatBar->getMinWidth(); - const S32 chatbar_panel_max_width = mNearbyChatBar->getMaxWidth(); - lldebugs << "chatbar_panel_width: " << chatbar_panel_width - << ", chatbar_panel_min_width: " << chatbar_panel_min_width - << ", chatbar_panel_max_width: " << chatbar_panel_max_width - << ", chiclet_panel_width: " << chiclet_panel_width - << ", chiclet_panel_min_width: " << chiclet_panel_min_width - << llendl; + // bottom tray is narrowed + if (delta_width < 0) + { + if (extra_shrink_width > 0) + { + // is world rect was extra shrunk and decreasing again only update this value + // to delta_width negative + extra_shrink_width -= delta_width; // use "-=" because delta_width is negative + should_be_reshaped = false; + } + else + { + extra_shrink_width = processWidthDecreased(delta_width); - // bottom tray is narrowed - if (shrink) - { - processWidthDecreased(delta_width); + // increase new width to extra_shrink_width value to not reshape less than bottom tray minimum + width += extra_shrink_width; + } + } + // bottom tray is widen + else + { + if (extra_shrink_width > delta_width) + { + // Less than minimum width is more than increasing (delta_width) + // only reduce it value and make no reshape + extra_shrink_width -= delta_width; + should_be_reshaped = false; + } + else + { + if (extra_shrink_width > 0) + { + // If we have some extra shrink width let's reduce delta_width & width + delta_width -= extra_shrink_width; + width -= extra_shrink_width; + extra_shrink_width = 0; + } + processWidthIncreased(delta_width); + } + } } - // bottom tray is widen - else + + lldebugs << "There is no enough width to reshape all children: " << extra_shrink_width << llendl; + if (should_be_reshaped) { - processWidthIncreased(delta_width); + lldebugs << "Reshape all children with width: " << width << llendl; + LLPanel::reshape(width, height, called_from_parent); } - lldebugs << "New resize state: " << mResizeState << llendl; + if (mNearbyChatBar) log(mNearbyChatBar, "after"); + if (mChicletPanel) log(mChicletPanel, "after"); } -void LLBottomTray::processWidthDecreased(S32 delta_width) +S32 LLBottomTray::processWidthDecreased(S32 delta_width) { bool still_should_be_processed = true; @@ -445,7 +458,6 @@ void LLBottomTray::processWidthDecreased(S32 delta_width) { // we have some space to decrease chiclet panel S32 panel_delta_min = chiclet_panel_width - chiclet_panel_min_width; - mResizeState |= RS_CHICLET_PANEL; S32 delta_panel = llmin(-delta_width, panel_delta_min); @@ -473,27 +485,25 @@ void LLBottomTray::processWidthDecreased(S32 delta_width) { // we have some space to decrease chatbar panel S32 panel_delta_min = chatbar_panel_width - chatbar_panel_min_width; - mResizeState |= RS_CHATBAR_INPUT; S32 delta_panel = llmin(-delta_width, panel_delta_min); - // is chatbar panel width enough to process resizing? + // whether chatbar panel width is enough to process resizing? delta_width += panel_delta_min; - still_should_be_processed = delta_width < 0; mNearbyChatBar->reshape(mNearbyChatBar->getRect().getWidth() - delta_panel, mNearbyChatBar->getRect().getHeight()); + log(mChicletPanel, "after processing panel decreasing via nearby chatbar panel"); + lldebugs << "RS_CHATBAR_INPUT" << ", delta_panel: " << delta_panel << ", delta_width: " << delta_width << llendl; - - log(mChicletPanel, "after nearby was processed"); - } + S32 extra_shrink_width = 0; S32 buttons_freed_width = 0; if (still_should_be_processed) { @@ -516,7 +526,9 @@ void LLBottomTray::processWidthDecreased(S32 delta_width) if (delta_width < 0) { - llwarns << "WARNING: there is no enough room for bottom tray, resizing still should be processed" << llendl; + extra_shrink_width = -delta_width; + lldebugs << "There is no enough room for bottom tray, resizing still should be processed: " + << extra_shrink_width << llendl; } if (buttons_freed_width > 0) @@ -527,10 +539,14 @@ void LLBottomTray::processWidthDecreased(S32 delta_width) lldebugs << buttons_freed_width << llendl; } } + + return extra_shrink_width; } void LLBottomTray::processWidthIncreased(S32 delta_width) { + if (delta_width <= 0) return; + const S32 chiclet_panel_width = mChicletPanel->getParent()->getRect().getWidth(); const S32 chiclet_panel_min_width = mChicletPanel->getMinWidth(); @@ -609,7 +625,6 @@ void LLBottomTray::processWidthIncreased(S32 delta_width) S32 chatbar_panel_width_ = mNearbyChatBar->getRect().getWidth(); if (delta_width > 0 && chatbar_panel_width_ < chatbar_panel_max_width) { - mResizeState |= RS_CHATBAR_INPUT; S32 delta_panel_max = chatbar_panel_max_width - chatbar_panel_width_; S32 delta_panel = llmin(delta_width, delta_panel_max); delta_width -= delta_panel_max; diff --git a/indra/newview/llbottomtray.h b/indra/newview/llbottomtray.h index 3847168ae1..e88cd8edde 100644 --- a/indra/newview/llbottomtray.h +++ b/indra/newview/llbottomtray.h @@ -103,7 +103,7 @@ private: void updateResizeState(S32 new_width, S32 cur_width); void verifyChildControlsSizes(); - void processWidthDecreased(S32 delta_width); + S32 processWidthDecreased(S32 delta_width); void processWidthIncreased(S32 delta_width); void log(LLView* panel, const std::string& descr); bool processShowButton(EResizeState shown_object_type, S32* available_width, S32* buttons_required_width); diff --git a/indra/newview/llchatbar.cpp b/indra/newview/llchatbar.cpp index 4523267edd..442dc660cd 100644 --- a/indra/newview/llchatbar.cpp +++ b/indra/newview/llchatbar.cpp @@ -210,8 +210,9 @@ void LLChatBar::refreshGestures() // collect list of unique gestures std::map <std::string, BOOL> unique; - LLGestureManager::item_map_t::iterator it; - for (it = LLGestureManager::instance().mActive.begin(); it != LLGestureManager::instance().mActive.end(); ++it) + LLGestureManager::item_map_t::const_iterator it; + const LLGestureManager::item_map_t& active_gestures = LLGestureManager::instance().getActiveGestures(); + for (it = active_gestures.begin(); it != active_gestures.end(); ++it) { LLMultiGesture* gesture = (*it).second; if (gesture) diff --git a/indra/newview/llchathistory.cpp b/indra/newview/llchathistory.cpp index 5efecfa78f..f228373063 100644 --- a/indra/newview/llchathistory.cpp +++ b/indra/newview/llchathistory.cpp @@ -84,6 +84,10 @@ public: if (level == "profile") { + LLSD params; + params["object_id"] = getAvatarId(); + + LLFloaterReg::showInstance("inspect_object", params); } else if (level == "block") { diff --git a/indra/newview/llchiclet.cpp b/indra/newview/llchiclet.cpp index fd86192650..9e290c8c04 100644 --- a/indra/newview/llchiclet.cpp +++ b/indra/newview/llchiclet.cpp @@ -838,11 +838,15 @@ void im_chiclet_callback(LLChicletPanel* panel, const LLSD& data){ LLUUID session_id = data["session_id"].asUUID(); LLUUID from_id = data["from_id"].asUUID(); const std::string from = data["from"].asString(); + S32 unread = data["num_unread"].asInteger(); - //we do not show balloon (indicator of new messages) for system messages and our own messages - if (from_id.isNull() || from_id == gAgentID || SYSTEM_FROM == from) return; + // if new message came + if(unread != 0) + { + //we do not show balloon (indicator of new messages) for system messages and our own messages + if (from_id.isNull() || from_id == gAgentID || SYSTEM_FROM == from) return; + } - S32 unread = data["num_unread"].asInteger(); LLIMFloater* im_floater = LLIMFloater::findInstance(session_id); if (im_floater && im_floater->getVisible()) { @@ -862,7 +866,6 @@ void im_chiclet_callback(LLChicletPanel* panel, const LLSD& data){ llwarns << "Unable to set counter for chiclet " << session_id << llendl; } } - } diff --git a/indra/newview/llfloatergesture.cpp b/indra/newview/llfloatergesture.cpp index c114eed4a2..ca0ba96a08 100644 --- a/indra/newview/llfloatergesture.cpp +++ b/indra/newview/llfloatergesture.cpp @@ -89,6 +89,52 @@ LLFloaterGesture::LLFloaterGesture(const LLSD& key) //LLUICtrlFactory::getInstance()->buildFloater(this, "floater_gesture.xml"); } +void LLFloaterGesture::done() +{ + //this method can be called twice: for GestureFolder and once after loading all sudir of GestureFolder + if (gInventory.isCategoryComplete(mGestureFolderID)) + { + LL_DEBUGS("Gesture")<< "mGestureFolderID loaded" << LL_ENDL; + // we load only gesture folder without childred. + LLInventoryModel::cat_array_t* categories; + LLInventoryModel::item_array_t* items; + folder_ref_t unloaded_folders; + LL_DEBUGS("Gesture")<< "Get subdirs of Gesture Folder...." << LL_ENDL; + gInventory.getDirectDescendentsOf(mGestureFolderID, categories, items); + if (categories->empty()) + { + gInventory.removeObserver(this); + LL_INFOS("Gesture")<< "Gesture dos NOT contains sub-directories."<< LL_ENDL; + return; + } + LL_DEBUGS("Gesture")<< "There are " << categories->size() << " Folders "<< LL_ENDL; + for (LLInventoryModel::cat_array_t::iterator it = categories->begin(); it != categories->end(); it++) + { + if (!gInventory.isCategoryComplete(it->get()->getUUID())) + { + unloaded_folders.push_back(it->get()->getUUID()); + LL_DEBUGS("Gesture")<< it->get()->getName()<< " Folder added to fetchlist"<< LL_ENDL; + } + + } + if (!unloaded_folders.empty()) + { + LL_DEBUGS("Gesture")<< "Fetching subdirectories....." << LL_ENDL; + fetchDescendents(unloaded_folders); + } + else + { + LL_DEBUGS("Gesture")<< "All Gesture subdirectories have been loaded."<< LL_ENDL; + gInventory.removeObserver(this); + buildGestureList(); + } + } + else + { + LL_WARNS("Gesture")<< "Gesture list was NOT loaded"<< LL_ENDL; + } +} + // virtual LLFloaterGesture::~LLFloaterGesture() { @@ -121,7 +167,14 @@ BOOL LLFloaterGesture::postBuild() childSetVisible("play_btn", true); childSetVisible("stop_btn", false); setDefaultBtn("play_btn"); - + mGestureFolderID = gInventory.findCategoryUUIDForType(LLFolderType::FT_GESTURE, false); + + folder_ref_t folders; + folders.push_back(mGestureFolderID); + //perform loading Gesture directory anyway to make sure that all subdirectory are loaded too. See method done() for details. + gInventory.addObserver(this); + fetchDescendents(folders); + buildGestureList(); childSetFocus("gesture_list"); @@ -171,101 +224,125 @@ void LLFloaterGesture::buildGestureList() if (! (list && scroll)) return; - // attempt to preserve scroll position through re-builds - // since we do re-build any time anything dirties - S32 current_scroll_pos = scroll->getScrollPos(); - + LLUUID selected_item = list->getCurrentID(); + LL_DEBUGS("Gesture")<< "Rebuilding gesture list "<< LL_ENDL; list->operateOnAll(LLCtrlListInterface::OP_DELETE); - LLGestureManager::item_map_t::iterator it; - for (it = LLGestureManager::instance().mActive.begin(); it != LLGestureManager::instance().mActive.end(); ++it) + LLGestureManager::item_map_t::const_iterator it; + const LLGestureManager::item_map_t& active_gestures = LLGestureManager::instance().getActiveGestures(); + for (it = active_gestures.begin(); it != active_gestures.end(); ++it) { - const LLUUID& item_id = (*it).first; - LLMultiGesture* gesture = (*it).second; + addGesture(it->first,it->second, list); + } + if (gInventory.isCategoryComplete(mGestureFolderID)) + { + LLIsType is_gesture(LLAssetType::AT_GESTURE); + LLInventoryModel::cat_array_t categories; + LLInventoryModel::item_array_t items; + gInventory.collectDescendentsIf(mGestureFolderID, categories, items, + LLInventoryModel::EXCLUDE_TRASH, is_gesture); - // Note: Can have NULL item if inventory hasn't arrived yet. - std::string item_name = getString("loading"); - LLInventoryItem* item = gInventory.getItem(item_id); - if (item) + for (LLInventoryModel::item_array_t::iterator it = items.begin(); it!= items.end(); ++it) { - item_name = item->getName(); + LLInventoryItem* item = it->get(); + if (active_gestures.find(item->getUUID()) == active_gestures.end()) + { + // if gesture wasn't loaded yet, we can display only name + addGesture(item->getUUID(), NULL, list); + } } + } + // attempt to preserve scroll position through re-builds + // since we do re-build any time anything dirties + if(list->selectByValue(LLSD(selected_item))) + { + scroll->scrollToShowSelected(); + } +} - std::string font_style = "NORMAL"; - // If gesture is playing, bold it +void LLFloaterGesture::addGesture(const LLUUID& item_id , LLMultiGesture* gesture,LLCtrlListInterface * list ) +{ + // Note: Can have NULL item if inventory hasn't arrived yet. + static std::string item_name = getString("loading"); + LLInventoryItem* item = gInventory.getItem(item_id); + if (item) + { + item_name = item->getName(); + } + + static std::string font_style = "NORMAL"; + // If gesture is playing, bold it - LLSD element; - element["id"] = item_id; + LLSD element; + element["id"] = item_id; - if (gesture) + if (gesture) + { + if (gesture->mPlaying) { - if (gesture->mPlaying) - { - font_style = "BOLD"; - } + font_style = "BOLD"; + } - element["columns"][0]["column"] = "trigger"; - element["columns"][0]["value"] = gesture->mTrigger; - element["columns"][0]["font"]["name"] = "SANSSERIF"; - element["columns"][0]["font"]["style"] = font_style; + element["columns"][0]["column"] = "trigger"; + element["columns"][0]["value"] = gesture->mTrigger; + element["columns"][0]["font"]["name"] = "SANSSERIF"; + element["columns"][0]["font"]["style"] = font_style; - std::string key_string = LLKeyboard::stringFromKey(gesture->mKey); - std::string buffer; + std::string key_string = LLKeyboard::stringFromKey(gesture->mKey); + std::string buffer; - if (gesture->mKey == KEY_NONE) - { - buffer = "---"; - key_string = "~~~"; // alphabetize to end - } - else - { - buffer = LLKeyboard::stringFromAccelerator( gesture->mMask, gesture->mKey ); - } + if (gesture->mKey == KEY_NONE) + { + buffer = "---"; + key_string = "~~~"; // alphabetize to end + } + else + { + buffer = LLKeyboard::stringFromAccelerator(gesture->mMask, + gesture->mKey); + } - element["columns"][1]["column"] = "shortcut"; - element["columns"][1]["value"] = buffer; - element["columns"][1]["font"]["name"] = "SANSSERIF"; - element["columns"][1]["font"]["style"] = font_style; + element["columns"][1]["column"] = "shortcut"; + element["columns"][1]["value"] = buffer; + element["columns"][1]["font"]["name"] = "SANSSERIF"; + element["columns"][1]["font"]["style"] = font_style; - // hidden column for sorting - element["columns"][2]["column"] = "key"; - element["columns"][2]["value"] = key_string; - element["columns"][2]["font"]["name"] = "SANSSERIF"; - element["columns"][2]["font"]["style"] = font_style; + // hidden column for sorting + element["columns"][2]["column"] = "key"; + element["columns"][2]["value"] = key_string; + element["columns"][2]["font"]["name"] = "SANSSERIF"; + element["columns"][2]["font"]["style"] = font_style; - // Only add "playing" if we've got the name, less confusing. JC - if (item && gesture->mPlaying) - { - item_name += " " + getString("playing"); - } - element["columns"][3]["column"] = "name"; - element["columns"][3]["value"] = item_name; - element["columns"][3]["font"]["name"] = "SANSSERIF"; - element["columns"][3]["font"]["style"] = font_style; - } - else + // Only add "playing" if we've got the name, less confusing. JC + if (item && gesture->mPlaying) { - element["columns"][0]["column"] = "trigger"; - element["columns"][0]["value"] = ""; - element["columns"][0]["font"]["name"] = "SANSSERIF"; - element["columns"][0]["font"]["style"] = font_style; - element["columns"][0]["column"] = "trigger"; - element["columns"][0]["value"] = "---"; - element["columns"][0]["font"]["name"] = "SANSSERIF"; - element["columns"][0]["font"]["style"] = font_style; - element["columns"][2]["column"] = "key"; - element["columns"][2]["value"] = "~~~"; - element["columns"][2]["font"]["name"] = "SANSSERIF"; - element["columns"][2]["font"]["style"] = font_style; - element["columns"][3]["column"] = "name"; - element["columns"][3]["value"] = item_name; - element["columns"][3]["font"]["name"] = "SANSSERIF"; - element["columns"][3]["font"]["style"] = font_style; + item_name += " " + getString("playing"); } - list->addElement(element, ADD_BOTTOM); + element["columns"][3]["column"] = "name"; + element["columns"][3]["value"] = item_name; + element["columns"][3]["font"]["name"] = "SANSSERIF"; + element["columns"][3]["font"]["style"] = font_style; } - - scroll->setScrollPos(current_scroll_pos); + else + { + element["columns"][0]["column"] = "trigger"; + element["columns"][0]["value"] = ""; + element["columns"][0]["font"]["name"] = "SANSSERIF"; + element["columns"][0]["font"]["style"] = font_style; + element["columns"][0]["column"] = "trigger"; + element["columns"][0]["value"] = "---"; + element["columns"][0]["font"]["name"] = "SANSSERIF"; + element["columns"][0]["font"]["style"] = font_style; + element["columns"][2]["column"] = "key"; + element["columns"][2]["value"] = "~~~"; + element["columns"][2]["font"]["name"] = "SANSSERIF"; + element["columns"][2]["font"]["style"] = font_style; + element["columns"][3]["column"] = "name"; + element["columns"][3]["value"] = item_name; + element["columns"][3]["font"]["name"] = "SANSSERIF"; + element["columns"][3]["font"]["style"] = font_style; + } + list->addElement(element, ADD_BOTTOM); } void LLFloaterGesture::onClickInventory() @@ -284,14 +361,21 @@ void LLFloaterGesture::onClickPlay() LLCtrlListInterface *list = childGetListInterface("gesture_list"); if (!list) return; const LLUUID& item_id = list->getCurrentID(); + if(item_id.isNull()) return; - if (LLGestureManager::instance().isGesturePlaying(item_id)) + LL_DEBUGS("Gesture")<<" Trying to play gesture id: "<< item_id <<LL_ENDL; + if(!LLGestureManager::instance().isGestureActive(item_id)) { - LLGestureManager::instance().stopGesture(item_id); + // we need to inform server about gesture activating to be consistent with LLPreviewGesture. + BOOL inform_server = TRUE; + BOOL deactivate_similar = FALSE; + LLGestureManager::instance().activateGestureWithAsset(item_id, gInventory.getItem(item_id)->getAssetUUID(), inform_server, deactivate_similar); + LL_DEBUGS("Gesture")<< "Activating gesture with inventory ID: " << item_id <<LL_ENDL; + LLGestureManager::instance().setGestureLoadedCallback(item_id, boost::bind(&LLFloaterGesture::playGesture, this, item_id)); } else { - LLGestureManager::instance().playGesture(item_id); + playGesture(item_id); } } @@ -345,3 +429,14 @@ void LLFloaterGesture::onCommitList() childSetVisible("stop_btn", false); } } +void LLFloaterGesture::playGesture(LLUUID item_id) +{ + if (LLGestureManager::instance().isGesturePlaying(item_id)) + { + LLGestureManager::instance().stopGesture(item_id); + } + else + { + LLGestureManager::instance().playGesture(item_id); + } +} diff --git a/indra/newview/llfloatergesture.h b/indra/newview/llfloatergesture.h index 9c1ab27cb0..9d047bf1cf 100644 --- a/indra/newview/llfloatergesture.h +++ b/indra/newview/llfloatergesture.h @@ -38,7 +38,7 @@ #define LL_LLFLOATERGESTURE_H #include "llfloater.h" - +#include "llinventorymodel.h" #include "lldarray.h" class LLScrollContainer; @@ -51,31 +51,35 @@ class LLGestureOptions; class LLScrollListCtrl; class LLFloaterGestureObserver; class LLFloaterGestureInventoryObserver; +class LLMultiGesture; class LLFloaterGesture -: public LLFloater +: public LLFloater, LLInventoryFetchDescendentsObserver { + LOG_CLASS(LLFloaterGesture); public: LLFloaterGesture(const LLSD& key); virtual ~LLFloaterGesture(); virtual BOOL postBuild(); - + virtual void done (); void refreshAll(); protected: // Reads from the gesture manager's list of active gestures // and puts them in this list. void buildGestureList(); - + void addGesture(const LLUUID& item_id, LLMultiGesture* gesture, LLCtrlListInterface * list); void onClickInventory(); void onClickEdit(); void onClickPlay(); void onClickNew(); void onCommitList(); + void playGesture(LLUUID item_id); protected: LLUUID mSelectedID; + LLUUID mGestureFolderID; LLFloaterGestureObserver* mObserver; }; diff --git a/indra/newview/llfriendcard.cpp b/indra/newview/llfriendcard.cpp index 1ff2566dca..481b75cf73 100644 --- a/indra/newview/llfriendcard.cpp +++ b/indra/newview/llfriendcard.cpp @@ -91,44 +91,39 @@ const LLUUID& get_folder_uuid(const LLUUID& parentFolderUUID, LLInventoryCollect return LLUUID::null; } - -// LLViewerInventoryCategory::fetchDescendents has it own period of fetching. -// for now it is FETCH_TIMER_EXPIRY = 10.0f; So made our period a bit more. -const F32 FETCH_FRIENDS_DESCENDENTS_PERIOD = 11.0f; - - /** - * Intended to call passed callback after the specified period of time. + * Class for fetching initial friend cards data * - * Implemented to fix an issue when Inventory folders are in incomplete state. See EXT-2061, EXT-1935, EXT-813. - * For now it uses to periodically sync Inventory Friends/All folder with a Agent's Friends List - * until it is complete. - */ -class FriendListUpdater : public LLEventTimer + * Implemented to fix an issue when Inventory folders are in incomplete state. + * See EXT-2320, EXT-2061, EXT-1935, EXT-813. + * Uses a callback to sync Inventory Friends/All folder with agent's Friends List. + */ +class LLInitialFriendCardsFetch : public LLInventoryFetchDescendentsObserver { public: - typedef boost::function<bool()> callback_t; + typedef boost::function<void()> callback_t; - FriendListUpdater(callback_t cb, F32 period) - : LLEventTimer(period) - , mCallback(cb) - { - mEventTimer.start(); - } + LLInitialFriendCardsFetch(callback_t cb) + : mCheckFolderCallback(cb) {} - virtual BOOL tick() // from LLEventTimer - { - return mCallback(); - } + /* virtual */ void done(); private: - callback_t mCallback; + callback_t mCheckFolderCallback; }; +void LLInitialFriendCardsFetch::done() +{ + // This observer is no longer needed. + gInventory.removeObserver(this); + + mCheckFolderCallback(); + + delete this; +} // LLFriendCardsManager Constructor / Destructor LLFriendCardsManager::LLFriendCardsManager() -: mFriendsAllFolderCompleted(true) { LLAvatarTracker::instance().addObserver(this); } @@ -167,30 +162,6 @@ const LLUUID LLFriendCardsManager::extractAvatarID(const LLUUID& avatarID) return rv; } -// be sure LLInventoryModel::buildParentChildMap() has been called before it. -// and this method must be called before any actions with friend list -void LLFriendCardsManager::ensureFriendFoldersExist() -{ - const LLUUID callingCardsFolderID = gInventory.findCategoryUUIDForType(LLFolderType::FT_CALLINGCARD); - - LLUUID friendFolderUUID = findFriendFolderUUIDImpl(); - - if (friendFolderUUID.isNull()) - { - friendFolderUUID = gInventory.createNewCategory(callingCardsFolderID, - LLFolderType::FT_CALLINGCARD, get_friend_folder_name()); - } - - LLUUID friendAllSubfolderUUID = findFriendAllSubfolderUUIDImpl(); - - if (friendAllSubfolderUUID.isNull()) - { - friendAllSubfolderUUID = gInventory.createNewCategory(friendFolderUUID, - LLFolderType::FT_CALLINGCARD, get_friend_all_subfolder_name()); - } -} - - bool LLFriendCardsManager::isItemInAnyFriendsList(const LLViewerInventoryItem* item) { if (item->getType() != LLAssetType::AT_CALLINGCARD) @@ -305,63 +276,12 @@ bool LLFriendCardsManager::isAnyFriendCategory(const LLUUID& catID) const return TRUE == gInventory.isObjectDescendentOf(catID, friendFolderID); } -bool LLFriendCardsManager::syncFriendsFolder() +void LLFriendCardsManager::syncFriendCardsFolders() { - //lets create "Friends" and "Friends/All" in the Inventory "Calling Cards" if they are absent - LLFriendCardsManager::instance().ensureFriendFoldersExist(); - - LLAvatarTracker::buddy_map_t all_buddies; - LLAvatarTracker::instance().copyBuddyList(all_buddies); - - // 1. Remove Friend Cards for non-friends - LLInventoryModel::cat_array_t cats; - LLInventoryModel::item_array_t items; - - gInventory.collectDescendents(findFriendAllSubfolderUUIDImpl(), cats, items, LLInventoryModel::EXCLUDE_TRASH); - - LLInventoryModel::item_array_t::const_iterator it; - for (it = items.begin(); it != items.end(); ++it) - { - lldebugs << "Check if buddy is in list: " << (*it)->getName() << " " << (*it)->getCreatorUUID() << llendl; - if (NULL == get_ptr_in_map(all_buddies, (*it)->getCreatorUUID())) - { - lldebugs << "NONEXISTS, so remove it" << llendl; - removeFriendCardFromInventory((*it)->getCreatorUUID()); - } - } - - // 2. Add missing Friend Cards for friends - LLAvatarTracker::buddy_map_t::const_iterator buddy_it = all_buddies.begin(); - llinfos << "try to build friends, count: " << all_buddies.size() << llendl; - mFriendsAllFolderCompleted = true; - for(; buddy_it != all_buddies.end(); ++buddy_it) - { - const LLUUID& buddy_id = (*buddy_it).first; - addFriendCardToInventory(buddy_id); - } - - if (!mFriendsAllFolderCompleted) - { - forceFriendListIsLoaded(findFriendAllSubfolderUUIDImpl()); - - static bool timer_started = false; - if (!timer_started) - { - lldebugs << "Create and start timer to sync Inventory Friends All folder with Friends list" << llendl; - - // do not worry about destruction of the FriendListUpdater. - // It will be deleted by LLEventTimer::updateClass when FriendListUpdater::tick() returns true. - new FriendListUpdater(boost::bind(&LLFriendCardsManager::syncFriendsFolder, this), - FETCH_FRIENDS_DESCENDENTS_PERIOD); - } - timer_started = true; - } - else - { - lldebugs << "Friends/All Inventory folder is synchronized with the Agent's Friends List" << llendl; - } + const LLUUID callingCardsFolderID = gInventory.findCategoryUUIDForType(LLFolderType::FT_CALLINGCARD); - return mFriendsAllFolderCompleted; + fetchAndCheckFolderDescendents(callingCardsFolderID, + boost::bind(&LLFriendCardsManager::ensureFriendsFolderExists, this)); } void LLFriendCardsManager::collectFriendsLists(folderid_buddies_map_t& folderBuddiesMap) const @@ -482,6 +402,122 @@ void LLFriendCardsManager::findMatchedFriendCards(const LLUUID& avatarID, LLInve } } +void LLFriendCardsManager::fetchAndCheckFolderDescendents(const LLUUID& folder_id, callback_t cb) +{ + // This instance will be deleted in LLInitialFriendCardsFetch::done(). + LLInitialFriendCardsFetch* fetch = new LLInitialFriendCardsFetch(cb); + + LLInventoryFetchDescendentsObserver::folder_ref_t folders; + folders.push_back(folder_id); + + fetch->fetchDescendents(folders); + if(fetch->isEverythingComplete()) + { + // everything is already here - call done. + fetch->done(); + } + else + { + // it's all on it's way - add an observer, and the inventory + // will call done for us when everything is here. + gInventory.addObserver(fetch); + } +} + +// Make sure LLInventoryModel::buildParentChildMap() has been called before it. +// This method must be called before any actions with friends list. +void LLFriendCardsManager::ensureFriendsFolderExists() +{ + const LLUUID calling_cards_folder_ID = gInventory.findCategoryUUIDForType(LLFolderType::FT_CALLINGCARD); + + // If "Friends" folder exists in "Calling Cards" we should check if "All" sub-folder + // exists in "Friends", otherwise we create it. + LLUUID friends_folder_ID = findFriendFolderUUIDImpl(); + if (friends_folder_ID.notNull()) + { + fetchAndCheckFolderDescendents(friends_folder_ID, + boost::bind(&LLFriendCardsManager::ensureFriendsAllFolderExists, this)); + } + else + { + if (!gInventory.isCategoryComplete(calling_cards_folder_ID)) + { + LLViewerInventoryCategory* cat = gInventory.getCategory(calling_cards_folder_ID); + std::string cat_name = cat ? cat->getName() : "unknown"; + llwarns << "Failed to find \"" << cat_name << "\" category descendents in Category Tree." << llendl; + } + + friends_folder_ID = gInventory.createNewCategory(calling_cards_folder_ID, + LLFolderType::FT_CALLINGCARD, get_friend_folder_name()); + + gInventory.createNewCategory(friends_folder_ID, + LLFolderType::FT_CALLINGCARD, get_friend_all_subfolder_name()); + + // Now when we have all needed folders we can sync their contents with buddies list. + syncFriendsFolder(); + } +} + +// Make sure LLFriendCardsManager::ensureFriendsFolderExists() has been called before it. +void LLFriendCardsManager::ensureFriendsAllFolderExists() +{ + LLUUID friends_all_folder_ID = findFriendAllSubfolderUUIDImpl(); + if (friends_all_folder_ID.notNull()) + { + fetchAndCheckFolderDescendents(friends_all_folder_ID, + boost::bind(&LLFriendCardsManager::syncFriendsFolder, this)); + } + else + { + LLUUID friends_folder_ID = findFriendFolderUUIDImpl(); + + if (!gInventory.isCategoryComplete(friends_folder_ID)) + { + LLViewerInventoryCategory* cat = gInventory.getCategory(friends_folder_ID); + std::string cat_name = cat ? cat->getName() : "unknown"; + llwarns << "Failed to find \"" << cat_name << "\" category descendents in Category Tree." << llendl; + } + + friends_all_folder_ID = gInventory.createNewCategory(friends_folder_ID, + LLFolderType::FT_CALLINGCARD, get_friend_all_subfolder_name()); + + // Now when we have all needed folders we can sync their contents with buddies list. + syncFriendsFolder(); + } +} + +void LLFriendCardsManager::syncFriendsFolder() +{ + LLAvatarTracker::buddy_map_t all_buddies; + LLAvatarTracker::instance().copyBuddyList(all_buddies); + + // 1. Remove Friend Cards for non-friends + LLInventoryModel::cat_array_t cats; + LLInventoryModel::item_array_t items; + + gInventory.collectDescendents(findFriendAllSubfolderUUIDImpl(), cats, items, LLInventoryModel::EXCLUDE_TRASH); + + LLInventoryModel::item_array_t::const_iterator it; + for (it = items.begin(); it != items.end(); ++it) + { + lldebugs << "Check if buddy is in list: " << (*it)->getName() << " " << (*it)->getCreatorUUID() << llendl; + if (NULL == get_ptr_in_map(all_buddies, (*it)->getCreatorUUID())) + { + lldebugs << "NONEXISTS, so remove it" << llendl; + removeFriendCardFromInventory((*it)->getCreatorUUID()); + } + } + + // 2. Add missing Friend Cards for friends + LLAvatarTracker::buddy_map_t::const_iterator buddy_it = all_buddies.begin(); + llinfos << "try to build friends, count: " << all_buddies.size() << llendl; + for(; buddy_it != all_buddies.end(); ++buddy_it) + { + const LLUUID& buddy_id = (*buddy_it).first; + addFriendCardToInventory(buddy_id); + } +} + class CreateFriendCardCallback : public LLInventoryCallback { public: @@ -494,9 +530,8 @@ public: } }; -bool LLFriendCardsManager::addFriendCardToInventory(const LLUUID& avatarID) +void LLFriendCardsManager::addFriendCardToInventory(const LLUUID& avatarID) { - LLInventoryModel* invModel = &gInventory; bool shouldBeAdded = true; std::string name; @@ -518,13 +553,6 @@ bool LLFriendCardsManager::addFriendCardToInventory(const LLUUID& avatarID) lldebugs << "is found in sentRequests: " << name << llendl; } - LLUUID friendListFolderID = findFriendAllSubfolderUUIDImpl(); - if (friendListFolderID.notNull() && shouldBeAdded && !invModel->isCategoryComplete(friendListFolderID)) - { - mFriendsAllFolderCompleted = false; - shouldBeAdded = false; - lldebugs << "Friends/All category is not completed" << llendl; - } if (shouldBeAdded) { putAvatarData(avatarID); @@ -533,10 +561,8 @@ bool LLFriendCardsManager::addFriendCardToInventory(const LLUUID& avatarID) // TODO: mantipov: Is CreateFriendCardCallback really needed? Probably not LLPointer<LLInventoryCallback> cb = new CreateFriendCardCallback(); - create_inventory_callingcard(avatarID, friendListFolderID, cb); + create_inventory_callingcard(avatarID, findFriendAllSubfolderUUIDImpl(), cb); } - - return shouldBeAdded; } void LLFriendCardsManager::removeFriendCardFromInventory(const LLUUID& avatarID) @@ -582,11 +608,4 @@ void LLFriendCardsManager::onFriendListUpdate(U32 changed_mask) } } -void LLFriendCardsManager::forceFriendListIsLoaded(const LLUUID& folder_id) const -{ - bool fetching_inventory = gInventory.fetchDescendentsOf(folder_id); - lldebugs << "Trying to fetch descendants of Friends/All Inventory folder, fetched: " - << fetching_inventory << llendl; -} - // EOF diff --git a/indra/newview/llfriendcard.h b/indra/newview/llfriendcard.h index feea05bc1d..98dc3153d0 100644 --- a/indra/newview/llfriendcard.h +++ b/indra/newview/llfriendcard.h @@ -58,14 +58,6 @@ public: } /** - * Ensures that all necessary folders are created in Inventory. - * - * For now it processes Calling Card, Calling Card/Friends & Calling Card/Friends/All folders - */ - void ensureFriendFoldersExist(); - - - /** * Determines if specified Inventory Calling Card exists in any of lists * in the Calling Card/Friends/ folder (Default, or Custom) */ @@ -88,11 +80,10 @@ public: bool isAnyFriendCategory(const LLUUID& catID) const; /** - * Synchronizes content of the Calling Card/Friends/All Global Inventory folder with Agent's Friend List - * - * @return true - if folder is already synchronized, false otherwise. + * Checks whether "Friends" and "Friends/All" folders exist in "Calling Cards" category + * (creates them otherwise) and fetches their contents to synchronize with Agent's Friends List. */ - bool syncFriendsFolder(); + void syncFriendCardsFolders(); /*! * \brief @@ -108,6 +99,8 @@ public: void collectFriendsLists(folderid_buddies_map_t& folderBuddiesMap) const; private: + typedef boost::function<void()> callback_t; + LLFriendCardsManager(); ~LLFriendCardsManager(); @@ -133,10 +126,29 @@ private: const LLUUID& findFriendCardInventoryUUIDImpl(const LLUUID& avatarID); void findMatchedFriendCards(const LLUUID& avatarID, LLInventoryModel::item_array_t& items) const; + void fetchAndCheckFolderDescendents(const LLUUID& folder_id, callback_t cb); + + /** + * Checks whether "Calling Cards/Friends" folder exists. If not, creates it with "All" + * sub-folder and synchronizes its contents with buddies list. + */ + void ensureFriendsFolderExists(); + + /** + * Checks whether "Calling Cards/Friends/All" folder exists. If not, creates it and + * synchronizes its contents with buddies list. + */ + void ensureFriendsAllFolderExists(); + + /** + * Synchronizes content of the Calling Card/Friends/All Global Inventory folder with Agent's Friend List + */ + void syncFriendsFolder(); + /** * Adds avatar specified by its UUID into the Calling Card/Friends/All Global Inventory folder */ - bool addFriendCardToInventory(const LLUUID& avatarID); + void addFriendCardToInventory(const LLUUID& avatarID); /** * Removes an avatar specified by its UUID from the Calling Card/Friends/All Global Inventory folder @@ -146,20 +158,11 @@ private: void onFriendListUpdate(U32 changed_mask); - /** - * Force fetching of the Inventory folder specified by passed folder's LLUUID. - * - * It only sends request to server, server reply should be processed in other place. - * Because request can be sent via UDP we need to periodically check if request was completed with success. - */ - void forceFriendListIsLoaded(const LLUUID& folder_id) const; - private: typedef std::set<LLUUID> avatar_uuid_set_t; avatar_uuid_set_t mBuddyIDSet; - bool mFriendsAllFolderCompleted; }; #endif // LL_LLFRIENDCARD_H diff --git a/indra/newview/llgesturemgr.cpp b/indra/newview/llgesturemgr.cpp index 59274c8638..8e774dc199 100644 --- a/indra/newview/llgesturemgr.cpp +++ b/indra/newview/llgesturemgr.cpp @@ -37,7 +37,6 @@ // system #include <functional> #include <algorithm> -#include <boost/tokenizer.hpp> // library #include "lldatapacker.h" @@ -206,6 +205,9 @@ struct LLLoadInfo // If inform_server is true, will send a message upstream to update // the user_gesture_active table. +/** + * It will load a gesture from remote storage + */ void LLGestureManager::activateGestureWithAsset(const LLUUID& item_id, const LLUUID& asset_id, BOOL inform_server, @@ -921,8 +923,8 @@ void LLGestureManager::onLoadComplete(LLVFS *vfs, delete info; info = NULL; - - LLGestureManager::instance().mLoadingCount--; + LLGestureManager& self = LLGestureManager::instance(); + self.mLoadingCount--; if (0 == status) { @@ -944,15 +946,15 @@ void LLGestureManager::onLoadComplete(LLVFS *vfs, { if (deactivate_similar) { - LLGestureManager::instance().deactivateSimilarGestures(gesture, item_id); + self.deactivateSimilarGestures(gesture, item_id); // Display deactivation message if this was the last of the bunch. - if (LLGestureManager::instance().mLoadingCount == 0 - && LLGestureManager::instance().mDeactivateSimilarNames.length() > 0) + if (self.mLoadingCount == 0 + && self.mDeactivateSimilarNames.length() > 0) { // we're done with this set of deactivations LLSD args; - args["NAMES"] = LLGestureManager::instance().mDeactivateSimilarNames; + args["NAMES"] = self.mDeactivateSimilarNames; LLNotifications::instance().add("DeactivatedGesturesTrigger", args); } } @@ -965,9 +967,9 @@ void LLGestureManager::onLoadComplete(LLVFS *vfs, else { // Watch this item and set gesture name when item exists in inventory - LLGestureManager::instance().watchItem(item_id); + self.watchItem(item_id); } - LLGestureManager::instance().mActive[item_id] = gesture; + self.mActive[item_id] = gesture; // Everything has been successful. Add to the active list. gInventory.addChangedMask(LLInventoryObserver::LABEL, item_id); @@ -989,14 +991,21 @@ void LLGestureManager::onLoadComplete(LLVFS *vfs, gAgent.sendReliableMessage(); } + callback_map_t::iterator i_cb = self.mCallbackMap.find(item_id); + + if(i_cb != self.mCallbackMap.end()) + { + i_cb->second(gesture); + self.mCallbackMap.erase(i_cb); + } - LLGestureManager::instance().notifyObservers(); + self.notifyObservers(); } else { llwarns << "Unable to load gesture" << llendl; - LLGestureManager::instance().mActive.erase(item_id); + self.mActive.erase(item_id); delete gesture; gesture = NULL; diff --git a/indra/newview/llgesturemgr.h b/indra/newview/llgesturemgr.h index 947773d66d..7c3b742780 100644 --- a/indra/newview/llgesturemgr.h +++ b/indra/newview/llgesturemgr.h @@ -57,6 +57,12 @@ public: class LLGestureManager : public LLSingleton<LLGestureManager>, public LLInventoryCompletionObserver { public: + + typedef boost::function<void (LLMultiGesture* loaded_gesture)> gesture_loaded_callback_t; + // Maps inventory item_id to gesture + typedef std::map<LLUUID, LLMultiGesture*> item_map_t; + typedef std::map<LLUUID, gesture_loaded_callback_t> callback_map_t; + LLGestureManager(); ~LLGestureManager(); @@ -97,6 +103,7 @@ public: BOOL isGesturePlaying(const LLUUID& item_id); + const item_map_t& getActiveGestures() const { return mActive; } // Force a gesture to be played, for example, if it is being // previewed. void playGesture(LLMultiGesture* gesture); @@ -106,7 +113,15 @@ public: // Also remove from playing list void stopGesture(LLMultiGesture* gesture); void stopGesture(const LLUUID& item_id); - + /** + * Add cb into callbackMap. + * Note: + * Manager will call cb after gesture will be loaded and will remove cb automatically. + */ + void setGestureLoadedCallback(LLUUID inv_item_id, gesture_loaded_callback_t cb) + { + mCallbackMap[inv_item_id] = cb; + } // Trigger the first gesture that matches this key. // Returns TRUE if it finds a gesture bound to that key. BOOL triggerGesture(KEY key, MASK mask); @@ -144,13 +159,7 @@ protected: LLAssetType::EType type, void* user_data, S32 status, LLExtStat ext_status); -public: - BOOL mValid; - std::vector<LLMultiGesture*> mPlaying; - - // Maps inventory item_id to gesture - typedef std::map<LLUUID, LLMultiGesture*> item_map_t; - +private: // Active gestures. // NOTE: The gesture pointer CAN BE NULL. This means that // there is a gesture with that item_id, but the asset data @@ -159,8 +168,11 @@ public: S32 mLoadingCount; std::string mDeactivateSimilarNames; - + std::vector<LLGestureManagerObserver*> mObservers; + callback_map_t mCallbackMap; + std::vector<LLMultiGesture*> mPlaying; + BOOL mValid; }; #endif diff --git a/indra/newview/llimfloater.cpp b/indra/newview/llimfloater.cpp index 5ea900e46d..059912d5d4 100644 --- a/indra/newview/llimfloater.cpp +++ b/indra/newview/llimfloater.cpp @@ -120,11 +120,7 @@ void LLIMFloater::newIMCallback(const LLSD& data){ LLUUID session_id = data["session_id"].asUUID(); LLIMFloater* floater = LLFloaterReg::findTypedInstance<LLIMFloater>("impanel", session_id); - if (floater == NULL) - { - llwarns << "new_im_callback for non-existent session_id " << session_id << llendl; - return; - } + if (floater == NULL) return; // update if visible, otherwise will be updated when opened if (floater->getVisible()) diff --git a/indra/newview/llnearbychatbar.cpp b/indra/newview/llnearbychatbar.cpp index 94b8791147..333646d2c5 100644 --- a/indra/newview/llnearbychatbar.cpp +++ b/indra/newview/llnearbychatbar.cpp @@ -97,9 +97,10 @@ void LLGestureComboBox::refreshGestures() clearRows(); mGestures.clear(); - LLGestureManager::item_map_t::iterator it; + LLGestureManager::item_map_t::const_iterator it; + const LLGestureManager::item_map_t& active_gestures = LLGestureManager::instance().getActiveGestures(); LLSD::Integer idx(0); - for (it = LLGestureManager::instance().mActive.begin(); it != LLGestureManager::instance().mActive.end(); ++it) + for (it = active_gestures.begin(); it != active_gestures.end(); ++it) { LLMultiGesture* gesture = (*it).second; if (gesture) diff --git a/indra/newview/llnearbychathandler.cpp b/indra/newview/llnearbychathandler.cpp index b4e0ab198a..f3b63c8616 100644 --- a/indra/newview/llnearbychathandler.cpp +++ b/indra/newview/llnearbychathandler.cpp @@ -332,7 +332,8 @@ void LLNearbyChatHandler::processChat(const LLChat& chat_msg) //only messages from AGENTS if(CHAT_SOURCE_OBJECT == chat_msg.mSourceType) { - return;//dn't show toast for messages from objects + if(chat_msg.mChatType == CHAT_TYPE_DEBUG_MSG) + return;//ok for now we don't skip messeges from object, so skip only debug messages } LLUUID id; diff --git a/indra/newview/llscreenchannel.cpp b/indra/newview/llscreenchannel.cpp index ed606d5457..81eb133b07 100644 --- a/indra/newview/llscreenchannel.cpp +++ b/indra/newview/llscreenchannel.cpp @@ -455,7 +455,7 @@ void LLScreenChannel::createOverflowToast(S32 bottom, F32 timer) if(!mOverflowToastPanel) return; - mOverflowToastPanel->setOnFadeCallback(boost::bind(&LLScreenChannel::closeOverflowToastPanel, this)); + mOverflowToastPanel->setOnFadeCallback(boost::bind(&LLScreenChannel::onOverflowToastHide, this)); LLTextBox* text_box = mOverflowToastPanel->getChild<LLTextBox>("toast_text"); std::string text = llformat(mOverflowFormatString.c_str(),mHiddenToastsNum); diff --git a/indra/newview/llstartup.cpp b/indra/newview/llstartup.cpp index 2c59d62b4b..696b0d9af1 100644 --- a/indra/newview/llstartup.cpp +++ b/indra/newview/llstartup.cpp @@ -1691,8 +1691,11 @@ bool idle_startup() //all categories loaded. lets create "My Favorites" category gInventory.findCategoryUUIDForType(LLFolderType::FT_FAVORITE,true); - // lets create "Friends" and "Friends/All" in the Inventory "Calling Cards" and fill it with buddies - LLFriendCardsManager::instance().syncFriendsFolder(); + // Checks whether "Friends" and "Friends/All" folders exist in "Calling Cards" folder, + // fetches their contents if needed and synchronizes it with buddies list. + // If the folders are not found they are created. + LLFriendCardsManager::instance().syncFriendCardsFolders(); + // set up callbacks llinfos << "Registering Callbacks" << llendl; diff --git a/indra/newview/skins/default/xui/en/floater_gesture.xml b/indra/newview/skins/default/xui/en/floater_gesture.xml index b23482655c..a3ac878202 100644 --- a/indra/newview/skins/default/xui/en/floater_gesture.xml +++ b/indra/newview/skins/default/xui/en/floater_gesture.xml @@ -84,21 +84,21 @@ top_delta="0" width="18" /> <button - follows="bottom|left" + follows="bottom|right" font="SansSerifBigBold" height="18" image_selected="TrashItem_Press" image_unselected="TrashItem_Off" image_disabled="TrashItem_Disabled" layout="topleft" - left_pad="230" name="del_btn" + right="-5" tool_tip="Delete this gesture" top_delta="0" width="18" /> </panel> <button - follows="bottom|right" + follows="left|bottom" height="23" label="Edit" layout="topleft" @@ -107,7 +107,7 @@ top_pad="5" width="83" /> <button - follows="bottom|right" + follows="left|bottom" height="23" label="Play" layout="topleft" @@ -116,7 +116,7 @@ top_delta="0" width="83" /> <button - follows="bottom|right" + follows="left|bottom" height="23" label="Stop" layout="topleft" diff --git a/indra/newview/skins/default/xui/en/panel_bottomtray.xml b/indra/newview/skins/default/xui/en/panel_bottomtray.xml index 3c16a439d9..a902f50582 100644 --- a/indra/newview/skins/default/xui/en/panel_bottomtray.xml +++ b/indra/newview/skins/default/xui/en/panel_bottomtray.xml @@ -333,6 +333,6 @@ as for parent layout_panel (chiclet_list_panel) to resize bottom tray properly. min_width="4" right="-1" top="0" - width="26"/> + width="4"/> </layout_stack> </panel> diff --git a/indra/newview/skins/default/xui/en/panel_group_notify.xml b/indra/newview/skins/default/xui/en/panel_group_notify.xml index ef3120174e..984a799b41 100644 --- a/indra/newview/skins/default/xui/en/panel_group_notify.xml +++ b/indra/newview/skins/default/xui/en/panel_group_notify.xml @@ -1,77 +1,117 @@ -<?xml version="1.0" encoding="utf-8" standalone="yes" ?> -<panel background_visible="true" bevel_style="in" bg_alpha_color="0 0 0 0" - height="155" label="instant_message" layout="topleft" left="0" - name="panel_group_notify" top="0" width="350"> - <string - name="message_max_lines_count"> - 4 - </string> - <panel follows="top" background_visible="true" bevel_style="in" bg_alpha_color="black" - height="30" label="header" layout="topleft" left="0" name="header" - top="0" width="350"> - <icon follows="left|top|right|bottom" height="20" width="20" layout="topleft" - top="5" left="5" mouse_opaque="true" name="group_icon"/> - <text type="string" length="1" follows="left|top|right|bottom" - font="SansSerifBigBold" height="20" layout="topleft" left_pad="10" name="title" - text_color="GroupNotifyTextColor" top="5" width="275" use_ellipses="true"> - Sender Name / Group Name - </text> - </panel> - <text - follows="top" - height="20" - layout="topleft" - left="25" - name="subject" - text_color="GroupNotifyTextColor" - font="SansSerifBig" - top="40" - use_ellipses="true" - value="subject" - width="300" - word_wrap="true"> - subject - </text> - <text - follows="top" - height="20" - layout="topleft" - left="25" - name="datetime" - text_color="GroupNotifyTextColor" - font="SansSerif" - top="80" - use_ellipses="true" - value="datetime" - width="300" - word_wrap="true"> - datetime - </text> - <text - follows="left|top|bottom|right" - height="0" - layout="topleft" - left="25" - name="message" - text_color="GroupNotifyTextColor" - top="100" - use_ellipses="true" - value="message" - width="300" - word_wrap="true" - visible="true" > - </text> - <icon - follows="left|bottom|right" height="15" width="15" - layout="topleft" bottom="122" left="25" mouse_opaque="true" name="attachment_icon" visible="true" - /> - <text font="SansSerif" font.style="UNDERLINE" font_shadow="none" - type="string" length="1" follows="left|bottom|right" layout="topleft" - left="45" bottom="122" height="15" width="280" name="attachment" - text_color="GroupNotifyTextColor" visible="true"> - Attachment - </text> - - <button label="OK" layout="topleft" bottom="145" left="140" height="20" - width="70" name="btn_ok" follows="bottom" /> -</panel>
\ No newline at end of file +<?xml version="1.0" encoding="utf-8" standalone="yes" ?>
+<panel
+ background_visible="true"
+ bevel_style="in"
+ bg_alpha_color="0 0 0 0"
+ height="135"
+ label="instant_message"
+ layout="topleft"
+ left="0"
+ name="panel_group_notify"
+ top="0"
+ width="305">
+ <string
+ name="message_max_lines_count"
+ value="4" />
+ <panel
+ background_visible="true"
+ bevel_style="in"
+ bg_alpha_color="black"
+ follows="top"
+ height="30"
+ label="header"
+ layout="topleft"
+ left="0"
+ name="header"
+ top="0"
+ width="305">
+ <icon
+ follows="left|top|right|bottom"
+ height="20"
+ layout="topleft"
+ left="5"
+ mouse_opaque="true"
+ name="group_icon"
+ top="5"
+ width="20" />
+ <text
+ follows="left|top|right|bottom"
+ font="SansSerifBigBold"
+ height="20"
+ layout="topleft"
+ left_pad="10"
+ name="title"
+ text_color="GroupNotifyTextColor"
+ top="5"
+ use_ellipses="true"
+ value="Sender Name / Group Name"
+ width="230" />
+ </panel>
+ <text
+ follows="top"
+ font="SansSerifBig"
+ height="20"
+ layout="topleft"
+ left="25"
+ name="subject"
+ text_color="GroupNotifyTextColor"
+ top="40"
+ use_ellipses="true"
+ value="subject"
+ width="270"
+ wrap="true" />
+ <text
+ follows="top"
+ font="SansSerif"
+ height="20"
+ layout="topleft"
+ left="25"
+ name="datetime"
+ text_color="GroupNotifyTextColor"
+ top="80"
+ use_ellipses="true"
+ value="datetime"
+ width="270"
+ wrap="true" />
+ <text
+ follows="left|top|bottom|right"
+ height="0"
+ layout="topleft"
+ left="25"
+ name="message"
+ text_color="GroupNotifyTextColor"
+ top="100"
+ use_ellipses="true"
+ value="message"
+ width="270"
+ wrap="true" />
+ <icon
+ bottom="122"
+ follows="left|bottom|right"
+ height="15"
+ layout="topleft"
+ left="25"
+ mouse_opaque="true"
+ name="attachment_icon"
+ width="15" />
+ <text
+ bottom="122"
+ follows="left|bottom|right"
+ font="SansSerif"
+ height="15"
+ layout="topleft"
+ left="45"
+ name="attachment"
+ text_color="GroupNotifyTextColor"
+ value="Attachment"
+ width="280" />
+ <button
+ bottom="130"
+ follows="bottom"
+ height="20"
+ label="OK"
+ layout="topleft"
+ left="25"
+ name="btn_ok"
+ width="70" />
+</panel>
diff --git a/indra/newview/skins/default/xui/en/panel_nearby_chat_bar.xml b/indra/newview/skins/default/xui/en/panel_nearby_chat_bar.xml index a77094e942..ecf35523cd 100644 --- a/indra/newview/skins/default/xui/en/panel_nearby_chat_bar.xml +++ b/indra/newview/skins/default/xui/en/panel_nearby_chat_bar.xml @@ -23,7 +23,7 @@ layout="topleft" left_delta="7" left="0" - max_length="254" + max_length="512" name="chat_box" tool_tip="Press Enter to say, Ctrl+Enter to shout" top="0" |