diff options
145 files changed, 1546 insertions, 3659 deletions
| @@ -552,3 +552,4 @@ ec09daf1899c1c01c4ba0ba950fae572f2a612a8 6.2.2-release  ab2ec5c5423b277d23fd0511ce50c15123ff2e03 6.2.3-release  67297f9902857e357570c44722ad84de3aff974e 6.2.4-release  9777aec6dc4a30a24537297ac040861ce16b82ae 6.3.0-release +ece699718f163921717bb95a6131e94af4c4138f 6.3.1-release diff --git a/doc/contributions.txt b/doc/contributions.txt index 466dffded7..0c68ae3100 100755 --- a/doc/contributions.txt +++ b/doc/contributions.txt @@ -1073,6 +1073,7 @@ Nicky Dasmijn  	MAINT-6665  	SL-10291  	SL-10293 +	SL-11061  Nicky Perian  	OPEN-1  	STORM-1087 diff --git a/indra/CMakeLists.txt b/indra/CMakeLists.txt index 6c20a813ba..62a8f3f003 100644 --- a/indra/CMakeLists.txt +++ b/indra/CMakeLists.txt @@ -3,8 +3,8 @@  # cmake_minimum_required should appear before any  # other commands to guarantee full compatibility  # with the version specified -## prior to 3.4, the Windows manifest handling was missing -cmake_minimum_required(VERSION 3.4.0 FATAL_ERROR) +## 3.8 added VS_DEBUGGER_WORKING_DIRECTORY support +cmake_minimum_required(VERSION 3.8.0 FATAL_ERROR)  set(ROOT_PROJECT_NAME "SecondLife" CACHE STRING      "The root project/makefile/solution name. Defaults to SecondLife.") @@ -83,6 +83,12 @@ add_dependencies(viewer secondlife-bin)  add_subdirectory(${VIEWER_PREFIX}doxygen EXCLUDE_FROM_ALL) +# sets the 'startup project' for debugging from visual studio. +set_property( +    DIRECTORY ${VIEWER_PREFIX} +    PROPERTY VS_STARTUP_PROJECT secondlife-bin +    ) +  if (LL_TESTS)    # Define after the custom targets are created so    # individual apps can add themselves as dependencies diff --git a/indra/cmake/00-Common.cmake b/indra/cmake/00-Common.cmake index 40fc706a99..03da30649a 100644 --- a/indra/cmake/00-Common.cmake +++ b/indra/cmake/00-Common.cmake @@ -151,6 +151,8 @@ endif (LINUX)  if (DARWIN) +  # Warnings should be fatal -- thanks, Nicky Perian, for spotting reversed default +  set(CLANG_DISABLE_FATAL_WARNINGS OFF)    set(CMAKE_CXX_LINK_FLAGS "-Wl,-headerpad_max_install_names,-search_paths_first")    set(CMAKE_SHARED_LINKER_FLAGS "${CMAKE_CXX_LINK_FLAGS}")    set(DARWIN_extra_cstar_flags "-Wno-unused-local-typedef -Wno-deprecated-declarations") diff --git a/indra/llaudio/llvorbisencode.h b/indra/llaudio/llvorbisencode.h index 6b22a2cb59..7372765075 100644 --- a/indra/llaudio/llvorbisencode.h +++ b/indra/llaudio/llvorbisencode.h @@ -40,7 +40,7 @@ const S32 LLVORBISENC_UNSUPPORTED_WORD_SIZE        = 9; // unsupported word size  const S32 LLVORBISENC_CLIP_TOO_LONG                = 10; // source file is too long  const S32 LLVORBISENC_CHUNK_SIZE_ERR               = 11; // chunk size is wrong -const F32 LLVORBIS_CLIP_MAX_TIME                               = 10.0f; +const F32 LLVORBIS_CLIP_MAX_TIME                               = 30.0f;  const U8  LLVORBIS_CLIP_MAX_CHANNELS                   = 2;  const U32 LLVORBIS_CLIP_SAMPLE_RATE                            = 44100;  const U32 LLVORBIS_CLIP_MAX_SAMPLES_PER_CHANNEL        = (U32)(LLVORBIS_CLIP_MAX_TIME * LLVORBIS_CLIP_SAMPLE_RATE); diff --git a/indra/llcommon/llstring.h b/indra/llcommon/llstring.h index 30bec3a6f8..b619a9e48c 100644 --- a/indra/llcommon/llstring.h +++ b/indra/llcommon/llstring.h @@ -1735,7 +1735,8 @@ bool LLStringUtilBase<T>::startsWith(  	const string_type& substr)  {  	if(string.empty() || (substr.empty())) return false; -	if(0 == string.find(substr)) return true; +	if (substr.length() > string.length()) return false; +	if (0 == string.compare(0, substr.length(), substr)) return true;  	return false;  } @@ -1746,9 +1747,11 @@ bool LLStringUtilBase<T>::endsWith(  	const string_type& substr)  {  	if(string.empty() || (substr.empty())) return false; -	std::string::size_type idx = string.rfind(substr); -	if(std::string::npos == idx) return false; -	return (idx == (string.size() - substr.size())); +	size_t sub_len = substr.length(); +	size_t str_len = string.length(); +	if (sub_len > str_len) return false; +	if (0 == string.compare(str_len - sub_len, sub_len, substr)) return true; +	return false;  }  // static diff --git a/indra/llcommon/lluri.cpp b/indra/llcommon/lluri.cpp index 758b98e143..9942bc0cf8 100644 --- a/indra/llcommon/lluri.cpp +++ b/indra/llcommon/lluri.cpp @@ -173,6 +173,19 @@ namespace  			"-._~";  		return s;  	} +	const std::string path() +	{ +		static const std::string s = +			"ABCDEFGHIJKLMNOPQRSTUVWXYZ" +			"abcdefghijklmnopqrstuvwxyz" +			"0123456789" +			"$-_.+" +			"!*'()," +			"{}|\\^~[]`" +			"<>#%" +			";/?:@&="; +		return s; +	}  	const std::string sub_delims()  	{  		static const std::string s = "!$&'()*+,;="; @@ -187,6 +200,12 @@ namespace  		{ return LLURI::escape(s, unreserved() + ":@!$'()*+,"); }	 // sub_delims - "&;=" + ":@"  	std::string escapeQueryValue(const std::string& s)  		{ return LLURI::escape(s, unreserved() + ":@!$'()*+,="); }	// sub_delims - "&;" + ":@" +	std::string escapeUriQuery(const std::string& s) +		{ return LLURI::escape(s, unreserved() + ":@?&$;*+=%/"); } +	std::string escapeUriData(const std::string& s) +		{ return LLURI::escape(s, unreserved() + "%"); } +	std::string escapeUriPath(const std::string& s) +		{ return LLURI::escape(s, path()); }  }  //static @@ -202,6 +221,85 @@ std::string LLURI::escape(const std::string& str)  	return escape(str, default_allowed, true);  } +//static +std::string LLURI::escapePathAndData(const std::string &str) +{ +    std::string result; + +    const std::string data_marker = "data:"; +    if (str.compare(0, data_marker.length(), data_marker) == 0) +    { +        // This is not url, but data, data part needs to be properly escaped +        // data part is separated by ',' from header. Minimal data uri is "data:," +        // See "data URI scheme" +        size_t separator = str.find(','); +        if (separator != std::string::npos) +        { +            size_t header_size = separator + 1; +            std::string header = str.substr(0, header_size); +            // base64 is url-safe +            if (header.find("base64") != std::string::npos) +            { +                // assume url-safe data +                result = str; +            } +            else +            { +                std::string data = str.substr(header_size, str.length() - header_size); + +                // Notes: File can be partially pre-escaped, that's why escaping ignores '%' +                // It somewhat limits user from displaying strings like "%20" in text +                // but that's how viewer worked for a while and user can double-escape it + + +                // Header doesn't need escaping +                result = header + escapeUriData(data); +            } +        } +    } +    else +    { +        // try processing it as path with query separator +        // The query component is indicated by the first question +        // mark("?") character and terminated by a number sign("#") +        size_t delim_pos = str.find('?'); +        if (delim_pos == std::string::npos) +        { +            // alternate separator +            delim_pos = str.find(';'); +        } + +        if (delim_pos != std::string::npos) +        { +            size_t path_size = delim_pos + 1; +            std::string query; +            std::string fragment; + +            size_t fragment_pos = str.find('#'); +            if (fragment_pos != std::string::npos) +            { +                query = str.substr(path_size, fragment_pos - path_size); +                fragment = str.substr(fragment_pos); +            } +            else +            { +                query = str.substr(path_size); +            } + +            std::string path = str.substr(0, path_size); + +            result = escapeUriPath(path) + escapeUriQuery(query) + escapeUriPath(fragment); +        } +    } + +    if (result.empty()) +    { +        // Not a known scheme or no data part, try just escaping as Uri path +        result = escapeUriPath(str); +    } +    return result; +} +  LLURI::LLURI()  {  } diff --git a/indra/llcommon/lluri.h b/indra/llcommon/lluri.h index 9e44cc7da2..b8fca0ca51 100644 --- a/indra/llcommon/lluri.h +++ b/indra/llcommon/lluri.h @@ -158,6 +158,14 @@ public:  		bool is_allowed_sorted = false);  	/** +	 * @brief Break string into data part and path or sheme +	 * and escape path (if present) and data. +	 * Data part is not allowed to have path related symbols +	 * @param str The raw URI to escape. +	 */ +	static std::string escapePathAndData(const std::string &str); + +	/**  	 * @brief unescape an escaped URI string.  	 *  	 * @param str The escped URI to unescape. diff --git a/indra/llcommon/tests/lluri_test.cpp b/indra/llcommon/tests/lluri_test.cpp index 4c64f15ca7..1a4c6641b9 100644 --- a/indra/llcommon/tests/lluri_test.cpp +++ b/indra/llcommon/tests/lluri_test.cpp @@ -383,6 +383,41 @@ namespace tut  		ensure_equals("query",		u.query(),		"redirect-http-hack=secondlife:///app/login?first_name=Callum&last_name=Linden&location=specify&grid=vaak®ion=/Morris/128/128&web_login_key=efaa4795-c2aa-4c58-8966-763c27931e78");  		ensure_equals("query map element", u.queryMap()["redirect-http-hack"].asString(), "secondlife:///app/login?first_name=Callum&last_name=Linden&location=specify&grid=vaak®ion=/Morris/128/128&web_login_key=efaa4795-c2aa-4c58-8966-763c27931e78");  	} + +	template<> template<> +	void URITestObject::test<20>() +	{ +        set_test_name("escapePathAndData uri test"); + +        // Basics scheme:[//authority]path[?query][#fragment] +        ensure_equals(LLURI::escapePathAndData("dirname?query"), +            "dirname?query"); +        ensure_equals(LLURI::escapePathAndData("dirname?query=data"), +            "dirname?query=data"); +        ensure_equals(LLURI::escapePathAndData("host://dirname/subdir name?query#fragment"), +            "host://dirname/subdir%20name?query#fragment"); +        ensure_equals(LLURI::escapePathAndData("host://dirname/subdir name?query=some@>data#fragment"), +            "host://dirname/subdir%20name?query=some@%3Edata#fragment"); +        ensure_equals(LLURI::escapePathAndData("host://dir[name/subdir name?query=some[data#fra[gment"), +            "host://dir[name/subdir%20name?query=some%5Bdata#fra[gment"); +        ensure_equals(LLURI::escapePathAndData("mailto:zero@ll.com"), +            "mailto:zero@ll.com"); +        // pre-escaped +        ensure_equals(LLURI::escapePathAndData("host://dirname/subdir%20name"), +            "host://dirname/subdir%20name"); + +        // data:[<mediatype>][;base64],<data> +        ensure_equals(LLURI::escapePathAndData("data:,Hello, World!"), +            "data:,Hello%2C%20World%21"); +        ensure_equals(LLURI::escapePathAndData("data:text/html,<h1>Hello, World!</h1>"), +            "data:text/html,%3Ch1%3EHello%2C%20World%21%3C%2Fh1%3E"); +        // pre-escaped +        ensure_equals(LLURI::escapePathAndData("data:text/html,%3Ch1%3EHello%2C%20World!</h1>"), +            "data:text/html,%3Ch1%3EHello%2C%20World%21%3C%2Fh1%3E"); +        // assume that base64 does not need escaping +        ensure_equals(LLURI::escapePathAndData("data:image;base64,SGVs/bG8sIFd/vcmxkIQ%3D%3D!-&*?="), +            "data:image;base64,SGVs/bG8sIFd/vcmxkIQ%3D%3D!-&*?="); +    }  } diff --git a/indra/llcorehttp/_httplibcurl.cpp b/indra/llcorehttp/_httplibcurl.cpp index abd304f6a5..975ce8a4d5 100644 --- a/indra/llcorehttp/_httplibcurl.cpp +++ b/indra/llcorehttp/_httplibcurl.cpp @@ -355,7 +355,8 @@ bool HttpLibcurl::completeRequest(CURLM * multi_handle, CURL * handle, CURLcode  	}      if (op->mStatus)      { -        int http_status(HTTP_OK); +        // note: CURLINFO_RESPONSE_CODE requires a long - https://curl.haxx.se/libcurl/c/CURLINFO_RESPONSE_CODE.html +        long http_status(HTTP_OK);          if (handle)          { diff --git a/indra/llimage/llimagebmp.cpp b/indra/llimage/llimagebmp.cpp index 867b2bb47b..90b7272efa 100644 --- a/indra/llimage/llimagebmp.cpp +++ b/indra/llimage/llimagebmp.cpp @@ -181,7 +181,7 @@ bool LLImageBMP::updateData()  		}  	}  	else -	if( 12 <= header.mSize && 64 <= header.mSize ) +	if( 12 <= header.mSize && header.mSize <= 64 )  	{  		setLastError("OS/2 2.x BMP files are not supported");  		return false; diff --git a/indra/llmath/lloctree.h b/indra/llmath/lloctree.h index 280d2653d3..0e2f62f9db 100644 --- a/indra/llmath/lloctree.h +++ b/indra/llmath/lloctree.h @@ -401,7 +401,7 @@ public:  				child->insert(data);  			}  		} -		else  +		else if (parent)  		{  			//it's not in here, give it to the root  			OCT_ERRS << "Octree insertion failed, starting over from root!" << LL_ENDL; @@ -416,6 +416,13 @@ public:  			node->insert(data);  		} +		else +		{ +			// It's not in here, and we are root. +			// LLOctreeRoot::insert() should have expanded +			// root by now, something is wrong +			OCT_ERRS << "Octree insertion failed! Root expansion failed." << LL_ENDL; +		}  		return false;  	} @@ -763,10 +770,15 @@ public:  			{  				LLOctreeNode<T>::insert(data);  			} -			else +			else if (node->isInside(data->getPositionGroup()))  			{  				node->insert(data);  			} +			else +			{ +				// calling node->insert(data) will return us to root +				OCT_ERRS << "Failed to insert data at child node" << LL_ENDL; +			}  		}  		else if (this->getChildCount() == 0)  		{ diff --git a/indra/llmessage/lliosocket.cpp b/indra/llmessage/lliosocket.cpp index b15b98db80..7caf0766b7 100644 --- a/indra/llmessage/lliosocket.cpp +++ b/indra/llmessage/lliosocket.cpp @@ -265,7 +265,7 @@ LLSocket::~LLSocket()  void LLSocket::setBlocking(S32 timeout)  {  	// set up the socket options -	ll_apr_warn_status(apr_socket_timeout_set(mSocket, timeout)); +	ll_apr_warn_status(apr_socket_timeout_set(mSocket, timeout)); // Sets both receive and send timeout SO_RCVTIMEO, SO_SNDTIMEO  	ll_apr_warn_status(apr_socket_opt_set(mSocket, APR_SO_NONBLOCK, 0));  	ll_apr_warn_status(apr_socket_opt_set(mSocket, APR_SO_SNDBUF, LL_SEND_BUFFER_SIZE));  	ll_apr_warn_status(apr_socket_opt_set(mSocket, APR_SO_RCVBUF, LL_RECV_BUFFER_SIZE)); diff --git a/indra/llmessage/llproxy.cpp b/indra/llmessage/llproxy.cpp index eefac1de21..950599217f 100644 --- a/indra/llmessage/llproxy.cpp +++ b/indra/llmessage/llproxy.cpp @@ -476,7 +476,8 @@ static apr_status_t tcp_blocking_handshake(LLSocket::ptr_t handle, char * dataou    	rv = apr_socket_send(apr_socket, dataout, &outlen);  	if (APR_SUCCESS != rv)  	{ -		LL_WARNS("Proxy") << "Error sending data to proxy control channel, status: " << rv << LL_ENDL; +		char buf[MAX_STRING]; +		LL_WARNS("Proxy") << "Error sending data to proxy control channel, status: " << rv << " " << apr_strerror(rv, buf, MAX_STRING) << LL_ENDL;  		ll_apr_warn_status(rv);  	}  	else if (expected_len != outlen) @@ -486,13 +487,16 @@ static apr_status_t tcp_blocking_handshake(LLSocket::ptr_t handle, char * dataou  		rv = -1;  	} +	ms_sleep(1); +  	if (APR_SUCCESS == rv)  	{  		expected_len = maxinlen;  		rv = apr_socket_recv(apr_socket, datain, &maxinlen);  		if (rv != APR_SUCCESS)  		{ -			LL_WARNS("Proxy") << "Error receiving data from proxy control channel, status: " << rv << LL_ENDL; +			char buf[MAX_STRING]; +			LL_WARNS("Proxy") << "Error receiving data from proxy control channel, status: " << rv << " " << apr_strerror(rv, buf, MAX_STRING) << LL_ENDL;  			ll_apr_warn_status(rv);  		}  		else if (expected_len < maxinlen) diff --git a/indra/llrender/llfontfreetype.cpp b/indra/llrender/llfontfreetype.cpp index ab668dc192..c41730ebaa 100644 --- a/indra/llrender/llfontfreetype.cpp +++ b/indra/llrender/llfontfreetype.cpp @@ -157,7 +157,7 @@ void ft_close_cb(FT_Stream stream) {  }  #endif -BOOL LLFontFreetype::loadFace(const std::string& filename, F32 point_size, F32 vert_dpi, F32 horz_dpi, S32 components, BOOL is_fallback) +BOOL LLFontFreetype::loadFace(const std::string& filename, F32 point_size, F32 vert_dpi, F32 horz_dpi, S32 components, BOOL is_fallback, S32 face_n)  {  	// Don't leak face objects.  This is also needed to deal with  	// changed font file names. @@ -168,40 +168,8 @@ BOOL LLFontFreetype::loadFace(const std::string& filename, F32 point_size, F32 v  	}  	int error; -  #ifdef LL_WINDOWS -	pFileStream = new llifstream(filename, std::ios::binary); -	if (pFileStream->is_open()) -	{ -		std::streampos beg = pFileStream->tellg(); -		pFileStream->seekg(0, std::ios::end); -		std::streampos end = pFileStream->tellg(); -		std::size_t file_size = end - beg; -		pFileStream->seekg(0, std::ios::beg); - -		pFtStream = new LLFT_Stream(); -		pFtStream->base = 0; -		pFtStream->pos = 0; -		pFtStream->size = file_size; -		pFtStream->descriptor.pointer = pFileStream; -		pFtStream->read = ft_read_cb; -		pFtStream->close = ft_close_cb; - -		FT_Open_Args args; -		args.flags = FT_OPEN_STREAM; -		args.stream = (FT_StreamRec*)pFtStream; - -		error = FT_Open_Face(gFTLibrary, -							 &args, -							 0, -							 &mFTFace); -	} -	else -	{ -		delete pFileStream; -		pFileStream = NULL; -		return FALSE; -	} +	error = ftOpenFace(filename, face_n);  #else  	error = FT_New_Face( gFTLibrary,  						 filename.c_str(), @@ -212,11 +180,7 @@ BOOL LLFontFreetype::loadFace(const std::string& filename, F32 point_size, F32 v  	if (error)  	{  #ifdef LL_WINDOWS -		pFileStream->close(); -		delete pFileStream; -		delete pFtStream; -		pFileStream = NULL; -		pFtStream = NULL; +		clearFontStreams();  #endif  		return FALSE;  	} @@ -235,11 +199,7 @@ BOOL LLFontFreetype::loadFace(const std::string& filename, F32 point_size, F32 v  		// Clean up freetype libs.  		FT_Done_Face(mFTFace);  #ifdef LL_WINDOWS -		pFileStream->close(); -		delete pFileStream; -		delete pFtStream; -		pFileStream = NULL; -		pFtStream = NULL; +		clearFontStreams();  #endif  		mFTFace = NULL;  		return FALSE; @@ -285,18 +245,88 @@ BOOL LLFontFreetype::loadFace(const std::string& filename, F32 point_size, F32 v  	if(mFTFace->style_flags & FT_STYLE_FLAG_BOLD)  	{  		mStyle |= LLFontGL::BOLD; -		mStyle &= ~LLFontGL::NORMAL;  	}  	if(mFTFace->style_flags & FT_STYLE_FLAG_ITALIC)  	{  		mStyle |= LLFontGL::ITALIC; -		mStyle &= ~LLFontGL::NORMAL;  	}  	return TRUE;  } +S32 LLFontFreetype::getNumFaces(const std::string& filename) +{ +	if (mFTFace) +	{ +		FT_Done_Face(mFTFace); +		mFTFace = NULL; +	} + +	S32 num_faces = 1; + +#ifdef LL_WINDOWS +	int error = ftOpenFace(filename, 0); +		 +	if (error) +	{ +		return 0; +	} +	else +	{ +		num_faces = mFTFace->num_faces; +	} +	 +	FT_Done_Face(mFTFace); +	clearFontStreams(); +	mFTFace = NULL; +#endif + +	return num_faces; +} + +#ifdef LL_WINDOWS +S32 LLFontFreetype::ftOpenFace(const std::string& filename, S32 face_n) +{ +	S32 error = -1; +	pFileStream = new llifstream(filename, std::ios::binary); +	if (pFileStream->is_open()) +	{ +		std::streampos beg = pFileStream->tellg(); +		pFileStream->seekg(0, std::ios::end); +		std::streampos end = pFileStream->tellg(); +		std::size_t file_size = end - beg; +		pFileStream->seekg(0, std::ios::beg); + +		pFtStream = new LLFT_Stream(); +		pFtStream->base = 0; +		pFtStream->pos = 0; +		pFtStream->size = file_size; +		pFtStream->descriptor.pointer = pFileStream; +		pFtStream->read = ft_read_cb; +		pFtStream->close = ft_close_cb; + +		FT_Open_Args args; +		args.flags = FT_OPEN_STREAM; +		args.stream = (FT_StreamRec*)pFtStream; +		error = FT_Open_Face(gFTLibrary, &args, face_n, &mFTFace); +	} +	return error; +} + +void LLFontFreetype::clearFontStreams() +{ +	if (pFileStream) +	{ +		pFileStream->close(); +	} +	delete pFileStream; +	delete pFtStream; +	pFileStream = NULL; +	pFtStream = NULL; +} +#endif +  void LLFontFreetype::setFallbackFonts(const font_vector_t &font)  {  	mFallbackFonts = font; diff --git a/indra/llrender/llfontfreetype.h b/indra/llrender/llfontfreetype.h index aadebf5e70..1afe84e770 100644 --- a/indra/llrender/llfontfreetype.h +++ b/indra/llrender/llfontfreetype.h @@ -84,7 +84,14 @@ public:  	// is_fallback should be true for fallback fonts that aren't used  	// to render directly (Unicode backup, primarily) -	BOOL loadFace(const std::string& filename, F32 point_size, F32 vert_dpi, F32 horz_dpi, S32 components, BOOL is_fallback); +	BOOL loadFace(const std::string& filename, F32 point_size, F32 vert_dpi, F32 horz_dpi, S32 components, BOOL is_fallback, S32 face_n = 0); + +	S32 getNumFaces(const std::string& filename); + +#ifdef LL_WINDOWS +	S32 ftOpenFace(const std::string& filename, S32 face_n); +	void clearFontStreams(); +#endif  	typedef std::vector<LLPointer<LLFontFreetype> > font_vector_t; diff --git a/indra/llrender/llfontgl.cpp b/indra/llrender/llfontgl.cpp index 8cd18c5fa1..86a4c35e6d 100644 --- a/indra/llrender/llfontgl.cpp +++ b/indra/llrender/llfontgl.cpp @@ -89,14 +89,24 @@ void LLFontGL::destroyGL()  	mFontFreetype->destroyGL();  } -BOOL LLFontGL::loadFace(const std::string& filename, F32 point_size, F32 vert_dpi, F32 horz_dpi, S32 components, BOOL is_fallback) +BOOL LLFontGL::loadFace(const std::string& filename, F32 point_size, F32 vert_dpi, F32 horz_dpi, S32 components, BOOL is_fallback, S32 face_n)  {  	if(mFontFreetype == reinterpret_cast<LLFontFreetype*>(NULL))  	{  		mFontFreetype = new LLFontFreetype;  	} -	return mFontFreetype->loadFace(filename, point_size, vert_dpi, horz_dpi, components, is_fallback); +	return mFontFreetype->loadFace(filename, point_size, vert_dpi, horz_dpi, components, is_fallback, face_n); +} + +S32 LLFontGL::getNumFaces(const std::string& filename) +{ +	if (mFontFreetype == reinterpret_cast<LLFontFreetype*>(NULL)) +	{ +		mFontFreetype = new LLFontFreetype; +	} + +	return mFontFreetype->getNumFaces(filename);  }  static LLTrace::BlockTimerStatHandle FTM_RENDER_FONTS("Fonts"); @@ -860,10 +870,6 @@ void LLFontGL::destroyAllGL()  U8 LLFontGL::getStyleFromString(const std::string &style)  {  	S32 ret = 0; -	if (style.find("NORMAL") != style.npos) -	{ -		ret |= NORMAL; -	}  	if (style.find("BOLD") != style.npos)  	{  		ret |= BOLD; @@ -883,7 +889,7 @@ U8 LLFontGL::getStyleFromString(const std::string &style)  std::string LLFontGL::getStringFromStyle(U8 style)  {  	std::string style_string; -	if (style & NORMAL) +	if (style == NORMAL)  	{  		style_string += "|NORMAL";  	} diff --git a/indra/llrender/llfontgl.h b/indra/llrender/llfontgl.h index 7d0e53f60f..10891faed9 100644 --- a/indra/llrender/llfontgl.h +++ b/indra/llrender/llfontgl.h @@ -87,7 +87,9 @@ public:  	void destroyGL(); -	BOOL loadFace(const std::string& filename, F32 point_size, const F32 vert_dpi, const F32 horz_dpi, const S32 components, BOOL is_fallback); +	BOOL loadFace(const std::string& filename, F32 point_size, const F32 vert_dpi, const F32 horz_dpi, const S32 components, BOOL is_fallback, S32 face_n = 0); + +	S32 getNumFaces(const std::string& filename);  	S32 render(const LLWString &text, S32 begin_offset,   				const LLRect& rect,  diff --git a/indra/llrender/llfontregistry.cpp b/indra/llrender/llfontregistry.cpp index 3c829596ce..dbe71e2882 100644 --- a/indra/llrender/llfontregistry.cpp +++ b/indra/llrender/llfontregistry.cpp @@ -44,6 +44,8 @@ using std::map;  bool font_desc_init_from_xml(LLXMLNodePtr node, LLFontDescriptor& desc);  bool init_from_xml(LLFontRegistry* registry, LLXMLNodePtr node); +const std::string MACOSX_FONT_PATH_LIBRARY = "/Library/Fonts/"; +  LLFontDescriptor::LLFontDescriptor():  	mStyle(0)  { @@ -61,6 +63,16 @@ LLFontDescriptor::LLFontDescriptor(const std::string& name,  }  LLFontDescriptor::LLFontDescriptor(const std::string& name, +	const std::string& size, +	const U8 style, +	const string_vec_t& file_names, +	const string_vec_t& ft_collection_listections) : +	LLFontDescriptor(name, size, style, file_names) +{ +	mFontCollectionsList = ft_collection_listections; +} + +LLFontDescriptor::LLFontDescriptor(const std::string& name,  								   const std::string& size,   								   const U8 style):  	mName(name), @@ -162,7 +174,7 @@ LLFontDescriptor LLFontDescriptor::normalize() const  	if (removeSubString(new_name,"Italic"))  		new_style |= LLFontGL::ITALIC; -	return LLFontDescriptor(new_name,new_size,new_style,getFileNames()); +	return LLFontDescriptor(new_name,new_size,new_style,getFileNames(),getFontCollectionsList());  }  LLFontRegistry::LLFontRegistry(bool create_gl_textures) @@ -213,6 +225,7 @@ bool LLFontRegistry::parseFontInfo(const std::string& xml_filename)  			success = success || init_succ;  		}  	} +  	//if (success)  	//	dump(); @@ -260,6 +273,16 @@ bool font_desc_init_from_xml(LLXMLNodePtr node, LLFontDescriptor& desc)  		{  			std::string font_file_name = child->getTextContents();  			desc.getFileNames().push_back(font_file_name); +			 +			if (child->hasAttribute("load_collection")) +			{ +				BOOL col = FALSE; +				child->getAttributeBOOL("load_collection", col); +				if (col) +				{ +					desc.getFontCollectionsList().push_back(font_file_name); +				} +			}  		}  		else if (child->hasName("os"))  		{ @@ -306,8 +329,15 @@ bool init_from_xml(LLFontRegistry* registry, LLXMLNodePtr node)  					match_file_names.insert(match_file_names.begin(),  											desc.getFileNames().begin(),  											desc.getFileNames().end()); + +					string_vec_t collections_list = match_desc->getFontCollectionsList(); +					collections_list.insert(collections_list.begin(), +						desc.getFontCollectionsList().begin(), +						desc.getFontCollectionsList().end()); +  					LLFontDescriptor new_desc = *match_desc;  					new_desc.getFileNames() = match_file_names; +					new_desc.getFontCollectionsList() = collections_list;  					registry->mFontMap.erase(*match_desc);  					registry->mFontMap[new_desc] = NULL;  				} @@ -393,6 +423,7 @@ LLFontGL *LLFontRegistry::createFont(const LLFontDescriptor& desc)  	// Build list of font names to look for.  	// Files specified for this font come first, followed by those from the default descriptor.  	string_vec_t file_names = match_desc->getFileNames(); +	string_vec_t ft_collection_list = match_desc->getFontCollectionsList();  	string_vec_t default_file_names;  	LLFontDescriptor default_desc("default",s_template_string,0);  	const LLFontDescriptor *match_default_desc = getMatchingFontDesc(default_desc); @@ -401,6 +432,9 @@ LLFontGL *LLFontRegistry::createFont(const LLFontDescriptor& desc)  		file_names.insert(file_names.end(),  						  match_default_desc->getFileNames().begin(),  						  match_default_desc->getFileNames().end()); +		ft_collection_list.insert(ft_collection_list.end(), +			match_default_desc->getFontCollectionsList().begin(), +			match_default_desc->getFontCollectionsList().end());  	}  	// Add ultimate fallback list - generated dynamically on linux, @@ -433,39 +467,62 @@ LLFontGL *LLFontRegistry::createFont(const LLFontDescriptor& desc)  		file_name_it != file_names.end();   		++file_name_it)  	{ -		LLFontGL *fontp = new LLFontGL; -		std::string font_path = local_path + *file_name_it; +		LLFontGL *fontp = NULL; +		string_vec_t font_paths; +		font_paths.push_back(local_path + *file_name_it); +		font_paths.push_back(sys_path + *file_name_it); +#if LL_DARWIN +		font_paths.push_back(MACOSX_FONT_PATH_LIBRARY + *file_name_it); +#endif +		 +		bool is_ft_collection = (std::find(ft_collection_list.begin(), ft_collection_list.end(), *file_name_it) != ft_collection_list.end());  		// *HACK: Fallback fonts don't render, so we can use that to suppress  		// creation of OpenGL textures for test apps. JC  		BOOL is_fallback = !is_first_found || !mCreateGLTextures;  		F32 extra_scale = (is_fallback)?fallback_scale:1.0; -		if (!fontp->loadFace(font_path, extra_scale * point_size, -							 LLFontGL::sVertDPI, LLFontGL::sHorizDPI, 2, is_fallback)) +		F32 point_size_scale = extra_scale * point_size; +		bool is_font_loaded = false; +		for(string_vec_t::iterator font_paths_it = font_paths.begin(); +			font_paths_it != font_paths.end(); +			++font_paths_it)  		{ -			font_path = sys_path + *file_name_it; - -			if (!fontp->loadFace(font_path, extra_scale * point_size, -								 LLFontGL::sVertDPI, LLFontGL::sHorizDPI, 2, is_fallback)) +			fontp = new LLFontGL; +			S32 num_faces = is_ft_collection ? fontp->getNumFaces(*font_paths_it) : 1; +			for (S32 i = 0; i < num_faces; i++)  			{ -				LL_INFOS_ONCE("LLFontRegistry") << "Couldn't load font " << *file_name_it << " from path " << local_path << LL_ENDL; -				delete fontp; -				fontp = NULL; +				if (fontp == NULL) +				{ +					fontp = new LLFontGL; +				} +				if (fontp->loadFace(*font_paths_it, point_size_scale, +								 LLFontGL::sVertDPI, LLFontGL::sHorizDPI, 2, is_fallback, i)) +				{ +					is_font_loaded = true; +					if (is_first_found) +					{ +						result = fontp; +						is_first_found = false; +					} +					else +					{ +						fontlist.push_back(fontp->mFontFreetype); +						delete fontp; +						fontp = NULL; +					} +				} +				else +				{ +					delete fontp; +					fontp = NULL; +				}  			} +			if (is_font_loaded) break;  		} -		 -		if(fontp) +		if(!is_font_loaded)  		{ -			if (is_first_found) -			{ -				result = fontp; -				is_first_found = false; -			} -			else -			{ -				fontlist.push_back(fontp->mFontFreetype); -				delete fontp; -				fontp = NULL; -			} +			LL_INFOS_ONCE("LLFontRegistry") << "Couldn't load font " << *file_name_it <<  LL_ENDL; +			delete fontp; +			fontp = NULL;  		}  	} diff --git a/indra/llrender/llfontregistry.h b/indra/llrender/llfontregistry.h index 177eb6c8a5..e30c81c630 100644 --- a/indra/llrender/llfontregistry.h +++ b/indra/llrender/llfontregistry.h @@ -40,6 +40,7 @@ public:  	LLFontDescriptor();  	LLFontDescriptor(const std::string& name, const std::string& size, const U8 style);  	LLFontDescriptor(const std::string& name, const std::string& size, const U8 style, const string_vec_t& file_names); +	LLFontDescriptor(const std::string& name, const std::string& size, const U8 style, const string_vec_t& file_names, const string_vec_t& font_collections);  	LLFontDescriptor normalize() const;  	bool operator<(const LLFontDescriptor& b) const; @@ -52,6 +53,8 @@ public:  	void setSize(const std::string& size) { mSize = size; }  	const std::vector<std::string>& getFileNames() const { return mFileNames; }  	std::vector<std::string>& getFileNames() { return mFileNames; } +	const std::vector<std::string>& getFontCollectionsList() const { return mFontCollectionsList; } +	std::vector<std::string>& getFontCollectionsList() { return mFontCollectionsList; }  	const U8 getStyle() const { return mStyle; }  	void setStyle(U8 style) { mStyle = style; } @@ -59,6 +62,7 @@ private:  	std::string mName;  	std::string mSize;  	string_vec_t mFileNames; +	string_vec_t mFontCollectionsList;  	U8 mStyle;  }; diff --git a/indra/llui/lltextbox.cpp b/indra/llui/lltextbox.cpp index 41c7d67f24..0afd32f332 100644 --- a/indra/llui/lltextbox.cpp +++ b/indra/llui/lltextbox.cpp @@ -122,6 +122,7 @@ void LLTextBox::setEnabled(BOOL enabled)  		LLTextBase::setReadOnly(read_only);  		updateSegments();  	} +	LLTextBase::setEnabled(enabled);  }  void LLTextBox::setText(const LLStringExplicit& text , const LLStyle::Params& input_params ) diff --git a/indra/llui/lltransutil.cpp b/indra/llui/lltransutil.cpp index 220cee4c90..b1534bb5e4 100644 --- a/indra/llui/lltransutil.cpp +++ b/indra/llui/lltransutil.cpp @@ -44,7 +44,7 @@ bool LLTransUtil::parseStrings(const std::string& xml_filename, const std::set<s  	bool success = LLUICtrlFactory::getLayeredXMLNode(xml_filename, root, LLDir::ALL_SKINS);  	if (!success)  	{ -		LL_ERRS() << "Couldn't load string table " << xml_filename << LL_ENDL; +		LL_ERRS() << "Couldn't load string table " << xml_filename << ". Please reinstall viewer from  https://secondlife.com/support/downloads/ and contact https://support.secondlife.com if issue persists after reinstall." << LL_ENDL;  		return false;  	} diff --git a/indra/llwindow/llwindowmacosx-objc.h b/indra/llwindow/llwindowmacosx-objc.h index 10bd3cbb91..99af161102 100644 --- a/indra/llwindow/llwindowmacosx-objc.h +++ b/indra/llwindow/llwindowmacosx-objc.h @@ -110,9 +110,9 @@ void glSwapBuffers(void* context);  CGLContextObj getCGLContextObj(GLViewRef view);  unsigned long getVramSize(GLViewRef view);  float getDeviceUnitSize(GLViewRef view); -const CGPoint getContentViewBoundsPosition(NSWindowRef window); -const CGSize getContentViewBoundsSize(NSWindowRef window); -const CGSize getDeviceContentViewSize(NSWindowRef window, GLViewRef view); +CGPoint getContentViewBoundsPosition(NSWindowRef window); +CGSize getContentViewBoundsSize(NSWindowRef window); +CGSize getDeviceContentViewSize(NSWindowRef window, GLViewRef view);  void getWindowSize(NSWindowRef window, float* size);  void setWindowSize(NSWindowRef window, int width, int height);  void getCursorPos(NSWindowRef window, float* pos); diff --git a/indra/llwindow/llwindowmacosx-objc.mm b/indra/llwindow/llwindowmacosx-objc.mm index 8fece7c5c7..f895c17643 100644 --- a/indra/llwindow/llwindowmacosx-objc.mm +++ b/indra/llwindow/llwindowmacosx-objc.mm @@ -258,17 +258,17 @@ float getDeviceUnitSize(GLViewRef view)  	return [(LLOpenGLView*)view convertSizeToBacking:NSMakeSize(1, 1)].width;  } -const CGPoint getContentViewBoundsPosition(NSWindowRef window) +CGPoint getContentViewBoundsPosition(NSWindowRef window)  {  	return [[(LLNSWindow*)window contentView] bounds].origin;  } -const CGSize getContentViewBoundsSize(NSWindowRef window) +CGSize getContentViewBoundsSize(NSWindowRef window)  {  	return [[(LLNSWindow*)window contentView] bounds].size;  } -const CGSize getDeviceContentViewSize(NSWindowRef window, GLViewRef view) +CGSize getDeviceContentViewSize(NSWindowRef window, GLViewRef view)  {      return [(NSOpenGLView*)view convertRectToBacking:[[(LLNSWindow*)window contentView] bounds]].size;  } diff --git a/indra/llwindow/llwindowmacosx.cpp b/indra/llwindow/llwindowmacosx.cpp index 6dec131a34..3554f90be8 100644 --- a/indra/llwindow/llwindowmacosx.cpp +++ b/indra/llwindow/llwindowmacosx.cpp @@ -382,7 +382,10 @@ void callWindowFocus()  void callWindowUnfocus()  { -	gWindowImplementation->getCallbacks()->handleFocusLost(gWindowImplementation); +	if ( gWindowImplementation && gWindowImplementation->getCallbacks() ) +	{ +		gWindowImplementation->getCallbacks()->handleFocusLost(gWindowImplementation); +	}  }  void callWindowHide() diff --git a/indra/llwindow/llwindowwin32.cpp b/indra/llwindow/llwindowwin32.cpp index 985bd79d13..e05f507506 100644 --- a/indra/llwindow/llwindowwin32.cpp +++ b/indra/llwindow/llwindowwin32.cpp @@ -741,6 +741,17 @@ void LLWindowWin32::restore()  	SetFocus(mWindowHandle);  } +bool destroy_window_handler(HWND &hWnd) +{ +    __try +    { +        return DestroyWindow(hWnd); +    } +    __except (EXCEPTION_EXECUTE_HANDLER) +    { +        return false; +    } +}  // close() destroys all OS-specific code associated with a window.  // Usually called from LLWindowManager::destroyWindow() @@ -814,7 +825,7 @@ void LLWindowWin32::close()  	ShowWindow(mWindowHandle, SW_HIDE);  	// This causes WM_DESTROY to be sent *immediately* -	if (!DestroyWindow(mWindowHandle)) +	if (!destroy_window_handler(mWindowHandle))  	{  		OSMessageBox(mCallbacks->translateString("MBDestroyWinFailed"),  			mCallbacks->translateString("MBShutdownErr"), diff --git a/indra/media_plugins/cef/media_plugin_cef.cpp b/indra/media_plugins/cef/media_plugin_cef.cpp index 2a8eb20af9..eead92fd8e 100644 --- a/indra/media_plugins/cef/media_plugin_cef.cpp +++ b/indra/media_plugins/cef/media_plugin_cef.cpp @@ -531,7 +531,12 @@ void MediaPluginCEF::receiveMessage(const char* message_string)  				}  				// now we can set page zoom factor -				mCEFLib->setPageZoom(message_in.getValueReal("factor")); +				F32 factor = (F32)message_in.getValueReal("factor"); +#if LL_DARWIN +				//temporary fix for SL-10473: issue with displaying checkboxes on Mojave +				factor*=1.001; +#endif +				mCEFLib->setPageZoom(factor);  				// Plugin gets to decide the texture parameters to use.  				mDepth = 4; @@ -736,6 +741,10 @@ void MediaPluginCEF::receiveMessage(const char* message_string)  			if (message_name == "set_page_zoom_factor")  			{  				F32 factor = (F32)message_in.getValueReal("factor"); +#if LL_DARWIN +				//temporary fix for SL-10473: issue with displaying checkboxes on Mojave +				factor*=1.001; +#endif  				mCEFLib->setPageZoom(factor);  			}  			if (message_name == "browse_stop") @@ -813,7 +822,8 @@ void MediaPluginCEF::keyEvent(dullahan::EKeyEvent key_event, LLSD native_key_dat  	// adding new code below in unicodeInput means we don't send ascii chars  	// here too or we get double key presses on a mac.  	bool esc_key = (event_umodchars == 27); -	if (esc_key || ((unsigned char)event_chars < 0x10 || (unsigned char)event_chars >= 0x7f )) +	bool tab_key_up = (event_umodchars == 9) && (key_event == dullahan::EKeyEvent::KE_KEY_UP); +	if ((esc_key || ((unsigned char)event_chars < 0x10 || (unsigned char)event_chars >= 0x7f )) && !tab_key_up)  	{  		mCEFLib->nativeKeyboardEventOSX(key_event, event_modifiers,   										event_keycode, event_chars,  diff --git a/indra/newview/CMakeLists.txt b/indra/newview/CMakeLists.txt index c18b2c9a95..2b35d18329 100644 --- a/indra/newview/CMakeLists.txt +++ b/indra/newview/CMakeLists.txt @@ -201,7 +201,6 @@ set(viewer_SOURCE_FILES      llexperiencelog.cpp      llexternaleditor.cpp      llface.cpp -    llfacebookconnect.cpp      llfasttimerview.cpp      llfavoritesbar.cpp      llfeaturemanager.cpp @@ -245,7 +244,6 @@ set(viewer_SOURCE_FILES      llfloaterexperiencepicker.cpp      llfloaterexperienceprofile.cpp      llfloaterexperiences.cpp -    llfloaterfacebook.cpp      llfloaterflickr.cpp      llfloaterfonttest.cpp      llfloatergesture.cpp @@ -828,7 +826,6 @@ set(viewer_HEADER_FILES      llexperiencelog.h      llexternaleditor.h      llface.h -    llfacebookconnect.h      llfasttimerview.h      llfavoritesbar.h      llfeaturemanager.h @@ -872,7 +869,6 @@ set(viewer_HEADER_FILES      llfloaterexperiencepicker.h      llfloaterexperienceprofile.h      llfloaterexperiences.h -    llfloaterfacebook.h      llfloaterflickr.h      llfloaterfonttest.h      llfloatergesture.h @@ -1885,12 +1881,12 @@ if (WINDOWS)      # sets the 'working directory' for debugging from visual studio.      # Condition for version can be moved to requirements once build agents will be updated (see TOOL-3865) -    if ((NOT UNATTENDED) AND (${CMAKE_VERSION} VERSION_GREATER "3.7.2")) +    if (NOT UNATTENDED)          set_property(            TARGET ${VIEWER_BINARY_NAME}            PROPERTY VS_DEBUGGER_WORKING_DIRECTORY "${CMAKE_CURRENT_SOURCE_DIR}"            ) -    endif ((NOT UNATTENDED) AND (${CMAKE_VERSION} VERSION_GREATER "3.7.2")) +    endif (NOT UNATTENDED)      if (PACKAGE)        add_custom_command( diff --git a/indra/newview/VIEWER_VERSION.txt b/indra/newview/VIEWER_VERSION.txt index dc0208aba8..91e4a9f262 100644 --- a/indra/newview/VIEWER_VERSION.txt +++ b/indra/newview/VIEWER_VERSION.txt @@ -1 +1 @@ -6.3.1 +6.3.2 diff --git a/indra/newview/app_settings/commands.xml b/indra/newview/app_settings/commands.xml index 412d3a53b3..cab0c523b2 100644 --- a/indra/newview/app_settings/commands.xml +++ b/indra/newview/app_settings/commands.xml @@ -228,16 +228,6 @@             is_running_function="Floater.IsOpen"             is_running_parameters="snapshot"             /> -  <command name="facebook" -           available_in_toybox="true" -           icon="Command_Facebook_Icon" -           label_ref="Command_Facebook_Label" -           tooltip_ref="Command_Facebook_Tooltip" -           execute_function="Floater.ToggleOrBringToFront" -           execute_parameters="facebook" -           is_running_function="Floater.IsOpen" -           is_running_parameters="facebook" -           />    <command name="flickr"             available_in_toybox="true"             icon="Command_Flickr_Icon" diff --git a/indra/newview/app_settings/settings_per_account.xml b/indra/newview/app_settings/settings_per_account.xml index 3d4bd659f1..8f4ca6c633 100644 --- a/indra/newview/app_settings/settings_per_account.xml +++ b/indra/newview/app_settings/settings_per_account.xml @@ -414,5 +414,16 @@          <key>Value</key>          <string>Snapshot</string>        </map> +      <key>ExperienceSearchMaturity</key> +      <map> +        <key>Comment</key> +        <string>Setting for the user's preferred Max Content rating for Experiences search (Default rating is General)</string> +        <key>Persist</key> +        <integer>1</integer> +        <key>Type</key> +        <string>U32</string> +        <key>Value</key> +        <integer>2</integer> +      </map>      </map>  </llsd> diff --git a/indra/newview/app_settings/toolbars.xml b/indra/newview/app_settings/toolbars.xml index 36e4eb91fd..eec0d81e8b 100644 --- a/indra/newview/app_settings/toolbars.xml +++ b/indra/newview/app_settings/toolbars.xml @@ -21,7 +21,6 @@      <command name="voice"/>      <command name="minimap"/>      <command name="snapshot"/> -    <command name="facebook"/>    </left_toolbar>    <right_toolbar      button_display_mode="icons_only"> diff --git a/indra/newview/installers/windows/installer_template.nsi b/indra/newview/installers/windows/installer_template.nsi index d1d5301efe..8838b6d0be 100644 --- a/indra/newview/installers/windows/installer_template.nsi +++ b/indra/newview/installers/windows/installer_template.nsi @@ -346,6 +346,11 @@ Call CheckWillUninstallV2		# Check if Second Life is already installed  StrCmp $DO_UNINSTALL_V2 "" PRESERVE_DONE
  PRESERVE_DONE:
 +# Viewer had "SLLauncher" for some time and we was seting "IsHostApp" for viewer, make sure to clean it up
 +DeleteRegValue HKEY_CLASSES_ROOT "Applications\$VIEWER_EXE" "IsHostApp"
 +DeleteRegValue HKEY_CLASSES_ROOT "Applications\$VIEWER_EXE" "NoStartPage"
 +ClearErrors
 +
  Call RemoveProgFilesOnInst		# Remove existing files to prevent certain errors when running the new version of the viewer
  # This placeholder is replaced by the complete list of all the files in the installer, by viewer_manifest.py
 @@ -417,7 +422,7 @@ WriteRegStr HKEY_CLASSES_ROOT "x-grid-location-info\DefaultIcon" "" '"$INSTDIR\$  # URL param must be last item passed to viewer, it ignores subsequent params to avoid parameter injection attacks.
  WriteRegExpandStr HKEY_CLASSES_ROOT "x-grid-location-info\shell\open\command" "" '"$INSTDIR\$VIEWER_EXE" -url "%1"'
 -WriteRegStr HKEY_CLASSES_ROOT "Applications\$VIEWER_EXE" "IsHostApp" ""
 +WriteRegStr HKEY_CLASSES_ROOT "Applications\$INSTEXE" "IsHostApp" ""
  ##WriteRegStr HKEY_CLASSES_ROOT "Applications\${VIEWER_EXE}" "NoStartPage" ""
  # Write out uninstaller
 @@ -464,7 +469,7 @@ DeleteRegKey SHELL_CONTEXT "${INSTNAME_KEY}"  DeleteRegKey SHELL_CONTEXT "${MSCURRVER_KEY}\Uninstall\$INSTNAME"
  # BUG-2707 Remove entry that disabled SEHOP
  DeleteRegKey SHELL_CONTEXT "${MSNTCURRVER_KEY}\Image File Execution Options\$VIEWER_EXE"
 -##DeleteRegKey HKEY_CLASSES_ROOT "Applications\$INSTEXE"
 +DeleteRegKey HKEY_CLASSES_ROOT "Applications\$INSTEXE"
  DeleteRegKey HKEY_CLASSES_ROOT "Applications\${VIEWER_EXE}"
  # Clean up shortcuts
 diff --git a/indra/newview/installers/windows/lang_de.nsi b/indra/newview/installers/windows/lang_de.nsiBinary files differ index 8bb20476b3..eebcf027a8 100755 --- a/indra/newview/installers/windows/lang_de.nsi +++ b/indra/newview/installers/windows/lang_de.nsi diff --git a/indra/newview/llagent.cpp b/indra/newview/llagent.cpp index 9f0c923253..8b2d591da5 100644 --- a/indra/newview/llagent.cpp +++ b/indra/newview/llagent.cpp @@ -743,7 +743,7 @@ BOOL LLAgent::getFlying() const  //-----------------------------------------------------------------------------  // setFlying()  //----------------------------------------------------------------------------- -void LLAgent::setFlying(BOOL fly) +void LLAgent::setFlying(BOOL fly, BOOL fail_sound)  {  	if (isAgentAvatarValid())  	{ @@ -772,7 +772,10 @@ void LLAgent::setFlying(BOOL fly)  			// parcel doesn't let you start fly  			// gods can always fly  			// and it's OK if you're already flying -			make_ui_sound("UISndBadKeystroke"); +			if (fail_sound) +			{ +				make_ui_sound("UISndBadKeystroke"); +			}  			return;  		}  		if( !was_flying ) diff --git a/indra/newview/llagent.h b/indra/newview/llagent.h index b1b39b637e..ea6f68c482 100644 --- a/indra/newview/llagent.h +++ b/indra/newview/llagent.h @@ -337,7 +337,7 @@ private:  	//--------------------------------------------------------------------  public:  	BOOL			getFlying() const; -	void			setFlying(BOOL fly); +	void			setFlying(BOOL fly, BOOL fail_sound = FALSE);  	static void		toggleFlying();  	static bool		enableFlying();  	BOOL			canFly(); 			// Does this parcel allow you to fly? diff --git a/indra/newview/llappviewer.cpp b/indra/newview/llappviewer.cpp index f414ec0d09..90c7791c19 100644 --- a/indra/newview/llappviewer.cpp +++ b/indra/newview/llappviewer.cpp @@ -2419,9 +2419,9 @@ bool LLAppViewer::initConfiguration()  	bool set_defaults = true;  	if(!loadSettingsFromDirectory("Default", set_defaults))  	{ -		std::ostringstream msg; -		msg << "Unable to load default settings file. The installation may be corrupted."; -		OSMessageBox(msg.str(),LLStringUtil::null,OSMB_OK); +		OSMessageBox( +			"Unable to load default settings file. The installation may be corrupted.", +			LLStringUtil::null,OSMB_OK);  		return false;  	} @@ -2542,7 +2542,7 @@ bool LLAppViewer::initConfiguration()  	if(gSavedSettings.getBOOL("DisableCrashLogger"))  	{  		LL_WARNS() << "Crashes will be handled by system, stack trace logs and crash logger are both disabled" << LL_ENDL; -		LLAppViewer::instance()->disableCrashlogger(); +		disableCrashlogger();  	}  	// Handle initialization from settings. @@ -2559,7 +2559,7 @@ bool LLAppViewer::initConfiguration()  		LL_INFOS()	<< msg.str() << LL_ENDL;  		OSMessageBox( -			msg.str().c_str(), +			msg.str(),  			LLStringUtil::null,  			OSMB_OK); @@ -2669,7 +2669,34 @@ bool LLAppViewer::initConfiguration()  		ll_init_fail_log(gDirUtilp->getExpandedFilename(LL_PATH_LOGS, "test_failures.log"));  	} +	const LLControlVariable* skinfolder = gSavedSettings.getControl("SkinCurrent"); +	if(skinfolder && LLStringUtil::null != skinfolder->getValue().asString()) +	{ +		// Examining "Language" may not suffice -- see LLUI::getLanguage() +		// logic. Unfortunately LLUI::getLanguage() doesn't yet do us much +		// good because we haven't yet called LLUI::initClass(). +		gDirUtilp->setSkinFolder(skinfolder->getValue().asString(), +								 gSavedSettings.getString("Language")); +	} + +	if (gSavedSettings.getBOOL("SpellCheck")) +	{ +		std::list<std::string> dict_list; +		std::string dict_setting = gSavedSettings.getString("SpellCheckDictionary"); +		boost::split(dict_list, dict_setting, boost::is_any_of(std::string(","))); +		if (!dict_list.empty()) +		{ +			LLSpellChecker::setUseSpellCheck(dict_list.front()); +			dict_list.pop_front(); +			LLSpellChecker::instance().setSecondaryDictionaries(dict_list); +		} +	} +  	// Handle slurl use. NOTE: Don't let SL-55321 reappear. +	// This initial-SLURL logic, up through the call to +	// sendURLToOtherInstance(), must precede LLSplashScreen::show() -- +	// because if sendURLToOtherInstance() succeeds, we take a fast exit, +	// SKIPPING the splash screen and everything else.      // *FIX: This init code should be made more robust to prevent      // the issue SL-55321 from returning. One thought is to allow @@ -2714,6 +2741,27 @@ bool LLAppViewer::initConfiguration()  		}  	} +	// NextLoginLocation is set as a side effect of LLStartUp::setStartSLURL() +	std::string nextLoginLocation = gSavedSettings.getString( "NextLoginLocation" ); +	if ( !nextLoginLocation.empty() ) +	{ +		LL_DEBUGS("AppInit")<<"set start from NextLoginLocation: "<<nextLoginLocation<<LL_ENDL; +		LLStartUp::setStartSLURL(LLSLURL(nextLoginLocation)); +	} +	else if (   (   clp.hasOption("login") || clp.hasOption("autologin")) +			 && gSavedSettings.getString("CmdLineLoginLocation").empty()) +	{ +		// If automatic login from command line with --login switch +		// init StartSLURL location. +		std::string start_slurl_setting = gSavedSettings.getString("LoginLocation"); +		LL_DEBUGS("AppInit") << "start slurl setting '" << start_slurl_setting << "'" << LL_ENDL; +		LLStartUp::setStartSLURL(LLSLURL(start_slurl_setting)); +	} +	else +	{ +		// the login location will be set by the login panel (see LLPanelLogin) +	} +  	//RN: if we received a URL, hand it off to the existing instance.  	// don't call anotherInstanceRunning() when doing URL handoff, as  	// it relies on checking a marker file which will not work when running @@ -2729,30 +2777,6 @@ bool LLAppViewer::initConfiguration()  		}      } -	const LLControlVariable* skinfolder = gSavedSettings.getControl("SkinCurrent"); -	if(skinfolder && LLStringUtil::null != skinfolder->getValue().asString()) -	{ -		// Examining "Language" may not suffice -- see LLUI::getLanguage() -		// logic. Unfortunately LLUI::getLanguage() doesn't yet do us much -		// good because we haven't yet called LLUI::initClass(). -		gDirUtilp->setSkinFolder(skinfolder->getValue().asString(), -								 gSavedSettings.getString("Language")); -	} - -	if (gSavedSettings.getBOOL("SpellCheck")) -	{ -		std::list<std::string> dict_list; -		std::string dict_setting = gSavedSettings.getString("SpellCheckDictionary"); -		boost::split(dict_list, dict_setting, boost::is_any_of(std::string(","))); -		if (!dict_list.empty()) -		{ -			LLSpellChecker::setUseSpellCheck(dict_list.front()); -			dict_list.pop_front(); -			LLSpellChecker::instance().setSecondaryDictionaries(dict_list); -		} -	} - -  	// Display splash screen.  Must be after above check for previous  	// crash as this dialog is always frontmost.  	std::string splash_msg; @@ -2784,30 +2808,15 @@ bool LLAppViewer::initConfiguration()  	}  	LLStringUtil::truncate(gWindowTitle, 255); -	//RN: if we received a URL, hand it off to the existing instance. -	// don't call anotherInstanceRunning() when doing URL handoff, as -	// it relies on checking a marker file which will not work when running -	// out of different directories - -	if (LLStartUp::getStartSLURL().isValid() && -		(gSavedSettings.getBOOL("SLURLPassToOtherInstance"))) -	{ -		if (sendURLToOtherInstance(LLStartUp::getStartSLURL().getSLURLString())) -		{ -			// successfully handed off URL to existing instance, exit -			return false; -		} -	} -  	//  	// Check for another instance of the app running +	// This happens AFTER LLSplashScreen::show(). That may or may not be +	// important.  	//  	if (mSecondInstance && !gSavedSettings.getBOOL("AllowMultipleViewers"))  	{ -		std::ostringstream msg; -		msg << LLTrans::getString("MBAlreadyRunning");  		OSMessageBox( -			msg.str(), +			LLTrans::getString("MBAlreadyRunning"),  			LLStringUtil::null,  			OSMB_OK);  		return false; @@ -2825,27 +2834,6 @@ bool LLAppViewer::initConfiguration()  		}  	} -   	// NextLoginLocation is set from the command line option -	std::string nextLoginLocation = gSavedSettings.getString( "NextLoginLocation" ); -	if ( !nextLoginLocation.empty() ) -	{ -		LL_DEBUGS("AppInit")<<"set start from NextLoginLocation: "<<nextLoginLocation<<LL_ENDL; -		LLStartUp::setStartSLURL(LLSLURL(nextLoginLocation)); -	} -	else if (   (   clp.hasOption("login") || clp.hasOption("autologin")) -			 && gSavedSettings.getString("CmdLineLoginLocation").empty()) -	{ -		// If automatic login from command line with --login switch -		// init StartSLURL location. -		std::string start_slurl_setting = gSavedSettings.getString("LoginLocation"); -		LL_DEBUGS("AppInit") << "start slurl setting '" << start_slurl_setting << "'" << LL_ENDL; -		LLStartUp::setStartSLURL(LLSLURL(start_slurl_setting)); -	} -	else -	{ -		// the login location will be set by the login panel (see LLPanelLogin) -	} -  	gLastRunVersion = gSavedSettings.getString("LastRunVersion");  	loadColorSettings(); @@ -2869,7 +2857,14 @@ bool LLAppViewer::initConfiguration()  // keeps growing, necessitating a method all its own.  void LLAppViewer::initStrings()  { -	LLTransUtil::parseStrings("strings.xml", default_trans_args); +	std::string strings_file = "strings.xml"; +	std::string strings_path_full = gDirUtilp->findSkinnedFilenameBaseLang(LLDir::XUI, strings_file); +	if (strings_path_full.empty() || !LLFile::isfile(strings_path_full)) +	{ +		// initial check to make sure files are there failed +		LL_ERRS() << "Viewer failed to find localization and UI files. Please reinstall viewer from  https://secondlife.com/support/downloads/ and contact https://support.secondlife.com if issue persists after reinstall." << LL_ENDL; +	} +	LLTransUtil::parseStrings(strings_file, default_trans_args);  	LLTransUtil::parseLanguageStrings("language_settings.xml");  	// parseStrings() sets up the LLTrans substitution table. Add this one item. @@ -3154,6 +3149,10 @@ LLSD LLAppViewer::getViewerInfo() const      substitution["datetime"] = (S32)(gVFS ? gVFS->creationTime() : 0);      info["VFS_TIME"] = LLTrans::getString("AboutTime", substitution); +#if LL_DARWIN +    info["HIDPI"] = gHiDPISupport; +#endif +  	// Libraries  	info["J2C_VERSION"] = LLImageJ2C::getEngineInfo(); @@ -3296,6 +3295,9 @@ std::string LLAppViewer::getViewerInfoString(bool default_string) const  	}  	support << "\n" << LLTrans::getString("AboutOGL", args, default_string);  	support << "\n\n" << LLTrans::getString("AboutSettings", args, default_string); +#if LL_DARWIN +	support << "\n" << LLTrans::getString("AboutOSXHiDPI", args, default_string); +#endif  	support << "\n\n" << LLTrans::getString("AboutLibs", args, default_string);  	if (info.has("COMPILER"))  	{ diff --git a/indra/newview/llcommandlineparser.cpp b/indra/newview/llcommandlineparser.cpp index 90a5483dc9..fe14bc081f 100644 --- a/indra/newview/llcommandlineparser.cpp +++ b/indra/newview/llcommandlineparser.cpp @@ -374,12 +374,40 @@ bool LLCommandLineParser::parseCommandLine(int argc, char **argv)  bool LLCommandLineParser::parseCommandLineString(const std::string& str)  { +    std::string cmd_line_string(""); +    if (!str.empty()) +    { +        bool add_last_c = true; +        S32 last_c_pos = str.size() - 1; //don't get out of bounds on pos+1, last char will be processed separately +        for (S32 pos = 0; pos < last_c_pos; ++pos) +        { +            cmd_line_string.append(&str[pos], 1); +            if (str[pos] == '\\') +            { +                cmd_line_string.append("\\", 1); +                if (str[pos + 1] == '\\') +                { +                    ++pos; +                    add_last_c = (pos != last_c_pos); +                } +            } +        } +        if (add_last_c) +        { +            cmd_line_string.append(&str[last_c_pos], 1); +            if (str[last_c_pos] == '\\') +            { +                cmd_line_string.append("\\", 1); +            } +        } +    } +      // Split the string content into tokens -	const char* escape_chars = "\\"; -	const char* separator_chars = "\r\n "; -	const char* quote_chars = "\"'"; +    const char* escape_chars = "\\"; +    const char* separator_chars = "\r\n "; +    const char* quote_chars = "\"'";      boost::escaped_list_separator<char> sep(escape_chars, separator_chars, quote_chars); -    boost::tokenizer< boost::escaped_list_separator<char> > tok(str, sep); +    boost::tokenizer< boost::escaped_list_separator<char> > tok(cmd_line_string, sep);      std::vector<std::string> tokens;      // std::copy(tok.begin(), tok.end(), std::back_inserter(tokens));      for(boost::tokenizer< boost::escaped_list_separator<char> >::iterator i = tok.begin(); diff --git a/indra/newview/llcontrolavatar.cpp b/indra/newview/llcontrolavatar.cpp index 0f02c23cb0..d24dac385f 100644 --- a/indra/newview/llcontrolavatar.cpp +++ b/indra/newview/llcontrolavatar.cpp @@ -566,27 +566,49 @@ LLViewerObject* LLControlAvatar::lineSegmentIntersectRiggedAttachments(const LLV  									  LLVector4a* normal,  									  LLVector4a* tangent)  { -	LLViewerObject* hit = NULL; +    if (!mRootVolp) +    { +        return NULL; +    } -	if (lineSegmentBoundingBox(start, end)) -	{ -		LLVector4a local_end = end; -		LLVector4a local_intersection; +    LLViewerObject* hit = NULL; -        if (mRootVolp && -            mRootVolp->lineSegmentIntersect(start, local_end, face, pick_transparent, pick_rigged, face_hit, &local_intersection, tex_coord, normal, tangent)) +    if (lineSegmentBoundingBox(start, end)) +    { +        LLVector4a local_end = end; +        LLVector4a local_intersection; +        if (mRootVolp->lineSegmentIntersect(start, local_end, face, pick_transparent, pick_rigged, face_hit, &local_intersection, tex_coord, normal, tangent))          {              local_end = local_intersection;              if (intersection)              {                  *intersection = local_intersection;              } -			              hit = mRootVolp;          } -	} -		 -	return hit; +        else +        { +            std::vector<LLVOVolume*> volumes; +            getAnimatedVolumes(volumes); + +            for (std::vector<LLVOVolume*>::iterator vol_it = volumes.begin(); vol_it != volumes.end(); ++vol_it) +            { +                LLVOVolume *volp = *vol_it; +                if (mRootVolp != volp && volp->lineSegmentIntersect(start, local_end, face, pick_transparent, pick_rigged, face_hit, &local_intersection, tex_coord, normal, tangent)) +                { +                    local_end = local_intersection; +                    if (intersection) +                    { +                        *intersection = local_intersection; +                    } +                    hit = volp; +                    break; +                } +            } +        } +    } + +    return hit;  }  // virtual diff --git a/indra/newview/llfacebookconnect.cpp b/indra/newview/llfacebookconnect.cpp deleted file mode 100644 index 43b01fa2f1..0000000000 --- a/indra/newview/llfacebookconnect.cpp +++ /dev/null @@ -1,714 +0,0 @@ -/**  - * @file llfacebookconnect.h - * @author Merov, Cho, Gil - * @brief Connection to Facebook Service - * - * $LicenseInfo:firstyear=2013&license=viewerlgpl$ - * Second Life Viewer Source Code - * Copyright (C) 2013, Linden Research, Inc. - *  - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation; - * version 2.1 of the License only. - *  - * This library is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU - * Lesser General Public License for more details. - *  - * You should have received a copy of the GNU Lesser General Public - * License along with this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA - *  - * Linden Research, Inc., 945 Battery Street, San Francisco, CA  94111  USA - * $/LicenseInfo$ - */ - -#include "llviewerprecompiledheaders.h" - -#include "llfacebookconnect.h" -#include "llflickrconnect.h" -#include "lltwitterconnect.h" - -#include "llagent.h" -#include "llcallingcard.h"			// for LLAvatarTracker -#include "llcommandhandler.h" -#include "llnotificationsutil.h" -#include "llurlaction.h" -#include "llimagepng.h" -#include "llimagejpeg.h" -#include "lltrans.h" -#include "llevents.h" -#include "llviewerregion.h" -#include "llviewercontrol.h" - -#include "llfloaterwebcontent.h" -#include "llfloaterreg.h" -#include "llcorehttputil.h" - -boost::scoped_ptr<LLEventPump> LLFacebookConnect::sStateWatcher(new LLEventStream("FacebookConnectState")); -boost::scoped_ptr<LLEventPump> LLFacebookConnect::sInfoWatcher(new LLEventStream("FacebookConnectInfo")); -boost::scoped_ptr<LLEventPump> LLFacebookConnect::sContentWatcher(new LLEventStream("FacebookConnectContent")); - -// Local functions -void log_facebook_connect_error(const std::string& request, U32 status, const std::string& reason, const std::string& code, const std::string& description) -{ -    // Note: 302 (redirect) is *not* an error that warrants logging -    if (status != 302) -    { -		LL_WARNS("FacebookConnect") << request << " request failed with a " << status << " " << reason << ". Reason: " << code << " (" << description << ")" << LL_ENDL; -    } -} - -void toast_user_for_facebook_success() -{ -	LLSD args; -    args["MESSAGE"] = LLTrans::getString("facebook_post_success"); -    LLNotificationsUtil::add("FacebookConnect", args); -} - -LLCore::HttpHeaders::ptr_t get_headers() -{ -    LLCore::HttpHeaders::ptr_t httpHeaders(new LLCore::HttpHeaders); -    // The DebugSlshareLogTag mechanism is intended to trigger slshare-service -    // debug logging. slshare-service is coded to respond to an X-debug-tag -    // header by engaging debug logging for that request only. This way a -    // developer need not muck with the slshare-service image to engage debug -    // logging. Moreover, the value of X-debug-tag is embedded in each such -    // log line so the developer can quickly find the log lines pertinent to -    // THIS session. -    std::string logtag(gSavedSettings.getString("DebugSlshareLogTag")); -    if (! logtag.empty()) -    { -        httpHeaders->append("X-debug-tag", logtag); -    } -    return httpHeaders; -} - -/////////////////////////////////////////////////////////////////////////////// -// -class LLFacebookConnectHandler : public LLCommandHandler -{ -public: -	LLFacebookConnectHandler() : LLCommandHandler("fbc", UNTRUSTED_THROTTLE) { } -     -	bool handle(const LLSD& tokens, const LLSD& query_map, LLMediaCtrl* web) -	{ -		if (tokens.size() >= 1) -		{ -			if (tokens[0].asString() == "connect") -			{ -				if (tokens.size() >= 2 && tokens[1].asString() == "flickr") -				{ -					// this command probably came from the flickr_web browser, so close it -					LLFloaterReg::hideInstance("flickr_web"); - -					// connect to flickr -					if (query_map.has("oauth_token")) -					{ -						LLFlickrConnect::instance().connectToFlickr(query_map["oauth_token"], query_map.get("oauth_verifier")); -					} -					return true; -				} -				else if (tokens.size() >= 2 && tokens[1].asString() == "twitter") -				{ -					// this command probably came from the twitter_web browser, so close it -					LLFloaterReg::hideInstance("twitter_web"); - -					// connect to twitter -					if (query_map.has("oauth_token")) -					{ -						LLTwitterConnect::instance().connectToTwitter(query_map["oauth_token"], query_map.get("oauth_verifier")); -					} -					return true; -				} -				else //if (tokens.size() >= 2 && tokens[1].asString() == "facebook") -				{ -					// this command probably came from the fbc_web browser, so close it -					LLFloaterReg::hideInstance("fbc_web"); - -					// connect to facebook -					if (query_map.has("code")) -					{ -						LLFacebookConnect::instance().connectToFacebook(query_map["code"], query_map.get("state")); -					} -					return true; -				} -			} -		} -		return false; -	} -}; -LLFacebookConnectHandler gFacebookConnectHandler; - -/////////////////////////////////////////////////////////////////////////////// -// -void LLFacebookConnect::facebookConnectCoro(std::string authCode, std::string authState) -{ -    LLCore::HttpRequest::policy_t httpPolicy(LLCore::HttpRequest::DEFAULT_POLICY_ID); -    LLCoreHttpUtil::HttpCoroutineAdapter::ptr_t -        httpAdapter(new LLCoreHttpUtil::HttpCoroutineAdapter("FacebookConnect", httpPolicy)); -    LLCore::HttpRequest::ptr_t httpRequest(new LLCore::HttpRequest); -    LLCore::HttpOptions::ptr_t httpOpts(new LLCore::HttpOptions); - -    LLSD putData; -    if (!authCode.empty()) -    { -        putData["code"] = authCode; -    } -    if (!authState.empty()) -    { -        putData["state"] = authState; -    } - -    httpOpts->setWantHeaders(true); -    httpOpts->setFollowRedirects(false); - -    LLSD result = httpAdapter->putAndSuspend(httpRequest, getFacebookConnectURL("/connection"), putData, httpOpts, get_headers()); - -    LLSD httpResults = result[LLCoreHttpUtil::HttpCoroutineAdapter::HTTP_RESULTS]; -    LLCore::HttpStatus status = LLCoreHttpUtil::HttpCoroutineAdapter::getStatusFromLLSD(httpResults); -    if (!status) -    { -        if (status == LLCore::HttpStatus(HTTP_FOUND)) -        { -            std::string location = httpResults[LLCoreHttpUtil::HttpCoroutineAdapter::HTTP_RESULTS_HEADERS][HTTP_IN_HEADER_LOCATION]; -            if (location.empty()) -            { -                LL_WARNS("FacebookConnect") << "Missing Location header " << LL_ENDL; -            } -            else -            { -                openFacebookWeb(location); -            } -        } -    } -    else -    { -        LL_INFOS("FacebookConnect") << "Connect successful. " << LL_ENDL; -        setConnectionState(LLFacebookConnect::FB_CONNECTED); -    } - -} - -/////////////////////////////////////////////////////////////////////////////// -// -bool LLFacebookConnect::testShareStatus(LLSD &result) -{ -    LLSD httpResults = result[LLCoreHttpUtil::HttpCoroutineAdapter::HTTP_RESULTS]; -    LLCore::HttpStatus status = LLCoreHttpUtil::HttpCoroutineAdapter::getStatusFromLLSD(httpResults); - -    if (status) -        return true; - -    if (status == LLCore::HttpStatus(HTTP_FOUND)) -    { -        std::string location = httpResults[LLCoreHttpUtil::HttpCoroutineAdapter::HTTP_RESULTS_HEADERS][HTTP_IN_HEADER_LOCATION]; -        if (location.empty()) -        { -            LL_WARNS("FacebookConnect") << "Missing Location header " << LL_ENDL; -        } -        else -        { -            openFacebookWeb(location); -        } -    } -    if (status == LLCore::HttpStatus(HTTP_NOT_FOUND)) -    { -        LL_DEBUGS("FacebookConnect") << "Not connected. " << LL_ENDL; -        connectToFacebook(); -    } -    else -    { -        LL_WARNS("FacebookConnect") << "HTTP Status error " << status.toString() << LL_ENDL; -        setConnectionState(LLFacebookConnect::FB_POST_FAILED); -        log_facebook_connect_error("Share", status.getStatus(), status.toString(), -            result.get("error_code"), result.get("error_description")); -    } -    return false; -} - -void LLFacebookConnect::facebookShareCoro(std::string route, LLSD share) -{ -    LLCore::HttpRequest::policy_t httpPolicy(LLCore::HttpRequest::DEFAULT_POLICY_ID); -    LLCoreHttpUtil::HttpCoroutineAdapter::ptr_t -        httpAdapter(new LLCoreHttpUtil::HttpCoroutineAdapter("FacebookConnect", httpPolicy)); -    LLCore::HttpRequest::ptr_t httpRequest(new LLCore::HttpRequest); -    LLCore::HttpOptions::ptr_t httpOpts(new LLCore::HttpOptions); - -    httpOpts->setWantHeaders(true); -    httpOpts->setFollowRedirects(false); - -    LLSD result = httpAdapter->postAndSuspend(httpRequest, getFacebookConnectURL(route, true), share, httpOpts, get_headers()); - -    if (testShareStatus(result)) -    { -        toast_user_for_facebook_success(); -        LL_DEBUGS("FacebookConnect") << "Post successful. " << LL_ENDL; -        setConnectionState(LLFacebookConnect::FB_POSTED); -    } -} - -void LLFacebookConnect::facebookShareImageCoro(std::string route, LLPointer<LLImageFormatted> image, std::string caption) -{ -    LLCore::HttpRequest::policy_t httpPolicy(LLCore::HttpRequest::DEFAULT_POLICY_ID); -    LLCoreHttpUtil::HttpCoroutineAdapter::ptr_t -        httpAdapter(new LLCoreHttpUtil::HttpCoroutineAdapter("FacebookConnect", httpPolicy)); -    LLCore::HttpRequest::ptr_t httpRequest(new LLCore::HttpRequest); -    LLCore::HttpHeaders::ptr_t httpHeaders(get_headers()); -    LLCore::HttpOptions::ptr_t httpOpts(new LLCore::HttpOptions); - -    httpOpts->setWantHeaders(true); -    httpOpts->setFollowRedirects(false); - -    std::string imageFormat; -    if (dynamic_cast<LLImagePNG*>(image.get())) -    { -        imageFormat = "png"; -    } -    else if (dynamic_cast<LLImageJPEG*>(image.get())) -    { -        imageFormat = "jpg"; -    } -    else -    { -        LL_WARNS() << "Image to upload is not a PNG or JPEG" << LL_ENDL; -        return; -    } - -    // All this code is mostly copied from LLWebProfile::post() -    static const std::string boundary = "----------------------------0123abcdefab"; - -    std::string contentType = "multipart/form-data; boundary=" + boundary; -    httpHeaders->append("Content-Type", contentType.c_str()); - -    LLCore::BufferArray::ptr_t raw = LLCore::BufferArray::ptr_t(new LLCore::BufferArray()); //  -    LLCore::BufferArrayStream body(raw.get()); - -    // *NOTE: The order seems to matter. -    body << "--" << boundary << "\r\n" -        << "Content-Disposition: form-data; name=\"caption\"\r\n\r\n" -        << caption << "\r\n"; - -    body << "--" << boundary << "\r\n" -        << "Content-Disposition: form-data; name=\"image\"; filename=\"Untitled." << imageFormat << "\"\r\n" -        << "Content-Type: image/" << imageFormat << "\r\n\r\n"; - -    // Insert the image data. -    // *FIX: Treating this as a string will probably screw it up ... -    U8* image_data = image->getData(); -    for (S32 i = 0; i < image->getDataSize(); ++i) -    { -        body << image_data[i]; -    } - -    body << "\r\n--" << boundary << "--\r\n"; - -    setConnectionState(LLFacebookConnect::FB_POSTING); - -    LLSD result = httpAdapter->postAndSuspend(httpRequest, getFacebookConnectURL(route, true), raw, httpOpts, httpHeaders); - -    if (testShareStatus(result)) -    { -        toast_user_for_facebook_success(); -        LL_DEBUGS("FacebookConnect") << "Post successful. " << LL_ENDL; -        setConnectionState(LLFacebookConnect::FB_POSTED); -    } -} - -/////////////////////////////////////////////////////////////////////////////// -// -void LLFacebookConnect::facebookDisconnectCoro() -{ -    LLCore::HttpRequest::policy_t httpPolicy(LLCore::HttpRequest::DEFAULT_POLICY_ID); -    LLCoreHttpUtil::HttpCoroutineAdapter::ptr_t -        httpAdapter(new LLCoreHttpUtil::HttpCoroutineAdapter("FacebookConnect", httpPolicy)); -    LLCore::HttpRequest::ptr_t httpRequest(new LLCore::HttpRequest); -    LLCore::HttpOptions::ptr_t httpOpts(new LLCore::HttpOptions); - -    httpOpts->setFollowRedirects(false); - -    LLSD result = httpAdapter->deleteAndSuspend(httpRequest, getFacebookConnectURL("/connection"), httpOpts, get_headers()); - -    LLSD httpResults = result[LLCoreHttpUtil::HttpCoroutineAdapter::HTTP_RESULTS]; -    LLCore::HttpStatus status = LLCoreHttpUtil::HttpCoroutineAdapter::getStatusFromLLSD(httpResults); -    if (!status && (status != LLCore::HttpStatus(HTTP_FOUND))) -    { -        LL_WARNS("FacebookConnect") << "Failed to disconnect:" << status.toTerseString() << LL_ENDL; -        setConnectionState(LLFacebookConnect::FB_DISCONNECT_FAILED); -        log_facebook_connect_error("Disconnect", status.getStatus(), status.toString(), -            result.get("error_code"), result.get("error_description")); -    } -    else -    { -        LL_DEBUGS("FacebookConnect") << "Facebook Disconnect successful. " << LL_ENDL; -        clearInfo(); -        clearContent(); -        //Notify state change -        setConnectionState(LLFacebookConnect::FB_NOT_CONNECTED); -    } - -} - -/////////////////////////////////////////////////////////////////////////////// -// -void LLFacebookConnect::facebookConnectedCheckCoro(bool autoConnect) -{ -    LLCore::HttpRequest::policy_t httpPolicy(LLCore::HttpRequest::DEFAULT_POLICY_ID); -    LLCoreHttpUtil::HttpCoroutineAdapter::ptr_t -        httpAdapter(new LLCoreHttpUtil::HttpCoroutineAdapter("FacebookConnect", httpPolicy)); -    LLCore::HttpRequest::ptr_t httpRequest(new LLCore::HttpRequest); -    LLCore::HttpOptions::ptr_t httpOpts(new LLCore::HttpOptions); - -    setConnectionState(LLFacebookConnect::FB_CONNECTION_IN_PROGRESS); - -    httpOpts->setFollowRedirects(false); - -    LLSD result = httpAdapter->getAndSuspend(httpRequest, getFacebookConnectURL("/connection", true), httpOpts, get_headers()); - -    LLSD httpResults = result[LLCoreHttpUtil::HttpCoroutineAdapter::HTTP_RESULTS]; -    LLCore::HttpStatus status = LLCoreHttpUtil::HttpCoroutineAdapter::getStatusFromLLSD(httpResults); - -    if (!status) -    { -        if ( status == LLCore::HttpStatus(HTTP_NOT_FOUND) ) -        { -            LL_DEBUGS("FacebookConnect") << "Not connected. " << LL_ENDL; -            if (autoConnect) -            { -                connectToFacebook(); -            } -            else -            { -                setConnectionState(LLFacebookConnect::FB_NOT_CONNECTED); -            } -        } -        else -        { -            LL_WARNS("FacebookConnect") << "Failed to test connection:" << status.toTerseString() << LL_ENDL; - -            setConnectionState(LLFacebookConnect::FB_DISCONNECT_FAILED); -            log_facebook_connect_error("Connected", status.getStatus(), status.toString(), -                result.get("error_code"), result.get("error_description")); -        } -    } -    else -    { -        LL_DEBUGS("FacebookConnect") << "Connect successful. " << LL_ENDL; -        setConnectionState(LLFacebookConnect::FB_CONNECTED); -    } -} - -/////////////////////////////////////////////////////////////////////////////// -// -void LLFacebookConnect::facebookConnectInfoCoro() -{ -    LLCore::HttpRequest::policy_t httpPolicy(LLCore::HttpRequest::DEFAULT_POLICY_ID); -    LLCoreHttpUtil::HttpCoroutineAdapter::ptr_t -        httpAdapter(new LLCoreHttpUtil::HttpCoroutineAdapter("FacebookConnect", httpPolicy)); -    LLCore::HttpRequest::ptr_t httpRequest(new LLCore::HttpRequest); -    LLCore::HttpOptions::ptr_t httpOpts(new LLCore::HttpOptions); - -    httpOpts->setWantHeaders(true); -    httpOpts->setFollowRedirects(false); - -    LLSD result = httpAdapter->getAndSuspend(httpRequest, getFacebookConnectURL("/info", true), httpOpts, get_headers()); - -    LLSD httpResults = result[LLCoreHttpUtil::HttpCoroutineAdapter::HTTP_RESULTS]; -    LLCore::HttpStatus status = LLCoreHttpUtil::HttpCoroutineAdapter::getStatusFromLLSD(httpResults); - -    if (status == LLCore::HttpStatus(HTTP_FOUND)) -    { -        std::string location = httpResults[LLCoreHttpUtil::HttpCoroutineAdapter::HTTP_RESULTS_HEADERS][HTTP_IN_HEADER_LOCATION]; -        if (location.empty()) -        { -            LL_WARNS("FacebookConnect") << "Missing Location header " << LL_ENDL; -        } -        else -        { -            openFacebookWeb(location); -        } -    } -    else if (!status) -    { -        LL_WARNS("FacebookConnect") << "Facebook Info failed: " << status.toString() << LL_ENDL; -        log_facebook_connect_error("Info", status.getStatus(), status.toString(), -            result.get("error_code"), result.get("error_description")); -    } -    else -    { -        LL_INFOS("FacebookConnect") << "Facebook: Info received" << LL_ENDL; -        result.erase(LLCoreHttpUtil::HttpCoroutineAdapter::HTTP_RESULTS); -        storeInfo(result); -    } -} - -/////////////////////////////////////////////////////////////////////////////// -// -void LLFacebookConnect::facebookConnectFriendsCoro() -{ -    LLCore::HttpRequest::policy_t httpPolicy(LLCore::HttpRequest::DEFAULT_POLICY_ID); -    LLCoreHttpUtil::HttpCoroutineAdapter::ptr_t -        httpAdapter(new LLCoreHttpUtil::HttpCoroutineAdapter("FacebookConnect", httpPolicy)); -    LLCore::HttpRequest::ptr_t httpRequest(new LLCore::HttpRequest); -    LLCore::HttpOptions::ptr_t httpOpts(new LLCore::HttpOptions); - -    httpOpts->setFollowRedirects(false); - -    LLSD result = httpAdapter->getAndSuspend(httpRequest, getFacebookConnectURL("/friends", true), httpOpts, get_headers()); - -    LLSD httpResults = result[LLCoreHttpUtil::HttpCoroutineAdapter::HTTP_RESULTS]; -    LLCore::HttpStatus status = LLCoreHttpUtil::HttpCoroutineAdapter::getStatusFromLLSD(httpResults); - -    if (status == LLCore::HttpStatus(HTTP_FOUND)) -    { -        std::string location = httpResults[LLCoreHttpUtil::HttpCoroutineAdapter::HTTP_RESULTS_HEADERS][HTTP_IN_HEADER_LOCATION]; -        if (location.empty()) -        { -            LL_WARNS("FacebookConnect") << "Missing Location header " << LL_ENDL; -        } -        else -        { -            openFacebookWeb(location); -        } -    } -    else if (!status) -    { -        LL_WARNS("FacebookConnect") << "Facebook Friends failed: " << status.toString() << LL_ENDL; -        log_facebook_connect_error("Info", status.getStatus(), status.toString(), -            result.get("error_code"), result.get("error_description")); -    } -    else -    { -        LL_INFOS("FacebookConnect") << "Facebook: Friends received" << LL_ENDL; -        result.erase(LLCoreHttpUtil::HttpCoroutineAdapter::HTTP_RESULTS); -        LLSD content = result[LLCoreHttpUtil::HttpCoroutineAdapter::HTTP_RESULTS_CONTENT]; -        storeContent(content); -    } -} - -/////////////////////////////////////////////////////////////////////////////// -// -LLFacebookConnect::LLFacebookConnect() -:	mConnectionState(FB_NOT_CONNECTED), -	mConnected(false), -	mInfo(), -    mContent(), -	mRefreshInfo(false), -	mRefreshContent(false), -	mReadFromMaster(false) -{ -} - -void LLFacebookConnect::openFacebookWeb(std::string url) -{ -	LLFloaterWebContent::Params p; -    p.url(url); -    p.show_chrome(true); -    p.allow_back_forward_navigation(false); -    p.clean_browser(true); -	LLFloater *floater = LLFloaterReg::showInstance("fbc_web", p); -	//the internal web browser has a bug that prevents it from gaining focus unless a mouse event occurs first (it seems). -	//So when showing the internal web browser, set focus to it's containing floater "fbc_web". When a mouse event  -	//occurs on the "webbrowser" panel part of the floater, a mouse cursor will properly show and the "webbrowser" will gain focus. -	//fbc_web floater contains the "webbrowser" panel.    JIRA: ACME-744 -	gFocusMgr.setKeyboardFocus( floater ); - -	//LLUrlAction::openURLExternal(url); -} - -std::string LLFacebookConnect::getFacebookConnectURL(const std::string& route, bool include_read_from_master) -{ -    std::string url(""); -    LLViewerRegion *regionp = gAgent.getRegion(); -    if (regionp) -    { -		//url = "http://pdp15.lindenlab.com/fbc/agent/" + gAgentID.asString(); // TEMPORARY FOR TESTING - CHO -		url = regionp->getCapability("FacebookConnect"); -        url += route; -     -        if (include_read_from_master && mReadFromMaster) -        { -            url += "?read_from_master=true"; -        } -    } -	return url; -} - -void LLFacebookConnect::connectToFacebook(const std::string& auth_code, const std::string& auth_state) -{ -    setConnectionState(LLFacebookConnect::FB_CONNECTION_IN_PROGRESS); - -    LLCoros::instance().launch("LLFacebookConnect::facebookConnectCoro", -        boost::bind(&LLFacebookConnect::facebookConnectCoro, this, auth_code, auth_state)); -} - -void LLFacebookConnect::disconnectFromFacebook() -{ -    LLCoros::instance().launch("LLFacebookConnect::facebookDisconnectCoro", -        boost::bind(&LLFacebookConnect::facebookDisconnectCoro, this)); -} - -void LLFacebookConnect::checkConnectionToFacebook(bool auto_connect) -{ -    setConnectionState(LLFacebookConnect::FB_DISCONNECTING); - -    LLCoros::instance().launch("LLFacebookConnect::facebookConnectedCheckCoro", -        boost::bind(&LLFacebookConnect::facebookConnectedCheckCoro, this, auto_connect)); -} - -void LLFacebookConnect::loadFacebookInfo() -{ -	if(mRefreshInfo) -	{ -        LLCoros::instance().launch("LLFacebookConnect::facebookConnectInfoCoro", -            boost::bind(&LLFacebookConnect::facebookConnectInfoCoro, this)); -	} -} - -void LLFacebookConnect::loadFacebookFriends() -{ -	if(mRefreshContent) -	{ -        LLCoros::instance().launch("LLFacebookConnect::facebookConnectFriendsCoro", -            boost::bind(&LLFacebookConnect::facebookConnectFriendsCoro, this)); -	} -} - -void LLFacebookConnect::postCheckin(const std::string& location, const std::string& name,  -    const std::string& description, const std::string& image, const std::string& message) -{ -    setConnectionState(LLFacebookConnect::FB_POSTING); - -	LLSD body; -	if (!location.empty()) -    { -		body["location"] = location; -    } -	if (!name.empty()) -    { -		body["name"] = name; -    } -	if (!description.empty()) -    { -		body["description"] = description; -    } -	if (!image.empty()) -    { -		body["image"] = image; -    } -	if (!message.empty()) -    { -		body["message"] = message; -    } - -    LLCoros::instance().launch("LLFacebookConnect::facebookShareCoro", -        boost::bind(&LLFacebookConnect::facebookShareCoro, this, "/share/checkin", body)); -} - -void LLFacebookConnect::sharePhoto(const std::string& image_url, const std::string& caption) -{ -    setConnectionState(LLFacebookConnect::FB_POSTING); - -	LLSD body; -	body["image"] = image_url; -	body["caption"] = caption; -	 -    LLCoros::instance().launch("LLFacebookConnect::facebookShareCoro", -        boost::bind(&LLFacebookConnect::facebookShareCoro, this, "/share/photo", body)); -} - -void LLFacebookConnect::sharePhoto(LLPointer<LLImageFormatted> image, const std::string& caption) -{ -    setConnectionState(LLFacebookConnect::FB_POSTING); - -    LLCoros::instance().launch("LLFacebookConnect::facebookShareImageCoro", -        boost::bind(&LLFacebookConnect::facebookShareImageCoro, this, "/share/photo", image, caption)); -} - -void LLFacebookConnect::updateStatus(const std::string& message) -{ -	LLSD body; -	body["message"] = message; - -    setConnectionState(LLFacebookConnect::FB_POSTING); - -    LLCoros::instance().launch("LLFacebookConnect::facebookShareCoro", -        boost::bind(&LLFacebookConnect::facebookShareCoro, this, "/share/wall", body)); -} - -void LLFacebookConnect::storeInfo(const LLSD& info) -{ -	mInfo = info; -	mRefreshInfo = false; - -	sInfoWatcher->post(info); -} - -const LLSD& LLFacebookConnect::getInfo() const -{ -	return mInfo; -} - -void LLFacebookConnect::clearInfo() -{ -	mInfo = LLSD(); -} - -void LLFacebookConnect::storeContent(const LLSD& content) -{ -    mContent = content; -	mRefreshContent = false; - -	sContentWatcher->post(content); -} - -const LLSD& LLFacebookConnect::getContent() const -{ -    return mContent; -} - -void LLFacebookConnect::clearContent() -{ -    mContent = LLSD(); -} - -void LLFacebookConnect::setDataDirty() -{ -	mRefreshInfo = true; -	mRefreshContent = true; -} - -void LLFacebookConnect::setConnectionState(LLFacebookConnect::EConnectionState connection_state) -{ -	if(connection_state == FB_CONNECTED) -	{ -		mReadFromMaster = true; -		setConnected(true); -		setDataDirty(); -	} -	else if(connection_state == FB_NOT_CONNECTED) -	{ -		setConnected(false); -	} -	else if(connection_state == FB_POSTED) -	{ -		mReadFromMaster = false; -	} - -	if (mConnectionState != connection_state) -	{ -		// set the connection state before notifying watchers -		mConnectionState = connection_state; - -		LLSD state_info; -		state_info["enum"] = connection_state; -		sStateWatcher->post(state_info); -	} -} - -void LLFacebookConnect::setConnected(bool connected) -{ -	mConnected = connected; -} diff --git a/indra/newview/llfacebookconnect.h b/indra/newview/llfacebookconnect.h deleted file mode 100644 index 7fd4070f54..0000000000 --- a/indra/newview/llfacebookconnect.h +++ /dev/null @@ -1,116 +0,0 @@ -/**  - * @file llfacebookconnect.h - * @author Merov, Cho, Gil - * @brief Connection to Facebook Service - * - * $LicenseInfo:firstyear=2013&license=viewerlgpl$ - * Second Life Viewer Source Code - * Copyright (C) 2013, Linden Research, Inc. - *  - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation; - * version 2.1 of the License only. - *  - * This library is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU - * Lesser General Public License for more details. - *  - * You should have received a copy of the GNU Lesser General Public - * License along with this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA - *  - * Linden Research, Inc., 945 Battery Street, San Francisco, CA  94111  USA - * $/LicenseInfo$ - */ - -#ifndef LL_LLFACEBOOKCONNECT_H -#define LL_LLFACEBOOKCONNECT_H - -#include "llsingleton.h" -#include "llimage.h" -#include "llcoros.h" -#include "lleventcoro.h" - -class LLEventPump; - -/** - * @class LLFacebookConnect - * - * Manages authentication to, and interaction with, a web service allowing the - * the viewer to get Facebook OpenGraph data. - */ -class LLFacebookConnect : public LLSingleton<LLFacebookConnect> -{ -	LLSINGLETON(LLFacebookConnect); -	~LLFacebookConnect() {}; -	LOG_CLASS(LLFacebookConnect); -public: -    enum EConnectionState -	{ -		FB_NOT_CONNECTED = 0, -		FB_CONNECTION_IN_PROGRESS = 1, -		FB_CONNECTED = 2, -		FB_CONNECTION_FAILED = 3, -		FB_POSTING = 4, -		FB_POSTED = 5, -		FB_POST_FAILED = 6, -		FB_DISCONNECTING = 7, -		FB_DISCONNECT_FAILED = 8 -	}; -	 -	void connectToFacebook(const std::string& auth_code = "", const std::string& auth_state = "");	// Initiate the complete FB connection. Please use checkConnectionToFacebook() in normal use. -	void disconnectFromFacebook();																	// Disconnect from the FBC service. -    void checkConnectionToFacebook(bool auto_connect = false);										// Check if an access token is available on the FBC service. If not, call connectToFacebook(). -     -	void loadFacebookInfo(); -    void loadFacebookFriends(); -	void postCheckin(const std::string& location, const std::string& name, const std::string& description, const std::string& picture, const std::string& message); -    void sharePhoto(const std::string& image_url, const std::string& caption); -	void sharePhoto(LLPointer<LLImageFormatted> image, const std::string& caption); -	void updateStatus(const std::string& message); -	 -	void storeInfo(const LLSD& info); -	const LLSD& getInfo() const; -	void clearInfo(); -	void storeContent(const LLSD& content); -    const LLSD& getContent() const; -	void clearContent(); -	void setDataDirty(); -     -    void setConnectionState(EConnectionState connection_state); -	void setConnected(bool connected); -	bool isConnected() { return mConnected; } -	bool isTransactionOngoing() { return ((mConnectionState == FB_CONNECTION_IN_PROGRESS) || (mConnectionState == FB_POSTING) || (mConnectionState == FB_DISCONNECTING)); } -    EConnectionState getConnectionState() { return mConnectionState; } -     -    void openFacebookWeb(std::string url); - -private: - - 	std::string getFacebookConnectURL(const std::string& route = "", bool include_read_from_master = false); - -    EConnectionState mConnectionState; -	BOOL mConnected; -	LLSD mInfo; -    LLSD mContent; -	bool mRefreshInfo; -	bool mRefreshContent; -	bool mReadFromMaster; -	 -	static boost::scoped_ptr<LLEventPump> sStateWatcher; -	static boost::scoped_ptr<LLEventPump> sInfoWatcher; -	static boost::scoped_ptr<LLEventPump> sContentWatcher; - -    bool testShareStatus(LLSD &results); -    void facebookConnectCoro(std::string authCode, std::string authState); -    void facebookConnectedCheckCoro(bool autoConnect); -    void facebookDisconnectCoro(); -    void facebookShareCoro(std::string route, LLSD share); -    void facebookShareImageCoro(std::string route, LLPointer<LLImageFormatted> image, std::string caption); -    void facebookConnectInfoCoro(); -    void facebookConnectFriendsCoro(); -}; - -#endif // LL_LLFACEBOOKCONNECT_H diff --git a/indra/newview/llfasttimerview.cpp b/indra/newview/llfasttimerview.cpp index f68e63cb96..d90f03b403 100644 --- a/indra/newview/llfasttimerview.cpp +++ b/indra/newview/llfasttimerview.cpp @@ -43,6 +43,7 @@  #include "llsdserialize.h"  #include "lltooltip.h"  #include "llbutton.h" +#include "llscrollbar.h"  #include "llappviewer.h"  #include "llviewertexturelist.h" @@ -128,7 +129,8 @@ void LLFastTimerView::setPauseState(bool pause_state)  BOOL LLFastTimerView::postBuild()  {  	LLButton& pause_btn = getChildRef<LLButton>("pause_btn"); -	 +	mScrollBar = getChild<LLScrollbar>("scroll_vert"); +  	pause_btn.setCommitCallback(boost::bind(&LLFastTimerView::onPause, this));  	return TRUE;  } @@ -183,7 +185,7 @@ BOOL LLFastTimerView::handleDoubleClick(S32 x, S32 y, MASK mask)  BOOL LLFastTimerView::handleMouseDown(S32 x, S32 y, MASK mask)  { -	if (x < mBarRect.mLeft)  +	if (x < mScrollBar->getRect().mLeft)  	{  		BlockTimerStatHandle* idp = getLegendID(y);  		if (idp) @@ -284,7 +286,7 @@ BOOL LLFastTimerView::handleHover(S32 x, S32 y, MASK mask)  			}  		}  	} -	else if (x < mBarRect.mLeft)  +	else if (x < mScrollBar->getRect().mLeft)   	{  		BlockTimerStatHandle* timer_id = getLegendID(y);  		if (timer_id) @@ -335,7 +337,7 @@ BOOL LLFastTimerView::handleToolTip(S32 x, S32 y, MASK mask)  	else  	{  		// tooltips for timer legend -		if (x < mBarRect.mLeft)  +		if (x < mScrollBar->getRect().mLeft)   		{  			BlockTimerStatHandle* idp = getLegendID(y);  			if (idp) @@ -352,11 +354,19 @@ BOOL LLFastTimerView::handleToolTip(S32 x, S32 y, MASK mask)  BOOL LLFastTimerView::handleScrollWheel(S32 x, S32 y, S32 clicks)  { -	setPauseState(true); -	mScrollIndex = llclamp(	mScrollIndex + clicks, -							0, -							llmin((S32)mRecording.getNumRecordedPeriods(), (S32)mRecording.getNumRecordedPeriods() - MAX_VISIBLE_HISTORY)); -	return TRUE; +    if (x < mBarRect.mLeft) +    { +        // Inside mScrollBar and list of timers +        mScrollBar->handleScrollWheel(x,y,clicks); +    } +    else +    { +        setPauseState(true); +        mScrollIndex = llclamp(mScrollIndex + clicks, +            0, +            llmin((S32)mRecording.getNumRecordedPeriods(), (S32)mRecording.getNumRecordedPeriods() - MAX_VISIBLE_HISTORY)); +    } +    return TRUE;  }  static BlockTimerStatHandle FTM_RENDER_TIMER("Timers"); @@ -1197,6 +1207,7 @@ void LLFastTimerView::drawLegend()  	{  		LLLocalClipRect clip(mLegendRect);  		S32 cur_line = 0; +		S32 scroll_offset = 0; // element's y offset from top of the inner scroll's rect  		ft_display_idx.clear();  		std::map<BlockTimerStatHandle*, S32> display_line;  		for (block_timer_tree_df_iterator_t it = LLTrace::begin_block_timer_tree_df(FTM_FRAME); @@ -1204,10 +1215,24 @@ void LLFastTimerView::drawLegend()  			++it)  		{  			BlockTimerStatHandle* idp = (*it); +			// Needed to figure out offsets and parenting  			display_line[idp] = cur_line; -			ft_display_idx.push_back(idp);  			cur_line++; +			if (scroll_offset < mScrollBar->getDocPos()) +			{ +				// only offset for visible items +				scroll_offset += TEXT_HEIGHT + 2; +				if (idp->getTreeNode().mCollapsed) +				{ +					it.skipDescendants(); +				} +				continue; +			} + +			// used for mouse clicks +			ft_display_idx.push_back(idp); +			// Actual draw, first bar (square), then text  			x = MARGIN;  			LLRect bar_rect(x, y, x + TEXT_HEIGHT, y - TEXT_HEIGHT); @@ -1281,11 +1306,14 @@ void LLFastTimerView::drawLegend()  			y -= (TEXT_HEIGHT + 2); +			scroll_offset += TEXT_HEIGHT + 2;  			if (idp->getTreeNode().mCollapsed)   			{  				it.skipDescendants();  			}  		} +		// Recalculate scroll size +		mScrollBar->setDocSize(scroll_offset - mLegendRect.getHeight());  	}  } diff --git a/indra/newview/llfasttimerview.h b/indra/newview/llfasttimerview.h index 3e30bd86ba..ff65f8da07 100644 --- a/indra/newview/llfasttimerview.h +++ b/indra/newview/llfasttimerview.h @@ -33,6 +33,8 @@  #include "lltracerecording.h"  #include <deque> +class LLScrollbar; +  class LLFastTimerView : public LLFloater  {  public: @@ -142,6 +144,8 @@ private:  									mLegendRect;  	LLFrameTimer					mHighlightTimer;  	LLTrace::PeriodicRecording		mRecording; + +	LLScrollbar* 					mScrollBar;  };  #endif diff --git a/indra/newview/llfloaterfacebook.cpp b/indra/newview/llfloaterfacebook.cpp deleted file mode 100644 index e84cbc289f..0000000000 --- a/indra/newview/llfloaterfacebook.cpp +++ /dev/null @@ -1,1132 +0,0 @@ -/** -* @file llfloaterfacebook.cpp -* @brief Implementation of llfloaterfacebook -* @author Gilbert@lindenlab.com -* -* $LicenseInfo:firstyear=2013&license=viewerlgpl$ -* Second Life Viewer Source Code -* Copyright (C) 2013, Linden Research, Inc. -* -* This library is free software; you can redistribute it and/or -* modify it under the terms of the GNU Lesser General Public -* License as published by the Free Software Foundation; -* version 2.1 of the License only. -* -* This library is distributed in the hope that it will be useful, -* but WITHOUT ANY WARRANTY; without even the implied warranty of -* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU -* Lesser General Public License for more details. -* -* You should have received a copy of the GNU Lesser General Public -* License along with this library; if not, write to the Free Software -* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA -* -* Linden Research, Inc., 945 Battery Street, San Francisco, CA  94111  USA -* $/LicenseInfo$ -*/ - -#include "llviewerprecompiledheaders.h" - -#include "llfloaterfacebook.h" - -#include "llagent.h" -#include "llagentui.h" -#include "llcheckboxctrl.h" -#include "llcombobox.h" -#include "llfacebookconnect.h" -#include "llfloaterbigpreview.h" -#include "llfloaterreg.h" -#include "lliconctrl.h" -#include "llimagefiltersmanager.h" -#include "llresmgr.h"		// LLLocale -#include "llsdserialize.h" -#include "llloadingindicator.h" -#include "llslurl.h" -#include "lltrans.h" -#include "llsnapshotlivepreview.h" -#include "llviewerregion.h" -#include "llviewercontrol.h" -#include "llviewermedia.h" -#include "lltabcontainer.h" -#include "llavatarlist.h" -#include "llpanelpeoplemenus.h" -#include "llaccordionctrl.h" -#include "llaccordionctrltab.h" - -static LLPanelInjector<LLFacebookStatusPanel> t_panel_status("llfacebookstatuspanel"); -static LLPanelInjector<LLFacebookPhotoPanel> t_panel_photo("llfacebookphotopanel"); -static LLPanelInjector<LLFacebookCheckinPanel> t_panel_checkin("llfacebookcheckinpanel"); -static LLPanelInjector<LLFacebookFriendsPanel> t_panel_friends("llfacebookfriendspanel"); - -const std::string DEFAULT_CHECKIN_LOCATION_URL = "http://maps.secondlife.com/"; -const std::string DEFAULT_CHECKIN_ICON_URL = "http://map.secondlife.com.s3.amazonaws.com/map_placeholder.png"; -const std::string DEFAULT_CHECKIN_QUERY_PARAMETERS = "?sourceid=slshare_checkin&utm_source=facebook&utm_medium=checkin&utm_campaign=slshare"; -const std::string DEFAULT_PHOTO_QUERY_PARAMETERS = "?sourceid=slshare_photo&utm_source=facebook&utm_medium=photo&utm_campaign=slshare"; - -const S32 MAX_QUALITY = 100;         // Max quality value for jpeg images -const S32 MIN_QUALITY = 0;           // Min quality value for jpeg images -const S32 TARGET_DATA_SIZE = 950000; // Size of the image (compressed) we're trying to send to Facebook - -std::string get_map_url() -{ -    LLVector3d center_agent; -    LLViewerRegion *regionp = gAgent.getRegion(); -    if (regionp) -    { -        center_agent = regionp->getCenterGlobal(); -    } -    int x_pos = center_agent[0] / 256.0; -    int y_pos = center_agent[1] / 256.0; -    std::string map_url = gSavedSettings.getString("CurrentMapServerURL") + llformat("map-1-%d-%d-objects.jpg", x_pos, y_pos); -    return map_url; -} - -// Compute target jpeg quality : see https://wiki.lindenlab.com/wiki/Facebook_Image_Quality for details -S32 compute_jpeg_quality(S32 width, S32 height) -{ -    F32 target_compression_ratio = (F32)(width * height * 3) / (F32)(TARGET_DATA_SIZE); -    S32 quality = (S32)(110.0f - (2.0f * target_compression_ratio)); -    return llclamp(quality, MIN_QUALITY, MAX_QUALITY); -} - -/////////////////////////// -//LLFacebookStatusPanel////// -/////////////////////////// - -LLFacebookStatusPanel::LLFacebookStatusPanel() : -    mMessageTextEditor(NULL), -    mPostButton(NULL), -    mCancelButton(NULL), -    mAccountCaptionLabel(NULL), -    mAccountNameLabel(NULL), -    mPanelButtons(NULL), -    mConnectButton(NULL), -    mDisconnectButton(NULL) -{ -    mCommitCallbackRegistrar.add("SocialSharing.Connect", boost::bind(&LLFacebookStatusPanel::onConnect, this)); -    mCommitCallbackRegistrar.add("SocialSharing.Disconnect", boost::bind(&LLFacebookStatusPanel::onDisconnect, this)); - -    setVisibleCallback(boost::bind(&LLFacebookStatusPanel::onVisibilityChange, this, _2)); - -    mCommitCallbackRegistrar.add("SocialSharing.SendStatus", boost::bind(&LLFacebookStatusPanel::onSend, this)); -} - -BOOL LLFacebookStatusPanel::postBuild() -{ -    mAccountCaptionLabel = getChild<LLTextBox>("account_caption_label"); -    mAccountNameLabel = getChild<LLTextBox>("account_name_label"); -    mPanelButtons = getChild<LLUICtrl>("panel_buttons"); -    mConnectButton = getChild<LLUICtrl>("connect_btn"); -    mDisconnectButton = getChild<LLUICtrl>("disconnect_btn"); - -    mMessageTextEditor = getChild<LLUICtrl>("status_message"); -    mPostButton = getChild<LLUICtrl>("post_status_btn"); -    mCancelButton = getChild<LLUICtrl>("cancel_status_btn"); - -    return LLPanel::postBuild(); -} - -void LLFacebookStatusPanel::draw() -{ -    LLFacebookConnect::EConnectionState connection_state = LLFacebookConnect::instance().getConnectionState(); - -    //Disable the 'disconnect' button and the 'use another account' button when disconnecting in progress -    bool disconnecting = connection_state == LLFacebookConnect::FB_DISCONNECTING; -    mDisconnectButton->setEnabled(!disconnecting); - -    //Disable the 'connect' button when a connection is in progress -    bool connecting = connection_state == LLFacebookConnect::FB_CONNECTION_IN_PROGRESS; -    mConnectButton->setEnabled(!connecting); - -    if (mMessageTextEditor && mPostButton && mCancelButton) -    { -        bool no_ongoing_connection = !(LLFacebookConnect::instance().isTransactionOngoing()); -        std::string message = mMessageTextEditor->getValue().asString(); -        mMessageTextEditor->setEnabled(no_ongoing_connection); -        mCancelButton->setEnabled(no_ongoing_connection); -        mPostButton->setEnabled(no_ongoing_connection && !message.empty()); -    } - -    LLPanel::draw(); -} - -void LLFacebookStatusPanel::onSend() -{ -    LLEventPumps::instance().obtain("FacebookConnectState").stopListening("LLFacebookStatusPanel"); // just in case it is already listening -    LLEventPumps::instance().obtain("FacebookConnectState").listen("LLFacebookStatusPanel", boost::bind(&LLFacebookStatusPanel::onFacebookConnectStateChange, this, _1)); - -    // Connect to Facebook if necessary and then post -    if (LLFacebookConnect::instance().isConnected()) -    { -        sendStatus(); -    } -    else -    { -        LLFacebookConnect::instance().checkConnectionToFacebook(true); -    } -} - -bool LLFacebookStatusPanel::onFacebookConnectStateChange(const LLSD& data) -{ -    switch (data.get("enum").asInteger()) -    { -    case LLFacebookConnect::FB_CONNECTED: -        sendStatus(); -        break; - -    case LLFacebookConnect::FB_POSTED: -        LLEventPumps::instance().obtain("FacebookConnectState").stopListening("LLFacebookStatusPanel"); -        clearAndClose(); -        break; -    } - -    return false; -} - -bool LLFacebookStatusPanel::onFacebookConnectAccountStateChange(const LLSD& data) -{ -    if (LLFacebookConnect::instance().isConnected()) -    { -        //In process of disconnecting so leave the layout as is -        if (data.get("enum").asInteger() != LLFacebookConnect::FB_DISCONNECTING) -        { -            showConnectedLayout(); -        } -    } -    else -    { -        showDisconnectedLayout(); -    } - -    return false; -} - -void LLFacebookStatusPanel::sendStatus() -{ -    std::string message = mMessageTextEditor->getValue().asString(); -    if (!message.empty()) -    { -        LLFacebookConnect::instance().updateStatus(message); -    } -} - -void LLFacebookStatusPanel::onVisibilityChange(BOOL visible) -{ -    if (visible) -    { -        LLEventPumps::instance().obtain("FacebookConnectState").stopListening("LLFacebookAccountPanel"); -        LLEventPumps::instance().obtain("FacebookConnectState").listen("LLFacebookAccountPanel", boost::bind(&LLFacebookStatusPanel::onFacebookConnectAccountStateChange, this, _1)); - -        LLEventPumps::instance().obtain("FacebookConnectInfo").stopListening("LLFacebookAccountPanel"); -        LLEventPumps::instance().obtain("FacebookConnectInfo").listen("LLFacebookAccountPanel", boost::bind(&LLFacebookStatusPanel::onFacebookConnectInfoChange, this)); - -        //Connected -        if (LLFacebookConnect::instance().isConnected()) -        { -            showConnectedLayout(); -        } -        //Check if connected (show disconnected layout in meantime) -        else -        { -            showDisconnectedLayout(); -        } -        if ((LLFacebookConnect::instance().getConnectionState() == LLFacebookConnect::FB_NOT_CONNECTED) || -            (LLFacebookConnect::instance().getConnectionState() == LLFacebookConnect::FB_CONNECTION_FAILED)) -        { -            LLFacebookConnect::instance().checkConnectionToFacebook(); -        } -    } -    else -    { -        LLEventPumps::instance().obtain("FacebookConnectState").stopListening("LLFacebookAccountPanel"); -        LLEventPumps::instance().obtain("FacebookConnectInfo").stopListening("LLFacebookAccountPanel"); -    } -} - -bool LLFacebookStatusPanel::onFacebookConnectInfoChange() -{ -    LLSD info = LLFacebookConnect::instance().getInfo(); -    std::string clickable_name; - -    //Strings of format [http://www.somewebsite.com Click Me] become clickable text -    if (info.has("link") && info.has("name")) -    { -        clickable_name = "[" + info["link"].asString() + " " + info["name"].asString() + "]"; -    } - -    mAccountNameLabel->setText(clickable_name); - -    return false; -} - -void LLFacebookStatusPanel::showConnectButton() -{ -    if (!mConnectButton->getVisible()) -    { -        mConnectButton->setVisible(TRUE); -        mDisconnectButton->setVisible(FALSE); -    } -} - -void LLFacebookStatusPanel::hideConnectButton() -{ -    if (mConnectButton->getVisible()) -    { -        mConnectButton->setVisible(FALSE); -        mDisconnectButton->setVisible(TRUE); -    } -} - -void LLFacebookStatusPanel::showDisconnectedLayout() -{ -    mAccountCaptionLabel->setText(getString("facebook_disconnected")); -    mAccountNameLabel->setText(std::string("")); -    showConnectButton(); -} - -void LLFacebookStatusPanel::showConnectedLayout() -{ -    LLFacebookConnect::instance().loadFacebookInfo(); - -    mAccountCaptionLabel->setText(getString("facebook_connected")); -    hideConnectButton(); -} - -void LLFacebookStatusPanel::onConnect() -{ -    LLFacebookConnect::instance().checkConnectionToFacebook(true); -} - -void LLFacebookStatusPanel::onDisconnect() -{ -    LLFacebookConnect::instance().disconnectFromFacebook(); -} - -void LLFacebookStatusPanel::clearAndClose() -{ -    mMessageTextEditor->setValue(""); - -    LLFloater* floater = getParentByType<LLFloater>(); -    if (floater) -    { -        floater->closeFloater(); -    } -} - -/////////////////////////// -//LLFacebookPhotoPanel/////// -/////////////////////////// - -LLFacebookPhotoPanel::LLFacebookPhotoPanel() : -    mResolutionComboBox(NULL), -    mRefreshBtn(NULL), -    mBtnPreview(NULL), -    mWorkingLabel(NULL), -    mThumbnailPlaceholder(NULL), -    mCaptionTextBox(NULL), -    mPostButton(NULL), -    mBigPreviewFloater(NULL), -    mQuality(MAX_QUALITY) -{ -    mCommitCallbackRegistrar.add("SocialSharing.SendPhoto", boost::bind(&LLFacebookPhotoPanel::onSend, this)); -    mCommitCallbackRegistrar.add("SocialSharing.RefreshPhoto", boost::bind(&LLFacebookPhotoPanel::onClickNewSnapshot, this)); -    mCommitCallbackRegistrar.add("SocialSharing.BigPreview", boost::bind(&LLFacebookPhotoPanel::onClickBigPreview, this)); -} - -LLFacebookPhotoPanel::~LLFacebookPhotoPanel() -{ -    if (mPreviewHandle.get()) -    { -        mPreviewHandle.get()->die(); -    } -} - -BOOL LLFacebookPhotoPanel::postBuild() -{ -    setVisibleCallback(boost::bind(&LLFacebookPhotoPanel::onVisibilityChange, this, _2)); - -    mResolutionComboBox = getChild<LLUICtrl>("resolution_combobox"); -    mResolutionComboBox->setValue("[i1200,i630]"); // hardcoded defaults ftw! -    mResolutionComboBox->setCommitCallback(boost::bind(&LLFacebookPhotoPanel::updateResolution, this, TRUE)); -    mFilterComboBox = getChild<LLUICtrl>("filters_combobox"); -    mFilterComboBox->setCommitCallback(boost::bind(&LLFacebookPhotoPanel::updateResolution, this, TRUE)); -    mRefreshBtn = getChild<LLUICtrl>("new_snapshot_btn"); -    mBtnPreview = getChild<LLButton>("big_preview_btn"); -    mWorkingLabel = getChild<LLUICtrl>("working_lbl"); -    mThumbnailPlaceholder = getChild<LLUICtrl>("thumbnail_placeholder"); -    mCaptionTextBox = getChild<LLUICtrl>("photo_caption"); -    mPostButton = getChild<LLUICtrl>("post_photo_btn"); -    mCancelButton = getChild<LLUICtrl>("cancel_photo_btn"); -    mBigPreviewFloater = dynamic_cast<LLFloaterBigPreview*>(LLFloaterReg::getInstance("big_preview")); - -    // Update filter list -    std::vector<std::string> filter_list = LLImageFiltersManager::getInstance()->getFiltersList(); -    LLComboBox* filterbox = static_cast<LLComboBox *>(mFilterComboBox); -    for (U32 i = 0; i < filter_list.size(); i++) -    { -        filterbox->add(filter_list[i]); -    } - -    return LLPanel::postBuild(); -} - -// virtual -S32 LLFacebookPhotoPanel::notify(const LLSD& info) -{ -    if (info.has("snapshot-updating")) -    { -        // Disable the Post button and whatever else while the snapshot is not updated -        // updateControls(); -        return 1; -    } - -    if (info.has("snapshot-updated")) -    { -        // Enable the send/post/save buttons. -        updateControls(); - -        // The refresh button is initially hidden. We show it after the first update, -        // i.e. after snapshot is taken -        LLUICtrl * refresh_button = getRefreshBtn(); -        if (!refresh_button->getVisible()) -        { -            refresh_button->setVisible(true); -        } -        return 1; -    } - -    return 0; -} - -void LLFacebookPhotoPanel::draw() -{ -    LLSnapshotLivePreview * previewp = static_cast<LLSnapshotLivePreview *>(mPreviewHandle.get()); - -    // Enable interaction only if no transaction with the service is on-going (prevent duplicated posts) -    bool no_ongoing_connection = !(LLFacebookConnect::instance().isTransactionOngoing()); -    mCancelButton->setEnabled(no_ongoing_connection); -    mCaptionTextBox->setEnabled(no_ongoing_connection); -    mResolutionComboBox->setEnabled(no_ongoing_connection); -    mFilterComboBox->setEnabled(no_ongoing_connection); -    mRefreshBtn->setEnabled(no_ongoing_connection); -    mBtnPreview->setEnabled(no_ongoing_connection); - -    // Reassign the preview floater if we have the focus and the preview exists -    if (hasFocus() && isPreviewVisible()) -    { -        attachPreview(); -    } - -    // Toggle the button state as appropriate -    bool preview_active = (isPreviewVisible() && mBigPreviewFloater->isFloaterOwner(getParentByType<LLFloater>())); -    mBtnPreview->setToggleState(preview_active); - -    // Display the thumbnail if one is available -    if (previewp && previewp->getThumbnailImage()) -    { -        const LLRect& thumbnail_rect = mThumbnailPlaceholder->getRect(); -        const S32 thumbnail_w = previewp->getThumbnailWidth(); -        const S32 thumbnail_h = previewp->getThumbnailHeight(); - -        // calc preview offset within the preview rect -        const S32 local_offset_x = (thumbnail_rect.getWidth() - thumbnail_w) / 2; -        const S32 local_offset_y = (thumbnail_rect.getHeight() - thumbnail_h) / 2; -        S32 offset_x = thumbnail_rect.mLeft + local_offset_x; -        S32 offset_y = thumbnail_rect.mBottom + local_offset_y; - -        gGL.matrixMode(LLRender::MM_MODELVIEW); -        // Apply floater transparency to the texture unless the floater is focused. -        F32 alpha = getTransparencyType() == TT_ACTIVE ? 1.0f : getCurrentTransparency(); -        LLColor4 color = LLColor4::white; -        gl_draw_scaled_image(offset_x, offset_y, -            thumbnail_w, thumbnail_h, -            previewp->getThumbnailImage(), color % alpha); -    } - -    // Update the visibility of the working (computing preview) label -    mWorkingLabel->setVisible(!(previewp && previewp->getSnapshotUpToDate())); - -    // Enable Post if we have a preview to send and no on going connection being processed -    mPostButton->setEnabled(no_ongoing_connection && (previewp && previewp->getSnapshotUpToDate())); - -    // Draw the rest of the panel on top of it -    LLPanel::draw(); -} - -LLSnapshotLivePreview* LLFacebookPhotoPanel::getPreviewView() -{ -    LLSnapshotLivePreview* previewp = (LLSnapshotLivePreview*)mPreviewHandle.get(); -    return previewp; -} - -void LLFacebookPhotoPanel::onVisibilityChange(BOOL visible) -{ -    if (visible) -    { -        if (mPreviewHandle.get()) -        { -            LLSnapshotLivePreview* preview = getPreviewView(); -            if (preview) -            { -                LL_DEBUGS() << "opened, updating snapshot" << LL_ENDL; -                preview->updateSnapshot(TRUE); -            } -        } -        else -        { -            LLRect full_screen_rect = getRootView()->getRect(); -            LLSnapshotLivePreview::Params p; -            p.rect(full_screen_rect); -            LLSnapshotLivePreview* previewp = new LLSnapshotLivePreview(p); -            mPreviewHandle = previewp->getHandle(); -            mQuality = MAX_QUALITY; - -            previewp->setContainer(this); -            previewp->setSnapshotType(LLSnapshotModel::SNAPSHOT_WEB); -            previewp->setSnapshotFormat(LLSnapshotModel::SNAPSHOT_FORMAT_JPEG); -            previewp->setSnapshotQuality(mQuality, false); -            previewp->setThumbnailSubsampled(TRUE);     // We want the preview to reflect the *saved* image -            previewp->setAllowRenderUI(FALSE);          // We do not want the rendered UI in our snapshots -            previewp->setAllowFullScreenPreview(FALSE);  // No full screen preview in SL Share mode -            previewp->setThumbnailPlaceholderRect(mThumbnailPlaceholder->getRect()); - -            updateControls(); -        } -    } -} - -void LLFacebookPhotoPanel::onClickNewSnapshot() -{ -    LLSnapshotLivePreview* previewp = getPreviewView(); -    if (previewp) -    { -        previewp->updateSnapshot(TRUE); -    } -} - -void LLFacebookPhotoPanel::onClickBigPreview() -{ -    // Toggle the preview -    if (isPreviewVisible()) -    { -        LLFloaterReg::hideInstance("big_preview"); -    } -    else -    { -        attachPreview(); -        LLFloaterReg::showInstance("big_preview"); -    } -} - -bool LLFacebookPhotoPanel::isPreviewVisible() -{ -    return (mBigPreviewFloater && mBigPreviewFloater->getVisible()); -} - -void LLFacebookPhotoPanel::attachPreview() -{ -    if (mBigPreviewFloater) -    { -        LLSnapshotLivePreview* previewp = getPreviewView(); -        mBigPreviewFloater->setPreview(previewp); -        mBigPreviewFloater->setFloaterOwner(getParentByType<LLFloater>()); -    } -} - -void LLFacebookPhotoPanel::onSend() -{ -    LLEventPumps::instance().obtain("FacebookConnectState").stopListening("LLFacebookPhotoPanel"); // just in case it is already listening -    LLEventPumps::instance().obtain("FacebookConnectState").listen("LLFacebookPhotoPanel", boost::bind(&LLFacebookPhotoPanel::onFacebookConnectStateChange, this, _1)); - -    // Connect to Facebook if necessary and then post -    if (LLFacebookConnect::instance().isConnected()) -    { -        sendPhoto(); -    } -    else -    { -        LLFacebookConnect::instance().checkConnectionToFacebook(true); -    } -} - -bool LLFacebookPhotoPanel::onFacebookConnectStateChange(const LLSD& data) -{ -    switch (data.get("enum").asInteger()) -    { -    case LLFacebookConnect::FB_CONNECTED: -        sendPhoto(); -        break; - -    case LLFacebookConnect::FB_POSTED: -        LLEventPumps::instance().obtain("FacebookConnectState").stopListening("LLFacebookPhotoPanel"); -        clearAndClose(); -        break; -    } - -    return false; -} - -void LLFacebookPhotoPanel::sendPhoto() -{ -    // Get the caption -    std::string caption = mCaptionTextBox->getValue().asString(); - -    // Get the image -    LLSnapshotLivePreview* previewp = getPreviewView(); - -    // Post to Facebook -    LLFacebookConnect::instance().sharePhoto(previewp->getFormattedImage(), caption); - -    updateControls(); -} - -void LLFacebookPhotoPanel::clearAndClose() -{ -    mCaptionTextBox->setValue(""); - -    LLFloater* floater = getParentByType<LLFloater>(); -    if (floater) -    { -        floater->closeFloater(); -        if (mBigPreviewFloater) -        { -            mBigPreviewFloater->closeOnFloaterOwnerClosing(floater); -        } -    } -} - -void LLFacebookPhotoPanel::updateControls() -{ -    LLSnapshotLivePreview* previewp = getPreviewView(); -    BOOL got_snap = previewp && previewp->getSnapshotUpToDate(); - -    // *TODO: Separate maximum size for Web images from postcards -    LL_DEBUGS() << "Is snapshot up-to-date? " << got_snap << LL_ENDL; - -    updateResolution(FALSE); -} - -void LLFacebookPhotoPanel::updateResolution(BOOL do_update) -{ -    LLComboBox* combobox = static_cast<LLComboBox *>(mResolutionComboBox); -    LLComboBox* filterbox = static_cast<LLComboBox *>(mFilterComboBox); - -    std::string sdstring = combobox->getSelectedValue(); -    LLSD sdres; -    std::stringstream sstream(sdstring); -    LLSDSerialize::fromNotation(sdres, sstream, sdstring.size()); - -    S32 width = sdres[0]; -    S32 height = sdres[1]; - -    // Note : index 0 of the filter drop down is assumed to be "No filter" in whichever locale -    std::string filter_name = (filterbox->getCurrentIndex() ? filterbox->getSimple() : ""); - -    LLSnapshotLivePreview * previewp = static_cast<LLSnapshotLivePreview *>(mPreviewHandle.get()); -    if (previewp && combobox->getCurrentIndex() >= 0) -    { -        S32 original_width = 0, original_height = 0; -        previewp->getSize(original_width, original_height); - -        if (width == 0 || height == 0) -        { -            // take resolution from current window size -            LL_DEBUGS() << "Setting preview res from window: " << gViewerWindow->getWindowWidthRaw() << "x" << gViewerWindow->getWindowHeightRaw() << LL_ENDL; -            previewp->setSize(gViewerWindow->getWindowWidthRaw(), gViewerWindow->getWindowHeightRaw()); -        } -        else -        { -            // use the resolution from the selected pre-canned drop-down choice -            LL_DEBUGS() << "Setting preview res selected from combo: " << width << "x" << height << LL_ENDL; -            previewp->setSize(width, height); -        } - -        checkAspectRatio(width); - -        previewp->getSize(width, height); - -        // Recompute quality setting -        mQuality = compute_jpeg_quality(width, height); -        previewp->setSnapshotQuality(mQuality, false); - -        if (original_width != width || original_height != height) -        { -            previewp->setSize(width, height); -            if (do_update) -            { -                previewp->updateSnapshot(TRUE); -                updateControls(); -            } -        } -        // Get the old filter, compare to the current one "filter_name" and set if changed -        std::string original_filter = previewp->getFilter(); -        if (original_filter != filter_name) -        { -            previewp->setFilter(filter_name); -            if (do_update) -            { -                previewp->updateSnapshot(FALSE, TRUE); -                updateControls(); -            } -        } -    } -} - -void LLFacebookPhotoPanel::checkAspectRatio(S32 index) -{ -    LLSnapshotLivePreview *previewp = getPreviewView(); - -    BOOL keep_aspect = FALSE; - -    if (0 == index) // current window size -    { -        keep_aspect = TRUE; -    } -    else // predefined resolution -    { -        keep_aspect = FALSE; -    } - -    if (previewp) -    { -        previewp->mKeepAspectRatio = keep_aspect; -    } -} - -LLUICtrl* LLFacebookPhotoPanel::getRefreshBtn() -{ -    return mRefreshBtn; -} - -//////////////////////// -//LLFacebookCheckinPanel// -//////////////////////// - -LLFacebookCheckinPanel::LLFacebookCheckinPanel() : -    mMapUrl(""), -    mReloadingMapTexture(false) -{ -    mCommitCallbackRegistrar.add("SocialSharing.SendCheckin", boost::bind(&LLFacebookCheckinPanel::onSend, this)); -} - -BOOL LLFacebookCheckinPanel::postBuild() -{ -    // Keep pointers to widgets so we don't traverse the UI hierarchy too often -    mPostButton = getChild<LLUICtrl>("post_place_btn"); -    mCancelButton = getChild<LLUICtrl>("cancel_place_btn"); -    mMessageTextEditor = getChild<LLUICtrl>("place_caption"); -    mMapLoadingIndicator = getChild<LLUICtrl>("map_loading_indicator"); -    mMapPlaceholder = getChild<LLIconCtrl>("map_placeholder"); -    mMapDefault = getChild<LLIconCtrl>("map_default"); -    mMapCheckBox = getChild<LLCheckBoxCtrl>("add_place_view_cb"); - -    return LLPanel::postBuild(); -} - -void LLFacebookCheckinPanel::draw() -{ -    bool no_ongoing_connection = !(LLFacebookConnect::instance().isTransactionOngoing()); -    mPostButton->setEnabled(no_ongoing_connection); -    mCancelButton->setEnabled(no_ongoing_connection); -    mMessageTextEditor->setEnabled(no_ongoing_connection); -    mMapCheckBox->setEnabled(no_ongoing_connection); - -    std::string map_url = get_map_url(); -    // Did we change location? -    if (map_url != mMapUrl) -    { -        mMapUrl = map_url; -        // Load the map tile -        mMapTexture = LLViewerTextureManager::getFetchedTextureFromUrl(mMapUrl, FTT_MAP_TILE, TRUE, LLGLTexture::BOOST_NONE, LLViewerTexture::LOD_TEXTURE); -        mMapTexture->setBoostLevel(LLGLTexture::BOOST_MAP); -        mReloadingMapTexture = true; -        // In the meantime, put the "loading" indicator on, hide the tile map and disable the checkbox -        mMapLoadingIndicator->setVisible(true); -        mMapPlaceholder->setVisible(false); -    } -    // Are we done loading the map tile? -    if (mReloadingMapTexture && mMapTexture->isFullyLoaded()) -    { -        // Don't do it again next time around -        mReloadingMapTexture = false; -        // Convert the map texture to the appropriate image object -        LLPointer<LLUIImage> ui_image = new LLUIImage(mMapUrl, mMapTexture); -        // Load the map widget with the correct map tile image -        mMapPlaceholder->setImage(ui_image); -        // Now hide the loading indicator, bring the tile in view and reenable the checkbox with its previous value -        mMapLoadingIndicator->setVisible(false); -        mMapPlaceholder->setVisible(true); -    } -    // Show the default icon if that's the checkbox value (the real one...) -    // This will hide/show the loading indicator and/or tile underneath -    mMapDefault->setVisible(!(mMapCheckBox->get())); - -    LLPanel::draw(); -} - -void LLFacebookCheckinPanel::onSend() -{ -    LLEventPumps::instance().obtain("FacebookConnectState").stopListening("LLFacebookCheckinPanel"); // just in case it is already listening -    LLEventPumps::instance().obtain("FacebookConnectState").listen("LLFacebookCheckinPanel", boost::bind(&LLFacebookCheckinPanel::onFacebookConnectStateChange, this, _1)); - -    // Connect to Facebook if necessary and then post -    if (LLFacebookConnect::instance().isConnected()) -    { -        sendCheckin(); -    } -    else -    { -        LLFacebookConnect::instance().checkConnectionToFacebook(true); -    } -} - -bool LLFacebookCheckinPanel::onFacebookConnectStateChange(const LLSD& data) -{ -    switch (data.get("enum").asInteger()) -    { -    case LLFacebookConnect::FB_CONNECTED: -        sendCheckin(); -        break; - -    case LLFacebookConnect::FB_POSTED: -        LLEventPumps::instance().obtain("FacebookConnectState").stopListening("LLFacebookCheckinPanel"); -        clearAndClose(); -        break; -    } - -    return false; -} - -void LLFacebookCheckinPanel::sendCheckin() -{ -    // Get the location SLURL -    LLSLURL slurl; -    LLAgentUI::buildSLURL(slurl); -    std::string slurl_string = slurl.getSLURLString(); - -    // Use a valid http:// URL if the scheme is secondlife:// -    LLURI slurl_uri(slurl_string); -    if (slurl_uri.scheme() == LLSLURL::SLURL_SECONDLIFE_SCHEME) -    { -        slurl_string = DEFAULT_CHECKIN_LOCATION_URL; -    } - -    // Add query parameters so Google Analytics can track incoming clicks! -    slurl_string += DEFAULT_CHECKIN_QUERY_PARAMETERS; - -    // Get the region name -    std::string region_name(""); -    LLViewerRegion *regionp = gAgent.getRegion(); -    if (regionp) -    { -        region_name = regionp->getName(); -    } - -    // Get the region description -    std::string description; -    LLAgentUI::buildLocationString(description, LLAgentUI::LOCATION_FORMAT_NORMAL_COORDS, gAgent.getPositionAgent()); - -    // Optionally add the region map view -    bool add_map_view = mMapCheckBox->getValue().asBoolean(); -    std::string map_url = (add_map_view ? get_map_url() : DEFAULT_CHECKIN_ICON_URL); - -    // Get the caption -    std::string caption = mMessageTextEditor->getValue().asString(); - -    // Post to Facebook -    LLFacebookConnect::instance().postCheckin(slurl_string, region_name, description, map_url, caption); -} - -void LLFacebookCheckinPanel::clearAndClose() -{ -    mMessageTextEditor->setValue(""); - -    LLFloater* floater = getParentByType<LLFloater>(); -    if (floater) -    { -        floater->closeFloater(); -    } -} - -/////////////////////////// -//LLFacebookFriendsPanel////// -/////////////////////////// - -LLFacebookFriendsPanel::LLFacebookFriendsPanel() : -    mFriendsStatusCaption(NULL), -    mSecondLifeFriends(NULL), -    mSuggestedFriends(NULL) -{ -} - -LLFacebookFriendsPanel::~LLFacebookFriendsPanel() -{ -    LLAvatarTracker::instance().removeObserver(this); -} - -BOOL LLFacebookFriendsPanel::postBuild() -{ -    mFriendsStatusCaption = getChild<LLTextBox>("facebook_friends_status"); - -    mSecondLifeFriends = getChild<LLAvatarList>("second_life_friends"); -    mSecondLifeFriends->setContextMenu(&LLPanelPeopleMenus::gPeopleContextMenu); - -    mSuggestedFriends = getChild<LLAvatarList>("suggested_friends"); -    mSuggestedFriends->setContextMenu(&LLPanelPeopleMenus::gSuggestedFriendsContextMenu); - -    setVisibleCallback(boost::bind(&LLFacebookFriendsPanel::updateFacebookList, this, _2)); - -    LLAvatarTracker::instance().addObserver(this); - -    return LLPanel::postBuild(); -} - -bool LLFacebookFriendsPanel::updateSuggestedFriendList() -{ -    const LLAvatarTracker& av_tracker = LLAvatarTracker::instance(); -    uuid_vec_t& second_life_friends = mSecondLifeFriends->getIDs(); -    second_life_friends.clear(); -    uuid_vec_t& suggested_friends = mSuggestedFriends->getIDs(); -    suggested_friends.clear(); - -    //Add suggested friends -    LLSD friends = LLFacebookConnect::instance().getContent(); -    for (LLSD::array_const_iterator i = friends.beginArray(); i != friends.endArray(); ++i) -    { -        LLUUID agent_id = (*i).asUUID(); -        if (agent_id.notNull()) -        { -            bool second_life_buddy = av_tracker.isBuddy(agent_id); -            if (second_life_buddy) -            { -                second_life_friends.push_back(agent_id); -            } -            else -            { -                //FB+SL but not SL friend -                suggested_friends.push_back(agent_id); -            } -        } -    } - -    //Force a refresh when there aren't any filter matches (prevent displaying content that shouldn't display) -    mSecondLifeFriends->setDirty(true, !mSecondLifeFriends->filterHasMatches()); -    mSuggestedFriends->setDirty(true, !mSuggestedFriends->filterHasMatches()); -    showFriendsAccordionsIfNeeded(); - -    return false; -} - -void LLFacebookFriendsPanel::showFriendsAccordionsIfNeeded() -{ -    // Show / hide the status text : needs to be done *before* showing / hidding the accordions -    if (!mSecondLifeFriends->filterHasMatches() && !mSuggestedFriends->filterHasMatches()) -    { -        // Show some explanation text if the lists are empty... -        mFriendsStatusCaption->setVisible(true); -        if (LLFacebookConnect::instance().isConnected()) -        { -            //...you're connected to FB but have no friends :( -            mFriendsStatusCaption->setText(getString("facebook_friends_empty")); -        } -        else -        { -            //...you're not connected to FB -            mFriendsStatusCaption->setText(getString("facebook_friends_no_connected")); -        } -        // Hide the lists -        getChild<LLAccordionCtrl>("friends_accordion")->setVisible(false); -        getChild<LLAccordionCtrlTab>("tab_second_life_friends")->setVisible(false); -        getChild<LLAccordionCtrlTab>("tab_suggested_friends")->setVisible(false); -    } -    else -    { -        // We have something in the lists, hide the explanatory text -        mFriendsStatusCaption->setVisible(false); - -        // Show the lists -        LLAccordionCtrl* accordion = getChild<LLAccordionCtrl>("friends_accordion"); -        accordion->setVisible(true); - -        // Expand and show accordions if needed, else - hide them -        getChild<LLAccordionCtrlTab>("tab_second_life_friends")->setVisible(mSecondLifeFriends->filterHasMatches()); -        getChild<LLAccordionCtrlTab>("tab_suggested_friends")->setVisible(mSuggestedFriends->filterHasMatches()); - -        // Rearrange accordions -        accordion->arrange(); -    } -} - -void LLFacebookFriendsPanel::changed(U32 mask) -{ -    if (mask & (LLFriendObserver::ADD | LLFriendObserver::REMOVE)) -    { -        LLFacebookConnect::instance().loadFacebookFriends(); -        updateFacebookList(true); -    } -} - - -void LLFacebookFriendsPanel::updateFacebookList(bool visible) -{ -    if (visible) -    { -        // We want this to be called to fetch the friends list once a connection is established -        LLEventPumps::instance().obtain("FacebookConnectState").stopListening("LLFacebookFriendsPanel"); -        LLEventPumps::instance().obtain("FacebookConnectState").listen("LLFacebookFriendsPanel", boost::bind(&LLFacebookFriendsPanel::onConnectedToFacebook, this, _1)); - -        // We then want this to be called to update the displayed lists once the list of friends is received -        LLEventPumps::instance().obtain("FacebookConnectContent").stopListening("LLFacebookFriendsPanel"); // just in case it is already listening -        LLEventPumps::instance().obtain("FacebookConnectContent").listen("LLFacebookFriendsPanel", boost::bind(&LLFacebookFriendsPanel::updateSuggestedFriendList, this)); - -        // Try to connect to Facebook -        if ((LLFacebookConnect::instance().getConnectionState() == LLFacebookConnect::FB_NOT_CONNECTED) || -            (LLFacebookConnect::instance().getConnectionState() == LLFacebookConnect::FB_CONNECTION_FAILED)) -        { -            LLFacebookConnect::instance().checkConnectionToFacebook(); -        } -        // Loads FB friends -        if (LLFacebookConnect::instance().isConnected()) -        { -            LLFacebookConnect::instance().loadFacebookFriends(); -        } -        // Sort the FB friends and update the lists -        updateSuggestedFriendList(); -    } -} - -bool LLFacebookFriendsPanel::onConnectedToFacebook(const LLSD& data) -{ -    LLSD::Integer connection_state = data.get("enum").asInteger(); - -    if (connection_state == LLFacebookConnect::FB_CONNECTED) -    { -        LLFacebookConnect::instance().loadFacebookFriends(); -    } -    else if (connection_state == LLFacebookConnect::FB_NOT_CONNECTED) -    { -        updateSuggestedFriendList(); -    } - -    return false; -} - -//////////////////////// -//LLFloaterFacebook/////// -//////////////////////// - -LLFloaterFacebook::LLFloaterFacebook(const LLSD& key) : LLFloater(key), -    mFacebookPhotoPanel(NULL), -    mStatusErrorText(NULL), -    mStatusLoadingText(NULL), -    mStatusLoadingIndicator(NULL) -{ -    mCommitCallbackRegistrar.add("SocialSharing.Cancel", boost::bind(&LLFloaterFacebook::onCancel, this)); -} - -void LLFloaterFacebook::onClose(bool app_quitting) -{ -    LLFloaterBigPreview* big_preview_floater = dynamic_cast<LLFloaterBigPreview*>(LLFloaterReg::getInstance("big_preview")); -    if (big_preview_floater) -    { -        big_preview_floater->closeOnFloaterOwnerClosing(this); -    } -    LLFloater::onClose(app_quitting); -} - -void LLFloaterFacebook::onCancel() -{ -    LLFloaterBigPreview* big_preview_floater = dynamic_cast<LLFloaterBigPreview*>(LLFloaterReg::getInstance("big_preview")); -    if (big_preview_floater) -    { -        big_preview_floater->closeOnFloaterOwnerClosing(this); -    } -    closeFloater(); -} - -BOOL LLFloaterFacebook::postBuild() -{ -    // Keep tab of the Photo Panel -    mFacebookPhotoPanel = static_cast<LLFacebookPhotoPanel*>(getChild<LLUICtrl>("panel_facebook_photo")); -    // Connection status widgets -    mStatusErrorText = getChild<LLTextBox>("connection_error_text"); -    mStatusLoadingText = getChild<LLTextBox>("connection_loading_text"); -    mStatusLoadingIndicator = getChild<LLUICtrl>("connection_loading_indicator"); -    return LLFloater::postBuild(); -} - -void LLFloaterFacebook::showPhotoPanel() -{ -    LLTabContainer* parent = dynamic_cast<LLTabContainer*>(mFacebookPhotoPanel->getParent()); -    if (!parent) -    { -        LL_WARNS() << "Cannot find panel container" << LL_ENDL; -        return; -    } - -    parent->selectTabPanel(mFacebookPhotoPanel); -} - -void LLFloaterFacebook::draw() -{ -    if (mStatusErrorText && mStatusLoadingText && mStatusLoadingIndicator) -    { -        mStatusErrorText->setVisible(false); -        mStatusLoadingText->setVisible(false); -        mStatusLoadingIndicator->setVisible(false); -        LLFacebookConnect::EConnectionState connection_state = LLFacebookConnect::instance().getConnectionState(); -        std::string status_text; - -        switch (connection_state) -        { -        case LLFacebookConnect::FB_NOT_CONNECTED: -            // No status displayed when first opening the panel and no connection done -        case LLFacebookConnect::FB_CONNECTED: -            // When successfully connected, no message is displayed -        case LLFacebookConnect::FB_POSTED: -            // No success message to show since we actually close the floater after successful posting completion -            break; -        case LLFacebookConnect::FB_CONNECTION_IN_PROGRESS: -            // Connection loading indicator -            mStatusLoadingText->setVisible(true); -            status_text = LLTrans::getString("SocialFacebookConnecting"); -            mStatusLoadingText->setValue(status_text); -            mStatusLoadingIndicator->setVisible(true); -            break; -        case LLFacebookConnect::FB_POSTING: -            // Posting indicator -            mStatusLoadingText->setVisible(true); -            status_text = LLTrans::getString("SocialFacebookPosting"); -            mStatusLoadingText->setValue(status_text); -            mStatusLoadingIndicator->setVisible(true); -            break; -        case LLFacebookConnect::FB_CONNECTION_FAILED: -            // Error connecting to the service -            mStatusErrorText->setVisible(true); -            status_text = LLTrans::getString("SocialFacebookErrorConnecting"); -            mStatusErrorText->setValue(status_text); -            break; -        case LLFacebookConnect::FB_POST_FAILED: -            // Error posting to the service -            mStatusErrorText->setVisible(true); -            status_text = LLTrans::getString("SocialFacebookErrorPosting"); -            mStatusErrorText->setValue(status_text); -            break; -        case LLFacebookConnect::FB_DISCONNECTING: -            // Disconnecting loading indicator -            mStatusLoadingText->setVisible(true); -            status_text = LLTrans::getString("SocialFacebookDisconnecting"); -            mStatusLoadingText->setValue(status_text); -            mStatusLoadingIndicator->setVisible(true); -            break; -        case LLFacebookConnect::FB_DISCONNECT_FAILED: -            // Error disconnecting from the service -            mStatusErrorText->setVisible(true); -            status_text = LLTrans::getString("SocialFacebookErrorDisconnecting"); -            mStatusErrorText->setValue(status_text); -            break; -        } -    } -    LLFloater::draw(); -} - diff --git a/indra/newview/llfloaterfacebook.h b/indra/newview/llfloaterfacebook.h deleted file mode 100644 index a4ca666b20..0000000000 --- a/indra/newview/llfloaterfacebook.h +++ /dev/null @@ -1,185 +0,0 @@ -/**  -* @file   llfloaterfacebook.h -* @brief  Header file for llfloaterfacebook -* @author Gilbert@lindenlab.com -* -* $LicenseInfo:firstyear=2013&license=viewerlgpl$ -* Second Life Viewer Source Code -* Copyright (C) 2013, Linden Research, Inc. -* -* This library is free software; you can redistribute it and/or -* modify it under the terms of the GNU Lesser General Public -* License as published by the Free Software Foundation; -* version 2.1 of the License only. -* -* This library is distributed in the hope that it will be useful, -* but WITHOUT ANY WARRANTY; without even the implied warranty of -* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU -* Lesser General Public License for more details. -* -* You should have received a copy of the GNU Lesser General Public -* License along with this library; if not, write to the Free Software -* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA -* -* Linden Research, Inc., 945 Battery Street, San Francisco, CA  94111  USA -* $/LicenseInfo$ -*/ -#ifndef LL_LLFLOATERFACEBOOK_H -#define LL_LLFLOATERFACEBOOK_H - -#include "llcallingcard.h" -#include "llfloater.h" -#include "lltextbox.h" -#include "llviewertexture.h" - -class LLIconCtrl; -class LLCheckBoxCtrl; -class LLSnapshotLivePreview; -class LLAvatarList; -class LLFloaterBigPreview; - -class LLFacebookStatusPanel : public LLPanel -{ -public: -    LLFacebookStatusPanel(); -	BOOL postBuild(); -	void draw(); -    void onSend(); -	bool onFacebookConnectStateChange(const LLSD& data); -	bool onFacebookConnectAccountStateChange(const LLSD& data); - -	void sendStatus(); -	void clearAndClose(); - -private: -	void onVisibilityChange(BOOL new_visibility); -	bool onFacebookConnectInfoChange(); -	void onConnect(); -	void onUseAnotherAccount(); -	void onDisconnect(); - -	void showConnectButton(); -	void hideConnectButton(); -	void showDisconnectedLayout(); -	void showConnectedLayout(); - -	LLTextBox * mAccountCaptionLabel; -	LLTextBox * mAccountNameLabel; -	LLUICtrl * mPanelButtons; -	LLUICtrl * mConnectButton; -	LLUICtrl * mDisconnectButton; -	LLUICtrl* mMessageTextEditor; -	LLUICtrl* mPostButton; -	LLUICtrl* mCancelButton; -}; - -class LLFacebookPhotoPanel : public LLPanel -{ -public: -	LLFacebookPhotoPanel(); -	~LLFacebookPhotoPanel(); - -	BOOL postBuild(); -	void draw(); - -	LLSnapshotLivePreview* getPreviewView(); -	void onVisibilityChange(BOOL new_visibility); -    void onClickBigPreview(); -	void onClickNewSnapshot(); -	void onSend(); -	S32 notify(const LLSD& info); -	bool onFacebookConnectStateChange(const LLSD& data); - -	void sendPhoto(); -	void clearAndClose(); - -	void updateControls(); -	void updateResolution(BOOL do_update); -	void checkAspectRatio(S32 index); -	LLUICtrl* getRefreshBtn(); - -private: -    bool isPreviewVisible(); -    void attachPreview(); -     -	LLHandle<LLView> mPreviewHandle; - -	LLUICtrl * mResolutionComboBox; -	LLUICtrl * mFilterComboBox; -	LLUICtrl * mRefreshBtn; -	LLUICtrl * mWorkingLabel; -	LLUICtrl * mThumbnailPlaceholder; -	LLUICtrl * mCaptionTextBox; -	LLUICtrl * mPostButton; -	LLUICtrl * mCancelButton; -	LLButton * mBtnPreview; -     -    LLFloaterBigPreview * mBigPreviewFloater; -     -    S32 mQuality;       // Compression quality -}; - -class LLFacebookCheckinPanel : public LLPanel -{ -public: -    LLFacebookCheckinPanel(); -	BOOL postBuild(); -	void draw(); -    void onSend(); -	bool onFacebookConnectStateChange(const LLSD& data); - -	void sendCheckin(); -	void clearAndClose(); - -private: -    std::string mMapUrl; -    LLPointer<LLViewerFetchedTexture> mMapTexture; -	LLUICtrl* mPostButton; -	LLUICtrl* mCancelButton; -	LLUICtrl* mMessageTextEditor; -    LLUICtrl* mMapLoadingIndicator; -    LLIconCtrl* mMapPlaceholder; -    LLIconCtrl* mMapDefault; -    LLCheckBoxCtrl* mMapCheckBox; -    bool mReloadingMapTexture; -}; - -class LLFacebookFriendsPanel : public LLPanel, public LLFriendObserver -{ -public: -	LLFacebookFriendsPanel(); -	~LLFacebookFriendsPanel(); -	BOOL postBuild(); -	virtual void changed(U32 mask); - -private: -	bool updateSuggestedFriendList(); -	void showFriendsAccordionsIfNeeded(); -	void updateFacebookList(bool visible); -	bool onConnectedToFacebook(const LLSD& data); -	 -	LLTextBox * mFriendsStatusCaption; -	LLAvatarList* mSecondLifeFriends; -	LLAvatarList* mSuggestedFriends; -}; - -class LLFloaterFacebook : public LLFloater -{ -public: -	LLFloaterFacebook(const LLSD& key); -	BOOL postBuild(); -	void draw(); -	void onClose(bool app_quitting); -	void onCancel(); -	 -	void showPhotoPanel(); - -private: -	LLFacebookPhotoPanel* mFacebookPhotoPanel; -    LLTextBox* mStatusErrorText; -    LLTextBox* mStatusLoadingText; -    LLUICtrl*  mStatusLoadingIndicator; -}; - -#endif // LL_LLFLOATERFACEBOOK_H - diff --git a/indra/newview/llfloaterland.cpp b/indra/newview/llfloaterland.cpp index 7f2e8fd82a..3098c6d118 100644 --- a/indra/newview/llfloaterland.cpp +++ b/indra/newview/llfloaterland.cpp @@ -1877,6 +1877,7 @@ LLPanelLandOptions::LLPanelLandOptions(LLParcelSelectionHandle& parcel)  	mLandingTypeCombo(NULL),  	mSnapshotCtrl(NULL),  	mLocationText(NULL), +	mSeeAvatarsText(NULL),  	mSetBtn(NULL),  	mClearBtn(NULL),  	mMatureCtrl(NULL), @@ -1923,6 +1924,14 @@ BOOL LLPanelLandOptions::postBuild()  	mSeeAvatarsCtrl = getChild<LLCheckBoxCtrl>( "SeeAvatarsCheck");  	childSetCommitCallback("SeeAvatarsCheck", onCommitAny, this); +	mSeeAvatarsText = getChild<LLTextBox>("allow_see_label"); +	if (mSeeAvatarsText) +	{ +		mSeeAvatarsText->setShowCursorHand(false); +		mSeeAvatarsText->setSoundFlags(LLView::MOUSE_UP); +		mSeeAvatarsText->setClickedCallback(boost::bind(&toggleSeeAvatars, this)); +	} +  	mCheckShowDirectory = getChild<LLCheckBoxCtrl>( "ShowDirectoryCheck");  	childSetCommitCallback("ShowDirectoryCheck", onCommitAny, this); @@ -2016,6 +2025,7 @@ void LLPanelLandOptions::refresh()  		mSeeAvatarsCtrl->set(TRUE);  		mSeeAvatarsCtrl->setEnabled(FALSE); +		mSeeAvatarsText->setEnabled(FALSE);  		mLandingTypeCombo->setCurrentByIndex(0);  		mLandingTypeCombo->setEnabled(FALSE); @@ -2074,6 +2084,7 @@ void LLPanelLandOptions::refresh()  		mSeeAvatarsCtrl->set(parcel->getSeeAVs());  		mSeeAvatarsCtrl->setEnabled(can_change_options && parcel->getHaveNewParcelLimitData()); +		mSeeAvatarsText->setEnabled(can_change_options && parcel->getHaveNewParcelLimitData());  		BOOL can_change_landing_point = LLViewerParcelMgr::isParcelModifiableByAgent(parcel,   														GP_LAND_SET_LANDING_POINT); @@ -2364,7 +2375,16 @@ void LLPanelLandOptions::onClickClear(void* userdata)  	self->refresh();  } - +void LLPanelLandOptions::toggleSeeAvatars(void* userdata) +{ +	LLPanelLandOptions* self = (LLPanelLandOptions*)userdata; +	if (self) +	{ +		self->getChild<LLCheckBoxCtrl>("SeeAvatarsCheck")->toggle(); +		self->getChild<LLCheckBoxCtrl>("SeeAvatarsCheck")->setBtnFocus(); +		self->onCommitAny(NULL, userdata); +	} +}  //---------------------------------------------------------------------------  // LLPanelLandAccess  //--------------------------------------------------------------------------- diff --git a/indra/newview/llfloaterland.h b/indra/newview/llfloaterland.h index e846d42666..0c49d78a20 100644 --- a/indra/newview/llfloaterland.h +++ b/indra/newview/llfloaterland.h @@ -327,6 +327,7 @@ private:  	static void onCommitAny(LLUICtrl* ctrl, void *userdata);  	static void onClickSet(void* userdata);  	static void onClickClear(void* userdata); +	static void toggleSeeAvatars(void* userdata);  private:  	LLCheckBoxCtrl*	mCheckEditObjects; @@ -345,6 +346,7 @@ private:  	LLTextureCtrl*	mSnapshotCtrl;  	LLTextBox*		mLocationText; +	LLTextBox*		mSeeAvatarsText;  	LLButton*		mSetBtn;  	LLButton*		mClearBtn; diff --git a/indra/newview/llfloatermodelpreview.cpp b/indra/newview/llfloatermodelpreview.cpp index 5a27f3c325..b6efc1590e 100644 --- a/indra/newview/llfloatermodelpreview.cpp +++ b/indra/newview/llfloatermodelpreview.cpp @@ -325,6 +325,8 @@ BOOL LLFloaterModelPreview::postBuild()  	childSetCommitCallback("import_scale", onImportScaleCommit, this);  	childSetCommitCallback("pelvis_offset", onPelvisOffsetCommit, this); +	getChild<LLLineEditor>("description_form")->setKeystrokeCallback(boost::bind(&LLFloaterModelPreview::onDescriptionKeystroke, this, _1), NULL); +  	getChild<LLCheckBoxCtrl>("show_edges")->setCommitCallback(boost::bind(&LLFloaterModelPreview::onViewOptionChecked, this, _1));  	getChild<LLCheckBoxCtrl>("show_physics")->setCommitCallback(boost::bind(&LLFloaterModelPreview::onViewOptionChecked, this, _1));  	getChild<LLCheckBoxCtrl>("show_textures")->setCommitCallback(boost::bind(&LLFloaterModelPreview::onViewOptionChecked, this, _1)); @@ -520,6 +522,16 @@ void LLFloaterModelPreview::onClickCalculateBtn()  	mUploadBtn->setEnabled(false);  } +void LLFloaterModelPreview::onDescriptionKeystroke(LLUICtrl* ctrl) +{ +	// Workaround for SL-4186, server doesn't allow name changes after 'calculate' stage +	LLLineEditor* input = static_cast<LLLineEditor*>(ctrl); +	if (input->isDirty()) // dirty will be reset after commit +	{ +		toggleCalculateButton(true); +	} +} +  //static  void LLFloaterModelPreview::onImportScaleCommit(LLUICtrl*,void* userdata)  { diff --git a/indra/newview/llfloatermodelpreview.h b/indra/newview/llfloatermodelpreview.h index 7ec6a58ac7..edc90d1695 100644 --- a/indra/newview/llfloatermodelpreview.h +++ b/indra/newview/llfloatermodelpreview.h @@ -137,7 +137,9 @@ protected:  	friend class LLModelPreview;  	friend class LLMeshFilePicker;  	friend class LLPhysicsDecomp; -	 + +	void		onDescriptionKeystroke(LLUICtrl*); +  	static void		onImportScaleCommit(LLUICtrl*, void*);  	static void		onPelvisOffsetCommit(LLUICtrl*, void*);  	static void		onUploadJointsCommit(LLUICtrl*,void*); diff --git a/indra/newview/llfloateroutfitsnapshot.cpp b/indra/newview/llfloateroutfitsnapshot.cpp index d80793f9e4..bfcd1b8b47 100644 --- a/indra/newview/llfloateroutfitsnapshot.cpp +++ b/indra/newview/llfloateroutfitsnapshot.cpp @@ -30,9 +30,7 @@  #include "llfloateroutfitsnapshot.h"  #include "llagent.h" -#include "llfacebookconnect.h"  #include "llfloaterreg.h" -#include "llfloaterfacebook.h"  #include "llfloaterflickr.h"  #include "llfloatertwitter.h"  #include "llimagefiltersmanager.h" diff --git a/indra/newview/llfloatersnapshot.cpp b/indra/newview/llfloatersnapshot.cpp index a7931137b0..2798e375c7 100644 --- a/indra/newview/llfloatersnapshot.cpp +++ b/indra/newview/llfloatersnapshot.cpp @@ -28,9 +28,7 @@  #include "llfloatersnapshot.h" -#include "llfacebookconnect.h"  #include "llfloaterreg.h" -#include "llfloaterfacebook.h"  #include "llfloaterflickr.h"  #include "llfloatertwitter.h"  #include "llimagefiltersmanager.h" @@ -1242,11 +1240,10 @@ BOOL LLFloaterSnapshot::isWaitingState()  BOOL LLFloaterSnapshotBase::ImplBase::updatePreviewList(bool initialized)  { -	LLFloaterFacebook* floater_facebook = LLFloaterReg::findTypedInstance<LLFloaterFacebook>("facebook");  	LLFloaterFlickr* floater_flickr = LLFloaterReg::findTypedInstance<LLFloaterFlickr>("flickr");  	LLFloaterTwitter* floater_twitter = LLFloaterReg::findTypedInstance<LLFloaterTwitter>("twitter"); -	if (!initialized && !floater_facebook && !floater_flickr && !floater_twitter) +	if (!initialized && !floater_flickr && !floater_twitter)  		return FALSE;  	BOOL changed = FALSE; diff --git a/indra/newview/llfloatertools.cpp b/indra/newview/llfloatertools.cpp index ee4fdbe9a5..c2c15ee12b 100644 --- a/indra/newview/llfloatertools.cpp +++ b/indra/newview/llfloatertools.cpp @@ -514,11 +514,6 @@ void LLFloaterTools::refresh()  		selection_info << getString("status_selectcount", selection_args);  		getChild<LLTextBox>("selection_count")->setText(selection_info.str()); - -		bool have_selection = !LLSelectMgr::getInstance()->getSelection()->isEmpty(); -		childSetVisible("selection_count",  have_selection); -		childSetVisible("remaining_capacity", have_selection); -		childSetVisible("selection_empty", !have_selection);  	} diff --git a/indra/newview/llfloaterwebcontent.cpp b/indra/newview/llfloaterwebcontent.cpp index 224e30f7de..c591dfacaf 100644 --- a/indra/newview/llfloaterwebcontent.cpp +++ b/indra/newview/llfloaterwebcontent.cpp @@ -30,7 +30,6 @@  #include "lliconctrl.h"  #include "llfloaterreg.h"  #include "llhttpconstants.h" -#include "llfacebookconnect.h"  #include "llflickrconnect.h"  #include "lltwitterconnect.h"  #include "lllayoutstack.h" @@ -289,17 +288,7 @@ void LLFloaterWebContent::onOpen(const LLSD& key)  //virtual  void LLFloaterWebContent::onClose(bool app_quitting)  { -    // If we close the web browsing window showing the facebook login, we need to signal to this object that the connection will not happen -	// MAINT-3440 note change here to use findInstance and not getInstance - latter creates an instance if it's not there which is bad. -    LLFloater* fbc_web = LLFloaterReg::findInstance("fbc_web"); -    if (fbc_web == this) -    { -        if (!LLFacebookConnect::instance().isConnected()) -        { -            LLFacebookConnect::instance().setConnectionState(LLFacebookConnect::FB_CONNECTION_FAILED); -        } -    } -	// Same with Flickr +    // If we close the web browsing window showing the Flickr login, we need to signal to this object that the connection will not happen  	// MAINT-3440 note change here to use findInstance and not getInstance - latter creates an instance if it's not there which is bad.  	LLFloater* flickr_web = LLFloaterReg::findInstance("flickr_web");      if (flickr_web == this) @@ -309,7 +298,7 @@ void LLFloaterWebContent::onClose(bool app_quitting)              LLFlickrConnect::instance().setConnectionState(LLFlickrConnect::FLICKR_CONNECTION_FAILED);          }      } -	// And Twitter +	// Same with Twitter  	// MAINT-3440 note change here to use findInstance and not getInstance - latter creates an instance if it's not there which is bad.  	LLFloater* twitter_web = LLFloaterReg::findInstance("twitter_web");      if (twitter_web == this) @@ -380,13 +369,6 @@ void LLFloaterWebContent::handleMediaEvent(LLPluginClassMedia* self, EMediaEvent  		// The browser instance wants its window closed.  		closeFloater();  	} -	else if(event == MEDIA_EVENT_GEOMETRY_CHANGE) -	{ -		if (mCurrentURL.find("facebook.com/dialog/oauth") == std::string::npos) // HACK to fix ACME-1317 - Cho -		{ -		geometryChanged(self->getGeometryX(), self->getGeometryY(), self->getGeometryWidth(), self->getGeometryHeight()); -	} -	}  	else if(event == MEDIA_EVENT_STATUS_TEXT_CHANGED )  	{  		const std::string text = self->getStatusText(); diff --git a/indra/newview/llglsandbox.cpp b/indra/newview/llglsandbox.cpp index a9b15fc8b6..fea01786f3 100644 --- a/indra/newview/llglsandbox.cpp +++ b/indra/newview/llglsandbox.cpp @@ -1005,7 +1005,10 @@ F32 gpu_benchmark()  	//number of samples to take  	const S32 samples = 64; -		 + +	//time limit, allocation operations shouldn't take longer then 30 seconds, same for actual benchmark. +	const F32 time_limit = 30; +  	ShaderProfileHelper initProfile;  	std::vector<LLRenderTarget> dest(count); @@ -1023,12 +1026,14 @@ F32 gpu_benchmark()  	gGL.setColorMask(true, true);  	LLGLDepthTest depth(GL_FALSE); +	LLTimer alloc_timer; +	alloc_timer.start();  	for (U32 i = 0; i < count; ++i)  	{  		//allocate render targets and textures  		if (!dest[i].allocate(res, res, GL_RGBA, false, false, LLTexUnit::TT_TEXTURE, true))  		{ -			LL_WARNS() << "Failed to allocate render target." << LL_ENDL; +			LL_WARNS("Benchmark") << "Failed to allocate render target." << LL_ENDL;  			// abandon the benchmark test  			delete[] pixels;  			return -1.f; @@ -1040,12 +1045,20 @@ F32 gpu_benchmark()  		if (!texHolder.bind(i))  		{  			// can use a dummy value mDummyTexUnit = new LLTexUnit(-1); -			LL_WARNS() << "Failed to bind tex unit." << LL_ENDL; +			LL_WARNS("Benchmark") << "Failed to bind tex unit." << LL_ENDL;  			// abandon the benchmark test  			delete[] pixels;  			return -1.f;  		}  		LLImageGL::setManualImage(GL_TEXTURE_2D, 0, GL_RGBA, res,res,GL_RGBA, GL_UNSIGNED_BYTE, pixels); + +		if (alloc_timer.getElapsedTimeF32() > time_limit) +		{ +			// abandon the benchmark test +			LL_WARNS("Benchmark") << "Allocation operation took longer then 30 seconds, stopping." << LL_ENDL; +			delete[] pixels; +			return -1.f; +		}  	}      delete [] pixels; @@ -1055,7 +1068,7 @@ F32 gpu_benchmark()  	if (!buff->allocateBuffer(3, 0, true))  	{ -		LL_WARNS() << "Failed to allocate buffer during benchmark." << LL_ENDL; +		LL_WARNS("Benchmark") << "Failed to allocate buffer during benchmark." << LL_ENDL;  		// abandon the benchmark test  		return -1.f;  	} @@ -1065,7 +1078,7 @@ F32 gpu_benchmark()  	if (! buff->getVertexStrider(v))  	{ -		LL_WARNS() << "GL LLVertexBuffer::getVertexStrider() returned false, " +		LL_WARNS("Benchmark") << "GL LLVertexBuffer::getVertexStrider() returned false, "  				   << "buff->getMappedData() is"  				   << (buff->getMappedData()? " not" : "")  				   << " NULL" << LL_ENDL; @@ -1086,7 +1099,8 @@ F32 gpu_benchmark()  	buff->setBuffer(LLVertexBuffer::MAP_VERTEX);  	glFinish(); -	for (S32 c = -1; c < samples; ++c) +	F32 time_passed = 0; // seconds +	for (S32 c = -1; c < samples && time_passed < time_limit; ++c)  	{  		LLTimer timer;  		timer.start(); @@ -1103,6 +1117,7 @@ F32 gpu_benchmark()  		glFinish();  		F32 time = timer.getElapsedTimeF32(); +		time_passed += time;  		if (c >= 0) // <-- ignore the first sample as it tends to be artificially slow  		{  @@ -1117,12 +1132,12 @@ F32 gpu_benchmark()  	F32 gbps = results[results.size()/2]; -	LL_INFOS() << "Memory bandwidth is " << llformat("%.3f", gbps) << "GB/sec according to CPU timers" << LL_ENDL; -   +	LL_INFOS("Benchmark") << "Memory bandwidth is " << llformat("%.3f", gbps) << "GB/sec according to CPU timers, " << (F32)results.size() << " tests took " << time_passed << " seconds" << LL_ENDL; +  #if LL_DARWIN      if (gbps > 512.f)      {  -        LL_WARNS() << "Memory bandwidth is improbably high and likely incorrect; discarding result." << LL_ENDL; +        LL_WARNS("Benchmark") << "Memory bandwidth is improbably high and likely incorrect; discarding result." << LL_ENDL;          //OSX is probably lying, discard result          return -1.f;      } @@ -1131,11 +1146,11 @@ F32 gpu_benchmark()  	F32 ms = gBenchmarkProgram.mTimeElapsed/1000000.f;  	F32 seconds = ms/1000.f; -	F64 samples_drawn = res*res*count*samples; +	F64 samples_drawn = res*res*count*results.size();  	F32 samples_sec = (samples_drawn/1000000000.0)/seconds;  	gbps = samples_sec*8; -	LL_INFOS() << "Memory bandwidth is " << llformat("%.3f", gbps) << "GB/sec according to ARB_timer_query" << LL_ENDL; +	LL_INFOS("Benchmark") << "Memory bandwidth is " << llformat("%.3f", gbps) << "GB/sec according to ARB_timer_query, total time " << seconds << " seconds" << LL_ENDL;  	return gbps;  } diff --git a/indra/newview/llgroupmgr.cpp b/indra/newview/llgroupmgr.cpp index 152d0eddcd..088d052533 100644 --- a/indra/newview/llgroupmgr.cpp +++ b/indra/newview/llgroupmgr.cpp @@ -2137,6 +2137,7 @@ void LLGroupMgr::sendCapGroupMembersRequest(const LLUUID& group_id)      static U32 lastGroupMemberRequestFrame = 0;  	// Have we requested the information already this frame? +    // Todo: make this per group, we can invite to one group and simultaneously be checking another one      if ((lastGroupMemberRequestFrame == gFrameCount) || (mMemberRequestInFlight))  		return; @@ -2166,6 +2167,9 @@ void LLGroupMgr::sendCapGroupMembersRequest(const LLUUID& group_id)  		return;  	} +    LLGroupMgrGroupData* group_datap = createGroupData(group_id); //make sure group exists +    group_datap->mMemberRequestID.generate(); // mark as pending +      lastGroupMemberRequestFrame = gFrameCount;      LLCoros::instance().launch("LLGroupMgr::groupMembersRequestCoro", diff --git a/indra/newview/llgroupmgr.h b/indra/newview/llgroupmgr.h index 940ef6eea1..cf9735e38a 100644 --- a/indra/newview/llgroupmgr.h +++ b/indra/newview/llgroupmgr.h @@ -258,6 +258,11 @@ public:  	bool isRoleMemberDataComplete() { return mRoleMemberDataComplete; }  	bool isGroupPropertiesDataComplete() { return mGroupPropertiesDataComplete; } +	bool isMemberDataPending() { return mMemberRequestID.notNull(); } +	bool isRoleDataPending() { return mRoleDataRequestID.notNull(); } +	bool isRoleMemberDataPending() { return (mRoleMembersRequestID.notNull() || mPendingRoleMemberRequest); } +	bool isGroupTitlePending() { return mTitlesRequestID.notNull(); } +  	bool isSingleMemberNotOwner();  	F32 getAccessTime() const { return mAccessTime; } diff --git a/indra/newview/llinventorybridge.cpp b/indra/newview/llinventorybridge.cpp index 074b0c9c14..a50a66a8ce 100644 --- a/indra/newview/llinventorybridge.cpp +++ b/indra/newview/llinventorybridge.cpp @@ -1399,13 +1399,6 @@ LLInvFVBridge* LLInvFVBridge::createBridge(LLAssetType::EType asset_type,  			// Only should happen for broken links.  			new_listener = new LLLinkItemBridge(inventory, root, uuid);  			break; -	    case LLAssetType::AT_MESH: -			if(!(inv_type == LLInventoryType::IT_MESH)) -			{ -				LL_WARNS() << LLAssetType::lookup(asset_type) << " asset has inventory type " << LLInventoryType::lookupHumanReadable(inv_type) << " on uuid " << uuid << LL_ENDL; -			} -			new_listener = new LLMeshBridge(inventory, root, uuid); -			break;  		case LLAssetType::AT_UNKNOWN:  			new_listener = new LLUnknownItemBridge(inventory, root, uuid);  			break; @@ -2101,7 +2094,9 @@ BOOL LLItemBridge::isItemCopyable() const  	LLViewerInventoryItem* item = getItem();  	if (item)  	{ -		// Can't copy worn objects. DEV-15183 +		// Can't copy worn objects. +		// Worn objects are tied to their inworld conterparts +		// Copy of modified worn object will return object with obsolete asset and inventory  		if(get_is_item_worn(mUUID))  		{  			return FALSE; @@ -6830,58 +6825,6 @@ void LLLinkItemBridge::buildContextMenu(LLMenuGL& menu, U32 flags)  	hide_context_entries(menu, items, disabled_items);  } -// +=================================================+ -// |        LLMeshBridge                             | -// +=================================================+ - -LLUIImagePtr LLMeshBridge::getIcon() const -{ -	return LLInventoryIcon::getIcon(LLAssetType::AT_MESH, LLInventoryType::IT_MESH, 0, FALSE); -} - -void LLMeshBridge::openItem() -{ -	LLViewerInventoryItem* item = getItem(); -	 -	if (item) -	{ -		// open mesh -	} -} - -void LLMeshBridge::buildContextMenu(LLMenuGL& menu, U32 flags) -{ -	LL_DEBUGS() << "LLMeshBridge::buildContextMenu()" << LL_ENDL; -	std::vector<std::string> items; -	std::vector<std::string> disabled_items; - -	if(isItemInTrash()) -	{ -		items.push_back(std::string("Purge Item")); -		if (!isItemRemovable()) -		{ -			disabled_items.push_back(std::string("Purge Item")); -		} - -		items.push_back(std::string("Restore Item")); -	} -    else if (isMarketplaceListingsFolder()) -    { -		addMarketplaceContextMenuOptions(flags, items, disabled_items); -		items.push_back(std::string("Properties")); -		getClipboardEntries(false, items, disabled_items, flags); -    } -	else -	{ -		items.push_back(std::string("Properties")); - -		getClipboardEntries(true, items, disabled_items, flags); -	} - -	addLinkReplaceMenuOption(items, disabled_items); -	hide_context_entries(menu, items, disabled_items); -} -  // +=================================================+  // |        LLLinkBridge                             | @@ -7358,8 +7301,7 @@ bool LLFolderViewGroupedItemBridge::canWearSelected(uuid_vec_t item_ids)  	for (uuid_vec_t::const_iterator it = item_ids.begin(); it != item_ids.end(); ++it)  	{  		LLViewerInventoryItem* item = gInventory.getItem(*it); -		LLAssetType::EType asset_type = item->getType(); -		if (!item || (asset_type >= LLAssetType::AT_COUNT) || (asset_type <= LLAssetType::AT_NONE)) +		if (!item || (item->getType() >= LLAssetType::AT_COUNT) || (item->getType() <= LLAssetType::AT_NONE))  		{  			return false;  		} diff --git a/indra/newview/llinventorybridge.h b/indra/newview/llinventorybridge.h index ce06e8fffc..f4df566fa6 100644 --- a/indra/newview/llinventorybridge.h +++ b/indra/newview/llinventorybridge.h @@ -603,23 +603,6 @@ protected:  	static std::string sPrefix;  }; - -class LLMeshBridge : public LLItemBridge -{ -	friend class LLInvFVBridge; -public: -	virtual LLUIImagePtr getIcon() const; -	virtual void openItem(); -	virtual void buildContextMenu(LLMenuGL& menu, U32 flags); - -protected: -	LLMeshBridge(LLInventoryPanel* inventory,  -		     LLFolderView* root, -		     const LLUUID& uuid) : -                       LLItemBridge(inventory, root, uuid) {} -}; - -  //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~  // Class LLInvFVBridgeAction  // @@ -650,17 +633,6 @@ protected:  	LLInventoryModel* mModel;  }; -class LLMeshBridgeAction: public LLInvFVBridgeAction -{ -	friend class LLInvFVBridgeAction; -public: -	virtual void	doIt() ; -	virtual ~LLMeshBridgeAction(){} -protected: -	LLMeshBridgeAction(const LLUUID& id,LLInventoryModel* model):LLInvFVBridgeAction(id,model){} - -}; -  //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~  // Recent Inventory Panel related classes diff --git a/indra/newview/llinventoryfilter.cpp b/indra/newview/llinventoryfilter.cpp index 9193613e9f..16385928b4 100644 --- a/indra/newview/llinventoryfilter.cpp +++ b/indra/newview/llinventoryfilter.cpp @@ -58,6 +58,7 @@ LLInventoryFilter::FilterOps::FilterOps(const Params& p)  	mHoursAgo(p.hours_ago),  	mDateSearchDirection(p.date_search_direction),  	mShowFolderState(p.show_folder_state), +	mFilterCreatorType(p.creator_type),  	mPermissions(p.permissions),  	mFilterTypes(p.types),  	mFilterUUID(p.uuid), @@ -78,8 +79,7 @@ LLInventoryFilter::LLInventoryFilter(const Params& p)  	mCurrentGeneration(0),  	mFirstRequiredGeneration(0),  	mFirstSuccessGeneration(0), -	mSearchType(SEARCHTYPE_NAME), -	mFilterCreatorType(FILTERCREATOR_ALL) +	mSearchType(SEARCHTYPE_NAME)  {  	// copy mFilterOps into mDefaultFilterOps  	markDefault(); @@ -489,7 +489,7 @@ bool LLInventoryFilter::checkAgainstCreator(const LLFolderViewModelItemInventory  {  	if (!listener) return TRUE;  	const BOOL is_folder = listener->getInventoryType() == LLInventoryType::IT_CATEGORY; -	switch(mFilterCreatorType) +	switch (mFilterOps.mFilterCreatorType)  	{  		case FILTERCREATOR_SELF:  			if(is_folder) return FALSE; @@ -601,9 +601,9 @@ void LLInventoryFilter::setSearchType(ESearchType type)  void LLInventoryFilter::setFilterCreator(EFilterCreatorType type)  { -	if(mFilterCreatorType != type) +	if (mFilterOps.mFilterCreatorType != type)  	{ -		mFilterCreatorType = type; +		mFilterOps.mFilterCreatorType = type;  		setModified();  	}  } @@ -1194,6 +1194,7 @@ void LLInventoryFilter::toParams(Params& params) const  	params.filter_ops.hours_ago = getHoursAgo();  	params.filter_ops.date_search_direction = getDateSearchDirection();  	params.filter_ops.show_folder_state = getShowFolderState(); +	params.filter_ops.creator_type = getFilterCreatorType();  	params.filter_ops.permissions = getFilterPermissions();  	params.substring = getFilterSubString();  	params.since_logoff = isSinceLogoff(); @@ -1216,6 +1217,7 @@ void LLInventoryFilter::fromParams(const Params& params)  	setHoursAgo(params.filter_ops.hours_ago);  	setDateSearchDirection(params.filter_ops.date_search_direction);  	setShowFolderState(params.filter_ops.show_folder_state); +	setFilterCreator(params.filter_ops.creator_type);  	setFilterPermissions(params.filter_ops.permissions);  	setFilterSubString(params.substring);  	setDateRangeLastLogoff(params.since_logoff); @@ -1278,6 +1280,11 @@ LLInventoryFilter::EFolderShow LLInventoryFilter::getShowFolderState() const  	return mFilterOps.mShowFolderState;   } +LLInventoryFilter::EFilterCreatorType LLInventoryFilter::getFilterCreatorType() const +{ +	return mFilterOps.mFilterCreatorType; +} +  bool LLInventoryFilter::isTimedOut()  {  	return mFilterTime.hasExpired(); diff --git a/indra/newview/llinventoryfilter.h b/indra/newview/llinventoryfilter.h index 01754ed023..4a1fec8454 100644 --- a/indra/newview/llinventoryfilter.h +++ b/indra/newview/llinventoryfilter.h @@ -126,6 +126,7 @@ public:  			Optional<U32>				date_search_direction;  			Optional<EFolderShow>		show_folder_state;  			Optional<PermissionMask>	permissions; +			Optional<EFilterCreatorType> creator_type;  			Params()  			:	types("filter_types", FILTERTYPE_OBJECT), @@ -138,6 +139,7 @@ public:  				hours_ago("hours_ago", 0),  				date_search_direction("date_search_direction", FILTERDATEDIRECTION_NEWER),  				show_folder_state("show_folder_state", SHOW_NON_EMPTY_FOLDERS), +				creator_type("creator_type", FILTERCREATOR_ALL),  				permissions("permissions", PERM_NONE)  			{}  		}; @@ -156,8 +158,9 @@ public:  		U32				mHoursAgo;  		U32				mDateSearchDirection; -		EFolderShow		mShowFolderState; -		PermissionMask	mPermissions; +		EFolderShow			mShowFolderState; +		PermissionMask		mPermissions; +		EFilterCreatorType	mFilterCreatorType;  	};  	struct Params : public LLInitParam::Block<Params> @@ -202,7 +205,6 @@ public:  	void 				setSearchType(ESearchType type);  	ESearchType			getSearchType() { return mSearchType; }  	void 				setFilterCreator(EFilterCreatorType type); -	EFilterCreatorType		getFilterCreator() { return mFilterCreatorType; }  	void 				setFilterSubString(const std::string& string);  	const std::string& 	getFilterSubString(BOOL trim = FALSE) const; @@ -243,8 +245,9 @@ public:  	// +-------------------------------------------------------------------+  	// + Presentation  	// +-------------------------------------------------------------------+ -	void 				setShowFolderState( EFolderShow state); -	EFolderShow 		getShowFolderState() const; +	void 					setShowFolderState( EFolderShow state); +	EFolderShow 			getShowFolderState() const; +	EFilterCreatorType		getFilterCreatorType() const;  	void 				setEmptyLookupMessage(const std::string& message);  	std::string			getEmptyLookupMessage() const; @@ -324,7 +327,6 @@ private:  	std::string 			mEmptyLookupMessage;  	ESearchType 			mSearchType; -	EFilterCreatorType		mFilterCreatorType;  };  #endif diff --git a/indra/newview/llinventorymodel.cpp b/indra/newview/llinventorymodel.cpp index b140c7c38e..c49d61df31 100644 --- a/indra/newview/llinventorymodel.cpp +++ b/indra/newview/llinventorymodel.cpp @@ -888,14 +888,6 @@ U32 LLInventoryModel::updateItem(const LLViewerInventoryItem* item, U32 mask)  		return mask;  	} -	// We're hiding mesh types -#if 0 -	if (item->getType() == LLAssetType::AT_MESH) -	{ -		return mask; -	} -#endif -  	LLPointer<LLViewerInventoryItem> old_item = getItem(item->getUUID());  	LLPointer<LLViewerInventoryItem> new_item;  	if(old_item) diff --git a/indra/newview/llmachineid.cpp b/indra/newview/llmachineid.cpp index b0ee8e7fcb..51127928d1 100644 --- a/indra/newview/llmachineid.cpp +++ b/indra/newview/llmachineid.cpp @@ -65,11 +65,11 @@ public:  S32 LLMachineID::init()  { -    memset(static_unique_id,0,sizeof(static_unique_id)); +    size_t len = sizeof(static_unique_id); +    memset(static_unique_id, 0, len);      S32 ret_code = 0;  #if	LL_WINDOWS  # pragma comment(lib, "wbemuuid.lib") -        size_t len = sizeof(static_unique_id);          // algorithm to detect BIOS serial number found at:          // http://msdn.microsoft.com/en-us/library/aa394077%28VS.85%29.aspx @@ -217,17 +217,27 @@ S32 LLMachineID::init()              // Get the value of the Name property              hr = pclsObj->Get(L"SerialNumber", 0, &vtProp, 0, 0); +            if (FAILED(hr)) +            { +                LL_WARNS() << "Failed to get SerialNumber. Error code = 0x" << hex << hres << LL_ENDL; +                pclsObj->Release(); +                pclsObj = NULL; +                continue; +            }              LL_INFOS("AppInit") << " Serial Number : " << vtProp.bstrVal << LL_ENDL; +              // use characters in the returned Serial Number to create a byte array of size len              BSTR serialNumber ( vtProp.bstrVal); +            unsigned int serial_size = SysStringLen(serialNumber);              unsigned int j = 0; -            while( vtProp.bstrVal[j] != 0) + +            while (j < serial_size && vtProp.bstrVal[j] != 0)              {                  for (unsigned int i = 0; i < len; i++)                  { -                    if (vtProp.bstrVal[j] == 0) +                    if (j >= serial_size || vtProp.bstrVal[j] == 0)                          break; -                     +                      static_unique_id[i] = (unsigned int)(static_unique_id[i] + serialNumber[j]);                      j++;                  } @@ -254,16 +264,8 @@ S32 LLMachineID::init()          ret_code = LLUUID::getNodeID(staticPtr);  #endif          has_static_unique_id = true; -        return ret_code; -} - -S32 LLMachineID::getUniqueID(unsigned char *unique_id, size_t len) -{ -    if (has_static_unique_id) -    { -        memcpy ( unique_id, &static_unique_id, len); -        LL_INFOS_ONCE("AppInit") << "UniqueID: 0x"; +        LL_INFOS("AppInit") << "UniqueID: 0x";          // Code between here and LL_ENDL is not executed unless the LL_DEBUGS          // actually produces output          for (size_t i = 0; i < len; ++i) @@ -271,11 +273,21 @@ S32 LLMachineID::getUniqueID(unsigned char *unique_id, size_t len)              // Copy each char to unsigned int to hexify. Sending an unsigned              // char to a std::ostream tries to represent it as a char, not              // what we want here. -            unsigned byte = unique_id[i]; +            unsigned byte = static_unique_id[i];              LL_CONT << std::hex << std::setw(2) << std::setfill('0') << byte;          }          // Reset default output formatting to avoid nasty surprises!          LL_CONT << std::dec << std::setw(0) << std::setfill(' ') << LL_ENDL; + +        return ret_code; +} + + +S32 LLMachineID::getUniqueID(unsigned char *unique_id, size_t len) +{ +    if (has_static_unique_id) +    { +        memcpy ( unique_id, &static_unique_id, len);          return 1;      }      return 0; diff --git a/indra/newview/llnamelistctrl.cpp b/indra/newview/llnamelistctrl.cpp index 909936d989..3209d23e43 100644 --- a/indra/newview/llnamelistctrl.cpp +++ b/indra/newview/llnamelistctrl.cpp @@ -34,6 +34,7 @@  #include "llcachename.h"  #include "llfloater.h"  #include "llfloaterreg.h" +#include "llfloatersnapshot.h" // gSnapshotFloaterView  #include "llinventory.h"  #include "llscrolllistitem.h"  #include "llscrolllistcell.h" @@ -236,24 +237,30 @@ BOOL LLNameListCtrl::handleToolTip(S32 x, S32 y, MASK mask)  				// Spawn at right side of cell  				LLPointer<LLUIImage> icon = LLUI::getUIImage("Info_Small"); -				LLCoordGL pos( sticky_rect.mRight - info_icon_size, sticky_rect.mTop - (sticky_rect.getHeight() - icon->getHeight())/2 ); - -				// Should we show a group or an avatar inspector? -				bool is_group = hit_item->isGroup(); -				bool is_experience = hit_item->isExperience(); - -				LLToolTip::Params params; -				params.background_visible( false ); -				params.click_callback( boost::bind(&LLNameListCtrl::showInspector, this, avatar_id, is_group, is_experience) ); -				params.delay_time(0.0f);		// spawn instantly on hover -				params.image( icon ); -				params.message(""); -				params.padding(0); -				params.pos(pos); -				params.sticky_rect(sticky_rect); - -				LLToolTipMgr::getInstance()->show(params); -				handled = TRUE; +				S32 screenX = sticky_rect.mRight - info_icon_size; +				S32 screenY = sticky_rect.mTop - (sticky_rect.getHeight() - icon->getHeight()) / 2; +				LLCoordGL pos(screenX, screenY); + +				LLFloater* snapshot_floatr = gSnapshotFloaterView->getFrontmostClosableFloater(); +				if (!snapshot_floatr || !snapshot_floatr->getRect().pointInRect(screenX + icon->getWidth(), screenY)) +				{ +					// Should we show a group or an avatar inspector? +					bool is_group = hit_item->isGroup(); +					bool is_experience = hit_item->isExperience(); + +					LLToolTip::Params params; +					params.background_visible(false); +					params.click_callback(boost::bind(&LLNameListCtrl::showInspector, this, avatar_id, is_group, is_experience)); +					params.delay_time(0.0f);		// spawn instantly on hover +					params.image(icon); +					params.message(""); +					params.padding(0); +					params.pos(pos); +					params.sticky_rect(sticky_rect); + +					LLToolTipMgr::getInstance()->show(params); +					handled = TRUE; +				}  			}  		}  	} diff --git a/indra/newview/llnotificationscripthandler.cpp b/indra/newview/llnotificationscripthandler.cpp index fef0631fa6..ba831ab2ed 100644 --- a/indra/newview/llnotificationscripthandler.cpp +++ b/indra/newview/llnotificationscripthandler.cpp @@ -35,7 +35,6 @@  #include "llnotificationmanager.h"  #include "llnotifications.h"  #include "llscriptfloater.h" -#include "llfacebookconnect.h"  #include "llavatarname.h"  #include "llavatarnamecache.h" diff --git a/indra/newview/llpanelexperiencepicker.cpp b/indra/newview/llpanelexperiencepicker.cpp index a7f2dbafa2..80aeee6da1 100644 --- a/indra/newview/llpanelexperiencepicker.cpp +++ b/indra/newview/llpanelexperiencepicker.cpp @@ -89,7 +89,7 @@ BOOL LLPanelExperiencePicker::postBuild()  	childSetAction(BTN_PROFILE, boost::bind(&LLPanelExperiencePicker::onBtnProfile, this));  	getChildView(BTN_PROFILE)->setEnabled(FALSE); -	getChild<LLComboBox>(TEXT_MATURITY)->setCurrentByIndex(2); +	getChild<LLComboBox>(TEXT_MATURITY)->setCurrentByIndex(gSavedPerAccountSettings.getU32("ExperienceSearchMaturity"));  	getChild<LLComboBox>(TEXT_MATURITY)->setCommitCallback(boost::bind(&LLPanelExperiencePicker::onMaturity, this));  	getChild<LLUICtrl>(TEXT_EDIT)->setFocus(TRUE); @@ -381,6 +381,7 @@ void LLPanelExperiencePicker::filterContent()  void LLPanelExperiencePicker::onMaturity()  { +	gSavedPerAccountSettings.setU32("ExperienceSearchMaturity", getChild<LLComboBox>(TEXT_MATURITY)->getCurrentIndex());  	if(mResponse.has("experience_keys") && mResponse["experience_keys"].beginArray() != mResponse["experience_keys"].endArray())  	{  		filterContent(); diff --git a/indra/newview/llpanelgroupinvite.cpp b/indra/newview/llpanelgroupinvite.cpp index 82ea8377de..d6b66ee622 100644 --- a/indra/newview/llpanelgroupinvite.cpp +++ b/indra/newview/llpanelgroupinvite.cpp @@ -606,11 +606,30 @@ void LLPanelGroupInvite::updateLists()  	{  		if (!mPendingUpdate)   		{ +			// Note: this will partially fail if some requests are already in progress  			LLGroupMgr::getInstance()->sendGroupPropertiesRequest(mImplementation->mGroupID);  			LLGroupMgr::getInstance()->sendGroupRoleDataRequest(mImplementation->mGroupID);  			LLGroupMgr::getInstance()->sendGroupRoleMembersRequest(mImplementation->mGroupID);  			LLGroupMgr::getInstance()->sendCapGroupMembersRequest(mImplementation->mGroupID);  		} +        else if (gdatap) +        { +            // restart requests that were interrupted/dropped/failed to start +            if (!gdatap->isRoleDataPending() && !gdatap->isRoleDataComplete()) +            { +                LLGroupMgr::getInstance()->sendGroupRoleDataRequest(mImplementation->mGroupID); +            } +            if (!gdatap->isRoleMemberDataPending() && !gdatap->isRoleMemberDataComplete()) +            { +                LLGroupMgr::getInstance()->sendGroupRoleMembersRequest(mImplementation->mGroupID); +            } +            // sendCapGroupMembersRequest has a per frame send limitation that could have +            // interrupted previous request +            if (!gdatap->isMemberDataPending() && !gdatap->isMemberDataComplete()) +            { +                LLGroupMgr::getInstance()->sendCapGroupMembersRequest(mImplementation->mGroupID); +            } +        }  		mPendingUpdate = TRUE;  	}   	else diff --git a/indra/newview/llpanelgrouproles.cpp b/indra/newview/llpanelgrouproles.cpp index 52a13304df..0efb234015 100644 --- a/indra/newview/llpanelgrouproles.cpp +++ b/indra/newview/llpanelgrouproles.cpp @@ -1962,6 +1962,7 @@ LLPanelGroupRolesSubTab::LLPanelGroupRolesSubTab()  	mRoleDescription(NULL),  	mMemberVisibleCheck(NULL),  	mDeleteRoleButton(NULL), +	mCopyRoleButton(NULL),  	mCreateRoleButton(NULL),  	mFirstOpen(TRUE),  	mHasRoleChange(FALSE) @@ -2012,6 +2013,14 @@ BOOL LLPanelGroupRolesSubTab::postBuildSubTab(LLView* root)  		mCreateRoleButton->setClickedCallback(onCreateRole, this);  		mCreateRoleButton->setEnabled(FALSE);  	} + +	mCopyRoleButton =  +		parent->getChild<LLButton>("role_copy", recurse); +	if ( mCopyRoleButton ) +	{ +		mCopyRoleButton->setClickedCallback(onCopyRole, this); +		mCopyRoleButton->setEnabled(FALSE); +	}  	mDeleteRoleButton =    		parent->getChild<LLButton>("role_delete", recurse); @@ -2226,6 +2235,7 @@ void LLPanelGroupRolesSubTab::update(LLGroupChange gc)  			mRoleTitle->clear();  			setFooterEnabled(FALSE);  			mDeleteRoleButton->setEnabled(FALSE); +			mCopyRoleButton->setEnabled(FALSE);  		}  	} @@ -2336,6 +2346,7 @@ void LLPanelGroupRolesSubTab::handleRoleSelect()  	mSelectedRole = item->getUUID();  	buildMembersList(); +	mCopyRoleButton->setEnabled(gAgent.hasPowerInGroup(mGroupID, GP_ROLE_CREATE));  	can_delete = can_delete && gAgent.hasPowerInGroup(mGroupID,  													  GP_ROLE_DELETE);  	mDeleteRoleButton->setEnabled(can_delete); @@ -2662,6 +2673,57 @@ void LLPanelGroupRolesSubTab::handleCreateRole()  }  // static  +void LLPanelGroupRolesSubTab::onCopyRole(void* user_data) +{ +	LLPanelGroupRolesSubTab* self = static_cast<LLPanelGroupRolesSubTab*>(user_data); +	if (!self) return; + +	self->handleCopyRole(); +} + +void LLPanelGroupRolesSubTab::handleCopyRole() +{ +	LLGroupMgrGroupData* gdatap = LLGroupMgr::getInstance()->getGroupData(mGroupID); + +	if (!gdatap) return; + +	LLScrollListItem* role_item = mRolesList->getFirstSelected(); +	if (!role_item || role_item->getUUID().isNull()) +	{ +		return; +	} + +	LLRoleData rd; +	if (!gdatap->getRoleData(role_item->getUUID(), rd)) +	{ +		return; +	} + +	LLUUID new_role_id; +	new_role_id.generate(); +	rd.mRoleName += "(Copy)"; +	gdatap->createRole(new_role_id,rd); + +	mRolesList->deselectAllItems(TRUE); +	LLSD row; +	row["id"] = new_role_id; +	row["columns"][0]["column"] = "name"; +	row["columns"][0]["value"] = rd.mRoleName; +	mRolesList->addElement(row, ADD_BOTTOM, this); +	mRolesList->selectByID(new_role_id); + +	// put focus on name field and select its contents +	if(mRoleName) +	{ +		mRoleName->setFocus(TRUE); +		mRoleName->onTabInto(); +		gFocusMgr.triggerFocusFlash(); +	} + +	notifyObservers(); +} + +// static   void LLPanelGroupRolesSubTab::onDeleteRole(void* user_data)  {  	LLPanelGroupRolesSubTab* self = static_cast<LLPanelGroupRolesSubTab*>(user_data); diff --git a/indra/newview/llpanelgrouproles.h b/indra/newview/llpanelgrouproles.h index aafbd242cb..459b77703f 100644 --- a/indra/newview/llpanelgrouproles.h +++ b/indra/newview/llpanelgrouproles.h @@ -269,6 +269,9 @@ public:  	static void onCreateRole(void*);  	void handleCreateRole(); +	static void onCopyRole(void*); +	void handleCopyRole(); +  	static void onDeleteRole(void*);  	void handleDeleteRole(); @@ -296,6 +299,7 @@ protected:  	LLCheckBoxCtrl* mMemberVisibleCheck;  	LLButton*       mDeleteRoleButton;  	LLButton*       mCreateRoleButton; +	LLButton*       mCopyRoleButton;  	LLUUID	mSelectedRole;  	BOOL	mHasRoleChange; diff --git a/indra/newview/llpanellogin.cpp b/indra/newview/llpanellogin.cpp index 142dea83e2..e253557797 100644 --- a/indra/newview/llpanellogin.cpp +++ b/indra/newview/llpanellogin.cpp @@ -178,7 +178,7 @@ LLPanelLogin::LLPanelLogin(const LLRect &rect,  	mPasswordModified = FALSE; -	LLPanelLogin::sInstance = this; +	sInstance = this;  	LLView* login_holder = gViewerWindow->getLoginPanelHolder();  	if (login_holder) @@ -234,29 +234,44 @@ LLPanelLogin::LLPanelLogin(const LLRect &rect,  	server_choice_combo->add(LLGridManager::getInstance()->getGridLabel(),   							 current_grid,  							 ADD_TOP);	 -	server_choice_combo->selectFirstItem();		 +	server_choice_combo->selectFirstItem();  	LLSLURL start_slurl(LLStartUp::getStartSLURL()); +	// The StartSLURL might have been set either by an explicit command-line +	// argument (CmdLineLoginLocation) or by default. +	// current_grid might have been set either by an explicit command-line +	// argument (CmdLineGridChoice) or by default. +	// If the grid specified by StartSLURL is the same as current_grid, the +	// distinction is moot. +	// If we have an explicit command-line SLURL, use that. +	// If we DON'T have an explicit command-line SLURL but we DO have an +	// explicit command-line grid, which is different from the default SLURL's +	// -- do NOT override the explicit command-line grid with the grid from +	// the default SLURL! +	bool force_grid{ start_slurl.getGrid() != current_grid && +					 gSavedSettings.getString("CmdLineLoginLocation").empty() && +				   ! gSavedSettings.getString("CmdLineGridChoice").empty() };  	if ( !start_slurl.isSpatial() ) // has a start been established by the command line or NextLoginLocation ?   	{  		// no, so get the preference setting  		std::string defaultStartLocation = gSavedSettings.getString("LoginLocation");  		LL_INFOS("AppInit")<<"default LoginLocation '"<<defaultStartLocation<<"'"<<LL_ENDL;  		LLSLURL defaultStart(defaultStartLocation); -		if ( defaultStart.isSpatial() ) +		if ( defaultStart.isSpatial() && ! force_grid )  		{  			LLStartUp::setStartSLURL(defaultStart);  		}  		else  		{ -			LL_INFOS("AppInit")<<"no valid LoginLocation, using home"<<LL_ENDL; +			LL_INFOS("AppInit") << (force_grid? "--grid specified" : "no valid LoginLocation") +								<< ", using home" << LL_ENDL;  			LLSLURL homeStart(LLSLURL::SIM_LOCATION_HOME);  			LLStartUp::setStartSLURL(homeStart);  		}  	} -	else +	else if (! force_grid)  	{ -		LLPanelLogin::onUpdateStartSLURL(start_slurl); // updates grid if needed +		onUpdateStartSLURL(start_slurl); // updates grid if needed  	}  	childSetAction("connect_btn", onClickConnect, this); @@ -380,7 +395,7 @@ void LLPanelLogin::setFocus(BOOL b)  	{  		if(b)  		{ -			LLPanelLogin::giveFocus(); +			giveFocus();  		}  		else  		{ @@ -748,7 +763,10 @@ void LLPanelLogin::closePanel()  {  	if (sInstance)  	{ -		LLPanelLogin::sInstance->getParent()->removeChild( LLPanelLogin::sInstance ); +		if (LLPanelLogin::sInstance->getParent()) +		{ +			LLPanelLogin::sInstance->getParent()->removeChild(LLPanelLogin::sInstance); +		}  		delete sInstance;  		sInstance = NULL; diff --git a/indra/newview/llpanelmaininventory.cpp b/indra/newview/llpanelmaininventory.cpp index db9d61c637..f63e604927 100644 --- a/indra/newview/llpanelmaininventory.cpp +++ b/indra/newview/llpanelmaininventory.cpp @@ -885,7 +885,7 @@ void LLFloaterInventoryFinder::updateElementsFromFilter()  	U32 hours = mFilter->getHoursAgo();  	U32 date_search_direction = mFilter->getDateSearchDirection(); -	LLInventoryFilter::EFilterCreatorType filter_creator = mFilter->getFilterCreator(); +	LLInventoryFilter::EFilterCreatorType filter_creator = mFilter->getFilterCreatorType();  	bool show_created_by_me = ((filter_creator == LLInventoryFilter::FILTERCREATOR_ALL) || (filter_creator == LLInventoryFilter::FILTERCREATOR_SELF));  	bool show_created_by_others = ((filter_creator == LLInventoryFilter::FILTERCREATOR_ALL) || (filter_creator == LLInventoryFilter::FILTERCREATOR_OTHERS)); @@ -898,7 +898,6 @@ void LLFloaterInventoryFinder::updateElementsFromFilter()  	getChild<LLUICtrl>("check_clothing")->setValue((S32) (filter_types & 0x1 << LLInventoryType::IT_WEARABLE));  	getChild<LLUICtrl>("check_gesture")->setValue((S32) (filter_types & 0x1 << LLInventoryType::IT_GESTURE));  	getChild<LLUICtrl>("check_landmark")->setValue((S32) (filter_types & 0x1 << LLInventoryType::IT_LANDMARK)); -	getChild<LLUICtrl>("check_mesh")->setValue((S32) (filter_types & 0x1 << LLInventoryType::IT_MESH));  	getChild<LLUICtrl>("check_notecard")->setValue((S32) (filter_types & 0x1 << LLInventoryType::IT_NOTECARD));  	getChild<LLUICtrl>("check_object")->setValue((S32) (filter_types & 0x1 << LLInventoryType::IT_OBJECT));  	getChild<LLUICtrl>("check_script")->setValue((S32) (filter_types & 0x1 << LLInventoryType::IT_LSL)); @@ -954,12 +953,6 @@ void LLFloaterInventoryFinder::draw()  		filtered_by_all_types = FALSE;  	} -	if (!getChild<LLUICtrl>("check_mesh")->getValue()) -	{ -		filter &= ~(0x1 << LLInventoryType::IT_MESH); -		filtered_by_all_types = FALSE; -	} -  	if (!getChild<LLUICtrl>("check_notecard")->getValue())  	{  		filter &= ~(0x1 << LLInventoryType::IT_NOTECARD); @@ -1108,7 +1101,6 @@ void LLFloaterInventoryFinder::selectAllTypes(void* user_data)  	self->getChild<LLUICtrl>("check_clothing")->setValue(TRUE);  	self->getChild<LLUICtrl>("check_gesture")->setValue(TRUE);  	self->getChild<LLUICtrl>("check_landmark")->setValue(TRUE); -	self->getChild<LLUICtrl>("check_mesh")->setValue(TRUE);  	self->getChild<LLUICtrl>("check_notecard")->setValue(TRUE);  	self->getChild<LLUICtrl>("check_object")->setValue(TRUE);  	self->getChild<LLUICtrl>("check_script")->setValue(TRUE); @@ -1128,7 +1120,6 @@ void LLFloaterInventoryFinder::selectNoTypes(void* user_data)  	self->getChild<LLUICtrl>("check_clothing")->setValue(FALSE);  	self->getChild<LLUICtrl>("check_gesture")->setValue(FALSE);  	self->getChild<LLUICtrl>("check_landmark")->setValue(FALSE); -	self->getChild<LLUICtrl>("check_mesh")->setValue(FALSE);  	self->getChild<LLUICtrl>("check_notecard")->setValue(FALSE);  	self->getChild<LLUICtrl>("check_object")->setValue(FALSE);  	self->getChild<LLUICtrl>("check_script")->setValue(FALSE); diff --git a/indra/newview/llpanelobjectinventory.cpp b/indra/newview/llpanelobjectinventory.cpp index cd1875e995..6702dae4d6 100644 --- a/indra/newview/llpanelobjectinventory.cpp +++ b/indra/newview/llpanelobjectinventory.cpp @@ -1122,92 +1122,6 @@ LLUIImagePtr LLTaskWearableBridge::getIcon() const  }  ///---------------------------------------------------------------------------- -/// Class LLTaskMeshBridge -///---------------------------------------------------------------------------- - -class LLTaskMeshBridge : public LLTaskInvFVBridge -{ -public: -	LLTaskMeshBridge( -		LLPanelObjectInventory* panel, -		const LLUUID& uuid, -		const std::string& name); - -	virtual LLUIImagePtr getIcon() const; -	virtual void openItem(); -	virtual void performAction(LLInventoryModel* model, std::string action); -	virtual void buildContextMenu(LLMenuGL& menu, U32 flags); -}; - -LLTaskMeshBridge::LLTaskMeshBridge( -	LLPanelObjectInventory* panel, -	const LLUUID& uuid, -	const std::string& name) : -	LLTaskInvFVBridge(panel, uuid, name) -{ -} - -LLUIImagePtr LLTaskMeshBridge::getIcon() const -{ -	return LLInventoryIcon::getIcon(LLAssetType::AT_MESH, LLInventoryType::IT_MESH, 0, FALSE); -} - -void LLTaskMeshBridge::openItem() -{ -	// open mesh -} - - -// virtual -void LLTaskMeshBridge::performAction(LLInventoryModel* model, std::string action) -{ -	if (action == "mesh action") -	{ -		LLInventoryItem* item = findItem(); -		if(item) -		{ -			// do action -		} -	} -	LLTaskInvFVBridge::performAction(model, action); -} - -void LLTaskMeshBridge::buildContextMenu(LLMenuGL& menu, U32 flags) -{ -	LLInventoryItem* item = findItem(); -	std::vector<std::string> items; -	std::vector<std::string> disabled_items; -	if(!item) -	{ -		hide_context_entries(menu, items, disabled_items); -		return; -	} - -	items.push_back(std::string("Task Open"));  -	if (!isItemCopyable()) -	{ -		disabled_items.push_back(std::string("Task Open")); -	} - -	items.push_back(std::string("Task Properties")); -	if ((flags & FIRST_SELECTED_ITEM) == 0) -	{ -		disabled_items.push_back(std::string("Task Properties")); -	} -	if(isItemRenameable()) -	{ -		items.push_back(std::string("Task Rename")); -	} -	if(isItemRemovable()) -	{ -		items.push_back(std::string("Task Remove")); -	} - - -	hide_context_entries(menu, items, disabled_items); -} - -///----------------------------------------------------------------------------  /// LLTaskInvFVBridge impl  //---------------------------------------------------------------------------- @@ -1288,11 +1202,6 @@ LLTaskInvFVBridge* LLTaskInvFVBridge::createObjectBridge(LLPanelObjectInventory*  						 object_id,  						 object_name);  		break; -	case LLAssetType::AT_MESH: -		new_bridge = new LLTaskMeshBridge(panel, -										  object_id, -										  object_name); -		break;  	default:  		LL_INFOS() << "Unhandled inventory type (llassetstorage.h): "  				<< (S32)type << LL_ENDL; @@ -1498,7 +1407,14 @@ void LLPanelObjectInventory::updateInventory()  			mIsInventoryEmpty = TRUE;  		} -		mHaveInventory = TRUE; +		mHaveInventory = !mIsInventoryEmpty || !objectp->isInventoryDirty(); +		if (objectp->isInventoryDirty()) +		{ +			// Inventory is dirty, yet we received inventoryChanged() callback. +			// User changed something during ongoing request. +			// Rerequest. It will clear dirty flag and won't create dupplicate requests. +			objectp->requestInventory(); +		}  	}  	else  	{ @@ -1768,7 +1684,7 @@ void LLPanelObjectInventory::deleteAllChildren()  BOOL LLPanelObjectInventory::handleDragAndDrop(S32 x, S32 y, MASK mask, BOOL drop, EDragAndDropType cargo_type, void *cargo_data, EAcceptance *accept, std::string& tooltip_msg)  { -	if (mFolders && mHaveInventory) +	if (mFolders)  	{  		LLFolderViewItem* folderp = mFolders->getNextFromChild(NULL);  		if (!folderp) diff --git a/indra/newview/llpanelobjectinventory.h b/indra/newview/llpanelobjectinventory.h index d700c8f4cf..7b9ecfb8f3 100644 --- a/indra/newview/llpanelobjectinventory.h +++ b/indra/newview/llpanelobjectinventory.h @@ -106,9 +106,9 @@ private:  	LLUUID mTaskUUID;  	LLUUID mAttachmentUUID; -	BOOL mHaveInventory; -	BOOL mIsInventoryEmpty; -	BOOL mInventoryNeedsUpdate; +	BOOL mHaveInventory; // 'Loading' label and used for initial request +	BOOL mIsInventoryEmpty; // 'Empty' label +	BOOL mInventoryNeedsUpdate; // for idle, set on changed callback  	LLFolderViewModelInventory	mInventoryViewModel;	  }; diff --git a/indra/newview/llpanelpeople.cpp b/indra/newview/llpanelpeople.cpp index 617ca05281..be174475e1 100644 --- a/indra/newview/llpanelpeople.cpp +++ b/indra/newview/llpanelpeople.cpp @@ -54,7 +54,6 @@  #include "llcallingcard.h"			// for LLAvatarTracker  #include "llcallbacklist.h"  #include "llerror.h" -#include "llfacebookconnect.h"  #include "llfloateravatarpicker.h"  #include "llfriendcard.h"  #include "llgroupactions.h" @@ -537,7 +536,6 @@ public:  LLPanelPeople::LLPanelPeople()  	:	LLPanel(), -		mTryToConnectToFacebook(true),  		mTabContainer(NULL),  		mOnlineFriendList(NULL),  		mAllFriendList(NULL), @@ -645,11 +643,9 @@ BOOL LLPanelPeople::postBuild()  	// updater is active only if panel is visible to user.  	friends_tab->setVisibleCallback(boost::bind(&Updater::setActive, mFriendListUpdater, _2));      friends_tab->setVisibleCallback(boost::bind(&LLPanelPeople::removePicker, this)); -	friends_tab->setVisibleCallback(boost::bind(&LLPanelPeople::updateFacebookList, this, _2));  	mOnlineFriendList = friends_tab->getChild<LLAvatarList>("avatars_online");  	mAllFriendList = friends_tab->getChild<LLAvatarList>("avatars_all"); -	mSuggestedFriends = friends_tab->getChild<LLAvatarList>("suggested_friends");  	mOnlineFriendList->setNoItemsCommentText(getString("no_friends_online"));  	mOnlineFriendList->setShowIcons("FriendsListShowIcons");  	mOnlineFriendList->showPermissions("FriendsListShowPermissions"); @@ -685,7 +681,6 @@ BOOL LLPanelPeople::postBuild()  	mRecentList->setContextMenu(&LLPanelPeopleMenus::gPeopleContextMenu);  	mAllFriendList->setContextMenu(&LLPanelPeopleMenus::gPeopleContextMenu);  	mOnlineFriendList->setContextMenu(&LLPanelPeopleMenus::gPeopleContextMenu); -	mSuggestedFriends->setContextMenu(&LLPanelPeopleMenus::gSuggestedFriendsContextMenu);  	setSortOrder(mRecentList,		(ESortOrder)gSavedSettings.getU32("RecentPeopleSortOrder"),	false);  	setSortOrder(mAllFriendList,	(ESortOrder)gSavedSettings.getU32("FriendsSortOrder"),		false); @@ -764,7 +759,7 @@ void LLPanelPeople::updateFriendListHelpText()  	// Seems sometimes all_friends can be empty because of issue with Inventory loading (clear cache, slow connection...)  	// So, lets check all lists to avoid overlapping the text with online list. See EXT-6448. -	bool any_friend_exists = mAllFriendList->filterHasMatches() || mOnlineFriendList->filterHasMatches() || mSuggestedFriends->filterHasMatches(); +	bool any_friend_exists = mAllFriendList->filterHasMatches() || mOnlineFriendList->filterHasMatches();  	no_friends_text->setVisible(!any_friend_exists);  	if (no_friends_text->getVisible())  	{ @@ -831,40 +826,9 @@ void LLPanelPeople::updateFriendList()  	mAllFriendList->setDirty(true, !mAllFriendList->filterHasMatches());  	//update trash and other buttons according to a selected item  	updateButtons(); -	updateSuggestedFriendList();  	showFriendsAccordionsIfNeeded();  } -bool LLPanelPeople::updateSuggestedFriendList() -{ -	const LLAvatarTracker& av_tracker = LLAvatarTracker::instance(); -	uuid_vec_t& suggested_friends = mSuggestedFriends->getIDs(); -	suggested_friends.clear(); - -	//Add suggested friends -	LLSD friends = LLFacebookConnect::instance().getContent(); -	for (LLSD::array_const_iterator i = friends.beginArray(); i != friends.endArray(); ++i) -	{ -		LLUUID agent_id = (*i).asUUID(); -		bool second_life_buddy = agent_id.notNull() ? av_tracker.isBuddy(agent_id) : false; - -		if(!second_life_buddy) -		{ -			//FB+SL but not SL friend -			if (agent_id.notNull()) -			{ -				suggested_friends.push_back(agent_id); -			} -		} -	} - -	//Force a refresh when there aren't any filter matches (prevent displaying content that shouldn't display) -	mSuggestedFriends->setDirty(true, !mSuggestedFriends->filterHasMatches()); -	showFriendsAccordionsIfNeeded(); - -	return false; -} -  void LLPanelPeople::updateNearbyList()  {  	if (!mNearbyList) @@ -888,51 +852,6 @@ void LLPanelPeople::updateRecentList()  	mRecentList->setDirty();  } -bool LLPanelPeople::onConnectedToFacebook(const LLSD& data) -{ -	LLSD::Integer connection_state = data.get("enum").asInteger(); - -	if (connection_state == LLFacebookConnect::FB_CONNECTED) -	{ -		LLFacebookConnect::instance().loadFacebookFriends(); -	} -	else if(connection_state == LLFacebookConnect::FB_NOT_CONNECTED) -	{ -		updateSuggestedFriendList(); -	}; - -	return false; -} - -void LLPanelPeople::updateFacebookList(bool visible) -{ -	if (visible) -	{ -		LLEventPumps::instance().obtain("FacebookConnectContent").stopListening("LLPanelPeople"); // just in case it is already listening -		LLEventPumps::instance().obtain("FacebookConnectContent").listen("LLPanelPeople", boost::bind(&LLPanelPeople::updateSuggestedFriendList, this)); - -		LLEventPumps::instance().obtain("FacebookConnectState").stopListening("LLPanelPeople"); // just in case it is already listening -		LLEventPumps::instance().obtain("FacebookConnectState").listen("LLPanelPeople", boost::bind(&LLPanelPeople::onConnectedToFacebook, this, _1)); - -		if (LLFacebookConnect::instance().isConnected()) -		{ -			LLFacebookConnect::instance().loadFacebookFriends(); -		} -		else if(mTryToConnectToFacebook) -		{ -			LLFacebookConnect::instance().checkConnectionToFacebook(); -			mTryToConnectToFacebook = false; -		} -     -		updateSuggestedFriendList(); -	} -	else -	{ -		LLEventPumps::instance().obtain("FacebookConnectState").stopListening("LLPanelPeople"); -		LLEventPumps::instance().obtain("FacebookConnectContent").stopListening("LLPanelPeople"); -	} -} -  void LLPanelPeople::updateButtons()  {  	std::string cur_tab		= getActiveTabName(); @@ -1151,11 +1070,9 @@ void LLPanelPeople::onFilterEdit(const std::string& search_string)  		mOnlineFriendList->setNameFilter(filter);  		mAllFriendList->setNameFilter(filter); -		mSuggestedFriends->setNameFilter(filter);          setAccordionCollapsedByUser("tab_online", false);          setAccordionCollapsedByUser("tab_all", false); -		setAccordionCollapsedByUser("tab_suggested_friends", false);          showFriendsAccordionsIfNeeded();  		// restore accordion tabs state _after_ all manipulations @@ -1600,7 +1517,6 @@ void LLPanelPeople::showFriendsAccordionsIfNeeded()  		// Expand and show accordions if needed, else - hide them  		showAccordion("tab_online", mOnlineFriendList->filterHasMatches());  		showAccordion("tab_all", mAllFriendList->filterHasMatches()); -		showAccordion("tab_suggested_friends", mSuggestedFriends->filterHasMatches());  		// Rearrange accordions  		LLAccordionCtrl* accordion = getChild<LLAccordionCtrl>("friends_accordion"); diff --git a/indra/newview/llpanelpeople.h b/indra/newview/llpanelpeople.h index c72c4fc08a..14205cebe2 100644 --- a/indra/newview/llpanelpeople.h +++ b/indra/newview/llpanelpeople.h @@ -57,8 +57,6 @@ public:  	// when voice is available  	/*virtual*/ void onChange(EStatusType status, const std::string &channelURI, bool proximal); -    bool mTryToConnectToFacebook; -  	// internals  	class Updater; @@ -80,10 +78,8 @@ private:  	// methods indirectly called by the updaters  	void					updateFriendListHelpText();  	void					updateFriendList(); -	bool					updateSuggestedFriendList();  	void					updateNearbyList();  	void					updateRecentList(); -	void					updateFacebookList(bool visible);  	bool					isItemsFreeOfFriends(const uuid_vec_t& uuids); @@ -131,8 +127,6 @@ private:  	void					onFriendListRefreshComplete(LLUICtrl*ctrl, const LLSD& param); -	bool					onConnectedToFacebook(const LLSD& data); -  	void					setAccordionCollapsedByUser(LLUICtrl* acc_tab, bool collapsed);  	void					setAccordionCollapsedByUser(const std::string& name, bool collapsed);  	bool					isAccordionCollapsedByUser(LLUICtrl* acc_tab); @@ -141,7 +135,6 @@ private:  	LLTabContainer*			mTabContainer;  	LLAvatarList*			mOnlineFriendList;  	LLAvatarList*			mAllFriendList; -	LLAvatarList*			mSuggestedFriends;  	LLAvatarList*			mNearbyList;  	LLAvatarList*			mRecentList;  	LLGroupList*			mGroupList; diff --git a/indra/newview/llpanelpeoplemenus.cpp b/indra/newview/llpanelpeoplemenus.cpp index 65769ff526..42cecc9986 100644 --- a/indra/newview/llpanelpeoplemenus.cpp +++ b/indra/newview/llpanelpeoplemenus.cpp @@ -52,7 +52,6 @@ namespace LLPanelPeopleMenus  PeopleContextMenu gPeopleContextMenu;  NearbyPeopleContextMenu gNearbyPeopleContextMenu; -SuggestedFriendsContextMenu gSuggestedFriendsContextMenu;  //== PeopleContextMenu =============================================================== @@ -413,36 +412,4 @@ void NearbyPeopleContextMenu::buildContextMenu(class LLMenuGL& menu, U32 flags)      hide_context_entries(menu, items, disabled_items);  } -//== SuggestedFriendsContextMenu =============================================================== - -LLContextMenu* SuggestedFriendsContextMenu::createMenu() -{ -	// set up the callbacks for all of the avatar menu items -	LLUICtrl::CommitCallbackRegistry::ScopedRegistrar registrar; -	LLUICtrl::EnableCallbackRegistry::ScopedRegistrar enable_registrar; -	LLContextMenu* menu; - -	// Set up for one person selected menu -	const LLUUID& id = mUUIDs.front(); -	registrar.add("Avatar.Profile",			boost::bind(&LLAvatarActions::showProfile,				id)); -	registrar.add("Avatar.AddFriend",		boost::bind(&LLAvatarActions::requestFriendshipDialog,	id)); - -	// create the context menu from the XUI -	menu = createFromFile("menu_people_nearby.xml"); -	buildContextMenu(*menu, 0x0); - -	return menu; -} - -void SuggestedFriendsContextMenu::buildContextMenu(class LLMenuGL& menu, U32 flags) -{  -	menuentry_vec_t items; -	menuentry_vec_t disabled_items; - -	items.push_back(std::string("view_profile")); -	items.push_back(std::string("add_friend")); - -	hide_context_entries(menu, items, disabled_items); -} -  } // namespace LLPanelPeopleMenus diff --git a/indra/newview/llpanelpeoplemenus.h b/indra/newview/llpanelpeoplemenus.h index 5ed20e0064..3bc1f8caf7 100644 --- a/indra/newview/llpanelpeoplemenus.h +++ b/indra/newview/llpanelpeoplemenus.h @@ -62,21 +62,8 @@ protected:  	/*virtual*/ void buildContextMenu(class LLMenuGL& menu, U32 flags);  }; -/** - * Menu used in the suggested friends list. - */ -class SuggestedFriendsContextMenu : public PeopleContextMenu -{ -public: -	/*virtual*/ LLContextMenu * createMenu(); - -protected: -	/*virtual*/ void buildContextMenu(class LLMenuGL& menu, U32 flags); -}; -  extern PeopleContextMenu gPeopleContextMenu;  extern NearbyPeopleContextMenu gNearbyPeopleContextMenu; -extern SuggestedFriendsContextMenu gSuggestedFriendsContextMenu;  } // namespace LLPanelPeopleMenus diff --git a/indra/newview/llpanelplaceprofile.cpp b/indra/newview/llpanelplaceprofile.cpp index 610b3a6396..104316e253 100644 --- a/indra/newview/llpanelplaceprofile.cpp +++ b/indra/newview/llpanelplaceprofile.cpp @@ -563,11 +563,8 @@ void LLPanelPlaceProfile::displaySelectedParcelInfo(LLParcel* parcel,  			mSaleToText->setText(getString("anyone"));  		} -		const U8* sign = (U8*)getString("price_text").c_str(); -		const U8* sqm = (U8*)getString("area_text").c_str(); - -		mSalesPriceText->setText(llformat("%s%d ", sign, parcel->getSalePrice())); -		mAreaText->setText(llformat("%d %s", area, sqm)); +		mSalesPriceText->setText(llformat("%s%d ", getString("price_text").c_str(), parcel->getSalePrice())); +		mAreaText->setText(llformat("%d %s", area, getString("area_text").c_str()));  		mTrafficText->setText(llformat("%.0f", dwell));  		// Can't have more than region max tasks, regardless of parcel @@ -575,10 +572,7 @@ void LLPanelPlaceProfile::displaySelectedParcelInfo(LLParcel* parcel,  		S32 primitives = llmin(ll_round(parcel->getMaxPrimCapacity() * parcel->getParcelPrimBonus()),  							   (S32)region->getMaxTasks()); -		const U8* available = (U8*)getString("available").c_str(); -		const U8* allocated = (U8*)getString("allocated").c_str(); - -		mPrimitivesText->setText(llformat("%d %s, %d %s", primitives, available, parcel->getPrimCount(), allocated)); +		mPrimitivesText->setText(llformat("%d %s, %d %s", primitives, getString("available").c_str(), parcel->getPrimCount(), getString("allocated").c_str()));  		if (parcel->getAllowOtherScripts())  		{ diff --git a/indra/newview/llpanelsnapshotoptions.cpp b/indra/newview/llpanelsnapshotoptions.cpp index 95c14e4226..23747a8efd 100644 --- a/indra/newview/llpanelsnapshotoptions.cpp +++ b/indra/newview/llpanelsnapshotoptions.cpp @@ -32,7 +32,6 @@  #include "llfloatersnapshot.h" // FIXME: create a snapshot model  #include "llfloaterreg.h" -#include "llfloaterfacebook.h"  #include "llfloaterflickr.h"  #include "llfloatertwitter.h" @@ -59,7 +58,6 @@ private:  	void onSaveToEmail();  	void onSaveToInventory();  	void onSaveToComputer(); -	void onSendToFacebook();  	void onSendToTwitter();  	void onSendToFlickr(); @@ -74,7 +72,6 @@ LLPanelSnapshotOptions::LLPanelSnapshotOptions()  	mCommitCallbackRegistrar.add("Snapshot.SaveToEmail",		boost::bind(&LLPanelSnapshotOptions::onSaveToEmail,		this));  	mCommitCallbackRegistrar.add("Snapshot.SaveToInventory",	boost::bind(&LLPanelSnapshotOptions::onSaveToInventory,	this));  	mCommitCallbackRegistrar.add("Snapshot.SaveToComputer",		boost::bind(&LLPanelSnapshotOptions::onSaveToComputer,	this)); -	mCommitCallbackRegistrar.add("Snapshot.SendToFacebook",		boost::bind(&LLPanelSnapshotOptions::onSendToFacebook, this));  	mCommitCallbackRegistrar.add("Snapshot.SendToTwitter",		boost::bind(&LLPanelSnapshotOptions::onSendToTwitter, this));  	mCommitCallbackRegistrar.add("Snapshot.SendToFlickr",		boost::bind(&LLPanelSnapshotOptions::onSendToFlickr, this));  	LLGlobalEconomy::getInstance()->addObserver(this); @@ -138,18 +135,6 @@ void LLPanelSnapshotOptions::onSaveToComputer()  	openPanel("panel_snapshot_local");  } -void LLPanelSnapshotOptions::onSendToFacebook() -{ -	LLFloaterReg::hideInstance("snapshot"); - -	LLFloaterFacebook* facebook_floater = dynamic_cast<LLFloaterFacebook*>(LLFloaterReg::getInstance("facebook")); -	if (facebook_floater) -	{ -		facebook_floater->showPhotoPanel(); -	} -	LLFloaterReg::showInstance("facebook"); -} -  void LLPanelSnapshotOptions::onSendToTwitter()  {  	LLFloaterReg::hideInstance("snapshot"); diff --git a/indra/newview/llpreviewnotecard.cpp b/indra/newview/llpreviewnotecard.cpp index d4a8bbdf45..1533a27469 100644 --- a/indra/newview/llpreviewnotecard.cpp +++ b/indra/newview/llpreviewnotecard.cpp @@ -32,6 +32,7 @@  #include "llagent.h"  #include "lldraghandle.h" +#include "llexternaleditor.h"  #include "llviewerwindow.h"  #include "llbutton.h"  #include "llfloaterreg.h" @@ -43,6 +44,7 @@  #include "roles_constants.h"  #include "llscrollbar.h"  #include "llselectmgr.h" +#include "lltrans.h"  #include "llviewertexteditor.h"  #include "llvfile.h"  #include "llviewerinventory.h" @@ -63,7 +65,8 @@  // Default constructor  LLPreviewNotecard::LLPreviewNotecard(const LLSD& key) //const LLUUID& item_id,  -	: LLPreview( key ) +	: LLPreview( key ), +	mLiveFile(NULL)  {  	const LLInventoryItem *item = getItem();  	if (item) @@ -74,13 +77,14 @@ LLPreviewNotecard::LLPreviewNotecard(const LLSD& key) //const LLUUID& item_id,  LLPreviewNotecard::~LLPreviewNotecard()  { +	delete mLiveFile;  }  BOOL LLPreviewNotecard::postBuild()  { -	LLViewerTextEditor *ed = getChild<LLViewerTextEditor>("Notecard Editor"); -	ed->setNotecardInfo(mItemUUID, mObjectID, getKey()); -	ed->makePristine(); +	mEditor = getChild<LLViewerTextEditor>("Notecard Editor"); +	mEditor->setNotecardInfo(mItemUUID, mObjectID, getKey()); +	mEditor->makePristine();  	childSetAction("Save", onClickSave, this);  	getChildView("lock")->setVisible( FALSE);	 @@ -88,6 +92,8 @@ BOOL LLPreviewNotecard::postBuild()  	childSetAction("Delete", onClickDelete, this);  	getChildView("Delete")->setEnabled(false); +	childSetAction("Edit", onClickEdit, this); +  	const LLInventoryItem* item = getItem();  	childSetCommitCallback("desc", LLPreview::onText, this); @@ -408,6 +414,16 @@ void LLPreviewNotecard::onClickDelete(void* user_data)  	}  } +// static +void LLPreviewNotecard::onClickEdit(void* user_data) +{ +	LLPreviewNotecard* preview = (LLPreviewNotecard*)user_data; +	if (preview) +	{ +		preview->openInExternalEditor(); +	} +} +  struct LLSaveNotecardInfo  {  	LLPreviewNotecard* mSelf; @@ -468,7 +484,7 @@ void LLPreviewNotecard::finishTaskUpload(LLUUID itemId, LLUUID newAssetId, LLUUI      }  } -bool LLPreviewNotecard::saveIfNeeded(LLInventoryItem* copyitem) +bool LLPreviewNotecard::saveIfNeeded(LLInventoryItem* copyitem, bool sync)  {  	LLViewerTextEditor* editor = getChild<LLViewerTextEditor>("Notecard Editor"); @@ -487,7 +503,10 @@ bool LLPreviewNotecard::saveIfNeeded(LLInventoryItem* copyitem)  		}  		editor->makePristine(); - +		if (sync) +		{ +			syncExternal(); +		}  		const LLInventoryItem* item = getItem();  		// save it out to database          if (item) @@ -566,6 +585,18 @@ bool LLPreviewNotecard::saveIfNeeded(LLInventoryItem* copyitem)  	return true;  } +void LLPreviewNotecard::syncExternal() +{ +	// Sync with external editor. +	std::string tmp_file = getTmpFileName(); +	llstat s; +	if (LLFile::stat(tmp_file, &s) == 0) // file exists +	{ +		if (mLiveFile) mLiveFile->ignoreNextUpdate(); +		writeToFile(tmp_file); +	} +} +  void LLPreviewNotecard::deleteNotecard()  {  	LLNotificationsUtil::add("DeleteNotecard", LLSD(), LLSD(), boost::bind(&LLPreviewNotecard::handleConfirmDeleteDialog,this, _1, _2)); @@ -714,4 +745,128 @@ bool LLPreviewNotecard::handleConfirmDeleteDialog(const LLSD& notification, cons  	return false;  } +void LLPreviewNotecard::openInExternalEditor() +{ +    delete mLiveFile; // deletes file + +    // Save the notecard to a temporary file. +    std::string filename = getTmpFileName(); +    writeToFile(filename); + +    // Start watching file changes. +    mLiveFile = new LLLiveLSLFile(filename, boost::bind(&LLPreviewNotecard::onExternalChange, this, _1)); +    mLiveFile->addToEventTimer(); + +    // Open it in external editor. +    { +        LLExternalEditor ed; +        LLExternalEditor::EErrorCode status; +        std::string msg; + +        status = ed.setCommand("LL_SCRIPT_EDITOR"); +        if (status != LLExternalEditor::EC_SUCCESS) +        { +            if (status == LLExternalEditor::EC_NOT_SPECIFIED) // Use custom message for this error. +            { +                msg = LLTrans::getString("ExternalEditorNotSet"); +            } +            else +            { +                msg = LLExternalEditor::getErrorMessage(status); +            } + +            LLNotificationsUtil::add("GenericAlert", LLSD().with("MESSAGE", msg)); +            return; +        } + +        status = ed.run(filename); +        if (status != LLExternalEditor::EC_SUCCESS) +        { +            msg = LLExternalEditor::getErrorMessage(status); +            LLNotificationsUtil::add("GenericAlert", LLSD().with("MESSAGE", msg)); +        } +    } +} + +bool LLPreviewNotecard::onExternalChange(const std::string& filename) +{ +    if (!loadNotecardText(filename)) +    { +        return false; +    } + +    // Disable sync to avoid recursive load->save->load calls. +    saveIfNeeded(NULL, false); +    return true; +} + +bool LLPreviewNotecard::loadNotecardText(const std::string& filename) +{ +    if (filename.empty()) +    { +        LL_WARNS() << "Empty file name" << LL_ENDL; +        return false; +    } + +    LLFILE* file = LLFile::fopen(filename, "rb");		/*Flawfinder: ignore*/ +    if (!file) +    { +        LL_WARNS() << "Error opening " << filename << LL_ENDL; +        return false; +    } + +    // read in the whole file +    fseek(file, 0L, SEEK_END); +    size_t file_length = (size_t)ftell(file); +    fseek(file, 0L, SEEK_SET); +    char* buffer = new char[file_length + 1]; +    size_t nread = fread(buffer, 1, file_length, file); +    if (nread < file_length) +    { +        LL_WARNS() << "Short read" << LL_ENDL; +    } +    buffer[nread] = '\0'; +    fclose(file); + +    mEditor->setText(LLStringExplicit(buffer)); +    delete[] buffer; + +    return true; +} + +bool LLPreviewNotecard::writeToFile(const std::string& filename) +{ +    LLFILE* fp = LLFile::fopen(filename, "wb"); +    if (!fp) +    { +        LL_WARNS() << "Unable to write to " << filename << LL_ENDL; +        return false; +    } + +    std::string utf8text = mEditor->getText(); + +    if (utf8text.size() == 0) +    { +        utf8text = " "; +    } + +    fputs(utf8text.c_str(), fp); +    fclose(fp); +    return true; +} + + +std::string LLPreviewNotecard::getTmpFileName() +{ +    std::string notecard_id = mObjectID.asString() + "_" + mItemUUID.asString(); + +    // Use MD5 sum to make the file name shorter and not exceed maximum path length. +    char notecard_id_hash_str[33];			   /* Flawfinder: ignore */ +    LLMD5 notecard_id_hash((const U8 *)notecard_id.c_str()); +    notecard_id_hash.hex_digest(notecard_id_hash_str); + +    return std::string(LLFile::tmpdir()) + "sl_notecard_" + notecard_id_hash_str + ".txt"; +} + +  // EOF diff --git a/indra/newview/llpreviewnotecard.h b/indra/newview/llpreviewnotecard.h index 46a6d0ef50..d9c14815c1 100644 --- a/indra/newview/llpreviewnotecard.h +++ b/indra/newview/llpreviewnotecard.h @@ -29,6 +29,7 @@  #include "llpreview.h"  #include "llassetstorage.h" +#include "llpreviewscript.h"  #include "lliconctrl.h"  //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ @@ -47,18 +48,18 @@ public:  	virtual ~LLPreviewNotecard();  	bool saveItem(); -	void setObjectID(const LLUUID& object_id); +	void setObjectID(const LLUUID& object_id) override;  	// llview -	virtual void draw(); -	virtual BOOL handleKeyHere(KEY key, MASK mask); -	virtual void setEnabled( BOOL enabled ); +	void draw() override; +	BOOL handleKeyHere(KEY key, MASK mask) override; +	void setEnabled( BOOL enabled ) override;  	// llfloater -	virtual BOOL canClose(); +	BOOL canClose() override;  	// llpanel -	virtual BOOL postBuild(); +	BOOL postBuild() override;  	// reach into the text editor, and grab the drag item  	const LLInventoryItem* getDragItem(); @@ -72,11 +73,13 @@ public:  	// asset system. :(  	void refreshFromInventory(const LLUUID& item_id = LLUUID::null); +	void syncExternal(); +  protected: -	void updateTitleButtons(); -	virtual void loadAsset(); -	bool saveIfNeeded(LLInventoryItem* copyitem = NULL); +	void updateTitleButtons() override; +	void loadAsset() override; +	bool saveIfNeeded(LLInventoryItem* copyitem = NULL, bool sync = true);  	void deleteNotecard(); @@ -89,6 +92,8 @@ protected:  	static void onClickDelete(void* data); +	static void onClickEdit(void* data); +  	static void onSaveComplete(const LLUUID& asset_uuid,  							   void* user_data,  							   S32 status, LLExtStat ext_status); @@ -99,6 +104,12 @@ protected:      static void finishInventoryUpload(LLUUID itemId, LLUUID newAssetId, LLUUID newItemId);      static void finishTaskUpload(LLUUID itemId, LLUUID newAssetId, LLUUID taskId); +    void openInExternalEditor(); +    bool onExternalChange(const std::string& filename); +    bool loadNotecardText(const std::string& filename); +    bool writeToFile(const std::string& filename); +    std::string getTmpFileName(); +  protected:  	LLViewerTextEditor* mEditor;  	LLButton* mSaveBtn; @@ -106,6 +117,8 @@ protected:  	LLUUID mAssetID;  	LLUUID mObjectID; + +	LLLiveLSLFile* mLiveFile;  }; diff --git a/indra/newview/llpreviewscript.cpp b/indra/newview/llpreviewscript.cpp index 60099b08b7..d177384b5a 100644 --- a/indra/newview/llpreviewscript.cpp +++ b/indra/newview/llpreviewscript.cpp @@ -41,7 +41,6 @@  #include "llinventorymodel.h"  #include "llkeyboard.h"  #include "lllineeditor.h" -#include "lllivefile.h"  #include "llhelp.h"  #include "llnotificationsutil.h"  #include "llresmgr.h" @@ -120,22 +119,6 @@ static bool have_script_upload_cap(LLUUID& object_id)  /// ---------------------------------------------------------------------------  /// LLLiveLSLFile  /// --------------------------------------------------------------------------- -class LLLiveLSLFile : public LLLiveFile -{ -public: -	typedef boost::function<bool (const std::string& filename)> change_callback_t; - -	LLLiveLSLFile(std::string file_path, change_callback_t change_cb); -	~LLLiveLSLFile(); - -	void ignoreNextUpdate() { mIgnoreNextUpdate = true; } - -protected: -	/*virtual*/ bool loadFile(); - -	change_callback_t	mOnChangeCallback; -	bool				mIgnoreNextUpdate; -};  LLLiveLSLFile::LLLiveLSLFile(std::string file_path, change_callback_t change_cb)  :	mOnChangeCallback(change_cb) @@ -1069,7 +1052,7 @@ void LLScriptEdCore::openInExternalEditor()  		{  			if (status == LLExternalEditor::EC_NOT_SPECIFIED) // Use custom message for this error.  			{ -				msg = getString("external_editor_not_set"); +				msg = LLTrans::getString("ExternalEditorNotSet");  			}  			else  			{ diff --git a/indra/newview/llpreviewscript.h b/indra/newview/llpreviewscript.h index 69cf9d9158..74e4c00d43 100644 --- a/indra/newview/llpreviewscript.h +++ b/indra/newview/llpreviewscript.h @@ -34,6 +34,7 @@  #include "lliconctrl.h"  #include "llframetimer.h"  #include "llfloatergotoline.h" +#include "lllivefile.h"  #include "llsyntaxid.h"  class LLLiveLSLFile; @@ -53,6 +54,23 @@ class LLScriptEdContainer;  class LLFloaterGotoLine;  class LLFloaterExperienceProfile; +class LLLiveLSLFile : public LLLiveFile +{ +public: +    typedef boost::function<bool(const std::string& filename)> change_callback_t; + +    LLLiveLSLFile(std::string file_path, change_callback_t change_cb); +    ~LLLiveLSLFile(); + +    void ignoreNextUpdate() { mIgnoreNextUpdate = true; } + +protected: +    /*virtual*/ bool loadFile(); + +    change_callback_t	mOnChangeCallback; +    bool				mIgnoreNextUpdate; +}; +  // Inner, implementation class.  LLPreviewScript and LLLiveLSLEditor each own one of these.  class LLScriptEdCore : public LLPanel  { diff --git a/indra/newview/llsearchableui.cpp b/indra/newview/llsearchableui.cpp index de90896548..93143eb33f 100644 --- a/indra/newview/llsearchableui.cpp +++ b/indra/newview/llsearchableui.cpp @@ -125,17 +125,13 @@ void ll::statusbar::SearchableItem::setNotHighlighted( )  	}  } -bool ll::statusbar::SearchableItem::hightlightAndHide( LLWString const &aFilter ) +bool ll::statusbar::SearchableItem::hightlightAndHide(LLWString const &aFilter, bool hide)  { -	if( mMenu && !mMenu->getVisible() && !mWasHiddenBySearch ) +	if ((mMenu && !mMenu->getVisible() && !mWasHiddenBySearch) || dynamic_cast<LLMenuItemTearOffGL*>(mMenu))  		return false;  	setNotHighlighted( ); -	bool bVisible(false); -	for( tSearchableItemList::iterator itr = mChildren.begin(); itr  != mChildren.end(); ++itr ) -		bVisible |= (*itr)->hightlightAndHide( aFilter ); -  	if( aFilter.empty() )  	{  		if( mCtrl ) @@ -143,17 +139,22 @@ bool ll::statusbar::SearchableItem::hightlightAndHide( LLWString const &aFilter  		return true;  	} +	bool bHighlighted(!hide);  	if( mLabel.find( aFilter ) != LLWString::npos )  	{  		if( mCtrl )  			mCtrl->setHighlighted( true ); -		return true; +		bHighlighted = true;  	} -	if( mCtrl && !bVisible ) +	bool bVisible(false); +	for (tSearchableItemList::iterator itr = mChildren.begin(); itr != mChildren.end(); ++itr) +		bVisible |= (*itr)->hightlightAndHide(aFilter, !bHighlighted); + +	if (mCtrl && !bVisible && !bHighlighted)  	{  		mWasHiddenBySearch = true;  		mMenu->setVisible(FALSE);  	} -	return bVisible; +	return bVisible || bHighlighted;  } diff --git a/indra/newview/llsearchableui.h b/indra/newview/llsearchableui.h index 42b2866fb6..9741557e49 100644 --- a/indra/newview/llsearchableui.h +++ b/indra/newview/llsearchableui.h @@ -107,7 +107,7 @@ namespace ll  			SearchableItem();  			void setNotHighlighted( ); -			bool hightlightAndHide( LLWString const &aFilter ); +			bool hightlightAndHide( LLWString const &aFilter, bool hide = true );  		};  		struct SearchData diff --git a/indra/newview/llselectmgr.cpp b/indra/newview/llselectmgr.cpp index 816515426a..90f8f84ea4 100644 --- a/indra/newview/llselectmgr.cpp +++ b/indra/newview/llselectmgr.cpp @@ -3864,6 +3864,14 @@ BOOL LLSelectMgr::selectGetAggregateTexturePermissions(LLAggregatePermissions& r  	return TRUE;  } +BOOL LLSelectMgr::isSelfAvatarSelected() +{ +	if (mAllowSelectAvatar) +	{ +		return (getSelection()->getObjectCount() == 1) && (getSelection()->getFirstRootObject() == gAgentAvatarp); +	} +	return FALSE; +}  //--------------------------------------------------------------------  // Duplicate objects @@ -3886,6 +3894,17 @@ void LLSelectMgr::selectDuplicate(const LLVector3& offset, BOOL select_copy)  		make_ui_sound("UISndInvalidOp");  		return;  	} +	if (!canDuplicate()) +	{ +		LLSelectNode* node = getSelection()->getFirstRootNode(NULL, true); +		if (node) +		{ +			LLSD args; +			args["OBJ_NAME"] = node->mName; +			LLNotificationsUtil::add("NoCopyPermsNoObject", args); +			return; +		} +	}  	LLDuplicateData	data;  	data.offset = offset; @@ -6765,8 +6784,28 @@ void LLSelectMgr::pauseAssociatedAvatars()          mSelectedObjects->mSelectType = getSelectTypeForObject(object); +        bool is_attached = false;          if (mSelectedObjects->mSelectType == SELECT_TYPE_ATTACHMENT &&  -            isAgentAvatarValid() && object->getParent() != NULL) +            isAgentAvatarValid()) +        { +            // Selection can be obsolete, confirm that this is an attachment +            LLViewerObject* parent = (LLViewerObject*)object->getParent(); +            while (parent != NULL) +            { +                if (parent->isAvatar()) +                { +                    is_attached = true; +                    break; +                } +                else +                { +                    parent = (LLViewerObject*)parent->getParent(); +                } +            } +        } + + +        if (is_attached)          {              if (object->isAnimatedObject())              { @@ -6784,14 +6823,12 @@ void LLSelectMgr::pauseAssociatedAvatars()                  mPauseRequests.push_back(gAgentAvatarp->requestPause());              }          } -        else +        else if (object && object->isAnimatedObject() && object->getControlAvatar())          { -            if (object && object->isAnimatedObject() && object->getControlAvatar()) -            { -                // Is a non-attached animated object. Pause the control avatar. -                mPauseRequests.push_back(object->getControlAvatar()->requestPause()); -            } +            // Is a non-attached animated object. Pause the control avatar. +            mPauseRequests.push_back(object->getControlAvatar()->requestPause());          } +      }  } diff --git a/indra/newview/llselectmgr.h b/indra/newview/llselectmgr.h index ce0fee8803..3e8bfdb00e 100644 --- a/indra/newview/llselectmgr.h +++ b/indra/newview/llselectmgr.h @@ -714,6 +714,8 @@ public:  	LLPermissions* findObjectPermissions(const LLViewerObject* object); +	BOOL isSelfAvatarSelected(); +  	void selectDelete();							// Delete on simulator  	void selectForceDelete();			// just delete, no into trash  	void selectDuplicate(const LLVector3& offset, BOOL select_copy);	// Duplicate on simulator diff --git a/indra/newview/llsidepanelinventory.cpp b/indra/newview/llsidepanelinventory.cpp index 689734e36a..ea7e649792 100644 --- a/indra/newview/llsidepanelinventory.cpp +++ b/indra/newview/llsidepanelinventory.cpp @@ -564,6 +564,7 @@ void LLSidepanelInventory::updateVerbs()  	mWearBtn->setEnabled(FALSE);  	mPlayBtn->setVisible(FALSE);  	mPlayBtn->setEnabled(FALSE); +	mPlayBtn->setToolTip(std::string(""));   	mTeleportBtn->setVisible(FALSE);   	mTeleportBtn->setEnabled(FALSE);   	mShopBtn->setVisible(TRUE); @@ -588,11 +589,23 @@ void LLSidepanelInventory::updateVerbs()  		 	mShopBtn->setVisible(FALSE);  			break;  		case LLInventoryType::IT_SOUND: +			mPlayBtn->setVisible(TRUE); +			mPlayBtn->setEnabled(TRUE); +			mPlayBtn->setToolTip(LLTrans::getString("InventoryPlaySoundTooltip")); +			mShopBtn->setVisible(FALSE); +			break;  		case LLInventoryType::IT_GESTURE: +			mPlayBtn->setVisible(TRUE); +			mPlayBtn->setEnabled(TRUE); +			mPlayBtn->setToolTip(LLTrans::getString("InventoryPlayGestureTooltip")); +			mShopBtn->setVisible(FALSE); +			break;  		case LLInventoryType::IT_ANIMATION:  			mPlayBtn->setVisible(TRUE);  			mPlayBtn->setEnabled(TRUE); -		 	mShopBtn->setVisible(FALSE); +			mPlayBtn->setEnabled(TRUE); +			mPlayBtn->setToolTip(LLTrans::getString("InventoryPlayAnimationTooltip")); +			mShopBtn->setVisible(FALSE);  			break;  		case LLInventoryType::IT_LANDMARK:  			mTeleportBtn->setVisible(TRUE); diff --git a/indra/newview/llsnapshotlivepreview.cpp b/indra/newview/llsnapshotlivepreview.cpp index 5a40af14a3..f5fea9dece 100644 --- a/indra/newview/llsnapshotlivepreview.cpp +++ b/indra/newview/llsnapshotlivepreview.cpp @@ -34,7 +34,6 @@  #include "lleconomy.h"  #include "llfloaterperms.h"  #include "llfloaterreg.h" -#include "llfloaterfacebook.h"  #include "llfloaterflickr.h"  #include "llfloatertwitter.h"  #include "llimagefilter.h" @@ -572,7 +571,7 @@ void LLSnapshotLivePreview::generateThumbnailImage(BOOL force_update)      if (mThumbnailSubsampled)      { -        // The thumbnail is be a subsampled version of the preview (used in SL Share previews, i.e. Flickr, Twitter, Facebook) +        // The thumbnail is be a subsampled version of the preview (used in SL Share previews, i.e. Flickr, Twitter)  		raw->resize( mPreviewImage->getWidth(),                       mPreviewImage->getHeight(),                       mPreviewImage->getComponents()); @@ -638,7 +637,7 @@ LLViewerTexture* LLSnapshotLivePreview::getBigThumbnailImage()  	if (raw)  	{ -        // The big thumbnail is a new filtered version of the preview (used in SL Share previews, i.e. Flickr, Twitter, Facebook) +        // The big thumbnail is a new filtered version of the preview (used in SL Share previews, i.e. Flickr, Twitter)          mBigThumbnailWidth = mPreviewImage->getWidth();          mBigThumbnailHeight = mPreviewImage->getHeight();          raw->resize( mBigThumbnailWidth, diff --git a/indra/newview/llsurfacepatch.cpp b/indra/newview/llsurfacepatch.cpp index d28a7cc048..f6cf714db4 100644 --- a/indra/newview/llsurfacepatch.cpp +++ b/indra/newview/llsurfacepatch.cpp @@ -99,7 +99,7 @@ void LLSurfacePatch::dirty()  	}  	else  	{ -		LL_WARNS() << "No viewer object for this surface patch!" << LL_ENDL; +		LL_WARNS("Terrain") << "No viewer object for this surface patch!" << LL_ENDL;  	}  	mDirtyZStats = TRUE; diff --git a/indra/newview/lltexturefetch.cpp b/indra/newview/lltexturefetch.cpp index c9133338fb..f6cb787156 100644 --- a/indra/newview/lltexturefetch.cpp +++ b/indra/newview/lltexturefetch.cpp @@ -66,6 +66,7 @@ bool LLTextureFetchDebugger::sDebuggerEnabled = false ;  LLTrace::CountStatHandle<F64> LLTextureFetch::sCacheHit("texture_cache_hit");  LLTrace::CountStatHandle<F64> LLTextureFetch::sCacheAttempt("texture_cache_attempt"); +LLTrace::EventStatHandle<LLUnit<F32, LLUnits::Percent> > LLTextureFetch::sCacheHitRate("texture_cache_hits");  LLTrace::SampleStatHandle<F32Seconds> LLTextureFetch::sCacheReadLatency("texture_cache_read_latency");  LLTrace::SampleStatHandle<F32Seconds> LLTextureFetch::sTexDecodeLatency("texture_decode_latency"); @@ -1311,6 +1312,7 @@ bool LLTextureFetchWorker::doWork(S32 param)  			LL_DEBUGS(LOG_TXT) << mID << ": Cached. Bytes: " << mFormattedImage->getDataSize()  							   << " Size: " << llformat("%dx%d",mFormattedImage->getWidth(),mFormattedImage->getHeight())  							   << " Desired Discard: " << mDesiredDiscard << " Desired Size: " << mDesiredSize << LL_ENDL; +			record(LLTextureFetch::sCacheHitRate, LLUnits::Ratio::fromValue(1));  		}  		else  		{ @@ -1326,7 +1328,7 @@ bool LLTextureFetchWorker::doWork(S32 param)  				LL_DEBUGS(LOG_TXT) << mID << ": Not in Cache" << LL_ENDL;  				setState(LOAD_FROM_NETWORK);  			} -			 +			record(LLTextureFetch::sCacheHitRate, LLUnits::Ratio::fromValue(0));  			// fall through  		}  	} diff --git a/indra/newview/lltexturefetch.h b/indra/newview/lltexturefetch.h index a01c01847e..cdf8868597 100644 --- a/indra/newview/lltexturefetch.h +++ b/indra/newview/lltexturefetch.h @@ -312,6 +312,7 @@ public:      static LLTrace::SampleStatHandle<F32Seconds> sCacheReadLatency;      static LLTrace::SampleStatHandle<F32Seconds> sTexDecodeLatency;      static LLTrace::SampleStatHandle<F32Seconds> sTexFetchLatency; +    static LLTrace::EventStatHandle<LLUnit<F32, LLUnits::Percent> > sCacheHitRate;  private:  	LLMutex mQueueMutex;        //to protect mRequestMap and mCommands only diff --git a/indra/newview/lltoolcomp.cpp b/indra/newview/lltoolcomp.cpp index 392c103d7c..f9c327b46e 100644 --- a/indra/newview/lltoolcomp.cpp +++ b/indra/newview/lltoolcomp.cpp @@ -267,7 +267,7 @@ BOOL LLToolCompTranslate::handleHover(S32 x, S32 y, MASK mask)  BOOL LLToolCompTranslate::handleMouseDown(S32 x, S32 y, MASK mask)  {  	mMouseDown = TRUE; -	gViewerWindow->pickAsync(x, y, mask, pickCallback, /*BOOL pick_transparent*/ TRUE); +	gViewerWindow->pickAsync(x, y, mask, pickCallback, /*BOOL pick_transparent*/ TRUE, LLFloaterReg::instanceVisible("build"));  	return TRUE;  } diff --git a/indra/newview/lltoolpie.cpp b/indra/newview/lltoolpie.cpp index 276d24e9ed..54df5198c8 100644 --- a/indra/newview/lltoolpie.cpp +++ b/indra/newview/lltoolpie.cpp @@ -111,9 +111,64 @@ BOOL LLToolPie::handleMouseDown(S32 x, S32 y, MASK mask)      mMouseOutsideSlop = FALSE;  	mMouseDownX = x;  	mMouseDownY = y; +	LLTimer pick_timer; +	BOOL pick_rigged = false; //gSavedSettings.getBOOL("AnimatedObjectsAllowLeftClick"); +	LLPickInfo transparent_pick = gViewerWindow->pickImmediate(x, y, TRUE /*includes transparent*/, pick_rigged); +	LLPickInfo visible_pick = gViewerWindow->pickImmediate(x, y, FALSE, pick_rigged); +	LLViewerObject *transp_object = transparent_pick.getObject(); +	LLViewerObject *visible_object = visible_pick.getObject(); + +	// Current set of priorities +	// 1. Transparent attachment pick +	// 2. Transparent actionable pick +	// 3. Visible attachment pick (e.x we click on attachment under invisible floor) +	// 4. Visible actionable pick +	// 5. Transparent pick (e.x. movement on transparent object/floor, our default pick) +	// left mouse down always picks transparent (but see handleMouseUp). +	// Also see LLToolPie::handleHover() - priorities are a bit different there. +	// Todo: we need a more consistent set of rules to work with +	if (transp_object == visible_object || !visible_object) +	{ +		// Note: if transparent object is null, then visible object is also null +		// since transparent pick includes non-tranpsarent one. +		// !transparent_object check will be covered by transparent_object == visible_object. +		mPick = transparent_pick; +	} +	else +	{ +		// Select between two non-null picks +		LLViewerObject *transp_parent = transp_object->getRootEdit(); +		LLViewerObject *visible_parent = visible_object->getRootEdit(); +		if (transp_object->isAttachment()) +		{ +			// 1. Transparent attachment +			mPick = transparent_pick; +		} +		else if (transp_object->getClickAction() != CLICK_ACTION_DISABLED +				 && (useClickAction(mask, transp_object, transp_parent) || transp_object->flagHandleTouch() || (transp_parent && transp_parent->flagHandleTouch()))) +		{ +			// 2. Transparent actionable pick +			mPick = transparent_pick; +		} +		else if (visible_object->isAttachment()) +		{ +			// 3. Visible attachment pick +			mPick = visible_pick; +		} +		else if (visible_object->getClickAction() != CLICK_ACTION_DISABLED +				 && (useClickAction(mask, visible_object, visible_parent) || visible_object->flagHandleTouch() || (visible_parent && visible_parent->flagHandleTouch()))) +		{ +			// 4. Visible actionable pick +			mPick = visible_pick; +		} +		else +		{ +			// 5. Default: transparent +			mPick = transparent_pick; +		} +	} +	LL_INFOS() << "pick_rigged is " << (S32) pick_rigged << " pick time elapsed " << pick_timer.getElapsedTimeF32() << LL_ENDL; -	//left mouse down always picks transparent (but see handleMouseUp) -	mPick = gViewerWindow->pickImmediate(x, y, TRUE, FALSE);  	mPick.mKeyMask = mask;  	mMouseButtonDown = true; diff --git a/indra/newview/lltranslate.cpp b/indra/newview/lltranslate.cpp index 1936e24761..e424983cf8 100644 --- a/indra/newview/lltranslate.cpp +++ b/indra/newview/lltranslate.cpp @@ -38,8 +38,12 @@  #include "llcoros.h"  #include "reader.h"  #include "llcorehttputil.h" +#include "llurlregistry.h" +static const std::string BING_NOTRANSLATE_OPENING_TAG("<div class=\"notranslate\">"); +static const std::string BING_NOTRANSLATE_CLOSING_TAG("</div>"); +  /**  * Handler of an HTTP machine translation service.  * @@ -99,6 +103,8 @@ public:      */      virtual bool isConfigured() const = 0; +    virtual LLTranslate::EService getCurrentService() = 0; +      virtual void verifyKey(const std::string &key, LLTranslate::KeyVerificationResult_fn fnc) = 0;      virtual void translateMessage(LanguagePair_t fromTo, std::string msg, LLTranslate::TranslationSuccess_fn success, LLTranslate::TranslationFailure_fn failure); @@ -248,6 +254,8 @@ public:          std::string& err_msg) const;      /*virtual*/ bool isConfigured() const; +    /*virtual*/ LLTranslate::EService getCurrentService() { return LLTranslate::EService::SERVICE_GOOGLE; } +      /*virtual*/ void verifyKey(const std::string &key, LLTranslate::KeyVerificationResult_fn fnc);  private: @@ -409,6 +417,8 @@ public:          std::string& err_msg) const;      /*virtual*/ bool isConfigured() const; +    /*virtual*/ LLTranslate::EService getCurrentService() { return LLTranslate::EService::SERVICE_BING; } +      /*virtual*/ void verifyKey(const std::string &key, LLTranslate::KeyVerificationResult_fn fnc);  private:      static std::string getAPIKey(); @@ -520,7 +530,59 @@ void LLTranslate::translateMessage(const std::string &from_lang, const std::stri  {      LLTranslationAPIHandler& handler = getPreferredHandler(); -    handler.translateMessage(LLTranslationAPIHandler::LanguagePair_t(from_lang, to_lang), mesg, success, failure); +    handler.translateMessage(LLTranslationAPIHandler::LanguagePair_t(from_lang, to_lang), addNoTranslateTags(mesg), success, failure); +} + +std::string LLTranslate::addNoTranslateTags(std::string mesg) +{ +    if (getPreferredHandler().getCurrentService() != SERVICE_BING) +    { +        return mesg; +    } + +    std::string upd_msg(mesg); +    LLUrlMatch match; +    S32 dif = 0; +    //surround all links (including SLURLs) with 'no-translate' tags to prevent unnecessary translation +    while (LLUrlRegistry::instance().findUrl(mesg, match)) +    { +        upd_msg.insert(dif + match.getStart(), BING_NOTRANSLATE_OPENING_TAG); +        upd_msg.insert(dif + BING_NOTRANSLATE_OPENING_TAG.size() + match.getEnd() + 1, BING_NOTRANSLATE_CLOSING_TAG); +        mesg.erase(match.getStart(), match.getEnd() - match.getStart()); +        dif += match.getEnd() - match.getStart() + BING_NOTRANSLATE_OPENING_TAG.size() + BING_NOTRANSLATE_CLOSING_TAG.size(); +    } +    return upd_msg; +} + +std::string LLTranslate::removeNoTranslateTags(std::string mesg) +{ +    if (getPreferredHandler().getCurrentService() != SERVICE_BING) +    { +        return mesg; +    } +    std::string upd_msg(mesg); +    LLUrlMatch match; +    S32 opening_tag_size = BING_NOTRANSLATE_OPENING_TAG.size(); +    S32 closing_tag_size = BING_NOTRANSLATE_CLOSING_TAG.size(); +    S32 dif = 0; +    //remove 'no-translate' tags we added to the links before +    while (LLUrlRegistry::instance().findUrl(mesg, match)) +    { +        if (upd_msg.substr(dif + match.getStart() - opening_tag_size, opening_tag_size) == BING_NOTRANSLATE_OPENING_TAG) +        { +            upd_msg.erase(dif + match.getStart() - opening_tag_size, opening_tag_size); +            dif -= opening_tag_size; + +            if (upd_msg.substr(dif + match.getEnd() + 1, closing_tag_size) == BING_NOTRANSLATE_CLOSING_TAG) +            { +                upd_msg.replace(dif + match.getEnd() + 1, closing_tag_size, " "); +                dif -= closing_tag_size - 1; +            } +        } +        mesg.erase(match.getStart(), match.getUrl().size()); +        dif += match.getUrl().size(); +    } +    return upd_msg;  }  /*static*/ diff --git a/indra/newview/lltranslate.h b/indra/newview/lltranslate.h index bf431cdfbb..e0722fbd83 100644 --- a/indra/newview/lltranslate.h +++ b/indra/newview/lltranslate.h @@ -91,6 +91,9 @@ public :  	 */  	static bool isTranslationConfigured(); +    static std::string addNoTranslateTags(std::string mesg); +    static std::string removeNoTranslateTags(std::string mesg); +  private:  	static LLTranslationAPIHandler& getPreferredHandler();  	static LLTranslationAPIHandler& getHandler(EService service); diff --git a/indra/newview/lltwitterconnect.cpp b/indra/newview/lltwitterconnect.cpp index 5d598aaebe..b2d2fa9d77 100644 --- a/indra/newview/lltwitterconnect.cpp +++ b/indra/newview/lltwitterconnect.cpp @@ -28,6 +28,7 @@  #include "llviewerprecompiledheaders.h"  #include "lltwitterconnect.h" +#include "llflickrconnect.h"  #include "llagent.h"  #include "llcallingcard.h"			// for LLAvatarTracker @@ -65,6 +66,49 @@ void toast_user_for_twitter_success()      LLNotificationsUtil::add("TwitterConnect", args);  } +class LLTwitterConnectHandler : public LLCommandHandler +{ +public: +    LLTwitterConnectHandler() : LLCommandHandler("fbc", UNTRUSTED_THROTTLE) {} + +    bool handle(const LLSD& tokens, const LLSD& query_map, LLMediaCtrl* web) +    { +        if (tokens.size() >= 1) +        { +            if (tokens[0].asString() == "connect") +            { +                if (tokens.size() >= 2 && tokens[1].asString() == "twitter") +                { +                    // this command probably came from the twitter_web browser, so close it +                    LLFloaterReg::hideInstance("twitter_web"); + +                    // connect to twitter +                    if (query_map.has("oauth_token")) +                    { +                        LLTwitterConnect::instance().connectToTwitter(query_map["oauth_token"], query_map.get("oauth_verifier")); +                    } +                    return true; +                } +                else if (tokens.size() >= 2 && tokens[1].asString() == "flickr") +                { +                    // this command probably came from the flickr_web browser, so close it +                    LLFloaterReg::hideInstance("flickr_web"); + +                    // connect to flickr +                    if (query_map.has("oauth_token")) +                    { +                        LLFlickrConnect::instance().connectToFlickr(query_map["oauth_token"], query_map.get("oauth_verifier")); +                    } +                    return true; +                } +            } +        } +        return false; +    } +}; +LLTwitterConnectHandler gTwitterConnectHandler; + +  ///////////////////////////////////////////////////////////////////////////////  //  void LLTwitterConnect::twitterConnectCoro(std::string requestToken, std::string oauthVerifier) diff --git a/indra/newview/llurldispatcher.cpp b/indra/newview/llurldispatcher.cpp index 794326e752..a1670351f4 100644 --- a/indra/newview/llurldispatcher.cpp +++ b/indra/newview/llurldispatcher.cpp @@ -47,6 +47,7 @@  // library includes  #include "llnotificationsutil.h"  #include "llsd.h" +#include "stringize.h"  static LLURLDispatcherListener sURLDispatcherListener; @@ -255,14 +256,23 @@ void LLURLDispatcherImpl::regionHandleCallback(U64 region_handle, const LLSLURL&  // Teleportation links are handled here because they are tightly coupled  // to SLURL parsing and sim-fragment parsing -class LLTeleportHandler : public LLCommandHandler +class LLTeleportHandler : public LLCommandHandler, public LLEventAPI  {  public:  	// Teleport requests *must* come from a trusted browser  	// inside the app, otherwise a malicious web page could  	// cause a constant teleport loop.  JC -	LLTeleportHandler() : LLCommandHandler("teleport", UNTRUSTED_THROTTLE) { } - +	LLTeleportHandler() : +		LLCommandHandler("teleport", UNTRUSTED_THROTTLE), +		LLEventAPI("LLTeleportHandler", "Low-level teleport API") +	{ +		LLEventAPI::add("teleport", +						"Teleport to specified [\"regionname\"] at\n" +						"specified region-relative [\"x\"], [\"y\"], [\"z\"].\n" +						"If [\"regionname\"] omitted, teleport to GLOBAL\n" +						"coordinates [\"x\"], [\"y\"], [\"z\"].", +						&LLTeleportHandler::from_event); +	}  	bool handle(const LLSD& tokens, const LLSD& query_map,  				LLMediaCtrl* web) @@ -293,6 +303,41 @@ public:  		return true;  	} +	void from_event(const LLSD& params) const +	{ +		Response response(LLSD(), params); +		if (params.has("regionname")) +		{ +			// region specified, coordinates (if any) are region-local +			LLVector3 local_pos( +				params.has("x")? params["x"].asReal() : 128, +				params.has("y")? params["y"].asReal() : 128, +				params.has("z")? params["z"].asReal() : 0); +			std::string regionname(params["regionname"]); +			std::string destination(LLSLURL(regionname, local_pos).getSLURLString()); +			// have to resolve region's global coordinates first +			teleport_via_slapp(regionname, destination); +			response["message"] = "Teleporting to " + destination; +		} +		else                        // no regionname +		{ +			// coordinates are global, and at least (x, y) are required +			if (! (params.has("x") && params.has("y"))) +			{ +				return response.error("Specify either regionname or global (x, y)"); +			} +			LLVector3d global_pos(params["x"].asReal(), params["y"].asReal(), +								  params["z"].asReal()); +			gAgent.teleportViaLocation(global_pos); +			LLFloaterWorldMap* instance = LLFloaterWorldMap::getInstance(); +			if (instance) +			{ +				instance->trackLocation(global_pos); +			} +			response["message"] = STRINGIZE("Teleporting to global " << global_pos); +		} +	} +  	static void teleport_via_slapp(std::string region_name, std::string callback_url)  	{ diff --git a/indra/newview/llviewerdisplay.cpp b/indra/newview/llviewerdisplay.cpp index e1409d31ce..3bbf3ace92 100644 --- a/indra/newview/llviewerdisplay.cpp +++ b/indra/newview/llviewerdisplay.cpp @@ -237,6 +237,7 @@ void display_stats()  static LLTrace::BlockTimerStatHandle FTM_PICK("Picking");  static LLTrace::BlockTimerStatHandle FTM_RENDER("Render"); +static LLTrace::BlockTimerStatHandle FTM_RENDER_HUD("Render HUD");  static LLTrace::BlockTimerStatHandle FTM_UPDATE_SKY("Update Sky");  static LLTrace::BlockTimerStatHandle FTM_UPDATE_DYNAMIC_TEXTURES("Update Dynamic Textures");  static LLTrace::BlockTimerStatHandle FTM_IMAGE_UPDATE("Update Images"); @@ -568,6 +569,7 @@ void display(BOOL rebuild, F32 zoom_factor, int subfield, BOOL for_snapshot)  	if (gDisconnected)  	{  		LLAppViewer::instance()->pingMainloopTimeout("Display:Disconnected"); +		LL_RECORD_BLOCK_TIME(FTM_RENDER_UI);  		render_ui();  		swap();  	} @@ -1293,7 +1295,8 @@ void render_ui(F32 zoom_factor, int subfield)  		{  			gPipeline.renderBloom(gSnapshot, zoom_factor, subfield);  		} -		 + +		LL_RECORD_BLOCK_TIME(FTM_RENDER_HUD);  		render_hud_elements();  		render_hud_attachments();  	} @@ -1308,8 +1311,6 @@ void render_ui(F32 zoom_factor, int subfield)  		gGL.color4f(1,1,1,1);  		if (gPipeline.hasRenderDebugFeatureMask(LLPipeline::RENDER_DEBUG_FEATURE_UI))  		{ -			LL_RECORD_BLOCK_TIME(FTM_RENDER_UI); -  			if (!gDisconnected)  			{  				render_ui_3d(); diff --git a/indra/newview/llviewerfloaterreg.cpp b/indra/newview/llviewerfloaterreg.cpp index 2a61c26b30..f475ab7d66 100644 --- a/indra/newview/llviewerfloaterreg.cpp +++ b/indra/newview/llviewerfloaterreg.cpp @@ -67,7 +67,6 @@  #include "llfloaterexperiences.h"  #include "llfloaterexperiencepicker.h"  #include "llfloaterevent.h" -#include "llfloaterfacebook.h"  #include "llfloaterflickr.h"  #include "llfloaterfonttest.h"  #include "llfloatergesture.h" @@ -353,11 +352,9 @@ void LLViewerFloaterReg::registerFloaters()  	LLFloaterReg::add("profile", "floater_web_profile.xml", (LLFloaterBuildFunc)&LLFloaterWebProfile::create);  	LLFloaterReg::add("how_to", "floater_how_to.xml", (LLFloaterBuildFunc)&LLFloaterWebContent::create); -	LLFloaterReg::add("fbc_web", "floater_fbc_web.xml", (LLFloaterBuildFunc)&LLFloaterWebContent::create);  	LLFloaterReg::add("flickr_web", "floater_fbc_web.xml", (LLFloaterBuildFunc)&LLFloaterWebContent::create);  	LLFloaterReg::add("twitter_web", "floater_fbc_web.xml", (LLFloaterBuildFunc)&LLFloaterWebContent::create); -	LLFloaterReg::add("facebook", "floater_facebook.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLFloaterFacebook>);  	LLFloaterReg::add("flickr", "floater_flickr.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLFloaterFlickr>);  	LLFloaterReg::add("twitter", "floater_twitter.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLFloaterTwitter>);  	LLFloaterReg::add("big_preview", "floater_big_preview.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLFloaterBigPreview>); diff --git a/indra/newview/llviewerkeyboard.cpp b/indra/newview/llviewerkeyboard.cpp index b89e1497a1..e930eb20d3 100644 --- a/indra/newview/llviewerkeyboard.cpp +++ b/indra/newview/llviewerkeyboard.cpp @@ -64,7 +64,12 @@ LLViewerKeyboard gViewerKeyboard;  void agent_jump( EKeystate s )  { -	if( KEYSTATE_UP == s  ) return; +	static BOOL first_fly_attempt(TRUE); +	if (KEYSTATE_UP == s) +	{ +		first_fly_attempt = TRUE; +		return; +	}  	F32 time = gKeyboard->getCurKeyElapsedTime();  	S32 frame_count = ll_round(gKeyboard->getCurKeyElapsedFrameCount()); @@ -77,7 +82,8 @@ void agent_jump( EKeystate s )  	}  	else  	{ -		gAgent.setFlying(TRUE); +		gAgent.setFlying(TRUE, first_fly_attempt); +		first_fly_attempt = FALSE;  		gAgent.moveUp(1);  	}  } diff --git a/indra/newview/llviewermedia.cpp b/indra/newview/llviewermedia.cpp index 857799889b..6cfc22a4e5 100644 --- a/indra/newview/llviewermedia.cpp +++ b/indra/newview/llviewermedia.cpp @@ -1683,7 +1683,7 @@ LLPluginClassMedia* LLViewerMediaImpl::newSourceFromMediaType(std::string media_  	// HACK: we always try to keep a spare running webkit plugin around to improve launch times.  	// If a spare was already created before PluginAttachDebuggerToPlugins was set, don't use it. -    // Do not use a spare if launching with full viewer control (e.g. Facebook, Twitter and few others) +    // Do not use a spare if launching with full viewer control (e.g. Twitter and few others)  	if ((plugin_basename == "media_plugin_cef") &&          !gSavedSettings.getBOOL("PluginAttachDebuggerToPlugins") && !clean_browser)  	{ @@ -1877,21 +1877,8 @@ void LLViewerMediaImpl::loadURI()  		// trim whitespace from front and back of URL - fixes EXT-5363  		LLStringUtil::trim( mMediaURL ); -		// *HACK: we don't know if the URI coming in is properly escaped -		// (the contract doesn't specify whether it is escaped or not. -		// but LLQtWebKit expects it to be, so we do our best to encode -		// special characters) -		// The strings below were taken right from http://www.ietf.org/rfc/rfc1738.txt -		// Note especially that '%' and '/' are there. -		std::string uri = LLURI::escape(mMediaURL, -										"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz" -										"0123456789" -										"$-_.+" -										"!*'()," -										"{}|\\^~[]`" -										"<>#%" -										";/?:@&=", -										false); +		// URI often comes unescaped +		std::string uri = LLURI::escapePathAndData(mMediaURL);          {              // Do not log the query parts              LLURI u(uri); diff --git a/indra/newview/llviewermenu.cpp b/indra/newview/llviewermenu.cpp index f1c073ed84..dc82719109 100644 --- a/indra/newview/llviewermenu.cpp +++ b/indra/newview/llviewermenu.cpp @@ -54,7 +54,6 @@  #include "lldaycyclemanager.h"  #include "lldebugview.h"  #include "llenvmanager.h" -#include "llfacebookconnect.h"  #include "llfilepicker.h"  #include "llfirstuse.h"  #include "llfloaterabout.h" @@ -4066,10 +4065,8 @@ void near_sit_down_point(BOOL success, void *)  	if (success)  	{  		gAgent.setFlying(FALSE); +		gAgent.clearControlFlags(AGENT_CONTROL_STAND_UP); // might have been set by autopilot  		gAgent.setControlFlags(AGENT_CONTROL_SIT_ON_GROUND); - -		// Might be first sit -		//LLFirstUse::useSit();  	}  } @@ -4754,6 +4751,12 @@ void handle_take()  				category_id.setNull();  			} +			// check inbox +			const LLUUID inbox_id = gInventory.findCategoryUUIDForType(LLFolderType::FT_INBOX); +			if (category_id == inbox_id || gInventory.isObjectDescendentOf(category_id, inbox_id)) +			{ +				category_id.setNull(); +			}  		}  	}  	if(category_id.isNull()) @@ -9206,7 +9209,6 @@ void initialize_menus()  	enable.add("Object.EnableSit", boost::bind(&enable_object_sit, _1));  	view_listener_t::addMenu(new LLObjectEnableReturn(), "Object.EnableReturn"); -	enable.add("Object.EnableDuplicate", boost::bind(&LLSelectMgr::canDuplicate, LLSelectMgr::getInstance()));  	view_listener_t::addMenu(new LLObjectEnableReportAbuse(), "Object.EnableReportAbuse");  	enable.add("Avatar.EnableMute", boost::bind(&enable_object_mute)); diff --git a/indra/newview/llviewermessage.cpp b/indra/newview/llviewermessage.cpp index f42c4c3c51..18b71edc1b 100644 --- a/indra/newview/llviewermessage.cpp +++ b/indra/newview/llviewermessage.cpp @@ -2415,7 +2415,7 @@ void translateSuccess(LLChat chat, LLSD toastArgs, std::string originalMsg, std:          && ((detected_language.empty()) || (expectLang != detected_language))          && (LLStringUtil::compareInsensitive(translation, originalMsg) != 0))      { -        chat.mText += " (" + translation + ")"; +        chat.mText += " (" + LLTranslate::removeNoTranslateTags(translation) + ")";      }      LLNotificationsUI::LLNotificationManager::instance().onChat(chat, toastArgs); diff --git a/indra/newview/llviewerregion.cpp b/indra/newview/llviewerregion.cpp index 439f675a2d..5b227c641b 100644 --- a/indra/newview/llviewerregion.cpp +++ b/indra/newview/llviewerregion.cpp @@ -2895,7 +2895,6 @@ void LLViewerRegionImpl::buildCapabilityNames(LLSD& capabilityNames)  	capabilityNames.append("EstateAccess");  	capabilityNames.append("EstateChangeInfo");  	capabilityNames.append("EventQueueGet"); -	capabilityNames.append("FacebookConnect");  	capabilityNames.append("FlickrConnect");  	capabilityNames.append("TwitterConnect"); diff --git a/indra/newview/llviewertexture.cpp b/indra/newview/llviewertexture.cpp index f39275af21..ae55c6f39b 100644 --- a/indra/newview/llviewertexture.cpp +++ b/indra/newview/llviewertexture.cpp @@ -1219,6 +1219,7 @@ void LLViewerFetchedTexture::loadFromFastCache()          F32 cachReadTime = fastCacheTimer.getElapsedTimeF32();          add(LLTextureFetch::sCacheHit, 1.0); +        record(LLTextureFetch::sCacheHitRate, LLUnits::Ratio::fromValue(1));          sample(LLTextureFetch::sCacheReadLatency, cachReadTime);  		mFullWidth = mRawImage->getWidth() << mRawDiscardLevel; @@ -1251,6 +1252,10 @@ void LLViewerFetchedTexture::loadFromFastCache()  			addToCreateTexture();  		}  	} +    else +    { +        record(LLTextureFetch::sCacheHitRate, LLUnits::Ratio::fromValue(0)); +    }  }  void LLViewerFetchedTexture::setForSculpt() diff --git a/indra/newview/llviewertexturelist.cpp b/indra/newview/llviewertexturelist.cpp index 4308405c64..06524847d1 100644 --- a/indra/newview/llviewertexturelist.cpp +++ b/indra/newview/llviewertexturelist.cpp @@ -512,7 +512,7 @@ LLViewerFetchedTexture* LLViewerTextureList::getImage(const LLUUID &image_id,  		if (boost_priority != LLViewerTexture::BOOST_ALM && imagep->getBoostLevel() == LLViewerTexture::BOOST_ALM)  		{  			// Workaround: we need BOOST_ALM texture for something, 'rise' to NONE -			imagep->setDecodePriority(LLViewerTexture::BOOST_NONE); +			imagep->setBoostLevel(LLViewerTexture::BOOST_NONE);  		}  		LLViewerFetchedTexture *texture = imagep.get(); diff --git a/indra/newview/llviewerwindow.cpp b/indra/newview/llviewerwindow.cpp index 543d17eb41..d9636aadbe 100644 --- a/indra/newview/llviewerwindow.cpp +++ b/indra/newview/llviewerwindow.cpp @@ -3817,7 +3817,7 @@ void LLViewerWindow::renderSelections( BOOL for_gl_pick, BOOL pick_parcel_walls,  					BOOL draw_handles = TRUE; -					if (tool == LLToolCompTranslate::getInstance() && !all_selected_objects_move) +					if (tool == LLToolCompTranslate::getInstance() && !all_selected_objects_move && !LLSelectMgr::getInstance()->isSelfAvatarSelected())  					{  						draw_handles = FALSE;  					} @@ -4732,6 +4732,7 @@ BOOL LLViewerWindow::rawSnapshot(LLImageRaw *raw, S32 image_width, S32 image_hei  				{  					// Required for showing the GUI in snapshots and performing bloom composite overlay  					// Call even if show_ui is FALSE +					LL_RECORD_BLOCK_TIME(FTM_RENDER_UI);  					render_ui(scale_factor, subfield);  					swap();  				} diff --git a/indra/newview/llvlcomposition.cpp b/indra/newview/llvlcomposition.cpp index c4430f4308..c63c5f6b23 100644 --- a/indra/newview/llvlcomposition.cpp +++ b/indra/newview/llvlcomposition.cpp @@ -99,6 +99,8 @@ void LLVLComposition::setDetailTextureID(S32 corner, const LLUUID& id)  	{  		return;  	} +	// This is terrain texture, but we are not setting it as BOOST_TERRAIN +	// since we will be manipulating it later as needed.  	mDetailTextures[corner] = LLViewerTextureManager::getFetchedTexture(id);  	mDetailTextures[corner]->setNoDelete() ;  	mRawImages[corner] = NULL; @@ -241,6 +243,7 @@ BOOL LLVLComposition::generateComposition()  			}  			mDetailTextures[i]->setBoostLevel(LLGLTexture::BOOST_TERRAIN); // in case we are at low detail  			mDetailTextures[i]->setMinDiscardLevel(ddiscard); +			mDetailTextures[i]->addTextureStats(BASE_SIZE*BASE_SIZE); // priority  			return FALSE;  		}  	} @@ -287,7 +290,7 @@ BOOL LLVLComposition::generateTexture(const F32 x, const F32 y,  				{  					mDetailTextures[i]->destroyRawImage() ;  				} -				LL_DEBUGS() << "cached raw data for terrain detail texture is not ready yet: " << mDetailTextures[i]->getID() << LL_ENDL; +				LL_DEBUGS("Terrain") << "cached raw data for terrain detail texture is not ready yet: " << mDetailTextures[i]->getID() << " Discard: " << ddiscard << LL_ENDL;  				return FALSE;  			} @@ -323,12 +326,12 @@ BOOL LLVLComposition::generateTexture(const F32 x, const F32 y,  	if (x_end > mWidth)  	{ -		LL_WARNS() << "x end > width" << LL_ENDL; +		LL_WARNS("Terrain") << "x end > width" << LL_ENDL;  		x_end = mWidth;  	}  	if (y_end > mWidth)  	{ -		LL_WARNS() << "y end > width" << LL_ENDL; +		LL_WARNS("Terrain") << "y end > width" << LL_ENDL;  		y_end = mWidth;  	} @@ -358,7 +361,7 @@ BOOL LLVLComposition::generateTexture(const F32 x, const F32 y,  	if (tex_comps != st_comps)  	{ -		LL_WARNS() << "Base texture comps != input texture comps" << LL_ENDL; +		LL_WARNS("Terrain") << "Base texture comps != input texture comps" << LL_ENDL;  		return FALSE;  	} diff --git a/indra/newview/llvoicevivox.cpp b/indra/newview/llvoicevivox.cpp index 0d3f65502a..e10ba77e16 100644 --- a/indra/newview/llvoicevivox.cpp +++ b/indra/newview/llvoicevivox.cpp @@ -658,6 +658,8 @@ void LLVivoxVoiceClient::voiceControlCoro()      mIsCoroutineActive = true;      LLCoros::set_consuming(true); +    U32 retry = 0; +      while (gAgent.getTeleportState() != LLAgent::TELEPORT_NONE)      {          LL_DEBUGS("Voice") << "Suspending voiceControlCoro() momentarily for teleport. Tuning: " << mTuningMode << ". Relog: " << mRelogRequested << LL_ENDL; @@ -666,7 +668,8 @@ void LLVivoxVoiceClient::voiceControlCoro()      do      { -        if (startAndConnectSession()) +        bool success = startAndConnectSession(); +        if (success)          {              if (mTuningMode)              { @@ -677,6 +680,7 @@ void LLVivoxVoiceClient::voiceControlCoro()              LL_DEBUGS("Voice") << "lost channel RelogRequested=" << mRelogRequested << LL_ENDL;                          endAndDisconnectSession(); +            retry = 0;          }          // if we hit this and mRelogRequested is true, that indicates @@ -689,7 +693,19 @@ void LLVivoxVoiceClient::voiceControlCoro()              << LL_ENDL;                      if (mRelogRequested)          { -            LL_INFOS("Voice") << "will attempt to reconnect to voice" << LL_ENDL; +            if (!success) +            { +                // We failed to connect, give it a bit time before retrying. +                retry++; +                F32 delay = llmin(5.f * (F32)retry, 60.f); +                llcoro::suspendUntilTimeout(delay); +                LL_INFOS("Voice") << "Voice failed to establish session after " << retry << " tries. Will attempt to reconnect." << LL_ENDL; +            } +            else +            { +                LL_INFOS("Voice") << "will attempt to reconnect to voice" << LL_ENDL; +            } +              while (isGatewayRunning() || gAgent.getTeleportState() != LLAgent::TELEPORT_NONE)              {                  LL_INFOS("Voice") << "waiting for SLVoice to exit" << LL_ENDL; @@ -770,12 +786,16 @@ bool LLVivoxVoiceClient::startAndLaunchDaemon()      {  #ifndef VIVOXDAEMON_REMOTEHOST          // Launch the voice daemon -        std::string exe_path = gDirUtilp->getAppRODataDir();  #if LL_WINDOWS +        // On windows use exe (not work or RO) directory +        std::string exe_path = gDirUtilp->getExecutableDir();          gDirUtilp->append(exe_path, "SLVoice.exe");  #elif LL_DARWIN +        // On MAC use resource directory +        std::string exe_path = gDirUtilp->getAppRODataDir();          gDirUtilp->append(exe_path, "SLVoice");  #else +        std::string exe_path = gDirUtilp->getExecutableDir();          gDirUtilp->append(exe_path, "SLVoice");  #endif          // See if the vivox executable exists diff --git a/indra/newview/pipeline.cpp b/indra/newview/pipeline.cpp index a72244929e..bd73c234a6 100644 --- a/indra/newview/pipeline.cpp +++ b/indra/newview/pipeline.cpp @@ -4062,7 +4062,6 @@ void LLPipeline::postSort(LLCamera& camera)  void render_hud_elements()  { -	LL_RECORD_BLOCK_TIME(FTM_RENDER_UI);  	gPipeline.disableLights();		  	LLGLDisable fog(GL_FOG); diff --git a/indra/newview/skins/default/textures/textures.xml b/indra/newview/skins/default/textures/textures.xml index 2f9fdabea3..5aba0546f3 100644 --- a/indra/newview/skins/default/textures/textures.xml +++ b/indra/newview/skins/default/textures/textures.xml @@ -133,7 +133,6 @@ with the same filename but different name    <texture name="Command_Chat_Icon"         file_name="toolbar_icons/chat.png"         preload="true" />    <texture name="Command_Compass_Icon"      file_name="toolbar_icons/land.png"         preload="true" />    <texture name="Command_Destinations_Icon" file_name="toolbar_icons/destinations.png" preload="true" /> -  <texture name="Command_Facebook_Icon"     file_name="toolbar_icons/facebook.png"     preload="true" />    <texture name="Command_Flickr_Icon"       file_name="toolbar_icons/flickr.png"       preload="true" />    <texture name="Command_Gestures_Icon"     file_name="toolbar_icons/gestures.png"     preload="true" />    <texture name="Command_Grid_Status_Icon"  file_name="toolbar_icons/grid_status.png"  preload="true" /> @@ -205,8 +204,6 @@ with the same filename but different name    <texture name="ExternalBrowser_Off" file_name="icons/ExternalBrowser_Off.png" preload="false" />    <texture name="Edit_Wrench" file_name="icons/Edit_Wrench.png" preload="false" /> -  <texture name="Facebook_Icon" file_name="icons/Facebook.png" preload="false" /> -    <texture name="Presets_Icon" file_name="icons/Presets_Icon.png" preload="true" />    <texture name="Favorite_Star_Active" file_name="navbar/Favorite_Star_Active.png" preload="false" /> @@ -593,7 +590,6 @@ with the same filename but different name    <texture name="Snapshot_Email" file_name="snapshot_email.png" preload="false" />    <texture name="Snapshot_Inventory" file_name="toolbar_icons/inventory.png" preload="false" />    <texture name="Snapshot_Profile" file_name="toolbar_icons/profile.png" preload="false" /> -  <texture name="Snapshot_Facebook" file_name="toolbar_icons/facebook.png" preload="false" />    <texture name="startup_logo"  file_name="windows/startup_logo.png" preload="true" /> diff --git a/indra/newview/skins/default/xui/de/floater_about_land.xml b/indra/newview/skins/default/xui/de/floater_about_land.xml index 1e18ab20e8..2bff6d3e2f 100644 --- a/indra/newview/skins/default/xui/de/floater_about_land.xml +++ b/indra/newview/skins/default/xui/de/floater_about_land.xml @@ -21,7 +21,7 @@  	<floater.string name="Remaining">  		Restzeit  	</floater.string> -	<tab_container name="landtab" tab_min_width="40" width="489"> +	<tab_container name="landtab" tab_min_width="40">  		<panel label="ALLGEMEIN" name="land_general_panel">  			<panel.string name="new users only">  				Nur neue Benutzer @@ -361,8 +361,8 @@ Nur große Parzellen können in der Suche aufgeführt werden.  			<text name="landing_point">  				Landepunkt: [LANDING]  			</text> -			<button label="Festlegen" label_selected="Festlegen" left="234" name="Set" right="-88" tool_tip="Legt Ihren Standort als Landepunkt fest, an dem Besucher ankommen. Legt die Position Ihres Avatars innerhalb dieser Parzelle fest." width="70"/> -			<button label="Löschen" label_selected="Löschen" left="312" name="Clear" tool_tip="Landepunkt löschen" width="70"/> +			<button label="Festlegen" label_selected="Festlegen" name="Set" tool_tip="Legt Ihren Standort als Landepunkt fest, an dem Besucher ankommen. Legt die Position Ihres Avatars innerhalb dieser Parzelle fest." width="70"/> +			<button label="Löschen" label_selected="Löschen" name="Clear" tool_tip="Landepunkt löschen" width="70"/>  			<text name="Teleport Routing: ">  				Teleport-Route:  			</text> @@ -433,7 +433,7 @@ Nur große Parzellen können in der Suche aufgeführt werden.  			<panel.string name="estate_override">  				Eine oder mehrere dieser Optionen gelten auf Grundbesitzebene  			</panel.string> -			<check_box label="Alle Besucher sind zugelassen (Bei Deaktivierung dieser Option werden Bannlinien generiert)" name="public_access"/> +			<check_box label="Alle Besucher sind zugelassen" tool_tip="Bei Deaktivierung dieser Option werden Bannlinien generiert" name="public_access"/>  			<check_box label="Muss 18+ sein [ESTATE_AGE_LIMIT]" name="limit_age_verified" tool_tip="Nur Einwohner, die mindestens 18 Jahre alt sind, können diese Parzelle betreten. Weitere Informationen finden Sie unter [SUPPORT_SITE]."/>  			<check_box label="Muss über Zahlungsinfo in Datei [ESTATE_PAYMENT_LIMIT] verfügen" name="limit_payment" tool_tip="Um diese Parzelle besuchen zu können, müssen Einwohner Zahlungsinformationen hinterlegt haben. Weitere Informationen finden Sie auf [SUPPORT_SITE]."/>  			<check_box label="Gruppe [GROUP] ohne Beschränkungen zulassen" name="GroupCheck" tool_tip="Gruppe im Register „Allgemein“ festlegen."/> diff --git a/indra/newview/skins/default/xui/en/floater_about_land.xml b/indra/newview/skins/default/xui/en/floater_about_land.xml index d04e738b22..9f853fd960 100644 --- a/indra/newview/skins/default/xui/en/floater_about_land.xml +++ b/indra/newview/skins/default/xui/en/floater_about_land.xml @@ -163,6 +163,7 @@               layout="topleft"               left_pad="2"               name="Description" +             spellcheck="true"               top_delta="0"               width="365"               word_wrap="true" /> @@ -1268,6 +1269,7 @@ Only large parcels can be listed in search.               layout="topleft"               left_pad="2"               name="edit objects check" +             tool_tip="If checked, Residents can create and rez objects on your land."               width="130" />              <check_box               height="16" @@ -1275,6 +1277,7 @@ Only large parcels can be listed in search.               layout="topleft"               left_pad="2"               name="edit group objects check" +             tool_tip="If checked, parcel group members can create and rez objects on your land."               width="70" />              <text               type="string" @@ -1293,6 +1296,7 @@ Only large parcels can be listed in search.               layout="topleft"               left_pad="2"               name="all object entry check" +             tool_tip="If checked, Residents can move existing objects from other parcels onto this parcel."               top_delta="0"               width="130" />              <check_box @@ -1301,6 +1305,7 @@ Only large parcels can be listed in search.               layout="topleft"               left_pad="2"               name="group object entry check" +             tool_tip="If checked, parcel group members can move existing objects from other parcels onto this parcel."               top_delta="0"               width="70" />              <text @@ -1320,6 +1325,7 @@ Only large parcels can be listed in search.               layout="topleft"               left_pad="2"               name="check other scripts" +             tool_tip="If checked, Residents can run scripts on your parcel, including attachments."               top_delta="0"               width="130" />              <check_box @@ -1328,6 +1334,7 @@ Only large parcels can be listed in search.               layout="topleft"               left_pad="2"               name="check group scripts" +             tool_tip="If checked, parcel group members can run scripts on your parcel, including attachments."               top_delta="0"               width="70" />            <panel @@ -1466,11 +1473,12 @@ Only large parcels can be listed in search.               length="1"               follows="left|top"               text_color="LtGray" +             text_readonly_color="LabelDisabledColor"               height="32"               layout="topleft"               left="274"               top="150" -             name="allow_label5" +             name="allow_see_label"               width="205"               word_wrap="true">                Avatars on other parcels can see and chat with avatars on this parcel @@ -1908,6 +1916,7 @@ Only large parcels can be listed in search.               layout="topleft"               left="8"               name="public_access" +             tool_tip=""               label="Anyone can visit (Unchecking this will create ban lines)"               top_pad="10"                width="278" /> diff --git a/indra/newview/skins/default/xui/en/floater_ban_duration.xml b/indra/newview/skins/default/xui/en/floater_ban_duration.xml index 5562f28877..6c537cc08d 100644 --- a/indra/newview/skins/default/xui/en/floater_ban_duration.xml +++ b/indra/newview/skins/default/xui/en/floater_ban_duration.xml @@ -28,12 +28,12 @@      draw_border="false"      enabled="true"      follows="left|top" -    height="40" +    height="47"      left="20"      mouse_opaque="true"      name="ban_duration_radio"      tab_stop="true" -    width="200"> +    width="150">         <radio_item          type="string"          follows="left|top" @@ -75,7 +75,7 @@      left_delta="70"      name="hours_textbox"      top_delta="5" -    width="75"> +    width="70">          hours.     </text> diff --git a/indra/newview/skins/default/xui/en/floater_experienceprofile.xml b/indra/newview/skins/default/xui/en/floater_experienceprofile.xml index 2dfba1ac44..f275fec066 100644 --- a/indra/newview/skins/default/xui/en/floater_experienceprofile.xml +++ b/indra/newview/skins/default/xui/en/floater_experienceprofile.xml @@ -493,6 +493,7 @@              layout="topleft"              left="11"              name="edit_experience_description" +            spellcheck="true"              max_length="2048"              text_color="black"              right="-11" diff --git a/indra/newview/skins/default/xui/en/floater_facebook.xml b/indra/newview/skins/default/xui/en/floater_facebook.xml deleted file mode 100644 index b34d70516a..0000000000 --- a/indra/newview/skins/default/xui/en/floater_facebook.xml +++ /dev/null @@ -1,95 +0,0 @@ -<?xml version="1.0" encoding="UTF-8" standalone="yes" ?> -<floater -  positioning="cascading" -  can_close="true" -  help_topic="floater_facebook" -  layout="topleft" -  name="floater_facebook" -  save_rect="true" -  single_instance="true" -  reuse_instance="true" -  title="POST TO FACEBOOK" -  min_height="462" -  min_width="304" -  height="462" -  width="272"> -   <tab_container -     name="tabs" -     tab_group="1" -     tab_min_width="64" -     tab_height="21" -     tab_position="top" -     top="7" -     height="437" -     follows="all" -     halign="center"> -     <panel -       filename="panel_facebook_status.xml" -       class="llfacebookstatuspanel" -       follows="all" -       label="STATUS" -       name="panel_facebook_status"/> -     <panel -       filename="panel_facebook_photo.xml" -       class="llfacebookphotopanel" -       follows="all" -       label="PHOTO" -       name="panel_facebook_photo"/> -     <panel -       filename="panel_facebook_place.xml" -       class="llfacebookcheckinpanel" -       follows="all" -       label="CHECK IN" -       name="panel_facebook_place"/> -     <panel -       filename="panel_facebook_friends.xml" -       class="llfacebookfriendspanel" -       follows="all" -       label="FRIENDS" -       name="panel_facebook_friends"/> -     <!--<panel -       filename="panel_facebook_account.xml" -       class="llfacebookaccountpanel" -       follows="all" -       label="ACCOUNT" -       name="panel_facebook_account"/>--> -   </tab_container> -     <text -      name="connection_error_text" -      type="string" -      follows="left|bottom|right" -      bottom="-5" -      left="10" -      width="250" -      height="20" -      wrap="true" -      halign="left" -      valign="center" -      text_color="DrYellow" -      font="SansSerif"> -      Error -     </text> -     <loading_indicator -      follows="left|bottom" -      height="24" -      width="24" -      name="connection_loading_indicator" -      top_delta="-2" -      left="10" -      visible="true"/> -     <text -      name="connection_loading_text" -      type="string" -      follows="left|bottom|right" -      top_delta="2" -      left_pad="5" -      width="250" -      height="20" -      wrap="true" -      halign="left" -      valign="center" -      text_color="EmphasisColor" -      font="SansSerif"> -      Loading... -    </text> -</floater> diff --git a/indra/newview/skins/default/xui/en/floater_fast_timers.xml b/indra/newview/skins/default/xui/en/floater_fast_timers.xml index fa7147d9ca..645003cc14 100644 --- a/indra/newview/skins/default/xui/en/floater_fast_timers.xml +++ b/indra/newview/skins/default/xui/en/floater_fast_timers.xml @@ -60,10 +60,21 @@                    min_width="100">        <panel top="0"               left="0" -             width="220" +             width="204"               height="440"               name="legend"               follows="all"/> +      <scroll_bar +        top ="0" +        right="-1" +        height="440" +        width="15" +        follows="top|right|bottom" +        name="scroll_vert" +        orientation="vertical" +        step_size="16" +        doc_size="3000" +          />      </layout_panel>      <layout_panel name="timers_panel"                    auto_resize="true" diff --git a/indra/newview/skins/default/xui/en/floater_gesture.xml b/indra/newview/skins/default/xui/en/floater_gesture.xml index 200e9b9537..9f051d9f8d 100644 --- a/indra/newview/skins/default/xui/en/floater_gesture.xml +++ b/indra/newview/skins/default/xui/en/floater_gesture.xml @@ -119,6 +119,7 @@       follows="left|bottom"       height="23"       label="Edit" +     tool_tip="Open window for editing selected gesture."       layout="topleft"       left="6"       name="edit_btn" @@ -128,6 +129,7 @@       follows="left|bottom"       height="23"       label="Play" +     tool_tip="Execute selected gesture in-world."       layout="topleft"       left_pad="6"       name="play_btn" diff --git a/indra/newview/skins/default/xui/en/floater_inventory_view_finder.xml b/indra/newview/skins/default/xui/en/floater_inventory_view_finder.xml index 1b4992b4ca..ca1d299553 100644 --- a/indra/newview/skins/default/xui/en/floater_inventory_view_finder.xml +++ b/indra/newview/skins/default/xui/en/floater_inventory_view_finder.xml @@ -2,7 +2,7 @@  <floater   legacy_header_height="18"   can_minimize="false" - height="468" + height="448"   layout="topleft"   name="Inventory Finder"   help_topic="inventory_finder" @@ -112,29 +112,12 @@       width="126" />      <icon       height="16" -     image_name="Inv_Mesh" -     layout="topleft" -     left="8" -     mouse_opaque="true" -     name="icon_mesh" -     top="142" -     width="16" /> -    <check_box -     height="16" -     label="Meshes" -     layout="topleft" -     left_pad="2" -     name="check_mesh" -     top_delta="0" -     width="126" /> -    <icon -     height="16"       image_name="Inv_Object"       layout="topleft"       left="8"       mouse_opaque="true"       name="icon_object" -     top="162" +     top="142"       width="16" />      <check_box       height="16" @@ -151,7 +134,7 @@       left="8"       mouse_opaque="true"       name="icon_script" -     top="182" +     top="162"       width="16" />      <check_box       height="16" @@ -168,7 +151,7 @@       left="8"       mouse_opaque="true"       name="icon_sound" -     top="202" +     top="182"       width="16" />      <check_box       height="16" @@ -185,7 +168,7 @@       left="8"       mouse_opaque="true"       name="icon_texture" -     top="222" +     top="202"       width="16" />      <check_box       height="16" @@ -202,7 +185,7 @@       left="8"       mouse_opaque="true"       name="icon_snapshot" -     top="242" +     top="222"       width="16" />      <check_box       height="16" @@ -220,7 +203,7 @@       layout="topleft"       left="8"       name="All" -     top="262" +     top="242"       width="100" />      <button       height="20" @@ -274,7 +257,7 @@       width="260"/>      <check_box       height="16" -     top="352" +     top="332"       label="Since Logoff"       layout="topleft"       left_delta="0" @@ -290,7 +273,7 @@       layout="topleft"       left_delta="0"       name="- OR -" -     top="370" +     top="350"       width="144">          - OR -      </text> @@ -298,7 +281,7 @@       height="16"       layout="topleft"       name="date_search_direction" -     top="388" +     top="368"       left="8"       width="270">       <radio_item @@ -368,6 +351,6 @@       layout="topleft"       name="Close"       right="-6" -     top="434" +     top="414"       width="76" />  </floater> diff --git a/indra/newview/skins/default/xui/en/floater_preferences_proxy.xml b/indra/newview/skins/default/xui/en/floater_preferences_proxy.xml index 93bfe53aae..659033efd4 100644 --- a/indra/newview/skins/default/xui/en/floater_preferences_proxy.xml +++ b/indra/newview/skins/default/xui/en/floater_preferences_proxy.xml @@ -58,12 +58,12 @@  	 label_width="95"  	 layout="topleft"  	 left_delta="210" -	 max_val="12000" +	 max_val="65535"  	 min_val="10"  	 name="web_proxy_port"  	 top_delta="0"  	 tool_tip="The port of the HTTP proxy you would like to use." -	 width="145" /> +	 width="150" />  	<check_box  	 control_name="Socks5ProxyEnabled"  	 height="16" @@ -111,11 +111,11 @@  	 label_width="95"  	 layout="topleft"  	 left_delta="210" -	 max_val="12000" +	 max_val="65535"  	 min_val="10"  	 name="socks_proxy_port"  	 top_delta="0" -	 width="145" +	 width="150"  	 tool_tip="The port of the SOCKS 5 proxy you would like to use."  	 commit_callback.function="Proxy.Change" />  	<text diff --git a/indra/newview/skins/default/xui/en/floater_preview_notecard.xml b/indra/newview/skins/default/xui/en/floater_preview_notecard.xml index 2e1c8ce670..dcbdfa8794 100644 --- a/indra/newview/skins/default/xui/en/floater_preview_notecard.xml +++ b/indra/newview/skins/default/xui/en/floater_preview_notecard.xml @@ -6,7 +6,7 @@   height="361"   layout="topleft"   min_height="243" - min_width="234" + min_width="330"   name="preview notecard"   help_topic="preview_notecard"   title="NOTECARD:" @@ -77,6 +77,16 @@       word_wrap="true">          Loading...      </text_editor> +      <button +     follows="left|bottom" +     height="22" +     label="Edit..." +     label_selected="Edit" +     layout="topleft" +     left="4" +     name="Edit" +     top="332" +     width="100" />      <button       follows="right|bottom"       height="22" diff --git a/indra/newview/skins/default/xui/en/floater_report_abuse.xml b/indra/newview/skins/default/xui/en/floater_report_abuse.xml index 8fa5b49573..d07e3cb31b 100644 --- a/indra/newview/skins/default/xui/en/floater_report_abuse.xml +++ b/indra/newview/skins/default/xui/en/floater_report_abuse.xml @@ -246,7 +246,7 @@           name="Land__Encroachment__Objects_textures"           value="63" />                  <combo_box.item -         label="Gaming Policy Violation" +         label="Skill Gaming Policy Violation"           name="Wagering_gambling"           value="67" />             </combo_box> diff --git a/indra/newview/skins/default/xui/en/floater_snapshot.xml b/indra/newview/skins/default/xui/en/floater_snapshot.xml index e50747cb5f..832c2ee7da 100644 --- a/indra/newview/skins/default/xui/en/floater_snapshot.xml +++ b/indra/newview/skins/default/xui/en/floater_snapshot.xml @@ -24,10 +24,6 @@          Sending Email      </string>      <string -        name="facebook_progress_str"> -        Posting to Facebook -    </string> -    <string          name="profile_progress_str">          Posting      </string> @@ -40,10 +36,6 @@          Saving to Computer      </string>   	<string -        name="facebook_succeeded_str"> - 	    Image uploaded - 	</string> - 	<string          name="profile_succeeded_str">   	    Image uploaded   	</string> @@ -60,10 +52,6 @@   	    Saved to Computer!   	</string>   	<string -     name="facebook_failed_str"> - 	    Failed to upload image to your Facebook timeline. - 	</string> - 	<string       name="profile_failed_str">   	    Failed to upload image to your Profile Feed.   	</string> diff --git a/indra/newview/skins/default/xui/en/fonts.xml b/indra/newview/skins/default/xui/en/fonts.xml index 8b1d50e58f..2d5263b78f 100644 --- a/indra/newview/skins/default/xui/en/fonts.xml +++ b/indra/newview/skins/default/xui/en/fonts.xml @@ -10,6 +10,8 @@        <file>simhei.ttf</file>        <file>ArialUni.ttf</file>        <file>msyh.ttc</file> +      <file load_collection="true">Cambria.ttc</file> +      <file>malgun.ttf</file>      </os>      <os name="Mac">        <file>ヒラギノ角ゴシック W3.ttc</file>   @@ -21,6 +23,7 @@        <file>AppleSDGothicNeo-Regular.otf</file>        <file>华文细黑.ttf</file>        <file>PingFang.ttc</file> +      <file>STIXGeneral.otf</file>      </os>    </font> diff --git a/indra/newview/skins/default/xui/en/menu_viewer.xml b/indra/newview/skins/default/xui/en/menu_viewer.xml index f2ee9c6447..7bb7b5d62c 100644 --- a/indra/newview/skins/default/xui/en/menu_viewer.xml +++ b/indra/newview/skins/default/xui/en/menu_viewer.xml @@ -307,13 +307,6 @@          </menu_item_check>          <menu_item_separator/>        <menu_item_call -        label="Facebook..." -        name="Facebook"> -        <menu_item_call.on_click -          function="Floater.Toggle" -          parameter="facebook"/> -      </menu_item_call> -      <menu_item_call          label="Twitter..."          name="Twitter">          <menu_item_call.on_click @@ -1051,8 +1044,7 @@             shortcut="control|D">              <menu_item_call.on_click                 function="Object.Duplicate" /> -            <menu_item_call.on_enable -               function="Object.EnableDuplicate" /> +            </menu_item_call>  		</menu>          <menu diff --git a/indra/newview/skins/default/xui/en/notifications.xml b/indra/newview/skins/default/xui/en/notifications.xml index b7cd6517ea..053c041849 100644 --- a/indra/newview/skins/default/xui/en/notifications.xml +++ b/indra/newview/skins/default/xui/en/notifications.xml @@ -6705,13 +6705,6 @@ Please select at least one type of content to search (General, Moderate, or Adul  [MESSAGE]    </notification> - <notification -  icon="notify.tga" -  name="FacebookConnect" -  type="notifytip"> -[MESSAGE] - </notification> -    <notification     icon="notify.tga"     name="FlickrConnect" @@ -8639,6 +8632,7 @@ Please check your network and firewall setup.     icon="alertmodal.tga"     name="NoVoiceConnect"     type="alertmodal"> +    <unique/>  We are unable to connect to the voice server:  [HOSTID] diff --git a/indra/newview/skins/default/xui/en/panel_facebook_friends.xml b/indra/newview/skins/default/xui/en/panel_facebook_friends.xml deleted file mode 100644 index 97994fb08b..0000000000 --- a/indra/newview/skins/default/xui/en/panel_facebook_friends.xml +++ /dev/null @@ -1,73 +0,0 @@ -<panel -	 height="400" -	 width="272" -	 layout="topleft" -    follows="all" -   name="panel_facebook_friends"> -  <string -   name="facebook_friends_empty" -   value="You currently do not have any Facebook friends who are also Second Life residents. Ask your Facebook friends to join Second Life today!" /> -  <string -   name="facebook_friends_no_connected" -   value="You're currently not connected to Facebook. Please go to the Status tab to connect and enable this feature." /> -  <accordion - background_visible="false" - bg_alpha_color="DkGray2" - bg_opaque_color="DkGray2" -   follows="all" -   height="383" -   layout="topleft" -   left="10" -   name="friends_accordion" -   right="-10" -   top_pad="2"> -    <accordion_tab -     layout="topleft" -     height="173" -     name="tab_second_life_friends" -     title="SL friends"> -      <avatar_list -       ignore_online_status="true" -       allow_select="true" -       follows="all" -       height="173" -       layout="topleft" -       left="0" -       name="second_life_friends" -       show_permissions_granted="true" -       top="0" -       width="272" /> -    </accordion_tab> -    <accordion_tab -     layout="topleft" -     height="173" -     name="tab_suggested_friends" -     title="Add these people as SL friends"> -      <avatar_list -       ignore_online_status="true" -       allow_select="true" -       follows="all" -       height="173" -       layout="topleft" -       left="0" -       name="suggested_friends" -       show_permissions_granted="true" -       top="0" -       width="272" /> -    </accordion_tab> -  </accordion> -    <text -        layout="topleft" -        word_wrap="true" -        height="64" -        width="250" -        follows="top|left|right" -        font="SansSerif" -        left="10" -		right="-10" -        name="facebook_friends_status" -        top="5" -        type="string"> -        Not connected to Facebook. -    </text> -</panel> diff --git a/indra/newview/skins/default/xui/en/panel_facebook_photo.xml b/indra/newview/skins/default/xui/en/panel_facebook_photo.xml deleted file mode 100644 index 22e6598352..0000000000 --- a/indra/newview/skins/default/xui/en/panel_facebook_photo.xml +++ /dev/null @@ -1,168 +0,0 @@ -    <panel -      height="400" -      width="272" -      layout="topleft" -      follows="all" -      name="panel_facebook_photo"> -            <combo_box -             control_name="FacebookPhotoResolution" -             follows="left|top" -			 layout="topleft" -             top="7" -             left="10" -             name="resolution_combobox" -             tool_tip="Image resolution" -             height="21" -             width="124"> -              <combo_box.item -               label="Current Window" -               name="CurrentWindow" -               value="[i0,i0]" /> -              <combo_box.item -               label="640x480" -               name="640x480" -               value="[i640,i480]" /> -              <combo_box.item -               label="800x600" -               name="800x600" -               value="[i800,i600]" /> -              <combo_box.item -               label="1024x768" -               name="1024x768" -               value="[i1024,i768]" /> -              <combo_box.item -               label="1200x630" -               name="1200x630" -               value="[i1200,i630]" /> -            </combo_box> -            <combo_box -                control_name="FacebookPhotoFilters" -                follows="left|top" -				layout="topleft" -                name="filters_combobox" -                tool_tip="Image filters" -                top="7" -                left_pad="4" -                height="21" -                width="124"> -                <combo_box.item -                label="No Filter" -                name="NoFilter" -                value="NoFilter" /> -            </combo_box> -            <panel -                height="150" -                width="252" -                visible="true" -				layout="topleft" -                name="thumbnail_placeholder" -                top_pad="5" -                follows="left|top|rith" -				right="-10" -                left="10"> -            </panel> -			<text -                follows="left|top" -				layout="topleft" -                font="SansSerif" -                text_color="EmphasisColor" -                height="14" -                top_pad="2" -                left="10" -                length="1" -                halign="center" -                name="working_lbl" -                translate="false" -                type="string" -                visible="true" -                width="251"> -                Refreshing... -            </text> -			<view_border  -			 bevel_style="in" -			 follows="left|top" -			 layout="topleft" -			 height="1" -			 left="10" -			 name="refresh_border" -			 width="250" -			 top_pad="0"/> -            <button -             follows="left|top" -			 layout="topleft" -             height="23" -             label="Refresh" -             left="10" -             top_pad="5" -             name="new_snapshot_btn" -             tool_tip="Click to refresh" -             visible="true" -             width="100" > -             <button.commit_callback -               function="SocialSharing.RefreshPhoto" /> -            </button> -            <button -                follows="right|top" -				layout="topleft" -                height="23" -                label="Preview" -                right="-10" -                top_delta="0" -                name="big_preview_btn" -                tool_tip="Click to toggle preview" -                is_toggle="true" -                visible="true" -                width="100" > -                <button.commit_callback -                function="SocialSharing.BigPreview" /> -            </button> -            <text -             length="1" -             follows="top|left|right" -			 layout="topleft" -             font="SansSerif" -             height="16" -             left="10" -             name="caption_label" -             top_pad="20" -             type="string"> -              Comment (optional): -            </text> -            <text_editor -             follows="left|top|right|bottom" -			 layout="topleft" -             height="87" -             width="250" -             left="10" -			 right="-10" -             length="1" -             max_length="700" -             name="photo_caption" -             type="string" -             word_wrap="true"> -            </text_editor> -          <button -           follows="left|top" -		   layout="topleft" -           top_pad="22" -           left="10" -           height="23" -           label="Post" -           name="post_photo_btn" -           width="100"> -            <button.commit_callback -             function="SocialSharing.SendPhoto" /> -          </button> -          <button -               follows="right|top" -			   layout="topleft" -               height="23" -               label="Cancel" -               name="cancel_photo_btn" -               right="-10" -               top_delta="0" -               width="100"> -            <button.commit_callback -             function="SocialSharing.Cancel" /> -          </button> -    </panel> diff --git a/indra/newview/skins/default/xui/en/panel_facebook_place.xml b/indra/newview/skins/default/xui/en/panel_facebook_place.xml deleted file mode 100644 index f87b008c4e..0000000000 --- a/indra/newview/skins/default/xui/en/panel_facebook_place.xml +++ /dev/null @@ -1,113 +0,0 @@ -    <panel -      height="400" -      width="272" -	  layout="topleft" -      follows="all" -      name="panel_facebook_place"> -          <text -            length="1" -            follows="top|left|right" -			layout="topleft" -            font="SansSerif" -            height="16" -            left="10" -            name="place_caption_label" -            top="5" -            type="string"> -            Say something about where you are: -          </text> -          <text_editor -            follows="top|left|right" -			layout="topleft" -            height="70" -            width="250" -            left="10" -			right="-10" -            length="1" -            max_length="700" -            name="place_caption" -            type="string" -            word_wrap="true"> -           </text_editor> -		  <check_box -              follows="left|top" -			  layout="topleft" -              initial_value="false" -			  height="16" -              top_pad="8" -              width="8" -              label="Include overhead view of location" -              name="add_place_view_cb" -              left="10"/> -              <panel -                  follows="left|top" -				  layout="topleft" -                  height="243" -                  width="250" -                  background_visible="true" -                  bg_opaque_color="Black" -                  bg_alpha_color="Black" -                  top_pad="8" -                  left="10" -				  right="-12" -                  visible="true" -                  name="map_border"> -              </panel> -              <icon -                follows="left|top" -				layout="topleft" -                height="243" -                width="250" -                image_name="Map_Placeholder_Icon" -                top_delta="0" -				right="-12" -                left="10" -                visible="true" -                name="map_placeholder"> -              </icon> -              <icon -                  follows="left|top" -				  layout="topleft" -                  height="243" -                  width="250" -                  image_name="Map_Placeholder_Icon" -                  top_delta="0" -                  left="10" -				  right="-12" -                  visible="true" -                  name="map_default"> -              </icon> -			  <loading_indicator -              follows="left|top" -			  layout="topleft" -              height="24" -              width="24" -              name="map_loading_indicator" -              top_delta="116" -              left="126" -              visible="false"/> -            <button -              follows="left|bottom" -			  layout="topleft" -              top_pad="95" -              left="10" -              height="23" -              label="Post" -              name="post_place_btn" -              width="100"> -              <button.commit_callback -                 function="SocialSharing.SendCheckin" /> -            </button> -            <button -              follows="right|bottom" -			  layout="topleft" -              height="23" -              label="Cancel" -              name="cancel_place_btn" -              right="-10" -              top_delta="0" -              width="100"> -              <button.commit_callback -                  function="SocialSharing.Cancel" /> -            </button> -    </panel> diff --git a/indra/newview/skins/default/xui/en/panel_facebook_status.xml b/indra/newview/skins/default/xui/en/panel_facebook_status.xml deleted file mode 100644 index fe0f3c9279..0000000000 --- a/indra/newview/skins/default/xui/en/panel_facebook_status.xml +++ /dev/null @@ -1,130 +0,0 @@ -    <panel -	 height="400" -	 width="272" -     follows="all" -	 layout="topleft" -     name="panel_facebook_status"> -        <string -      name="facebook_connected" -      value="You are connected to Facebook as:" /> -  <string -      name="facebook_disconnected" -      value="Not connected to Facebook" /> -  <text -   layout="topleft" -   length="1" -   follows="top|left" -   font="SansSerif" -   height="16" -   left="10" -   name="account_caption_label" -   top="5" -   type="string"> -    Not connected to Facebook. -  </text> -  <text -   layout="topleft" -   top_pad="2" -   length="1" -   follows="top|left" -   font="SansSerif" -   height="16" -   left="10" -   name="account_name_label" -   parse_urls="true" -   type="string"/> -  <panel -    layout="topleft" -    follows="left|top" -    name="panel_buttons" -    height="60" -    left="0"> -    <button -     layout="topleft" -     follows="left|top" -     top_pad="9" -     left="10" -     visible="true" -     height="23" -     label="Connect..." -     name="connect_btn" -     width="251"> -      <commit_callback function="SocialSharing.Connect"/> -    </button> - -    <button -     layout="topleft" -     follows="left|top|right" -     top_delta="0" -     left="10" -     right="-10" -     height="23" -     label="Disconnect" -     name="disconnect_btn" -     width="210" -     visible="false"> -      <commit_callback function="SocialSharing.Disconnect"/> -    </button> -    <text -      layout="topleft" -      length="1" -      follows="top|left|right" -      left="10" -      right="-10" -      height="16" -      name="account_learn_more_label" -      top_pad="5" -      type="string"> -      [http://community.secondlife.com/t5/English-Knowledge-Base/Second-Life-Share-Facebook/ta-p/2149711 Learn about posting to Facebook] -    </text> -  </panel> -         -       <text -        length="1" -        layout="topleft" -        follows="top|left|right" -        font="SansSerif" -        height="16" -        left="10" -        name="status_caption_label" -        top_pad="5" -        type="string"> -        What's on your mind? -       </text> -       <text_editor -        follows="left|top|right" -        layout="topleft" -        height="150" -        width="252" -        left="10" -        length="1" -        max_length="700" -        name="status_message" -        type="string" -        word_wrap="true"> -       </text_editor> -       <button -        follows="left|top" -        layout="topleft" -        top_pad="6" -        left="10" -        height="23" -        label="Post" -        name="post_status_btn" -        width="100"> -        <button.commit_callback -          function="SocialSharing.SendStatus" /> -       </button> -       <button -        follows="right|top" -        layout="topleft" -        height="23" -        label="Cancel" -        name="cancel_status_btn" -        right="-10" -        top_delta="0" -        width="100"> -        <button.commit_callback -          function="SocialSharing.Cancel" /> -       </button> -    </panel> diff --git a/indra/newview/skins/default/xui/en/panel_flickr_photo.xml b/indra/newview/skins/default/xui/en/panel_flickr_photo.xml index 6074ab9ef6..7fb2291423 100644 --- a/indra/newview/skins/default/xui/en/panel_flickr_photo.xml +++ b/indra/newview/skins/default/xui/en/panel_flickr_photo.xml @@ -158,6 +158,7 @@               length="1"               max_length="700"               name="photo_description" +             spellcheck="true"               type="string"               word_wrap="true">              </text_editor> diff --git a/indra/newview/skins/default/xui/en/panel_group_general.xml b/indra/newview/skins/default/xui/en/panel_group_general.xml index 26f54bacbc..e34335a2af 100644 --- a/indra/newview/skins/default/xui/en/panel_group_general.xml +++ b/indra/newview/skins/default/xui/en/panel_group_general.xml @@ -214,7 +214,7 @@ Hover your mouse over the options for more help.           layout="topleft"           left="10"           name="group_mature_check" -         tool_tip="Sets whether your group contains information rated as Moderate" +         tool_tip="Maturity ratings designate the type of content and behavior allowed in a group"           top_pad="4"           width="190">  			<combo_item name="select_mature" value="Select"> diff --git a/indra/newview/skins/default/xui/en/panel_group_roles.xml b/indra/newview/skins/default/xui/en/panel_group_roles.xml index 714d4166c0..f15f79e9aa 100644 --- a/indra/newview/skins/default/xui/en/panel_group_roles.xml +++ b/indra/newview/skins/default/xui/en/panel_group_roles.xml @@ -212,7 +212,15 @@ clicking on their names.         layout="topleft"         left="0"         name="role_create" -       width="120" /> +       width="100" /> +      <button +       follows="top|left" +       height="23" +       label="Copy Role" +       layout="topleft" +       left_pad="10" +       name="role_copy" +       width="100" />        <button         height="23"         follows="top|left" @@ -220,7 +228,7 @@ clicking on their names.         layout="topleft"         left_pad="10"         name="role_delete" -       width="120" /> +       width="100" />      </panel>      <panel       border="false" diff --git a/indra/newview/skins/default/xui/en/panel_landmark_info.xml b/indra/newview/skins/default/xui/en/panel_landmark_info.xml index fd6e96b9a7..13986c4030 100644 --- a/indra/newview/skins/default/xui/en/panel_landmark_info.xml +++ b/indra/newview/skins/default/xui/en/panel_landmark_info.xml @@ -277,6 +277,7 @@                   max_length="127"                   name="notes_editor"                   read_only="true" +                 spellcheck="true"                   text_readonly_color="white"                   text_type="ascii_with_newline"                   top_pad="5" diff --git a/indra/newview/skins/default/xui/en/panel_login_first.xml b/indra/newview/skins/default/xui/en/panel_login_first.xml index 213f9a6b0c..726e713595 100644 --- a/indra/newview/skins/default/xui/en/panel_login_first.xml +++ b/indra/newview/skins/default/xui/en/panel_login_first.xml @@ -111,7 +111,6 @@              combo_editor.font="SansSerifLarge"              max_chars="128"              top="0" -            commit_on_focus_lost="false"              combo_editor.prevalidate_callback="ascii"              tool_tip="The username you chose when you registered, like bobsmith12 or Steller Sunshine"              name="username_combo" @@ -141,7 +140,7 @@              follows="left|top"              image_unselected="PushButton_Login"              image_pressed="PushButton_Login_Pressed" -            image_hover="PushButton_Login_Over" +            image_hover_unselected="PushButton_Login_Over"              label="Log In"              label_color="White"              font="SansSerifLarge" diff --git a/indra/newview/skins/default/xui/en/panel_people.xml b/indra/newview/skins/default/xui/en/panel_people.xml index 8fc0f6f642..a47121ae99 100644 --- a/indra/newview/skins/default/xui/en/panel_people.xml +++ b/indra/newview/skins/default/xui/en/panel_people.xml @@ -367,24 +367,7 @@ Looking for people to hang out with? Try the [secondlife:///app/worldmap World M                           show_permissions_granted="true"                           top="0"                           width="307" /> -                </accordion_tab> -              <accordion_tab -               layout="topleft" -               height="173" -               name="tab_suggested_friends" -               title="People you may want to friend"> -                <avatar_list -                 ignore_online_status="true" -                 allow_select="true" -                 follows="all" -                 height="173" -                 layout="topleft" -                 left="0" -                 name="suggested_friends" -                 show_permissions_granted="true" -                 top="0" -                 width="307" /> -              </accordion_tab>               +                </accordion_tab>                         </accordion>              <text               follows="all" diff --git a/indra/newview/skins/default/xui/en/panel_postcard_message.xml b/indra/newview/skins/default/xui/en/panel_postcard_message.xml index 331a08b4bb..63c7259878 100644 --- a/indra/newview/skins/default/xui/en/panel_postcard_message.xml +++ b/indra/newview/skins/default/xui/en/panel_postcard_message.xml @@ -80,6 +80,7 @@       left="5"       max_length="700"       name="msg_form" +     spellcheck="true"       right="-4"       top_pad="5"       word_wrap="true"> diff --git a/indra/newview/skins/default/xui/en/panel_region_terrain.xml b/indra/newview/skins/default/xui/en/panel_region_terrain.xml index 5d060c0a0d..8243c2715d 100644 --- a/indra/newview/skins/default/xui/en/panel_region_terrain.xml +++ b/indra/newview/skins/default/xui/en/panel_region_terrain.xml @@ -94,6 +94,7 @@       layout="topleft"       left_delta="0"       name="texture_detail_0" +     default_image_id="0bc58228-74a0-7e83-89bc-5c23464bcec5"       top_delta="20"       width="100" />      <texture_picker @@ -102,6 +103,7 @@       layout="topleft"       left_pad="10"       name="texture_detail_1" +     default_image_id="63338ede-0037-c4fd-855b-015d77112fc8"       top_delta="0"       width="100" />      <texture_picker @@ -110,6 +112,7 @@       layout="topleft"       left_pad="10"       name="texture_detail_2" +     default_image_id="303cd381-8560-7579-23f1-f0a880799740"       top_delta="0"       width="100" />      <texture_picker @@ -118,6 +121,7 @@       layout="topleft"       left_pad="10"       name="texture_detail_3" +     default_image_id="53a2f406-4895-1d13-d541-d2e3b86bc19c"       top_delta="0"       width="100" />      <text diff --git a/indra/newview/skins/default/xui/en/panel_script_ed.xml b/indra/newview/skins/default/xui/en/panel_script_ed.xml index c56a5e17cd..ed37e9e2cc 100644 --- a/indra/newview/skins/default/xui/en/panel_script_ed.xml +++ b/indra/newview/skins/default/xui/en/panel_script_ed.xml @@ -28,10 +28,6 @@      name="Title">      Script: [NAME]    </panel.string> -  <panel.string -    name="external_editor_not_set"> -    Select an editor by setting the environment variable LL_SCRIPT_EDITOR or the ExternalEditor setting. -  </panel.string>    <menu_bar      bg_visible="false"      follows="left|top" diff --git a/indra/newview/skins/default/xui/en/panel_snapshot_options.xml b/indra/newview/skins/default/xui/en/panel_snapshot_options.xml index 305cce1cbe..981b9ab881 100644 --- a/indra/newview/skins/default/xui/en/panel_snapshot_options.xml +++ b/indra/newview/skins/default/xui/en/panel_snapshot_options.xml @@ -61,23 +61,6 @@     font="SansSerif"     halign="left"     height="22" -   image_overlay="Snapshot_Facebook" -   image_overlay_alignment="left" -   image_top_pad="0" -   imgoverlay_label_space="10" -   label="Share to Facebook" -   layout="topleft" -   left_delta="0" -   name="send_to_facebook_btn" -   top_pad="5"> -    <button.commit_callback -     function="Snapshot.SendToFacebook"/> -  </button> -  <button -   follows="left|top" -   font="SansSerif" -   halign="left" -   height="22"     image_overlay="Command_Twitter_Icon"     image_overlay_alignment="left"     image_top_pad="0" diff --git a/indra/newview/skins/default/xui/en/panel_snapshot_profile.xml b/indra/newview/skins/default/xui/en/panel_snapshot_profile.xml index d86cb92981..2fdbee49f0 100644 --- a/indra/newview/skins/default/xui/en/panel_snapshot_profile.xml +++ b/indra/newview/skins/default/xui/en/panel_snapshot_profile.xml @@ -126,6 +126,7 @@       length="1"       max_length="700"       name="caption" +     spellcheck="true"       width="200"       top_pad="2"       type="string" diff --git a/indra/newview/skins/default/xui/en/panel_twitter_photo.xml b/indra/newview/skins/default/xui/en/panel_twitter_photo.xml index 9a460ceead..8774d09a03 100644 --- a/indra/newview/skins/default/xui/en/panel_twitter_photo.xml +++ b/indra/newview/skins/default/xui/en/panel_twitter_photo.xml @@ -39,6 +39,7 @@             length="1"             max_length="140"             name="photo_status" +           spellcheck="true"             type="string"             word_wrap="true">            </text_editor> diff --git a/indra/newview/skins/default/xui/en/strings.xml b/indra/newview/skins/default/xui/en/strings.xml index 148effb01d..c386cb9457 100644 --- a/indra/newview/skins/default/xui/en/strings.xml +++ b/indra/newview/skins/default/xui/en/strings.xml @@ -58,6 +58,9 @@ Advanced Lighting Model: [GPU_SHADERS]  Texture memory: [TEXTURE_MEMORY]MB  VFS (cache) creation time: [VFS_TIME]  	</string> +	<string name="AboutOSXHiDPI"> +HiDPI display mode: [HIDPI] +	</string>  	<string name="AboutLibs">  J2C Decoder Version: [J2C_VERSION]  Audio Driver Version: [AUDIO_DRIVER_VERSION] @@ -199,13 +202,7 @@ Please try logging in again in a minute.</string>  	<string name="SentToInvalidRegion">You were sent to an invalid region.</string>  	<string name="TestingDisconnect">Testing viewer disconnect</string> -	<!-- SLShare: Facebook, Flickr, and Twitter --> -  <string name="SocialFacebookConnecting">Connecting to Facebook...</string> -  <string name="SocialFacebookPosting">Posting...</string> -  <string name="SocialFacebookDisconnecting">Disconnecting from Facebook...</string> -  <string name="SocialFacebookErrorConnecting">Problem connecting to Facebook</string> -  <string name="SocialFacebookErrorPosting">Problem posting to Facebook</string> -  <string name="SocialFacebookErrorDisconnecting">Problem disconnecting from Facebook</string> +	<!-- SLShare: Flickr and Twitter -->    <string name="SocialFlickrConnecting">Connecting to Flickr...</string>    <string name="SocialFlickrPosting">Posting...</string>    <string name="SocialFlickrDisconnecting">Disconnecting from Flickr...</string> @@ -2302,6 +2299,9 @@ For AI Character: Get the closest navigable point to the point provided.  	<string name="MarketplaceURL_Dashboard">https://marketplace.[MARKETPLACE_DOMAIN_NAME]/merchants/store/dashboard</string>  	<string name="MarketplaceURL_Imports">https://marketplace.[MARKETPLACE_DOMAIN_NAME]/merchants/store/imports</string>  	<string name="MarketplaceURL_LearnMore">https://marketplace.[MARKETPLACE_DOMAIN_NAME]/learn_more</string> +	<string name="InventoryPlayAnimationTooltip">Open window with Play options.</string> +	<string name="InventoryPlayGestureTooltip">Execute selected gesture in-world.</string> +	<string name="InventoryPlaySoundTooltip">Open window with Play options.</string>  	<string name="InventoryOutboxNotMerchantTitle">Anyone can sell items on the Marketplace.</string>  	<string name="InventoryOutboxNotMerchantTooltip"></string>  	<string name="InventoryOutboxNotMerchant"> @@ -3653,9 +3653,6 @@ If you continue to receive this message, contact the [SUPPORT_SITE].      Drag items from inventory here    </string> -  <string name="facebook_post_success"> -    You posted to Facebook. -  </string>    <string name="flickr_post_success">      You posted to Flickr.    </string> @@ -3943,7 +3940,7 @@ Please check http://status.secondlifegrid.net to see if there is a known problem    <string name="EmptyOutfitText">There are no items in this outfit</string>   <!-- External editor status codes --> - <string name="ExternalEditorNotSet">Select an editor using the ExternalEditor setting.</string> + <string name="ExternalEditorNotSet">Select an editor by setting the environment variable LL_SCRIPT_EDITOR or the ExternalEditor setting.</string>   <string name="ExternalEditorNotFound">Cannot find the external editor you specified.  Try enclosing path to the editor with double quotes.  (e.g. "/path to my/editor" "%s")</string> @@ -4088,7 +4085,6 @@ Try enclosing path to the editor with double quotes.    <string name="Command_Conversations_Label">Conversations</string>    <string name="Command_Compass_Label">Compass</string>    <string name="Command_Destinations_Label">Destinations</string> -  <string name="Command_Facebook_Label">Facebook</string>    <string name="Command_Flickr_Label">Flickr</string>    <string name="Command_Gestures_Label">Gestures</string>    <string name="Command_Grid_Status_Label">Grid status</string> @@ -4121,7 +4117,6 @@ Try enclosing path to the editor with double quotes.    <string name="Command_Conversations_Tooltip">Converse with everyone</string>    <string name="Command_Compass_Tooltip">Compass</string>    <string name="Command_Destinations_Tooltip">Destinations of interest</string> -  <string name="Command_Facebook_Tooltip">Post to Facebook</string>    <string name="Command_Flickr_Tooltip">Upload to Flickr</string>    <string name="Command_Gestures_Tooltip">Gestures for your avatar</string>    <string name="Command_Grid_Status_Tooltip">Show current Grid status</string> diff --git a/indra/newview/skins/default/xui/en/widgets/person_view.xml b/indra/newview/skins/default/xui/en/widgets/person_view.xml index 46c1b7ff75..bfe6941a8a 100644 --- a/indra/newview/skins/default/xui/en/widgets/person_view.xml +++ b/indra/newview/skins/default/xui/en/widgets/person_view.xml @@ -13,16 +13,6 @@    text_pad_right="4"    arrow_size="10"    max_folder_item_overlap="2"> -    <facebook_icon -      follows="left" -      height="14" -      image_name="Facebook_Icon" -      left="5" -      bottom="6" -      name="facebook_icon" -      tool_tip="Facebook User" -      visible="false" -      width="14" />      <avatar_icon        follows="left"        layout="topleft" diff --git a/indra/newview/skins/default/xui/fr/notifications.xml b/indra/newview/skins/default/xui/fr/notifications.xml index 3ac2cfb69b..4239c949fd 100644 --- a/indra/newview/skins/default/xui/fr/notifications.xml +++ b/indra/newview/skins/default/xui/fr/notifications.xml @@ -2987,7 +2987,7 @@ Si vous restez dans cette région, vous serez déconnecté(e).  Si vous restez dans cette région, vous serez déconnecté(e).  	</notification>  	<notification name="LoadWebPage"> -		Charger la page Web [URL] ? +Charger la page Web [URL] ?  [MESSAGE] | 
