diff options
Diffstat (limited to 'indra')
30 files changed, 789 insertions, 79 deletions
| diff --git a/indra/llui/lltextbase.cpp b/indra/llui/lltextbase.cpp index 88a5c3a587..f3a99dcef2 100644 --- a/indra/llui/lltextbase.cpp +++ b/indra/llui/lltextbase.cpp @@ -1522,7 +1522,7 @@ void LLTextBase::reflow()  		}  		S32 line_height = 0; -		S32 seg_line_offset = line_count; +		S32 seg_line_offset = line_count + 1;  		while(seg_iter != mSegments.end())  		{ diff --git a/indra/newview/CMakeLists.txt b/indra/newview/CMakeLists.txt index dbec4b5d65..7ed18801cf 100644 --- a/indra/newview/CMakeLists.txt +++ b/indra/newview/CMakeLists.txt @@ -203,6 +203,7 @@ set(viewer_SOURCE_FILES      llfloaterautoreplacesettings.cpp      llfloateravatar.cpp      llfloateravatarpicker.cpp +    llfloateravatarrendersettings.cpp      llfloateravatartextures.cpp      llfloaterbeacons.cpp      llfloaterbigpreview.cpp @@ -820,6 +821,7 @@ set(viewer_HEADER_FILES      llfloaterautoreplacesettings.h      llfloateravatar.h      llfloateravatarpicker.h +    llfloateravatarrendersettings.h      llfloateravatartextures.h      llfloaterbeacons.h      llfloaterbigpreview.h diff --git a/indra/newview/app_settings/settings.xml b/indra/newview/app_settings/settings.xml index fb644d3d5a..097a9ac7b9 100644 --- a/indra/newview/app_settings/settings.xml +++ b/indra/newview/app_settings/settings.xml @@ -8426,6 +8426,17 @@          <key>Value</key>              <integer>1</integer>          </map> +  <key>AlwaysRenderFriends</key> +    <map> +      <key>Comment</key> +      <string>Always render friends regardless of max complexity</string> +      <key>Persist</key> +      <integer>1</integer> +      <key>Type</key> +      <string>Boolean</string> +      <key>Value</key> +      <integer>0</integer> +    </map>    <key>RenderAvatar</key>      <map>        <key>Comment</key> diff --git a/indra/newview/llagentcamera.cpp b/indra/newview/llagentcamera.cpp index e335eabd1a..7723dbf978 100644 --- a/indra/newview/llagentcamera.cpp +++ b/indra/newview/llagentcamera.cpp @@ -1537,6 +1537,11 @@ LLVector3d LLAgentCamera::calcFocusPositionTargetGlobal()  	}  	else if (mCameraMode == CAMERA_MODE_CUSTOMIZE_AVATAR)  	{ +		LLVector3 focus_target = isAgentAvatarValid() +			? gAgentAvatarp->mHeadp->getWorldPosition() +			: gAgent.getPositionAgent(); +		LLVector3d focus_target_global = gAgent.getPosGlobalFromAgent(focus_target); +		mFocusTargetGlobal = focus_target_global;  		return mFocusTargetGlobal;  	}  	else if (!mFocusOnAvatar) diff --git a/indra/newview/llfloateravatarrendersettings.cpp b/indra/newview/llfloateravatarrendersettings.cpp new file mode 100644 index 0000000000..e7ac3f2737 --- /dev/null +++ b/indra/newview/llfloateravatarrendersettings.cpp @@ -0,0 +1,286 @@ +/** + * @file llfloateravatarrendersettings.cpp + * @brief Shows the list of avatars with non-default rendering settings + * + * $LicenseInfo:firstyear=2009&license=viewerlgpl$ + * Second Life Viewer Source Code + * Copyright (C) 2017, 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 "llfloateravatarrendersettings.h" + +#include "llavatarnamecache.h" +#include "llfloateravatarpicker.h" +#include "llfiltereditor.h" +#include "llfloaterreg.h" +#include "llnamelistctrl.h" +#include "llmenugl.h" +#include "llviewerobjectlist.h" +#include "llvoavatar.h" + +class LLSettingsContextMenu : public LLListContextMenu + +{ +public: +    LLSettingsContextMenu(LLFloaterAvatarRenderSettings* floater_settings) +        :   mFloaterSettings(floater_settings) +    {} +protected: +    LLContextMenu* createMenu() +    { +        LLUICtrl::CommitCallbackRegistry::ScopedRegistrar registrar; +        LLUICtrl::EnableCallbackRegistry::ScopedRegistrar enable_registrar; +        registrar.add("Settings.SetRendering", boost::bind(&LLFloaterAvatarRenderSettings::onCustomAction, mFloaterSettings, _2, mUUIDs.front())); +        enable_registrar.add("Settings.IsSelected", boost::bind(&LLFloaterAvatarRenderSettings::isActionChecked, mFloaterSettings, _2, mUUIDs.front())); +        LLContextMenu* menu = createFromFile("menu_avatar_rendering_settings.xml"); + +        return menu; +    } + +    LLFloaterAvatarRenderSettings* mFloaterSettings; +}; + +class LLAvatarRenderMuteListObserver : public LLMuteListObserver +{ +    /* virtual */ void onChange()  { LLFloaterAvatarRenderSettings::setNeedsUpdate();} +}; + +static LLAvatarRenderMuteListObserver sAvatarRenderMuteListObserver; + +LLFloaterAvatarRenderSettings::LLFloaterAvatarRenderSettings(const LLSD& key) +:   LLFloater(key), +	mAvatarSettingsList(NULL), +	mNeedsUpdate(false) +{ +    mContextMenu = new LLSettingsContextMenu(this); +    LLRenderMuteList::getInstance()->addObserver(&sAvatarRenderMuteListObserver); +    mCommitCallbackRegistrar.add("Settings.AddNewEntry", boost::bind(&LLFloaterAvatarRenderSettings::onClickAdd, this, _2)); +} + +LLFloaterAvatarRenderSettings::~LLFloaterAvatarRenderSettings() +{ +    delete mContextMenu; +    LLRenderMuteList::getInstance()->removeObserver(&sAvatarRenderMuteListObserver); +} + +BOOL LLFloaterAvatarRenderSettings::postBuild() +{ +    LLFloater::postBuild(); +    mAvatarSettingsList = getChild<LLNameListCtrl>("render_settings_list"); +    mAvatarSettingsList->setRightMouseDownCallback(boost::bind(&LLFloaterAvatarRenderSettings::onAvatarListRightClick, this, _1, _2, _3)); +    this->setVisibleCallback(boost::bind(&LLFloaterAvatarRenderSettings::removePicker, this)); +    getChild<LLFilterEditor>("people_filter_input")->setCommitCallback(boost::bind(&LLFloaterAvatarRenderSettings::onFilterEdit, this, _2)); + +	return TRUE; +} + +void LLFloaterAvatarRenderSettings::removePicker() +{ +    if(mPicker.get()) +    { +        mPicker.get()->closeFloater(); +    } +} + +void LLFloaterAvatarRenderSettings::draw() +{ +    if(mNeedsUpdate) +    { +        updateList(); +        mNeedsUpdate = false; +    } + +    LLFloater::draw(); +} + +void LLFloaterAvatarRenderSettings::onAvatarListRightClick(LLUICtrl* ctrl, S32 x, S32 y) +{ +    LLNameListCtrl* list = dynamic_cast<LLNameListCtrl*>(ctrl); +    if (!list) return; +    list->selectItemAt(x, y, MASK_NONE); +    uuid_vec_t selected_uuids; + +    if(list->getCurrentID().notNull()) +    { +        selected_uuids.push_back(list->getCurrentID()); +        mContextMenu->show(ctrl, selected_uuids, x, y); +    } +} + +void LLFloaterAvatarRenderSettings::onOpen(const LLSD& key) +{ +    updateList(); +} + +void LLFloaterAvatarRenderSettings::updateList() +{ +    mAvatarSettingsList->deleteAllItems(); +    LLAvatarName av_name; +    LLNameListCtrl::NameItem item_params; +    for (std::map<LLUUID, S32>::iterator iter = LLRenderMuteList::getInstance()->sVisuallyMuteSettingsMap.begin(); iter != LLRenderMuteList::getInstance()->sVisuallyMuteSettingsMap.end(); iter++) +    { +        item_params.value = iter->first; +        LLAvatarNameCache::get(iter->first, &av_name); +        if(!isHiddenRow(av_name.getCompleteName())) +        { +            item_params.columns.add().value(av_name.getCompleteName()).column("name"); +            std::string setting = getString(iter->second == 1 ? "av_never_render" : "av_always_render"); +            item_params.columns.add().value(setting).column("setting"); +            mAvatarSettingsList->addNameItemRow(item_params); +        } +    } +} + +void LLFloaterAvatarRenderSettings::onFilterEdit(const std::string& search_string) +{ +    std::string filter_upper = search_string; +    LLStringUtil::toUpper(filter_upper); +    if (mNameFilter != filter_upper) +    { +        mNameFilter = filter_upper; +        mNeedsUpdate = true; +    } +} + +bool LLFloaterAvatarRenderSettings::isHiddenRow(const std::string& av_name) +{ +    if (mNameFilter.empty()) return false; +    std::string upper_name = av_name; +    LLStringUtil::toUpper(upper_name); +    return std::string::npos == upper_name.find(mNameFilter); +} + +static LLVOAvatar* find_avatar(const LLUUID& id) +{ +    LLViewerObject *obj = gObjectList.findObject(id); +    while (obj && obj->isAttachment()) +    { +        obj = (LLViewerObject *)obj->getParent(); +    } + +    if (obj && obj->isAvatar()) +    { +        return (LLVOAvatar*)obj; +    } +    else +    { +        return NULL; +    } +} + + +void LLFloaterAvatarRenderSettings::onCustomAction (const LLSD& userdata, const LLUUID& av_id) +{ +    const std::string command_name = userdata.asString(); + +    S32 new_setting = 0; +    if ("default" == command_name) +    { +        new_setting = S32(LLVOAvatar::AV_RENDER_NORMALLY); +    } +    else if ("never" == command_name) +    { +        new_setting = S32(LLVOAvatar::AV_DO_NOT_RENDER); +    } +    else if ("always" == command_name) +    { +        new_setting = S32(LLVOAvatar::AV_ALWAYS_RENDER); +    } + +    LLVOAvatar *avatarp = find_avatar(av_id); +    if (avatarp) +    { +        avatarp->setVisualMuteSettings(LLVOAvatar::VisualMuteSettings(new_setting)); +    } +    else +    { +        LLRenderMuteList::getInstance()->saveVisualMuteSetting(av_id, new_setting); +    } +} + + +bool LLFloaterAvatarRenderSettings::isActionChecked(const LLSD& userdata, const LLUUID& av_id) +{ +    const std::string command_name = userdata.asString(); + +    S32 visual_setting = LLRenderMuteList::getInstance()->getSavedVisualMuteSetting(av_id); +    if ("default" == command_name) +    { +        return (visual_setting == S32(LLVOAvatar::AV_RENDER_NORMALLY)); +    } +    else if ("never" == command_name) +    { +        return (visual_setting == S32(LLVOAvatar::AV_DO_NOT_RENDER)); +    } +    else if ("always" == command_name) +    { +        return (visual_setting == S32(LLVOAvatar::AV_ALWAYS_RENDER)); +    } +    return false; +} + +void LLFloaterAvatarRenderSettings::setNeedsUpdate() +{ +    LLFloaterAvatarRenderSettings* instance = LLFloaterReg::getTypedInstance<LLFloaterAvatarRenderSettings>("avatar_render_settings"); +    if(!instance) return; +    instance->mNeedsUpdate = true; +} + +void LLFloaterAvatarRenderSettings::onClickAdd(const LLSD& userdata) +{ +    const std::string command_name = userdata.asString(); +    S32 visual_setting = 0; +    if ("never" == command_name) +    { +        visual_setting = S32(LLVOAvatar::AV_DO_NOT_RENDER); +    } +    else if ("always" == command_name) +    { +        visual_setting = S32(LLVOAvatar::AV_ALWAYS_RENDER); +    } + +    LLView * button = findChild<LLButton>("plus_btn", TRUE); +    LLFloater* root_floater = gFloaterView->getParentFloater(this); +    LLFloaterAvatarPicker * picker = LLFloaterAvatarPicker::show(boost::bind(&LLFloaterAvatarRenderSettings::callbackAvatarPicked, this, _1, visual_setting), +                                                                    FALSE, TRUE, FALSE, root_floater->getName(), button); + +    if (root_floater) +    { +        root_floater->addDependentFloater(picker); +    } + +    mPicker = picker->getHandle(); +} + +void LLFloaterAvatarRenderSettings::callbackAvatarPicked(const uuid_vec_t& ids, S32 visual_setting) +{ +    if (ids.empty()) return; + +    LLVOAvatar *avatarp = find_avatar(ids[0]); +    if (avatarp) +    { +        avatarp->setVisualMuteSettings(LLVOAvatar::VisualMuteSettings(visual_setting)); +    } +    else +    { +        LLRenderMuteList::getInstance()->saveVisualMuteSetting(ids[0], visual_setting); +    } +} diff --git a/indra/newview/llfloateravatarrendersettings.h b/indra/newview/llfloateravatarrendersettings.h new file mode 100644 index 0000000000..fe727bcf32 --- /dev/null +++ b/indra/newview/llfloateravatarrendersettings.h @@ -0,0 +1,71 @@ +/** + * @file llfloateravatarrendersettings.h + * @brief Shows the list of avatars with non-default rendering settings + * + * $LicenseInfo:firstyear=2009&license=viewerlgpl$ + * Second Life Viewer Source Code + * Copyright (C) 2017, 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_LLFLOATERAVATARRENDERSETTINGS_H +#define LL_LLFLOATERAVATARRENDERSETTINGS_H + +#include "llfloater.h" +#include "lllistcontextmenu.h" +#include "llmutelist.h" + +class LLNameListCtrl; + +class LLFloaterAvatarRenderSettings : public LLFloater +{ +public: + +    LLFloaterAvatarRenderSettings(const LLSD& key); +    virtual ~LLFloaterAvatarRenderSettings(); + +    /*virtual*/ BOOL postBuild(); +    /*virtual*/ void onOpen(const LLSD& key); +    /*virtual*/ void draw(); + +    void onAvatarListRightClick(LLUICtrl* ctrl, S32 x, S32 y); + +    void updateList(); +    void onFilterEdit(const std::string& search_string); +    void onCustomAction (const LLSD& userdata, const LLUUID& av_id); +    bool isActionChecked(const LLSD& userdata, const LLUUID& av_id); +    void onClickAdd(const LLSD& userdata); + +    static void setNeedsUpdate(); + +private: +    bool isHiddenRow(const std::string& av_name); +    void callbackAvatarPicked(const uuid_vec_t& ids, S32 visual_setting); +    void removePicker(); + +    bool mNeedsUpdate; +    LLListContextMenu* mContextMenu; +    LLNameListCtrl* mAvatarSettingsList; +    LLHandle<LLFloater> mPicker; + +    std::string mNameFilter; +}; + + +#endif //LL_LLFLOATERAVATARRENDERSETTINGS_H diff --git a/indra/newview/llfloaterpreference.cpp b/indra/newview/llfloaterpreference.cpp index df4bc043e5..1f460c05ec 100644 --- a/indra/newview/llfloaterpreference.cpp +++ b/indra/newview/llfloaterpreference.cpp @@ -360,6 +360,7 @@ LLFloaterPreference::LLFloaterPreference(const LLSD& key)  	mCommitCallbackRegistrar.add("Pref.ClickEnablePopup",		boost::bind(&LLFloaterPreference::onClickEnablePopup, this));  	mCommitCallbackRegistrar.add("Pref.ClickDisablePopup",		boost::bind(&LLFloaterPreference::onClickDisablePopup, this));	  	mCommitCallbackRegistrar.add("Pref.LogPath",				boost::bind(&LLFloaterPreference::onClickLogPath, this)); +	mCommitCallbackRegistrar.add("Pref.RenderExceptions",       boost::bind(&LLFloaterPreference::onClickRenderExceptions, this));  	mCommitCallbackRegistrar.add("Pref.HardwareDefaults",		boost::bind(&LLFloaterPreference::setHardwareDefaults, this));  	mCommitCallbackRegistrar.add("Pref.AvatarImpostorsEnable",	boost::bind(&LLFloaterPreference::onAvatarImpostorsEnable, this));  	mCommitCallbackRegistrar.add("Pref.UpdateIndirectMaxComplexity",	boost::bind(&LLFloaterPreference::updateMaxComplexity, this)); @@ -385,7 +386,7 @@ LLFloaterPreference::LLFloaterPreference(const LLSD& key)  	gSavedSettings.getControl("NameTagShowUsernames")->getCommitSignal()->connect(boost::bind(&handleNameTagOptionChanged,  _2));	  	gSavedSettings.getControl("NameTagShowFriends")->getCommitSignal()->connect(boost::bind(&handleNameTagOptionChanged,  _2));	  	gSavedSettings.getControl("UseDisplayNames")->getCommitSignal()->connect(boost::bind(&handleDisplayNamesOptionChanged,  _2)); -	 +  	gSavedSettings.getControl("AppearanceCameraMovement")->getCommitSignal()->connect(boost::bind(&handleAppearanceCameraMovementChanged,  _2));  	LLAvatarPropertiesProcessor::getInstance()->addObserver( gAgent.getID(), this ); @@ -786,10 +787,12 @@ void LLFloaterPreference::onOpen(const LLSD& key)  	LLButton* load_btn = findChild<LLButton>("PrefLoadButton");  	LLButton* save_btn = findChild<LLButton>("PrefSaveButton");  	LLButton* delete_btn = findChild<LLButton>("PrefDeleteButton"); +	LLButton* exceptions_btn = findChild<LLButton>("RenderExceptionsButton");  	load_btn->setEnabled(started);  	save_btn->setEnabled(started);  	delete_btn->setEnabled(started); +	exceptions_btn->setEnabled(started);  }  void LLFloaterPreference::onVertexShaderEnable() @@ -2075,6 +2078,11 @@ void LLFloaterPreference::onClickSpellChecker()      LLFloaterReg::showInstance("prefs_spellchecker");  } +void LLFloaterPreference::onClickRenderExceptions() +{ +    LLFloaterReg::showInstance("avatar_render_settings"); +} +  void LLFloaterPreference::onClickAdvanced()  {  	LLFloaterReg::showInstance("prefs_graphics_advanced"); diff --git a/indra/newview/llfloaterpreference.h b/indra/newview/llfloaterpreference.h index ea199cf034..2bb2e7e9ff 100644 --- a/indra/newview/llfloaterpreference.h +++ b/indra/newview/llfloaterpreference.h @@ -171,6 +171,7 @@ public:  	void onClickPermsDefault();  	void onClickAutoReplace();  	void onClickSpellChecker(); +	void onClickRenderExceptions();  	void onClickAdvanced();  	void applyUIColor(LLUICtrl* ctrl, const LLSD& param);  	void getUIColor(LLUICtrl* ctrl, const LLSD& param); diff --git a/indra/newview/llinventorymodelbackgroundfetch.cpp b/indra/newview/llinventorymodelbackgroundfetch.cpp index 4a77edc565..a8919db828 100644 --- a/indra/newview/llinventorymodelbackgroundfetch.cpp +++ b/indra/newview/llinventorymodelbackgroundfetch.cpp @@ -360,9 +360,12 @@ void LLInventoryModelBackgroundFetch::incrFetchCount(S32 fetching)  	}  } +static LLTrace::BlockTimerStatHandle FTM_BULK_FETCH("Bulk Fetch"); +  // Bundle up a bunch of requests to send all at once.  void LLInventoryModelBackgroundFetch::bulkFetch()  { +	LL_RECORD_BLOCK_TIME(FTM_BULK_FETCH);  	//Background fetch is called from gIdleCallbacks in a loop until background fetch is stopped.  	//If there are items in mFetchQueue, we want to check the time since the last bulkFetch was   	//sent.  If it exceeds our retry time, go ahead and fire off another batch.   diff --git a/indra/newview/llmarketplacefunctions.cpp b/indra/newview/llmarketplacefunctions.cpp index 54f95520db..a0e19f2d19 100644 --- a/indra/newview/llmarketplacefunctions.cpp +++ b/indra/newview/llmarketplacefunctions.cpp @@ -121,7 +121,6 @@ namespace {          {              // Prompt the user with the warning (so they know why things are failing)              LLSD subs; -            subs["[ERROR_REASON]"] = reason;              // We do show long descriptions in the alert (unlikely to be readable). The description string will be in the log though.              std::string description;              if (result.has(LLCoreHttpUtil::HttpCoroutineAdapter::HTTP_RESULTS_CONTENT)) @@ -145,6 +144,16 @@ namespace {              {                  description = result.asString();              } +            std::string reason_lc = reason; +            LLStringUtil::toLower(reason_lc); +            if (!description.empty() && reason_lc.find("unknown") != std::string::npos) +            { +                subs["[ERROR_REASON]"] = ""; +            } +            else +            { +                subs["[ERROR_REASON]"] = "'" + reason +"'\n"; +            }              subs["[ERROR_DESCRIPTION]"] = description;              LLNotificationsUtil::add("MerchantTransactionFailed", subs);          } diff --git a/indra/newview/llmutelist.cpp b/indra/newview/llmutelist.cpp index 3af9c2f912..02b28a2bf8 100644 --- a/indra/newview/llmutelist.cpp +++ b/indra/newview/llmutelist.cpp @@ -812,3 +812,99 @@ void LLMuteList::notifyObserversDetailed(const LLMute& mute)  		it = mObservers.upper_bound(observer);  	}  } + +LLRenderMuteList::LLRenderMuteList() +{} + +bool LLRenderMuteList::saveToFile() +{ +    std::string filename = gDirUtilp->getExpandedFilename(LL_PATH_PER_SL_ACCOUNT, "render_mute_settings.txt"); +    LLFILE* fp = LLFile::fopen(filename, "wb"); +    if (!fp) +    { +        LL_WARNS() << "Couldn't open render mute list file: " << filename << LL_ENDL; +        return false; +    } +    for (std::map<LLUUID, S32>::iterator it = sVisuallyMuteSettingsMap.begin(); it != sVisuallyMuteSettingsMap.end(); ++it) +    { +        if (it->second != 0) +        { +            std::string id_string; +            it->first.toString(id_string); +            fprintf(fp, "%d %s\n", (S32)it->second, id_string.c_str()); +        } +    } +    fclose(fp); +    return true; +} + +bool LLRenderMuteList::loadFromFile() +{ +	std::string filename = gDirUtilp->getExpandedFilename(LL_PATH_PER_SL_ACCOUNT, "render_mute_settings.txt"); +	LLFILE* fp = LLFile::fopen(filename, "rb"); +	if (!fp) +	{ +		LL_WARNS() << "Couldn't open render mute list file: " << filename << LL_ENDL; +		return false; +	} + +	char id_buffer[MAX_STRING]; +	char buffer[MAX_STRING]; +	while (!feof(fp) && fgets(buffer, MAX_STRING, fp)) +	{ +		id_buffer[0] = '\0'; +		S32 setting = 0; +		sscanf(buffer, " %d %254s\n", &setting, id_buffer); +		sVisuallyMuteSettingsMap[LLUUID(id_buffer)] = setting; +	} +	fclose(fp); +    return true; +} + +void LLRenderMuteList::saveVisualMuteSetting(const LLUUID& agent_id, S32 setting) +{ +    if(setting == 0) +    { +        sVisuallyMuteSettingsMap.erase(agent_id); +    } +    else +    { +        sVisuallyMuteSettingsMap[agent_id] = setting; +    } +    saveToFile(); +    notifyObservers(); +} + +S32 LLRenderMuteList::getSavedVisualMuteSetting(const LLUUID& agent_id) +{ +    std::map<LLUUID, S32>::iterator iter = sVisuallyMuteSettingsMap.find(agent_id); +    if (iter != sVisuallyMuteSettingsMap.end()) +    { +        return iter->second; +    } + +    return 0; +} + +void LLRenderMuteList::addObserver(LLMuteListObserver* observer) +{ +    mObservers.insert(observer); +} + +void LLRenderMuteList::removeObserver(LLMuteListObserver* observer) +{ +    mObservers.erase(observer); +} + +void LLRenderMuteList::notifyObservers() +{ +    for (observer_set_t::iterator it = mObservers.begin(); +        it != mObservers.end(); +        ) +    { +        LLMuteListObserver* observer = *it; +        observer->onChange(); +        // In case onChange() deleted an entry. +        it = mObservers.upper_bound(observer); +    } +} diff --git a/indra/newview/llmutelist.h b/indra/newview/llmutelist.h index 4ceddc97fd..9ab978353b 100644 --- a/indra/newview/llmutelist.h +++ b/indra/newview/llmutelist.h @@ -175,5 +175,25 @@ public:  	virtual void onChangeDetailed(const LLMute& ) { }  }; +class LLRenderMuteList : public LLSingleton<LLRenderMuteList> +{ +    LLSINGLETON(LLRenderMuteList); +public: +	bool loadFromFile(); +	bool saveToFile(); +	S32 getSavedVisualMuteSetting(const LLUUID& agent_id); +	void saveVisualMuteSetting(const LLUUID& agent_id, S32 setting); + +	void addObserver(LLMuteListObserver* observer); +	void removeObserver(LLMuteListObserver* observer); + +	std::map<LLUUID, S32> sVisuallyMuteSettingsMap; + +private: +	void notifyObservers(); +	typedef std::set<LLMuteListObserver*> observer_set_t; +	observer_set_t mObservers; +}; +  #endif //LL_MUTELIST_H diff --git a/indra/newview/llpanelsnapshotpostcard.cpp b/indra/newview/llpanelsnapshotpostcard.cpp index ebf9153da9..3d18e837af 100644 --- a/indra/newview/llpanelsnapshotpostcard.cpp +++ b/indra/newview/llpanelsnapshotpostcard.cpp @@ -106,6 +106,14 @@ BOOL LLPanelSnapshotPostcard::postBuild()  // virtual  void LLPanelSnapshotPostcard::onOpen(const LLSD& key)  { +	LLUICtrl* name_form = getChild<LLUICtrl>("name_form"); +	if (name_form && name_form->getValue().asString().empty()) +	{ +		std::string name_string; +		LLAgentUI::buildFullname(name_string); +		getChild<LLUICtrl>("name_form")->setValue(LLSD(name_string)); +	} +  	LLPanelSnapshot::onOpen(key);  } diff --git a/indra/newview/llselectmgr.cpp b/indra/newview/llselectmgr.cpp index 353c61da0c..983a7ca1ae 100644 --- a/indra/newview/llselectmgr.cpp +++ b/indra/newview/llselectmgr.cpp @@ -614,6 +614,12 @@ bool LLSelectMgr::linkObjects()  		return true;  	} +	if (!LLSelectMgr::getInstance()->selectGetSameRegion()) +	{ +		LLNotificationsUtil::add("CannotLinkAcrossRegions"); +		return true; +	} +  	LLSelectMgr::getInstance()->sendLink();  	return true; @@ -2778,6 +2784,35 @@ BOOL LLSelectMgr::selectGetRootsModify()  	return TRUE;  } +//----------------------------------------------------------------------------- +// selectGetSameRegion() - return TRUE if all objects are in same region +//----------------------------------------------------------------------------- +BOOL LLSelectMgr::selectGetSameRegion() +{ +    if (getSelection()->isEmpty()) +    { +        return TRUE; +    } +    LLViewerObject* object = getSelection()->getFirstObject(); +    if (!object) +    { +        return FALSE; +    } +    LLViewerRegion* current_region = object->getRegion(); + +    for (LLObjectSelection::root_iterator iter = getSelection()->root_begin(); +        iter != getSelection()->root_end(); iter++) +    { +        LLSelectNode* node = *iter; +        object = node->getObject(); +        if (!node->mValid || !object || current_region != object->getRegion()) +        { +            return FALSE; +        } +    } + +    return TRUE; +}  //-----------------------------------------------------------------------------  // selectGetNonPermanentEnforced() - return TRUE if all objects are not diff --git a/indra/newview/llselectmgr.h b/indra/newview/llselectmgr.h index 2a893af266..7ef0032645 100644 --- a/indra/newview/llselectmgr.h +++ b/indra/newview/llselectmgr.h @@ -624,6 +624,9 @@ public:  	BOOL selectGetRootsModify();  	BOOL selectGetModify(); +	// returns TRUE if all objects are in same region +	BOOL selectGetSameRegion(); +  	// returns TRUE if is all objects are non-permanent-enforced  	BOOL selectGetRootsNonPermanentEnforced();  	BOOL selectGetNonPermanentEnforced(); diff --git a/indra/newview/llstartup.cpp b/indra/newview/llstartup.cpp index 347409fcab..0a85344025 100644 --- a/indra/newview/llstartup.cpp +++ b/indra/newview/llstartup.cpp @@ -967,6 +967,8 @@ bool idle_startup()  		// Load media plugin cookies  		LLViewerMedia::loadCookieFile(); +		LLRenderMuteList::getInstance()->loadFromFile(); +  		//-------------------------------------------------  		// Handle startup progress screen  		//------------------------------------------------- diff --git a/indra/newview/llviewerfloaterreg.cpp b/indra/newview/llviewerfloaterreg.cpp index 46525e8455..cf18299b0b 100644 --- a/indra/newview/llviewerfloaterreg.cpp +++ b/indra/newview/llviewerfloaterreg.cpp @@ -38,6 +38,7 @@  #include "llfloaterautoreplacesettings.h"  #include "llfloateravatar.h"  #include "llfloateravatarpicker.h" +#include "llfloateravatarrendersettings.h"  #include "llfloateravatartextures.h"  #include "llfloaterbigpreview.h"  #include "llfloaterbeacons.h" @@ -194,6 +195,7 @@ void LLViewerFloaterReg::registerFloaters()  	LLFloaterReg::add("auction", "floater_auction.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLFloaterAuction>);  	LLFloaterReg::add("avatar", "floater_avatar.xml",  (LLFloaterBuildFunc)&LLFloaterReg::build<LLFloaterAvatar>);  	LLFloaterReg::add("avatar_picker", "floater_avatar_picker.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLFloaterAvatarPicker>); +	LLFloaterReg::add("avatar_render_settings", "floater_avatar_render_settings.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLFloaterAvatarRenderSettings>);  	LLFloaterReg::add("avatar_textures", "floater_avatar_textures.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLFloaterAvatarTextures>);  	LLFloaterReg::add("beacons", "floater_beacons.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLFloaterBeacons>); diff --git a/indra/newview/llviewerwindow.cpp b/indra/newview/llviewerwindow.cpp index 61505b7c07..2d3b48bab3 100644 --- a/indra/newview/llviewerwindow.cpp +++ b/indra/newview/llviewerwindow.cpp @@ -2724,8 +2724,16 @@ BOOL LLViewerWindow::handleKey(KEY key, MASK mask)  			return TRUE;  		} -		if ((gMenuBarView && gMenuBarView->handleAcceleratorKey(key, mask)) -			||(gLoginMenuBarView && gLoginMenuBarView->handleAcceleratorKey(key, mask))) +		if (gAgent.isInitialized() +			&& (gAgent.getTeleportState() == LLAgent::TELEPORT_NONE || gAgent.getTeleportState() == LLAgent::TELEPORT_LOCAL) +			&& gMenuBarView +			&& gMenuBarView->handleAcceleratorKey(key, mask)) +		{ +			LLViewerEventRecorder::instance().logKeyEvent(key, mask); +			return TRUE; +		} + +		if (gLoginMenuBarView && gLoginMenuBarView->handleAcceleratorKey(key, mask))  		{  			LLViewerEventRecorder::instance().logKeyEvent(key,mask);  			return TRUE; @@ -2855,8 +2863,16 @@ BOOL LLViewerWindow::handleKey(KEY key, MASK mask)  	}  	// give menus a chance to handle unmodified accelerator keys -	if ((gMenuBarView && gMenuBarView->handleAcceleratorKey(key, mask)) -		||(gLoginMenuBarView && gLoginMenuBarView->handleAcceleratorKey(key, mask))) +	if (gAgent.isInitialized() +		&& (gAgent.getTeleportState() == LLAgent::TELEPORT_NONE || gAgent.getTeleportState() == LLAgent::TELEPORT_LOCAL) +		&& gMenuBarView +		&& gMenuBarView->handleAcceleratorKey(key, mask)) +	{ +		LLViewerEventRecorder::instance().logKeyEvent(key, mask); +		return TRUE; +	} + +	if (gLoginMenuBarView && gLoginMenuBarView->handleAcceleratorKey(key, mask))  	{  		return TRUE;  	} diff --git a/indra/newview/llvoavatar.cpp b/indra/newview/llvoavatar.cpp index 760eee17f3..f6a16f7da1 100644 --- a/indra/newview/llvoavatar.cpp +++ b/indra/newview/llvoavatar.cpp @@ -728,7 +728,7 @@ LLVOAvatar::LLVOAvatar(const LLUUID& id,  	    LLSceneMonitor::getInstance()->freezeAvatar((LLCharacter*)this);  	} -	mVisuallyMuteSetting = getSavedVisualMuteSettings(); +	mVisuallyMuteSetting = LLVOAvatar::VisualMuteSettings(LLRenderMuteList::getInstance()->getSavedVisualMuteSetting(getID()));  }  std::string LLVOAvatar::avString() const @@ -7076,7 +7076,9 @@ BOOL LLVOAvatar::isFullyLoaded() const  bool LLVOAvatar::isTooComplex() const  {  	bool too_complex; -	if (isSelf() || mVisuallyMuteSetting == AV_ALWAYS_RENDER) +	bool render_friend =  (LLAvatarTracker::instance().isBuddy(getID()) && gSavedSettings.getBOOL("AlwaysRenderFriends")); + +	if (isSelf() || render_friend || mVisuallyMuteSetting == AV_ALWAYS_RENDER)  	{  		too_complex = false;  	} @@ -9230,25 +9232,12 @@ void LLVOAvatar::calculateUpdateRenderComplexity()      }  } -//static -std::map<LLUUID, LLVOAvatar::VisualMuteSettings> LLVOAvatar::sVisuallyMuteSettingsMap; -  void LLVOAvatar::setVisualMuteSettings(VisualMuteSettings set)  {      mVisuallyMuteSetting = set;      mNeedsImpostorUpdate = TRUE; -    sVisuallyMuteSettingsMap[getID()] = set; -} - -LLVOAvatar::VisualMuteSettings LLVOAvatar::getSavedVisualMuteSettings() -{ -    std::map<LLUUID, VisualMuteSettings>::iterator iter = sVisuallyMuteSettingsMap.find(getID()); -    if (iter != sVisuallyMuteSettingsMap.end()) -    { -        return iter->second; -    } -    return AV_RENDER_NORMALLY; +    LLRenderMuteList::getInstance()->saveVisualMuteSetting(getID(), S32(set));  }  void LLVOAvatar::calcMutedAVColor() diff --git a/indra/newview/llvoavatar.h b/indra/newview/llvoavatar.h index 73e4fbd108..bd89d4ef23 100644 --- a/indra/newview/llvoavatar.h +++ b/indra/newview/llvoavatar.h @@ -407,7 +407,6 @@ public:  	};  	void		setVisualMuteSettings(VisualMuteSettings set);  	VisualMuteSettings  getVisualMuteSettings()						{ return mVisuallyMuteSetting;	}; -	VisualMuteSettings  getSavedVisualMuteSettings();  	U32 		renderRigid();  	U32 		renderSkinned(); @@ -441,7 +440,6 @@ public:  	VisualMuteSettings		mVisuallyMuteSetting;			// Always or never visually mute this AV -	static std::map<LLUUID, VisualMuteSettings> sVisuallyMuteSettingsMap;  	//--------------------------------------------------------------------  	// Morph masks  	//-------------------------------------------------------------------- diff --git a/indra/newview/skins/default/xui/en/floater_avatar_render_settings.xml b/indra/newview/skins/default/xui/en/floater_avatar_render_settings.xml new file mode 100644 index 0000000000..03e812d36d --- /dev/null +++ b/indra/newview/skins/default/xui/en/floater_avatar_render_settings.xml @@ -0,0 +1,66 @@ +<?xml version="1.0" encoding="UTF-8" standalone="yes" ?> +<floater + can_resize="true" + positioning="cascading" + height="200" + min_height="100" + min_width="230" + layout="topleft" + name="floater_avatar_render_settings" + save_rect="true" + single_instance="true" + reuse_instance="true" + title="AVATAR RENDER SETTINGS" + width="300"> +    <string +     name="av_never_render" +     value="Never"/> +    <string +     name="av_always_render" +     value="Always"/> +    <filter_editor +     follows="left|top|right" +     height="23" +     layout="topleft" +     left="8" +     right="-47" +     label="Filter People" +     max_length_chars="300" +     name="people_filter_input" +     text_color="Black" +     text_pad_left="10" +     top="4" /> +    <menu_button +     follows="top|right" +     height="25" +     image_hover_unselected="Toolbar_Middle_Over" +     image_overlay="AddItem_Off" +     image_selected="Toolbar_Middle_Selected" +     image_unselected="Toolbar_Middle_Off" +     layout="topleft" +     left_pad="7" +     menu_filename="menu_avatar_rendering_settings_add.xml" +     menu_position="bottomleft" +     name="plus_btn" +     tool_tip="Actions on selected person" +     top="3" +     width="31" /> +    <name_list +     bottom="-8" +     draw_heading="true" +     follows="all" +     left="8" +     multi_select="false" +     name="render_settings_list" +     right="-8" +     top="32"> +        <name_list.columns +         label="Name" +         name="name" +         relative_width="0.65" /> +        <name_list.columns +         label="Render setting" +         name="setting" +         relative_width="0.35" /> +     </name_list> +</floater> diff --git a/indra/newview/skins/default/xui/en/floater_tos.xml b/indra/newview/skins/default/xui/en/floater_tos.xml index 590d9d1844..612c894b59 100644 --- a/indra/newview/skins/default/xui/en/floater_tos.xml +++ b/indra/newview/skins/default/xui/en/floater_tos.xml @@ -70,7 +70,7 @@       top="32"       word_wrap="true"       width="552"> -       You will need to go to my.secondlife.com and log in to accept the Terms of Service before you can proceed. Thank you! +       You will need to go to https://my.secondlife.com and log in to accept the Terms of Service before you can proceed. Thank you!       </text>      <web_browser        trusted_content="true"  diff --git a/indra/newview/skins/default/xui/en/menu_attachment_other.xml b/indra/newview/skins/default/xui/en/menu_attachment_other.xml index 2f60bab0b7..49b9ac273d 100644 --- a/indra/newview/skins/default/xui/en/menu_attachment_other.xml +++ b/indra/newview/skins/default/xui/en/menu_attachment_other.xml @@ -130,10 +130,13 @@     </menu_item_call>     <menu_item_separator /> -     +      <context_menu +       label="Render Avatar" +       layout="topleft" +        name="Render Avatar">        <menu_item_check          name="RenderNormally" -        label="Render Normally"> +        label="Default">          <menu_item_check.on_check            function="Avatar.CheckImpostorMode"            parameter="0" /> @@ -142,26 +145,26 @@  	      parameter="0" />        </menu_item_check>        <menu_item_check -        name="DoNotRender" -        label="Do Not Render"> +        name="AlwaysRenderFully" +        label="Always">          <menu_item_check.on_check            function="Avatar.CheckImpostorMode" -          parameter="1" /> +          parameter="2" />  	    <menu_item_check.on_click  	      function="Avatar.SetImpostorMode" -	      parameter="1" /> +	      parameter="2" />        </menu_item_check>        <menu_item_check -        name="AlwaysRenderFully" -        label="Render Fully"> +        name="DoNotRender" +        label="Never">          <menu_item_check.on_check            function="Avatar.CheckImpostorMode" -          parameter="2" /> +          parameter="1" />  	    <menu_item_check.on_click  	      function="Avatar.SetImpostorMode" -	      parameter="2" /> +	      parameter="1" />        </menu_item_check> - +      </context_menu>    <menu_item_separator         layout="topleft" name="Impostor seperator"/> diff --git a/indra/newview/skins/default/xui/en/menu_avatar_other.xml b/indra/newview/skins/default/xui/en/menu_avatar_other.xml index ddfff23410..c5426cb232 100644 --- a/indra/newview/skins/default/xui/en/menu_avatar_other.xml +++ b/indra/newview/skins/default/xui/en/menu_avatar_other.xml @@ -121,9 +121,13 @@     <menu_item_separator /> + <context_menu +       label="Render Avatar" +       layout="topleft" +        name="Render Avatar">        <menu_item_check          name="RenderNormally" -        label="Render Normally"> +        label="Default">          <menu_item_check.on_check            function="Avatar.CheckImpostorMode"            parameter="0" /> @@ -132,25 +136,26 @@  	      parameter="0" />        </menu_item_check>        <menu_item_check -        name="DoNotRender" -        label="Do Not Render"> +        name="AlwaysRenderFully" +        label="Always">          <menu_item_check.on_check            function="Avatar.CheckImpostorMode" -          parameter="1" /> +          parameter="2" />  	    <menu_item_check.on_click  	      function="Avatar.SetImpostorMode" -	      parameter="1" /> +	      parameter="2" />        </menu_item_check>        <menu_item_check -        name="AlwaysRenderFully" -        label="Render Fully"> +        name="DoNotRender" +        label="Never">          <menu_item_check.on_check            function="Avatar.CheckImpostorMode" -          parameter="2" /> +          parameter="1" />  	    <menu_item_check.on_click  	      function="Avatar.SetImpostorMode" -	      parameter="2" /> +	      parameter="1" />        </menu_item_check> +      </context_menu>    <menu_item_separator       layout="topleft"  name="Impostor seperator"/> diff --git a/indra/newview/skins/default/xui/en/menu_avatar_rendering_settings.xml b/indra/newview/skins/default/xui/en/menu_avatar_rendering_settings.xml new file mode 100644 index 0000000000..5163cd3115 --- /dev/null +++ b/indra/newview/skins/default/xui/en/menu_avatar_rendering_settings.xml @@ -0,0 +1,26 @@ +<?xml version="1.0" encoding="utf-8" standalone="yes" ?> +<context_menu + layout="topleft" + name="Settings"> +    <menu_item_check +     label="Default" +     layout="topleft" +     name="default"> +        <on_click function="Settings.SetRendering" parameter="default"/> +	<on_check function="Settings.IsSelected" parameter="default" />   +    </menu_item_check> +    <menu_item_check +     label="Always render" +     layout="topleft" +     name="always_render"> +        <on_click function="Settings.SetRendering" parameter="always"/> +	<on_check function="Settings.IsSelected" parameter="always" />   +    </menu_item_check> +    <menu_item_check +     label="Never render" +     layout="topleft" +     name="never_render"> +        <on_click function="Settings.SetRendering" parameter="never"/> +	<on_check function="Settings.IsSelected" parameter="never" />   +    </menu_item_check>   +</context_menu> diff --git a/indra/newview/skins/default/xui/en/menu_avatar_rendering_settings_add.xml b/indra/newview/skins/default/xui/en/menu_avatar_rendering_settings_add.xml new file mode 100644 index 0000000000..c64b24ed70 --- /dev/null +++ b/indra/newview/skins/default/xui/en/menu_avatar_rendering_settings_add.xml @@ -0,0 +1,18 @@ +<?xml version="1.0" encoding="utf-8" standalone="yes" ?> +<toggleable_menu  +     name="menu_settings_add.xml" +     left="0" bottom="0" visible="false" +     mouse_opaque="false"> +  <menu_item_call +   label="Always Render a Resident..." +   name="add_avatar_always_render"> +      <on_click +       function="Settings.AddNewEntry" parameter="always"/> +  </menu_item_call> +  <menu_item_call +   label="Never Render a Resident..." +   name="add_avatar_never_render"> +      <on_click +       function="Settings.AddNewEntry"  parameter="never"/> +  </menu_item_call> +</toggleable_menu> diff --git a/indra/newview/skins/default/xui/en/notifications.xml b/indra/newview/skins/default/xui/en/notifications.xml index a509adfcbc..3fcd91f89b 100644 --- a/indra/newview/skins/default/xui/en/notifications.xml +++ b/indra/newview/skins/default/xui/en/notifications.xml @@ -341,8 +341,7 @@ Initialization with the Marketplace failed because of a system or network error.          type="alertmodal">          The transaction with the Marketplace failed with the following error : -        Reason : '[ERROR_REASON]' -        [ERROR_DESCRIPTION] +        [ERROR_REASON][ERROR_DESCRIPTION]          <usetemplate          name="okbutton" @@ -1940,6 +1939,14 @@ Please make sure none are locked, and that you own all of them.    <notification     icon="alertmodal.tga" +   name="CannotLinkAcrossRegions" +   type="alertmodal"> +Objects cannot be linked across region boundaries. +    <tag>fail</tag> +  </notification> + +  <notification +   icon="alertmodal.tga"     name="CannotLinkDifferentOwners"     type="alertmodal">  Unable to link because not all of the objects have the same owner. diff --git a/indra/newview/skins/default/xui/en/panel_preferences_chat.xml b/indra/newview/skins/default/xui/en/panel_preferences_chat.xml index 8d55e311f6..440c6613d5 100644 --- a/indra/newview/skins/default/xui/en/panel_preferences_chat.xml +++ b/indra/newview/skins/default/xui/en/panel_preferences_chat.xml @@ -432,18 +432,16 @@          top_pad="6"          name="inventory_offer"          width="150" /> - +    <view_border +        bevel_style="none" +        height="0" +        layout="topleft" +        left="0" +        name="cost_text_border" +        top_pad="7" +        width="492"/>    </panel> -  <view_border -      bevel_style="none" -      height="0" -      layout="topleft" -      left="13" -      name="cost_text_border" -      top_pad="5" -      width="495"/> -    <panel        height="50"        layout="topleft" diff --git a/indra/newview/skins/default/xui/en/panel_preferences_graphics1.xml b/indra/newview/skins/default/xui/en/panel_preferences_graphics1.xml index 32cbbff8b7..4692a226d9 100644 --- a/indra/newview/skins/default/xui/en/panel_preferences_graphics1.xml +++ b/indra/newview/skins/default/xui/en/panel_preferences_graphics1.xml @@ -231,6 +231,34 @@       m    </text> +  <check_box +    control_name="WindLightUseAtmosShaders" +    height="16" +    initial_value="true" +    label="Atmospheric shaders" +    layout="topleft" +    left="30" +    name="WindLightUseAtmosShaders" +    top_delta="24" +    width="280"> +    <check_box.commit_callback +      function="Pref.VertexShaderEnable" /> +  </check_box> + +  <check_box +    control_name="RenderDeferred" +    height="16" +    initial_value="true" +    label="Advanced Lighting Model" +    layout="topleft" +    left="30" +    name="UseLightShaders" +    top_delta="24" +    width="256"> +    <check_box.commit_callback +      function="Pref.VertexShaderEnable" /> +  </check_box> +      <slider      control_name="IndirectMaxComplexity"      tool_tip="Controls at what point a visually complex avatar is drawn as a JellyDoll" @@ -246,7 +274,7 @@      max_val="101"      name="IndirectMaxComplexity"      show_text="false" -    top_delta="24" +    top_delta="60"      width="300">      <slider.commit_callback        function="Pref.UpdateIndirectMaxComplexity" @@ -265,34 +293,28 @@      width="65">         0    </text> -    <check_box -    control_name="WindLightUseAtmosShaders" +    control_name="AlwaysRenderFriends"      height="16"      initial_value="true" -    label="Atmospheric shaders" +    label="Always Render Friends"      layout="topleft"      left="30" -    name="WindLightUseAtmosShaders" +    name="AlwaysRenderFriends"      top_delta="24" -    width="280"> -    <check_box.commit_callback -      function="Pref.VertexShaderEnable" /> +    width="256">    </check_box> - -  <check_box -    control_name="RenderDeferred" -    height="16" -    initial_value="true" -    label="Advanced Lighting Model" +  <button +    height="23" +    label="Exceptions..."      layout="topleft" -    left="30" -    name="UseLightShaders" +    left="48" +    name="RenderExceptionsButton"      top_delta="24" -    width="256"> -    <check_box.commit_callback -      function="Pref.VertexShaderEnable" /> -  </check_box> +    width="100"> +    <button.commit_callback +      function="Pref.RenderExceptions"/> +  </button>  <!-- End of Basic Settings block --> diff --git a/indra/newview/skins/default/xui/en/strings.xml b/indra/newview/skins/default/xui/en/strings.xml index e3e770444c..5f686a87be 100644 --- a/indra/newview/skins/default/xui/en/strings.xml +++ b/indra/newview/skins/default/xui/en/strings.xml @@ -3885,7 +3885,7 @@ Abuse Report</string>    <string name="server_is_down">    Despite our best efforts, something unexpected has gone wrong. -Please check status.secondlifegrid.net to see if there is a known problem with the service. +Please check http://status.secondlifegrid.net to see if there is a known problem with the service.          If you continue to experience problems, please check your network and firewall setup.    </string> | 
