diff options
Diffstat (limited to 'indra')
29 files changed, 468 insertions, 124 deletions
| diff --git a/indra/CMakeLists.txt b/indra/CMakeLists.txt index 205ce402a0..500ffa3e8b 100644 --- a/indra/CMakeLists.txt +++ b/indra/CMakeLists.txt @@ -29,15 +29,6 @@ else()    set( USE_AUTOBUILD_3P ON )  endif() -# The viewer code base can now be successfully compiled with -std=c++14. But -# turning that on in the generic viewer-build-variables/variables file would -# potentially require tweaking each of our ~50 third-party library builds. -# Until we decide to set -std=c++14 in viewer-build-variables/variables, set -# it locally here: we want to at least prevent inadvertently reintroducing -# viewer code that would fail with C++14. -set(CMAKE_CXX_STANDARD 17) -set(CMAKE_CXX_STANDARD_REQUIRED ON) -  include(Variables)  include(BuildVersion) diff --git a/indra/llui/lllineeditor.cpp b/indra/llui/lllineeditor.cpp index 940cf398c0..60dbfd68c6 100644 --- a/indra/llui/lllineeditor.cpp +++ b/indra/llui/lllineeditor.cpp @@ -164,7 +164,8 @@ LLLineEditor::LLLineEditor(const LLLineEditor::Params& p)  	mHighlightColor(p.highlight_color()),  	mPreeditBgColor(p.preedit_bg_color()),  	mGLFont(p.font), -	mContextMenuHandle() +	mContextMenuHandle(), +    mShowContextMenu(true)  {  	llassert( mMaxLengthBytes > 0 ); @@ -825,7 +826,7 @@ BOOL LLLineEditor::handleMiddleMouseDown(S32 x, S32 y, MASK mask)  BOOL LLLineEditor::handleRightMouseDown(S32 x, S32 y, MASK mask)  {  	setFocus(TRUE); -	if (!LLUICtrl::handleRightMouseDown(x, y, mask)) +    if (!LLUICtrl::handleRightMouseDown(x, y, mask) && getShowContextMenu())  	{  		showContextMenu(x, y);  	} diff --git a/indra/llui/lllineeditor.h b/indra/llui/lllineeditor.h index ae4e05c065..f983828d2b 100644 --- a/indra/llui/lllineeditor.h +++ b/indra/llui/lllineeditor.h @@ -286,7 +286,10 @@ public:  	void			setBgImage(LLPointer<LLUIImage> image) { mBgImage = image; }  	void			setBgImageFocused(LLPointer<LLUIImage> image) { mBgImageFocused = image; } -private: +    void setShowContextMenu(bool show) { mShowContextMenu = show; } +    bool getShowContextMenu() const { return mShowContextMenu; } + +  private:  	// private helper methods  	void                    pasteHelper(bool is_primary); @@ -405,6 +408,8 @@ protected:  	LLHandle<LLContextMenu> mContextMenuHandle; +    bool mShowContextMenu; +  private:  	// Instances that by default point to the statics but can be overidden in XML.  	LLPointer<LLUIImage> mBgImage; diff --git a/indra/llui/lltabcontainer.cpp b/indra/llui/lltabcontainer.cpp index 8c841540a5..f48fc567b2 100644 --- a/indra/llui/lltabcontainer.cpp +++ b/indra/llui/lltabcontainer.cpp @@ -2143,14 +2143,19 @@ void LLTabContainer::commitHoveredButton(S32 x, S32 y)  {  	if (!getTabsHidden() && hasMouseCapture())  	{ -		for(tuple_list_t::iterator iter = mTabList.begin(); iter != mTabList.end(); ++iter) +		for (tuple_list_t::iterator iter = mTabList.begin(); iter != mTabList.end(); ++iter)  		{ -			LLTabTuple* tuple = *iter; -			S32 local_x = x - tuple->mButton->getRect().mLeft; -			S32 local_y = y - tuple->mButton->getRect().mBottom; -			if (tuple->mButton->pointInView(local_x, local_y) && tuple->mButton->getEnabled() && !tuple->mTabPanel->getVisible()) +			LLButton* button = (*iter)->mButton; +			LLPanel* panel = (*iter)->mTabPanel; +			if (button->getEnabled() && button->getVisible() && !panel->getVisible())  			{ -				tuple->mButton->onCommit(); +				S32 local_x = x - button->getRect().mLeft; +				S32 local_y = y - button->getRect().mBottom; +				if (button->pointInView(local_x, local_y)) +				{ +					button->onCommit(); +					break; +				}  			}  		}  	} diff --git a/indra/llui/llurlentry.cpp b/indra/llui/llurlentry.cpp index 6a9070634c..77e9edf5e5 100644 --- a/indra/llui/llurlentry.cpp +++ b/indra/llui/llurlentry.cpp @@ -35,7 +35,9 @@  #include "llavatarnamecache.h"  #include "llcachename.h" +#include "llkeyboard.h"  #include "llregex.h" +#include "llscrolllistctrl.h" // for LLUrlEntryKeybinding file parsing  #include "lltrans.h"  #include "lluicolortable.h"  #include "message.h" @@ -1609,3 +1611,122 @@ std::string LLUrlEntryIPv6::getUrl(const std::string &string) const  {  	return string;  } + + +// +// LLUrlEntryKeybinding Displays currently assigned key +// +LLUrlEntryKeybinding::LLUrlEntryKeybinding() +    : LLUrlEntryBase() +    , pHandler(NULL) +{ +    mPattern = boost::regex(APP_HEADER_REGEX "/keybinding/\\w+(\\?mode=\\w+)?$", +                            boost::regex::perl | boost::regex::icase); +    mMenuName = "menu_url_experience.xml"; + +    initLocalization(); +} + +std::string LLUrlEntryKeybinding::getLabel(const std::string& url, const LLUrlLabelCallback& cb) +{ +    std::string control = getControlName(url); + +    std::map<std::string, LLLocalizationData>::iterator iter = mLocalizations.find(control); + +    std::string keybind; +    if (pHandler) +    { +        keybind = pHandler->getKeyBindingAsString(getMode(url), control); +    } + +    if (iter != mLocalizations.end()) +    { +        return iter->second.mLocalization + ": " + keybind; +    } + +    return control + ": " + keybind; +} + +std::string LLUrlEntryKeybinding::getTooltip(const std::string& url) const +{ +    std::string control = getControlName(url); + +    std::map<std::string, LLLocalizationData>::const_iterator iter = mLocalizations.find(control); +    if (iter != mLocalizations.end()) +    { +        return iter->second.mTooltip; +    } +    return url; +} + +std::string LLUrlEntryKeybinding::getControlName(const std::string& url) const +{ +    std::string search = "/keybinding/"; +    size_t pos_start = url.find(search); +    if (pos_start == std::string::npos) +    { +        return std::string(); +    } +    pos_start += search.size(); + +    size_t pos_end = url.find("?mode="); +    if (pos_end == std::string::npos) +    { +        pos_end = url.size(); +    } +    return url.substr(pos_start, pos_end - pos_start); +} + +std::string LLUrlEntryKeybinding::getMode(const std::string& url) const +{ +    std::string search = "?mode="; +    size_t pos_start = url.find(search); +    if (pos_start == std::string::npos) +    { +        return std::string(); +    } +    pos_start += search.size(); +    return url.substr(pos_start, url.size() - pos_start); +} + +void LLUrlEntryKeybinding::initLocalization() +{ +    initLocalizationFromFile("control_table_contents_movement.xml"); +    initLocalizationFromFile("control_table_contents_camera.xml"); +    initLocalizationFromFile("control_table_contents_editing.xml"); +    initLocalizationFromFile("control_table_contents_media.xml"); +} + +void LLUrlEntryKeybinding::initLocalizationFromFile(const std::string& filename) +{ +    LLXMLNodePtr xmlNode; +    LLScrollListCtrl::Contents contents; +    if (!LLUICtrlFactory::getLayeredXMLNode(filename, xmlNode)) +    { +        LL_WARNS() << "Failed to load " << filename << LL_ENDL; +        return; +    } +    LLXUIParser parser; +    parser.readXUI(xmlNode, contents, filename); + +    if (!contents.validateBlock()) +    { +        LL_WARNS() << "Failed to validate " << filename << LL_ENDL; +        return; +    } + +    for (LLInitParam::ParamIterator<LLScrollListItem::Params>::const_iterator row_it = contents.rows.begin(); +         row_it != contents.rows.end(); +         ++row_it) +    { +        std::string control = row_it->value.getValue().asString(); +        if (!control.empty() && control != "menu_separator") +        { +            mLocalizations[control] = +                LLLocalizationData( +                                   row_it->columns.begin()->value.getValue().asString(), +                                   row_it->columns.begin()->tool_tip.getValue() +                ); +        } +    } +} diff --git a/indra/llui/llurlentry.h b/indra/llui/llurlentry.h index 63a1506731..5d0f5479f6 100644 --- a/indra/llui/llurlentry.h +++ b/indra/llui/llurlentry.h @@ -550,4 +550,37 @@ public:  	std::string mHostPath;  }; +class LLKeyBindingToStringHandler; + +/// +/// LLUrlEntryKeybinding A way to access keybindings and show currently used one in text. +/// secondlife:///app/keybinding/control_name +class LLUrlEntryKeybinding: public LLUrlEntryBase +{ +public: +    LLUrlEntryKeybinding(); +    /*virtual*/ std::string getLabel(const std::string& url, const LLUrlLabelCallback& cb); +    /*virtual*/ std::string getTooltip(const std::string& url) const; +    void setHandler(LLKeyBindingToStringHandler* handler) {pHandler = handler;} +private: +    std::string getControlName(const std::string& url) const; +    std::string getMode(const std::string& url) const; +    void initLocalization(); +    void initLocalizationFromFile(const std::string& filename); + +    struct LLLocalizationData +    { +        LLLocalizationData() {} +        LLLocalizationData(const std::string& localization, const std::string& tooltip) +            : mLocalization(localization) +            , mTooltip(tooltip) +        {} +        std::string mLocalization; +        std::string mTooltip; +    }; + +    std::map<std::string, LLLocalizationData> mLocalizations; +    LLKeyBindingToStringHandler* pHandler; +}; +  #endif diff --git a/indra/llui/llurlregistry.cpp b/indra/llui/llurlregistry.cpp index 23f3dca3fb..3bd7321777 100644 --- a/indra/llui/llurlregistry.cpp +++ b/indra/llui/llurlregistry.cpp @@ -73,6 +73,8 @@ LLUrlRegistry::LLUrlRegistry()  	registerUrl(new LLUrlEntryPlace());  	registerUrl(new LLUrlEntryInventory());      registerUrl(new LLUrlEntryExperienceProfile()); +    mUrlEntryKeybinding = new LLUrlEntryKeybinding(); +    registerUrl(mUrlEntryKeybinding);  	//LLUrlEntrySL and LLUrlEntrySLLabel have more common pattern,   	//so it should be registered in the end of list  	registerUrl(new LLUrlEntrySL()); @@ -307,3 +309,9 @@ bool LLUrlRegistry::isUrl(const LLWString &text)  	}  	return false;  } + +void LLUrlRegistry::setKeybindingHandler(LLKeyBindingToStringHandler* handler) +{ +    LLUrlEntryKeybinding *entry = (LLUrlEntryKeybinding*)mUrlEntryKeybinding; +    entry->setHandler(handler); +} diff --git a/indra/llui/llurlregistry.h b/indra/llui/llurlregistry.h index efafe543ab..186447c0be 100644 --- a/indra/llui/llurlregistry.h +++ b/indra/llui/llurlregistry.h @@ -36,6 +36,8 @@  #include <string>  #include <vector> +class LLKeyBindingToStringHandler; +  /// This default callback for findUrl() simply ignores any label updates  void LLUrlRegistryNullCallback(const std::string &url,  							   const std::string &label, @@ -88,6 +90,9 @@ public:  	bool isUrl(const std::string &text);  	bool isUrl(const LLWString &text); +    // Set handler for url registry to be capable of parsing and populating keybindings +    void setKeybindingHandler(LLKeyBindingToStringHandler* handler); +  private:  	std::vector<LLUrlEntryBase *> mUrlEntry;  	LLUrlEntryBase*	mUrlEntryTrusted; @@ -96,6 +101,7 @@ private:  	LLUrlEntryBase* mUrlEntryHTTPLabel;  	LLUrlEntryBase* mUrlEntrySLLabel;  	LLUrlEntryBase* mUrlEntryNoLink; +    LLUrlEntryBase* mUrlEntryKeybinding;  };  #endif diff --git a/indra/llwindow/llkeyboard.cpp b/indra/llwindow/llkeyboard.cpp index e65cc7563e..34720ff64e 100644 --- a/indra/llwindow/llkeyboard.cpp +++ b/indra/llwindow/llkeyboard.cpp @@ -367,6 +367,45 @@ std::string LLKeyboard::stringFromKey(KEY key, bool translate)  }  //static +std::string LLKeyboard::stringFromMouse(EMouseClickType click, bool translate) +{ +    std::string res; +    switch (click) +    { +        case CLICK_LEFT: +            res = "LMB"; +            break; +        case CLICK_MIDDLE: +            res = "MMB"; +            break; +        case CLICK_RIGHT: +            res = "RMB"; +            break; +        case CLICK_BUTTON4: +            res = "MB4"; +            break; +        case CLICK_BUTTON5: +            res = "MB5"; +            break; +        case CLICK_DOUBLELEFT: +            res = "Double LMB"; +            break; +        default: +            break; +    } + +    if (translate && !res.empty()) +    { +        LLKeyStringTranslatorFunc* trans = gKeyboard->mStringTranslator; +        if (trans != NULL) +        { +            res = trans(res.c_str()); +        } +    } +    return res; +} + +//static  std::string LLKeyboard::stringFromAccelerator(MASK accel_mask)  {      std::string res; @@ -433,6 +472,18 @@ std::string LLKeyboard::stringFromAccelerator( MASK accel_mask, KEY key )  	return res;  } +//static +std::string LLKeyboard::stringFromAccelerator(MASK accel_mask, EMouseClickType click) +{ +    std::string res; +    if (CLICK_NONE == click) +    { +        return res; +    } +    res.append(stringFromAccelerator(accel_mask)); +    res.append(stringFromMouse(click)); +    return res; +}  //static  BOOL LLKeyboard::maskFromString(const std::string& str, MASK *mask) diff --git a/indra/llwindow/llkeyboard.h b/indra/llwindow/llkeyboard.h index fb1ae10f50..dad150e3c1 100644 --- a/indra/llwindow/llkeyboard.h +++ b/indra/llwindow/llkeyboard.h @@ -96,8 +96,10 @@ public:  	static BOOL		maskFromString(const std::string& str, MASK *mask);		// False on failure  	static BOOL		keyFromString(const std::string& str, KEY *key);			// False on failure  	static std::string stringFromKey(KEY key, bool translate = true); +    static std::string stringFromMouse(EMouseClickType click, bool translate = true);  	static std::string stringFromAccelerator( MASK accel_mask ); // separated for convinience, returns with "+": "Shift+" or "Shift+Alt+"...  	static std::string stringFromAccelerator( MASK accel_mask, KEY key ); +    static std::string stringFromAccelerator(MASK accel_mask, EMouseClickType click);  	void setCallbacks(LLWindowCallbacks *cbs) { mCallbacks = cbs; }  	F32				getKeyElapsedTime( KEY key );  // Returns time in seconds since key was pressed. @@ -130,6 +132,13 @@ protected:  	static std::map<std::string,KEY> sNamesToKeys;  }; +// Interface to get key from assigned command +class LLKeyBindingToStringHandler +{ +public: +    virtual std::string getKeyBindingAsString(const std::string& mode, const std::string& control) const = 0; +}; +  extern LLKeyboard *gKeyboard;  #endif diff --git a/indra/newview/llagent.cpp b/indra/newview/llagent.cpp index 8cc9be7244..289a9caea4 100644 --- a/indra/newview/llagent.cpp +++ b/indra/newview/llagent.cpp @@ -481,7 +481,11 @@ void LLAgent::init()  	// *Note: this is where LLViewerCamera::getInstance() used to be constructed. -	setFlying( gSavedSettings.getBOOL("FlyingAtExit") ); +    bool is_flying = gSavedSettings.getBOOL("FlyingAtExit"); +    if(is_flying) +    { +        setFlying(is_flying); +    }  	*mEffectColor = LLUIColorTable::instance().getColor("EffectColor"); @@ -2534,12 +2538,6 @@ void LLAgent::setStartPosition( U32 location_id )      if (!requestPostCapability("HomeLocation", body,               boost::bind(&LLAgent::setStartPositionSuccess, this, _1)))          LL_WARNS() << "Unable to post to HomeLocation capability." << LL_ENDL; - -    const U32 HOME_INDEX = 1; -    if( HOME_INDEX == location_id ) -    { -        setHomePosRegion( mRegionp->getHandle(), getPositionAgent() ); -    }  }  void LLAgent::setStartPositionSuccess(const LLSD &result) diff --git a/indra/newview/llappviewer.cpp b/indra/newview/llappviewer.cpp index e70fcb6e86..8ca9e6ef5d 100644 --- a/indra/newview/llappviewer.cpp +++ b/indra/newview/llappviewer.cpp @@ -195,6 +195,7 @@  #include "llhudeffecttrail.h"  #include "llvectorperfoptions.h"  #include "llslurl.h" +#include "llurlregistry.h"  #include "llwatchdog.h"  // Included so that constants/settings might be initialized @@ -4288,6 +4289,7 @@ void LLAppViewer::loadKeyBindings()  			LL_ERRS("InitInfo") << "Unable to open default key bindings from " << key_bindings_file << LL_ENDL;  		}  	} +    LLUrlRegistry::instance().setKeybindingHandler(&gViewerInput);  }  void LLAppViewer::purgeCache() diff --git a/indra/newview/llconversationmodel.h b/indra/newview/llconversationmodel.h index 7c6980a7e6..457b2e83fb 100644 --- a/indra/newview/llconversationmodel.h +++ b/indra/newview/llconversationmodel.h @@ -40,7 +40,7 @@ class LLConversationItem;  class LLConversationItemSession;  class LLConversationItemParticipant; -typedef std::map<LLUUID, LLConversationItem*> conversations_items_map; +typedef std::map<LLUUID, LLPointer<LLConversationItem> > conversations_items_map;  typedef std::map<LLUUID, LLFolderViewItem*> conversations_widgets_map;  typedef std::vector<std::string> menuentry_vec_t; diff --git a/indra/newview/llfloaterimcontainer.cpp b/indra/newview/llfloaterimcontainer.cpp index 2720b7fcf7..172e672dc5 100644 --- a/indra/newview/llfloaterimcontainer.cpp +++ b/indra/newview/llfloaterimcontainer.cpp @@ -155,6 +155,20 @@ void LLFloaterIMContainer::sessionIDUpdated(const LLUUID& old_session_id, const  	LLFloaterIMSessionTab::addToHost(new_session_id);  } + +LLConversationItem* LLFloaterIMContainer::getSessionModel(const LLUUID& session_id) +{ +    conversations_items_map::iterator iter = mConversationsItems.find(session_id); +    if (iter == mConversationsItems.end()) +    { +        return NULL; +    } +    else +    { +        return iter->second.get(); +    } +} +  void LLFloaterIMContainer::sessionRemoved(const LLUUID& session_id)  {  	removeConversationListItem(session_id); @@ -608,7 +622,8 @@ void LLFloaterIMContainer::handleConversationModelEvent(const LLSD& event)  	}  	else if (type == "add_participant")  	{ -		LLConversationItemSession* session_model = dynamic_cast<LLConversationItemSession*>(mConversationsItems[session_id]); +        LLConversationItem* item = getSessionModel(session_id); +		LLConversationItemSession* session_model = dynamic_cast<LLConversationItemSession*>(item);  		LLConversationItemParticipant* participant_model = (session_model ? session_model->findParticipant(participant_id) : NULL);  		LLIMModel::LLIMSession * im_sessionp = LLIMModel::getInstance()->findIMSession(session_id);  		if (!participant_view && session_model && participant_model) @@ -1749,10 +1764,9 @@ BOOL LLFloaterIMContainer::selectConversationPair(const LLUUID& session_id, bool  void LLFloaterIMContainer::setTimeNow(const LLUUID& session_id, const LLUUID& participant_id)  { -	LLConversationItemSession* item = dynamic_cast<LLConversationItemSession*>(get_ptr_in_map(mConversationsItems,session_id)); +	LLConversationItemSession* item = dynamic_cast<LLConversationItemSession*>(getSessionModel(session_id));  	if (item)  	{ -		item->setTimeNow(participant_id);  		mConversationViewModel.requestSortAll();  		mConversationsRoot->arrangeAll();  	} @@ -1761,7 +1775,7 @@ void LLFloaterIMContainer::setTimeNow(const LLUUID& session_id, const LLUUID& pa  void LLFloaterIMContainer::setNearbyDistances()  {  	// Get the nearby chat session: that's the one with uuid nul -	LLConversationItemSession* item = dynamic_cast<LLConversationItemSession*>(get_ptr_in_map(mConversationsItems,LLUUID())); +    LLConversationItemSession* item = dynamic_cast<LLConversationItemSession*>(getSessionModel(LLUUID()));  	if (item)  	{  		// Get the positions of the nearby avatars and their ids diff --git a/indra/newview/llfloaterimcontainer.h b/indra/newview/llfloaterimcontainer.h index b4a9d377ab..82f3b00ebc 100644 --- a/indra/newview/llfloaterimcontainer.h +++ b/indra/newview/llfloaterimcontainer.h @@ -106,7 +106,7 @@ public:  	LLConversationViewModel& getRootViewModel() { return mConversationViewModel; }      LLUUID getSelectedSession() { return mSelectedSession; }      void setSelectedSession(LLUUID sessionID) { mSelectedSession = sessionID; } -	LLConversationItem* getSessionModel(const LLUUID& session_id) { return get_ptr_in_map(mConversationsItems,session_id); } +	LLConversationItem* getSessionModel(const LLUUID& session_id);  	LLConversationSort& getSortOrder() { return mConversationViewModel.getSorter(); }  	// Handling of lists of participants is public so to be common with llfloatersessiontab diff --git a/indra/newview/llfloaterpreference.cpp b/indra/newview/llfloaterpreference.cpp index 9ea49e935f..e59c2ee2cd 100644 --- a/indra/newview/llfloaterpreference.cpp +++ b/indra/newview/llfloaterpreference.cpp @@ -251,11 +251,49 @@ void fractionFromDecimal(F32 decimal_val, S32& numerator, S32& denominator)  		}  	}  } -// static -std::string LLFloaterPreference::sSkin = ""; + +// handle secondlife:///app/worldmap/{NAME}/{COORDS} URLs +// Also see LLUrlEntryKeybinding, the value of this command type +// is ability to show up to date value in chat +class LLKeybindingHandler: public LLCommandHandler +{ +public: +    // requires trusted browser to trigger +    LLKeybindingHandler(): LLCommandHandler("keybinding", UNTRUSTED_CLICK_ONLY) +    { +    } + +    bool handle(const LLSD& params, const LLSD& query_map, +                LLMediaCtrl* web) +    { +        if (params.size() < 1) return false; + +        LLFloaterPreference* prefsfloater = dynamic_cast<LLFloaterPreference*> +            (LLFloaterReg::showInstance("preferences")); + +        if (prefsfloater) +        { +            // find 'controls' panel and bring it the front +            LLTabContainer* tabcontainer = prefsfloater->getChild<LLTabContainer>("pref core"); +            LLPanel* panel = prefsfloater->getChild<LLPanel>("controls"); +            if (tabcontainer && panel) +            { +                tabcontainer->selectTabPanel(panel); +            } +        } + +        return true; +    } +}; +LLKeybindingHandler gKeybindHandler; + +  //////////////////////////////////////////////  // LLFloaterPreference +// static +std::string LLFloaterPreference::sSkin = ""; +  LLFloaterPreference::LLFloaterPreference(const LLSD& key)  	: LLFloater(key),  	mGotPersonalInfo(false), diff --git a/indra/newview/llfloaterurlentry.cpp b/indra/newview/llfloaterurlentry.cpp index 917d6dfcd0..48d6e01d32 100644 --- a/indra/newview/llfloaterurlentry.cpp +++ b/indra/newview/llfloaterurlentry.cpp @@ -175,10 +175,9 @@ void LLFloaterURLEntry::onBtnOK( void* userdata )  	// We assume that an empty scheme is an http url, as this is how we will treat it.  	if(scheme == "")  	{ -		scheme = "http"; +		scheme = "https";  	} -	// Discover the MIME type only for "http" scheme.  	if(!media_url.empty() &&   	   (scheme == "http" || scheme == "https"))  	{ @@ -204,13 +203,18 @@ void LLFloaterURLEntry::getMediaTypeCoro(std::string url, LLHandle<LLFloater> pa      LLCoreHttpUtil::HttpCoroutineAdapter::ptr_t          httpAdapter(new LLCoreHttpUtil::HttpCoroutineAdapter("getMediaTypeCoro", httpPolicy));      LLCore::HttpRequest::ptr_t httpRequest(new LLCore::HttpRequest); +    LLCore::HttpHeaders::ptr_t httpHeaders(new LLCore::HttpHeaders);      LLCore::HttpOptions::ptr_t httpOpts = LLCore::HttpOptions::ptr_t(new LLCore::HttpOptions); +    httpOpts->setFollowRedirects(true);      httpOpts->setHeadersOnly(true); +    httpHeaders->append(HTTP_OUT_HEADER_ACCEPT, "*/*"); +    httpHeaders->append(HTTP_OUT_HEADER_COOKIE, ""); +      LL_INFOS("HttpCoroutineAdapter", "genericPostCoro") << "Generic POST for " << url << LL_ENDL; -    LLSD result = httpAdapter->getAndSuspend(httpRequest, url, httpOpts); +    LLSD result = httpAdapter->getRawAndSuspend(httpRequest, url, httpOpts, httpHeaders);      LLSD httpResults = result[LLCoreHttpUtil::HttpCoroutineAdapter::HTTP_RESULTS];      LLCore::HttpStatus status = LLCoreHttpUtil::HttpCoroutineAdapter::getStatusFromLLSD(httpResults); @@ -226,12 +230,6 @@ void LLFloaterURLEntry::getMediaTypeCoro(std::string url, LLHandle<LLFloater> pa      // which have no mime type set.      std::string resolvedMimeType = LLMIMETypes::getDefaultMimeType(); -    if (!status) -    { -        floaterUrlEntry->headerFetchComplete(status.getType(), resolvedMimeType); -        return; -    } -      LLSD resultHeaders = httpResults[LLCoreHttpUtil::HttpCoroutineAdapter::HTTP_RESULTS_HEADERS];      if (resultHeaders.has(HTTP_IN_HEADER_CONTENT_TYPE)) diff --git a/indra/newview/llfriendcard.cpp b/indra/newview/llfriendcard.cpp index e395da7f1e..97fff033b6 100644 --- a/indra/newview/llfriendcard.cpp +++ b/indra/newview/llfriendcard.cpp @@ -534,20 +534,7 @@ void LLFriendCardsManager::syncFriendsFolder()  	// Create own calling card if it was not found in Friends/All folder  	if (!collector.isAgentCallingCardFound())  	{ -		LLAvatarName av_name; -		LLAvatarNameCache::get( gAgentID, &av_name ); - -		create_inventory_item(gAgentID, -							  gAgent.getSessionID(), -							  calling_cards_folder_id, -							  LLTransactionID::tnull, -							  av_name.getCompleteName(), -							  gAgentID.asString(), -							  LLAssetType::AT_CALLINGCARD, -							  LLInventoryType::IT_CALLINGCARD, -                              NO_INV_SUBTYPE, -							  PERM_MOVE | PERM_TRANSFER, -							  NULL); +		create_inventory_callingcard(gAgentID, calling_cards_folder_id);  	}      // All folders created and updated. diff --git a/indra/newview/llinventorybridge.cpp b/indra/newview/llinventorybridge.cpp index db347f7096..31b1cb7a23 100644 --- a/indra/newview/llinventorybridge.cpp +++ b/indra/newview/llinventorybridge.cpp @@ -4141,7 +4141,8 @@ void LLFolderBridge::buildContextMenuOptions(U32 flags, menuentry_vec_t&   items  			|| is_recent_panel  			|| !trash  			|| trash->getVersion() == LLViewerInventoryCategory::VERSION_UNKNOWN -			|| trash->getDescendentCount() == LLViewerInventoryCategory::VERSION_UNKNOWN) +			|| trash->getDescendentCount() == LLViewerInventoryCategory::VERSION_UNKNOWN +			|| gAgentAvatarp->hasAttachmentsInTrash())  		{  			disabled_items.push_back(std::string("Empty Trash"));  		} diff --git a/indra/newview/llkeyconflict.cpp b/indra/newview/llkeyconflict.cpp index 60f8aca94c..4a0ee8fd0c 100644 --- a/indra/newview/llkeyconflict.cpp +++ b/indra/newview/llkeyconflict.cpp @@ -74,40 +74,6 @@ std::string string_from_mask(MASK mask)      return res;  } -std::string string_from_mouse(EMouseClickType click, bool translate) -{ -    std::string res; -    switch (click) -    { -    case CLICK_LEFT: -        res = "LMB"; -        break; -    case CLICK_MIDDLE: -        res = "MMB"; -        break; -    case CLICK_RIGHT: -        res = "RMB"; -        break; -    case CLICK_BUTTON4: -        res = "MB4"; -        break; -    case CLICK_BUTTON5: -        res = "MB5"; -        break; -    case CLICK_DOUBLELEFT: -        res = "Double LMB"; -        break; -    default: -        break; -    } - -    if (translate && !res.empty()) -    { -        res = LLTrans::getString(res); -    } -    return res; -} -  // LLKeyConflictHandler  S32 LLKeyConflictHandler::sTemporaryFileUseCount = 0; @@ -270,7 +236,7 @@ std::string LLKeyConflictHandler::getStringFromKeyData(const LLKeyData& keydata)          result = LLKeyboard::stringFromAccelerator(keydata.mMask);      } -    result += string_from_mouse(keydata.mMouse, true); +    result += LLKeyboard::stringFromMouse(keydata.mMouse);      return result;  } @@ -545,7 +511,7 @@ void LLKeyConflictHandler::saveToSettings(bool temporary)                      {                          // set() because 'optional', for compatibility purposes                          // just copy old keys.xml and rename to key_bindings.xml, it should work -                        binding.mouse.set(string_from_mouse(data.mMouse, false), true); +                        binding.mouse.set(LLKeyboard::stringFromMouse(data.mMouse, false), true);                      }                      binding.command = iter->first;                      mode.bindings.add(binding); diff --git a/indra/newview/lllocationinputctrl.cpp b/indra/newview/lllocationinputctrl.cpp index d6f3068610..9fa35e3bd9 100644 --- a/indra/newview/lllocationinputctrl.cpp +++ b/indra/newview/lllocationinputctrl.cpp @@ -391,7 +391,9 @@ LLLocationInputCtrl::LLLocationInputCtrl(const LLLocationInputCtrl::Params& p)  		LL_WARNS() << "Error loading navigation bar context menu" << LL_ENDL;  	} -	getTextEntry()->setRightMouseUpCallback(boost::bind(&LLLocationInputCtrl::onTextEditorRightClicked,this,_2,_3,_4)); +    //don't show default context menu +    getTextEntry()->setShowContextMenu(false); +    getTextEntry()->setRightMouseDownCallback(boost::bind(&LLLocationInputCtrl::onTextEditorRightClicked, this, _2, _3, _4));  	updateWidgetlayout();  	// Connecting signal for updating location on "Show Coordinates" setting change. diff --git a/indra/newview/llpanelgrouplandmoney.cpp b/indra/newview/llpanelgrouplandmoney.cpp index a2e136bd5a..f276d6d785 100644 --- a/indra/newview/llpanelgrouplandmoney.cpp +++ b/indra/newview/llpanelgrouplandmoney.cpp @@ -1077,7 +1077,7 @@ void LLGroupMoneyDetailsTabEventHandler::processReply(LLMessageSystem* msg,  	msg->getS32Fast(_PREHASH_MoneyData, _PREHASH_CurrentInterval, current_interval );  	msg->getStringFast(_PREHASH_MoneyData, _PREHASH_StartDate, start_date); -	std::string time_str = LLTrans::getString("GroupMoneyDate"); +	std::string time_str = LLTrans::getString("GroupMoneyStartDate");  	LLSD substitution;  	// We don't do time zone corrections of the calculated number of seconds @@ -1232,7 +1232,7 @@ void LLGroupMoneySalesTabEventHandler::processReply(LLMessageSystem* msg,  	// Start with the date.  	if (text == mImplementationp->mLoadingText)  	{ -		std::string time_str = LLTrans::getString("GroupMoneyDate"); +		std::string time_str = LLTrans::getString("GroupMoneyStartDate");  		LLSD substitution;  		// We don't do time zone corrections of the calculated number of seconds diff --git a/indra/newview/llviewerinput.cpp b/indra/newview/llviewerinput.cpp index 226e0a9a56..3f8e6f57f6 100644 --- a/indra/newview/llviewerinput.cpp +++ b/indra/newview/llviewerinput.cpp @@ -991,34 +991,50 @@ LLViewerInput::LLViewerInput()  	}  } +LLViewerInput::~LLViewerInput() +{ + +} +  // static -BOOL LLViewerInput::modeFromString(const std::string& string, S32 *mode) +bool LLViewerInput::modeFromString(const std::string& string, S32 *mode)  { -	if (string == "FIRST_PERSON") +    if (string.empty()) +    { +        return false; +    } + +    std::string cmp_string = string; +    LLStringUtil::toLower(cmp_string); +	if (cmp_string == "first_person")  	{  		*mode = MODE_FIRST_PERSON; -		return TRUE; +		return true;  	} -	else if (string == "THIRD_PERSON") +	else if (cmp_string == "third_person")  	{  		*mode = MODE_THIRD_PERSON; -		return TRUE; +		return true;  	} -	else if (string == "EDIT_AVATAR") +	else if (cmp_string == "edit_avatar")  	{  		*mode = MODE_EDIT_AVATAR; -		return TRUE; +		return true;  	} -	else if (string == "SITTING") +	else if (cmp_string == "sitting")  	{  		*mode = MODE_SITTING; -		return TRUE; -	} -	else -	{ -		*mode = MODE_THIRD_PERSON; -		return FALSE; +		return true;  	} + +    S32 val = atoi(string.c_str()); +    if (val >= 0 || val < MODE_COUNT) +    { +        *mode = val; +        return true; +    } + +    return false;  }  // static @@ -1222,6 +1238,7 @@ BOOL LLViewerInput::bindKey(const S32 mode, const KEY key, const MASK mask, cons      bind.mKey = key;      bind.mMask = mask;      bind.mFunction = function; +    bind.mFunctionName = function_name;      if (result->mIsGlobal)      { @@ -1303,6 +1320,7 @@ BOOL LLViewerInput::bindMouse(const S32 mode, const EMouseClickType mouse, const      bind.mMouse = mouse;      bind.mMask = mask;      bind.mFunction = function; +    bind.mFunctionName = function_name;      if (result->mIsGlobal)      { @@ -1801,3 +1819,49 @@ bool LLViewerInput::isMouseBindUsed(const EMouseClickType mouse, const MASK mask      }      return false;  } + +std::string LLViewerInput::getKeyBindingAsString(const std::string& mode, const std::string& control) const +{ +    S32 keyboard_mode; +    if (!modeFromString(mode, &keyboard_mode)) +    { +        keyboard_mode = getMode(); +    } + +    std::string res; +    bool needs_separator = false; + +    // keybindings are sorted from having most mask to no mask (from restrictive to less restrictive), +    // but it's visually better to present this data in reverse +    std::vector<LLKeyboardBinding>::const_reverse_iterator iter_key = mKeyBindings[keyboard_mode].rbegin(); +    while (iter_key != mKeyBindings[keyboard_mode].rend()) +    { +        if (iter_key->mFunctionName == control) +        { +            if (needs_separator) +            { +                res.append(" | "); +            } +            res.append(LLKeyboard::stringFromAccelerator(iter_key->mMask, iter_key->mKey)); +            needs_separator = true; +        } +        iter_key++; +    } + +    std::vector<LLMouseBinding>::const_reverse_iterator iter_mouse = mMouseBindings[keyboard_mode].rbegin(); +    while (iter_mouse != mMouseBindings[keyboard_mode].rend()) +    { +        if (iter_mouse->mFunctionName == control) +        { +            if (needs_separator) +            { +                res.append(" | "); +            } +            res.append(LLKeyboard::stringFromAccelerator(iter_mouse->mMask, iter_mouse->mMouse)); +            needs_separator = true; +        } +        iter_mouse++; +    } + +    return res; +} diff --git a/indra/newview/llviewerinput.h b/indra/newview/llviewerinput.h index 52e95e2168..41e289ac1d 100644 --- a/indra/newview/llviewerinput.h +++ b/indra/newview/llviewerinput.h @@ -28,12 +28,13 @@  #define LL_LLVIEWERINPUT_H  #include "llkeyboard.h" // For EKeystate -#include "llinitparam.h"  const S32 MAX_KEY_BINDINGS = 128; // was 60  const S32 keybindings_xml_version = 1;  const std::string script_mouse_handler_name = "script_trigger_lbutton"; +class LLWindow; +  class LLNamedFunction  {  public: @@ -51,6 +52,7 @@ public:      MASK			mMask;      LLKeyFunc		mFunction; +    std::string     mFunctionName;  };  class LLMouseBinding @@ -60,6 +62,7 @@ public:      MASK			mMask;      LLKeyFunc		mFunction; +    std::string     mFunctionName;  }; @@ -72,11 +75,7 @@ typedef enum e_keyboard_mode  	MODE_COUNT  } EKeyboardMode; -class LLWindow; - -void bind_keyboard_functions(); - -class LLViewerInput +class LLViewerInput : public LLKeyBindingToStringHandler  {  public:  	struct KeyBinding : public LLInitParam::Block<KeyBinding> @@ -107,6 +106,7 @@ public:  	};  	LLViewerInput(); +    virtual ~LLViewerInput();  	BOOL			handleKey(KEY key, MASK mask, BOOL repeated);  	BOOL			handleKeyUp(KEY key, MASK mask); @@ -121,7 +121,7 @@ public:  	S32				loadBindingsXML(const std::string& filename);										// returns number bound, 0 on error  	EKeyboardMode	getMode() const; -	static BOOL		modeFromString(const std::string& string, S32 *mode);			// False on failure +	static bool		modeFromString(const std::string& string, S32 *mode);			// False on failure  	static BOOL		mouseFromString(const std::string& string, EMouseClickType *mode);// False on failure      bool            scanKey(KEY key, @@ -136,6 +136,9 @@ public:      bool            isMouseBindUsed(const EMouseClickType mouse, const MASK mask, const S32 mode) const;      bool            isLMouseHandlingDefault(const S32 mode) const { return mLMouseDefaultHandling[mode]; } +    // inherited from LLKeyBindingToStringHandler +    virtual std::string getKeyBindingAsString(const std::string& mode, const std::string& control) const override; +  private:      bool            scanKey(const std::vector<LLKeyboardBinding> &binding,                              S32 binding_count, diff --git a/indra/newview/llviewerinventory.cpp b/indra/newview/llviewerinventory.cpp index 50252556de..15942faa98 100644 --- a/indra/newview/llviewerinventory.cpp +++ b/indra/newview/llviewerinventory.cpp @@ -1046,14 +1046,29 @@ void create_inventory_item(const LLUUID& agent_id, const LLUUID& session_id,  	gAgent.sendReliableMessage();  } +void create_inventory_callingcard_callback(LLPointer<LLInventoryCallback> cb, +                                           const LLUUID &parent, +                                           const LLUUID &avatar_id, +                                           const LLAvatarName &av_name) +{ +    std::string item_desc = avatar_id.asString(); +    create_inventory_item(gAgent.getID(), +                          gAgent.getSessionID(), +                          parent, +                          LLTransactionID::tnull, +                          av_name.getUserName(), +                          item_desc, +                          LLAssetType::AT_CALLINGCARD, +                          LLInventoryType::IT_CALLINGCARD, +                          NO_INV_SUBTYPE, +                          PERM_MOVE | PERM_TRANSFER, +                          cb); +} +  void create_inventory_callingcard(const LLUUID& avatar_id, const LLUUID& parent /*= LLUUID::null*/, LLPointer<LLInventoryCallback> cb/*=NULL*/)  { -	std::string item_desc = avatar_id.asString();  	LLAvatarName av_name; -	LLAvatarNameCache::get(avatar_id, &av_name); -	create_inventory_item(gAgent.getID(), gAgent.getSessionID(), -						  parent, LLTransactionID::tnull, av_name.getUserName(), item_desc, LLAssetType::AT_CALLINGCARD, -                          LLInventoryType::IT_CALLINGCARD, NO_INV_SUBTYPE, PERM_MOVE | PERM_TRANSFER, cb); +    LLAvatarNameCache::get(avatar_id, boost::bind(&create_inventory_callingcard_callback, cb, parent, _1, _2));  }  void create_inventory_wearable(const LLUUID& agent_id, const LLUUID& session_id, diff --git a/indra/newview/llvoavatarself.cpp b/indra/newview/llvoavatarself.cpp index 8fc1dcd81f..914376f5d1 100644 --- a/indra/newview/llvoavatarself.cpp +++ b/indra/newview/llvoavatarself.cpp @@ -1247,6 +1247,27 @@ BOOL LLVOAvatarSelf::detachObject(LLViewerObject *viewer_object)  	return FALSE;  } +bool LLVOAvatarSelf::hasAttachmentsInTrash() +{ +    const LLUUID trash_id = gInventory.findCategoryUUIDForType(LLFolderType::FT_TRASH); + +    for (attachment_map_t::const_iterator iter = mAttachmentPoints.begin(); iter != mAttachmentPoints.end(); ++iter) +    { +        LLViewerJointAttachment *attachment = iter->second; +        for (LLViewerJointAttachment::attachedobjs_vec_t::iterator attachment_iter = attachment->mAttachedObjects.begin(); +             attachment_iter != attachment->mAttachedObjects.end(); +             ++attachment_iter) +        { +            LLViewerObject *attached_object = attachment_iter->get(); +            if (attached_object && gInventory.isObjectDescendentOf(attached_object->getAttachmentItemID(), trash_id)) +            { +                return true; +            } +        } +    } +    return false; +} +  // static  BOOL LLVOAvatarSelf::detachAttachmentIntoInventory(const LLUUID &item_id)  { diff --git a/indra/newview/llvoavatarself.h b/indra/newview/llvoavatarself.h index 279dbd61a6..6384e2b844 100644 --- a/indra/newview/llvoavatarself.h +++ b/indra/newview/llvoavatarself.h @@ -289,6 +289,8 @@ public:  	/*virtual*/ BOOL 	detachObject(LLViewerObject *viewer_object);  	static BOOL			detachAttachmentIntoInventory(const LLUUID& item_id); +    bool hasAttachmentsInTrash(); +  	//--------------------------------------------------------------------  	// HUDs  	//-------------------------------------------------------------------- diff --git a/indra/newview/llvocache.cpp b/indra/newview/llvocache.cpp index 55fc663496..8d1f5b5f5b 100644 --- a/indra/newview/llvocache.cpp +++ b/indra/newview/llvocache.cpp @@ -1086,6 +1086,8 @@ void LLVOCache::initCache(ELLPath location, U32 size, U32 cache_version)  	readCacheHeader();	 +	LL_INFOS() << "Viewer Object Cache Versions - expected: " << cache_version << " found: " << mMetaInfo.mVersion <<  LL_ENDL; +  	if( mMetaInfo.mVersion != cache_version  		|| mMetaInfo.mAddressSize != expected_address)   	{ @@ -1096,7 +1098,8 @@ void LLVOCache::initCache(ELLPath location, U32 size, U32 cache_version)  			clearCacheInMemory();  		}  		else //delete the current cache if the format does not match. -		{			 +		{ +			LL_INFOS() << "Viewer Object Cache Versions unmatched.  clearing cache." <<  LL_ENDL;  			removeCache();  		}  	}	 diff --git a/indra/newview/skins/default/xui/en/strings.xml b/indra/newview/skins/default/xui/en/strings.xml index 01f5b513c7..2be13d9818 100644 --- a/indra/newview/skins/default/xui/en/strings.xml +++ b/indra/newview/skins/default/xui/en/strings.xml @@ -2847,7 +2847,7 @@ If you continue to receive this message, please contact Second Life support for  	<string name="GroupMoneyBalance">Balance</string>  	<string name="GroupMoneyCredits">Credits</string>  	<string name="GroupMoneyDebits">Debits</string> -	<string name="GroupMoneyDate">[weekday,datetime,utc] [mth,datetime,utc] [day,datetime,utc], [year,datetime,utc]</string> +	<string name="GroupMoneyStartDate">Transactions since [weekday,datetime,utc] [mth,datetime,utc] [day,datetime,utc], [year,datetime,utc]</string>  	<!-- Viewer menu -->  	<string name="AcquiredItems">Acquired Items</string> | 
