summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rwxr-xr-x.hgtags5
-rwxr-xr-xBuildParams11
-rwxr-xr-xdoc/contributions.txt6
-rw-r--r--[-rwxr-xr-x]indra/cmake/LLAddBuildTest.cmake0
-rwxr-xr-xindra/edit-me-to-trigger-new-build.txt1
-rwxr-xr-xindra/llimage/llimage.cpp11
-rwxr-xr-xindra/llimage/llimage.h4
-rwxr-xr-xindra/llmath/llcamera.cpp86
-rwxr-xr-xindra/llmath/llcamera.h37
-rwxr-xr-xindra/llmessage/llcurl.cpp4
-rwxr-xr-xindra/llprimitive/llmodel.cpp20
-rwxr-xr-xindra/llrender/llgl.cpp3
-rwxr-xr-xindra/llrender/llgl.h1
-rwxr-xr-x[-rw-r--r--]indra/llrender/llimagegl.cpp0
-rwxr-xr-xindra/llrender/llrendertarget.cpp4
-rwxr-xr-xindra/llui/llbutton.cpp5
-rwxr-xr-xindra/llui/llbutton.h4
-rwxr-xr-xindra/llui/llchatentry.cpp10
-rwxr-xr-xindra/llui/llchatentry.h6
-rwxr-xr-xindra/llui/llfloater.cpp33
-rwxr-xr-xindra/llui/llfloater.h5
-rwxr-xr-xindra/llui/llfolderview.cpp26
-rwxr-xr-xindra/llui/llfolderviewitem.cpp30
-rwxr-xr-xindra/llui/llfolderviewitem.h1
-rwxr-xr-xindra/llui/llfolderviewmodel.cpp2
-rwxr-xr-xindra/llui/llfolderviewmodel.h31
-rwxr-xr-xindra/llui/lllayoutstack.cpp102
-rwxr-xr-xindra/llui/lllayoutstack.h10
-rwxr-xr-xindra/llui/llmenugl.cpp12
-rwxr-xr-xindra/llui/llresizebar.cpp110
-rwxr-xr-xindra/llui/llresizebar.h52
-rwxr-xr-xindra/llui/llscrolllistcolumn.cpp3
-rwxr-xr-xindra/llui/llscrolllistctrl.cpp18
-rwxr-xr-xindra/llui/llscrolllistctrl.h4
-rwxr-xr-xindra/llui/lltextbase.cpp89
-rwxr-xr-xindra/llui/lltextbase.h8
-rwxr-xr-xindra/llui/lltexteditor.cpp58
-rwxr-xr-xindra/llui/lltexteditor.h1
-rwxr-xr-xindra/llui/lltoolbar.cpp4
-rwxr-xr-xindra/llui/lltoolbar.h2
-rwxr-xr-xindra/llui/llurlaction.cpp42
-rwxr-xr-xindra/llui/llurlaction.h4
-rwxr-xr-xindra/llui/llurlentry.cpp4
-rwxr-xr-xindra/llwindow/llwindowwin32.cpp19
-rwxr-xr-xindra/lscript/lscript_compile/indra.l2
-rw-r--r--indra/newview/VIEWER_VERSION.txt2
-rwxr-xr-xindra/newview/app_settings/keywords.ini3
-rwxr-xr-xindra/newview/app_settings/settings.xml146
-rwxr-xr-xindra/newview/app_settings/settings_per_account.xml13
-rwxr-xr-xindra/newview/app_settings/shaders/class1/avatar/objectSkinV.glsl1
-rwxr-xr-xindra/newview/gpu_table.txt576
-rwxr-xr-xindra/newview/llagent.cpp13
-rwxr-xr-xindra/newview/llappviewer.cpp5
-rwxr-xr-xindra/newview/llchannelmanager.cpp2
-rwxr-xr-xindra/newview/llchathistory.cpp1
-rwxr-xr-xindra/newview/llchatitemscontainerctrl.cpp5
-rwxr-xr-xindra/newview/llconversationmodel.cpp9
-rwxr-xr-xindra/newview/llconversationmodel.h9
-rwxr-xr-xindra/newview/llconversationview.cpp49
-rwxr-xr-xindra/newview/llconversationview.h4
-rwxr-xr-xindra/newview/lldonotdisturbnotificationstorage.cpp19
-rwxr-xr-xindra/newview/lldrawpoolavatar.cpp139
-rwxr-xr-xindra/newview/lldrawpoolavatar.h1
-rwxr-xr-xindra/newview/llface.cpp112
-rwxr-xr-xindra/newview/llface.h2
-rwxr-xr-xindra/newview/llfavoritesbar.cpp7
-rwxr-xr-xindra/newview/llfavoritesbar.h1
-rwxr-xr-xindra/newview/llfloateravatarpicker.cpp8
-rwxr-xr-xindra/newview/llfloaterconversationpreview.cpp47
-rwxr-xr-xindra/newview/llfloaterconversationpreview.h3
-rwxr-xr-xindra/newview/llfloaterimcontainer.cpp231
-rwxr-xr-xindra/newview/llfloaterimcontainer.h17
-rwxr-xr-xindra/newview/llfloaterimnearbychat.cpp44
-rwxr-xr-xindra/newview/llfloaterimnearbychathandler.cpp1
-rwxr-xr-xindra/newview/llfloaterimsession.cpp30
-rwxr-xr-xindra/newview/llfloaterimsessiontab.cpp58
-rwxr-xr-xindra/newview/llfloaterimsessiontab.h8
-rwxr-xr-xindra/newview/llfloaterland.cpp2
-rwxr-xr-xindra/newview/llfloaterpreference.cpp4
-rwxr-xr-xindra/newview/llfolderviewmodelinventory.cpp69
-rwxr-xr-xindra/newview/llfolderviewmodelinventory.h3
-rwxr-xr-xindra/newview/llgroupactions.cpp125
-rwxr-xr-xindra/newview/llgroupactions.h8
-rwxr-xr-xindra/newview/llimview.cpp300
-rwxr-xr-xindra/newview/llinventoryfilter.cpp42
-rwxr-xr-xindra/newview/llinventoryfilter.h17
-rwxr-xr-xindra/newview/llinventorypanel.cpp3
-rwxr-xr-xindra/newview/lllogchat.cpp300
-rwxr-xr-xindra/newview/lllogchat.h24
-rwxr-xr-xindra/newview/llmenuoptionpathfindingrebakenavmesh.cpp2
-rwxr-xr-xindra/newview/llmeshrepository.h2
-rwxr-xr-xindra/newview/llnamelistctrl.cpp4
-rwxr-xr-xindra/newview/llnamelistctrl.h2
-rwxr-xr-xindra/newview/llnotificationstorage.h1
-rwxr-xr-xindra/newview/llnotificationtiphandler.cpp7
-rwxr-xr-xindra/newview/llpanelgroupinvite.cpp35
-rwxr-xr-xindra/newview/llpanellogin.cpp33
-rwxr-xr-xindra/newview/llpanelmaininventory.cpp7
-rwxr-xr-xindra/newview/llpanelmaininventory.h1
-rwxr-xr-xindra/newview/llpanelprofile.cpp20
-rwxr-xr-xindra/newview/llpersistentnotificationstorage.cpp24
-rwxr-xr-xindra/newview/llpersistentnotificationstorage.h3
-rwxr-xr-xindra/newview/llspatialpartition.cpp76
-rwxr-xr-xindra/newview/llstartup.cpp6
-rwxr-xr-xindra/newview/llsyswellwindow.cpp11
-rwxr-xr-xindra/newview/lltexturecache.cpp15
-rw-r--r--[-rwxr-xr-x]indra/newview/lltexturefetch.cpp0
-rwxr-xr-xindra/newview/lltoastimpanel.cpp26
-rwxr-xr-xindra/newview/lltoastimpanel.h2
-rwxr-xr-xindra/newview/lltoolbarview.cpp23
-rwxr-xr-xindra/newview/lltoolbarview.h2
-rwxr-xr-xindra/newview/lltoolpie.cpp9
-rwxr-xr-xindra/newview/llviewermenu.cpp45
-rwxr-xr-xindra/newview/llviewermenu.h1
-rwxr-xr-xindra/newview/llviewermessage.cpp33
-rwxr-xr-xindra/newview/llviewerobjectlist.cpp1
-rwxr-xr-xindra/newview/llviewerobjectlist.h1
-rwxr-xr-xindra/newview/llviewerpartsim.cpp11
-rwxr-xr-xindra/newview/llviewertexture.cpp23
-rwxr-xr-xindra/newview/llviewertexture.h1
-rwxr-xr-xindra/newview/llviewerwindow.cpp60
-rwxr-xr-xindra/newview/llviewerwindow.h11
-rwxr-xr-xindra/newview/llvopartgroup.cpp124
-rwxr-xr-xindra/newview/llvopartgroup.h15
-rwxr-xr-xindra/newview/llvovolume.cpp19
-rwxr-xr-xindra/newview/noise.h5
-rwxr-xr-xindra/newview/pipeline.cpp113
-rwxr-xr-xindra/newview/pipeline.h8
-rwxr-xr-xindra/newview/skins/default/colors.xml15
-rwxr-xr-xindra/newview/skins/default/textures/textures.xml3
-rw-r--r--indra/newview/skins/default/textures/widgets/horizontal_drag_handle.pngbin0 -> 197 bytes
-rw-r--r--indra/newview/skins/default/textures/widgets/vertical_drag_handle.pngbin0 -> 196 bytes
-rwxr-xr-xindra/newview/skins/default/xui/en/floater_im_container.xml103
-rwxr-xr-xindra/newview/skins/default/xui/en/floater_im_session.xml100
-rwxr-xr-xindra/newview/skins/default/xui/en/menu_attachment_other.xml11
-rwxr-xr-xindra/newview/skins/default/xui/en/menu_attachment_self.xml11
-rwxr-xr-xindra/newview/skins/default/xui/en/menu_avatar_other.xml11
-rwxr-xr-xindra/newview/skins/default/xui/en/menu_avatar_self.xml12
-rwxr-xr-xindra/newview/skins/default/xui/en/menu_conversation.xml8
-rwxr-xr-xindra/newview/skins/default/xui/en/menu_land.xml11
-rw-r--r--indra/newview/skins/default/xui/en/menu_mute_particle.xml15
-rwxr-xr-xindra/newview/skins/default/xui/en/menu_object.xml11
-rwxr-xr-xindra/newview/skins/default/xui/en/menu_people_friends_view.xml2
-rwxr-xr-xindra/newview/skins/default/xui/en/menu_url_agent.xml9
-rwxr-xr-xindra/newview/skins/default/xui/en/menu_url_objectim.xml7
-rwxr-xr-xindra/newview/skins/default/xui/en/menu_viewer.xml11
-rwxr-xr-xindra/newview/skins/default/xui/en/notifications.xml19
-rwxr-xr-xindra/newview/skins/default/xui/en/panel_preferences_chat.xml144
-rwxr-xr-xindra/newview/skins/default/xui/en/panel_preferences_graphics1.xml17
-rwxr-xr-xindra/newview/skins/default/xui/en/role_actions.xml4
-rwxr-xr-xindra/newview/skins/default/xui/en/strings.xml8
151 files changed, 3164 insertions, 1503 deletions
diff --git a/.hgtags b/.hgtags
index f0b0ec22fa..36e5d6442d 100755
--- a/.hgtags
+++ b/.hgtags
@@ -56,11 +56,11 @@ a82e5b1e22c7f90e3c7977d146b80588f004ed0d 2.5.0-start
54d772d8687c69b1d773f6ce14bbc7bdc9d6c05f 2.5.0-beta2
54d772d8687c69b1d773f6ce14bbc7bdc9d6c05f DRTVWR-33--2.5.0beta2
54d772d8687c69b1d773f6ce14bbc7bdc9d6c05f DRTVWR-33_2.5.0-beta2
+b542f8134a2bb5dd054ff4e509a44b2ee463b1bf nat-eventapi2-base
b723921b5c711bd24dbe77dc76ef488b544dac78 2.5.0-beta3
b723921b5c711bd24dbe77dc76ef488b544dac78 2.5.0-release
b723921b5c711bd24dbe77dc76ef488b544dac78 DRTVWR-31_2.5.0-release
b723921b5c711bd24dbe77dc76ef488b544dac78 DRTVWR-34_2.5.0-beta3
-b542f8134a2bb5dd054ff4e509a44b2ee463b1bf nat-eventapi2-base
63a6aedfce785a6c760377bf685b2dae616797d2 2.5.1-start
4dede9ae1ec74d41f6887719f6f1de7340d8578d 2.5.1-release
4dede9ae1ec74d41f6887719f6f1de7340d8578d DRTVWR-37_2.5.1-release
@@ -459,6 +459,7 @@ a314f1c94374ab1f6633dd2983f7090a68663eb2 3.5.2-beta4
a277b841729f2a62ba1e34acacc964bc13c1ad6f 3.5.3-release
fb1630153bac5552046ea914af3f14deabc1def8 3.6.0-materials-beta1
0a56f33ad6aa112032b14a41dad759ad377bdde9 3.6.0-release
-83357f31d8dbf048a8bfdc323f363bf4d588aca1 CHOP-951-a
75cf8e855ae1af6895a35da475314c2b5acf1850 3.6.1-release
f6741d5fe8d632651424484df0fe0cb4a01e9fbe 3.6.2-release
+fe4f7c5e9fd27e09d03deb1cc9ab3e5093f6309e 3.6.3-release
+83357f31d8dbf048a8bfdc323f363bf4d588aca1 CHOP-951-a
diff --git a/BuildParams b/BuildParams
index 5ee1bd11ea..327530934d 100755
--- a/BuildParams
+++ b/BuildParams
@@ -134,17 +134,6 @@ viewer-materials.build_debug_release_separately = true
viewer-materials.build_CYGWIN_Debug = false
viewer-materials.build_viewer_update_version_manager = false
-# viewer-chui
-#
-# ========================================
-
-viewer-chui.viewer_channel = "Project Viewer - CHUI"
-viewer-chui.login_channel = "Project Viewer - CHUI"
-viewer-chui.viewer_grid = agni
-viewer-chui.build_debug_release_separately = true
-viewer-chui.build_CYGWIN_Debug = false
-viewer-chui.build_viewer_update_version_manager = false
-
# =================================================================
# asset delivery 2010 projects
# =================================================================
diff --git a/doc/contributions.txt b/doc/contributions.txt
index f8b61923ec..a6d522de2f 100755
--- a/doc/contributions.txt
+++ b/doc/contributions.txt
@@ -175,8 +175,11 @@ Ansariel Hiller
STORM-1685
STORM-1713
STORM-1899
+ MAINT-2368
STORM-1931
Aralara Rajal
+Arare Chantilly
+ CHUIBUG-191
Ardy Lay
STORM-859
VWR-19499
@@ -484,6 +487,7 @@ Hiro Sommambulist
Hitomi Tiponi
STORM-1741
STORM-1862
+ BUG-1067
Holger Gilruth
Horatio Freund
Hoze Menges
@@ -918,6 +922,8 @@ Nicky Dasmijn
MAINT-873
SUN-72
BUG-2432
+ BUG-3605
+ CHUIBUG-197
Nicky Perian
OPEN-1
STORM-1087
diff --git a/indra/cmake/LLAddBuildTest.cmake b/indra/cmake/LLAddBuildTest.cmake
index 9bb3077797..9bb3077797 100755..100644
--- a/indra/cmake/LLAddBuildTest.cmake
+++ b/indra/cmake/LLAddBuildTest.cmake
diff --git a/indra/edit-me-to-trigger-new-build.txt b/indra/edit-me-to-trigger-new-build.txt
index e003ed7788..774e8c0676 100755
--- a/indra/edit-me-to-trigger-new-build.txt
+++ b/indra/edit-me-to-trigger-new-build.txt
@@ -3,3 +3,4 @@ Wed Nov 7 00:25:19 UTC 2012
+
diff --git a/indra/llimage/llimage.cpp b/indra/llimage/llimage.cpp
index 1c25256e95..c8a05e1fae 100755
--- a/indra/llimage/llimage.cpp
+++ b/indra/llimage/llimage.cpp
@@ -689,8 +689,17 @@ void LLImageRaw::fill( const LLColor4U& color )
}
}
+LLPointer<LLImageRaw> LLImageRaw::duplicate()
+{
+ if(getNumRefs() < 2)
+ {
+ return this; //nobody else refences to this image, no need to duplicate.
+ }
-
+ //make a duplicate
+ LLPointer<LLImageRaw> dup = new LLImageRaw(getData(), getWidth(), getHeight(), getComponents());
+ return dup;
+}
// Src and dst can be any size. Src and dst can each have 3 or 4 components.
void LLImageRaw::copy(LLImageRaw* src)
diff --git a/indra/llimage/llimage.h b/indra/llimage/llimage.h
index 4fc40ecff7..2277afc585 100755
--- a/indra/llimage/llimage.h
+++ b/indra/llimage/llimage.h
@@ -30,6 +30,7 @@
#include "lluuid.h"
#include "llstring.h"
#include "llthread.h"
+#include "llpointer.h"
const S32 MIN_IMAGE_MIP = 2; // 4x4, only used for expand/contract power of 2
const S32 MAX_IMAGE_MIP = 11; // 2048x2048
@@ -214,6 +215,9 @@ public:
// Copy operations
+ //duplicate this raw image if refCount > 1.
+ LLPointer<LLImageRaw> duplicate();
+
// Src and dst can be any size. Src and dst can each have 3 or 4 components.
void copy( LLImageRaw* src );
diff --git a/indra/llmath/llcamera.cpp b/indra/llmath/llcamera.cpp
index 22ba26f99b..33cf185196 100755
--- a/indra/llmath/llcamera.cpp
+++ b/indra/llmath/llcamera.cpp
@@ -42,6 +42,11 @@ LLCamera::LLCamera() :
mPlaneCount(6),
mFrustumCornerDist(0.f)
{
+ for (U32 i = 0; i < PLANE_MASK_NUM; i++)
+ {
+ mPlaneMask[i] = PLANE_MASK_NONE;
+ }
+
calculateFrustumPlanes();
}
@@ -52,6 +57,11 @@ LLCamera::LLCamera(F32 vertical_fov_rads, F32 aspect_ratio, S32 view_height_in_p
mPlaneCount(6),
mFrustumCornerDist(0.f)
{
+ for (U32 i = 0; i < PLANE_MASK_NUM; i++)
+ {
+ mPlaneMask[i] = PLANE_MASK_NONE;
+ }
+
mAspect = llclamp(aspect_ratio, MIN_ASPECT_RATIO, MAX_ASPECT_RATIO);
mNearPlane = llclamp(near_plane, MIN_NEAR_PLANE, MAX_NEAR_PLANE);
if(far_plane < 0) far_plane = DEFAULT_FAR_PLANE;
@@ -87,14 +97,14 @@ F32 LLCamera::getMaxView() const
void LLCamera::setUserClipPlane(LLPlane& plane)
{
- mPlaneCount = 7;
- mAgentPlanes[6] = plane;
- mPlaneMask[6] = plane.calcPlaneMask();
+ mPlaneCount = AGENT_PLANE_USER_CLIP_NUM;
+ mAgentPlanes[AGENT_PLANE_USER_CLIP] = plane;
+ mPlaneMask[AGENT_PLANE_USER_CLIP] = plane.calcPlaneMask();
}
void LLCamera::disableUserClipPlane()
{
- mPlaneCount = 6;
+ mPlaneCount = AGENT_PLANE_NO_USER_CLIP_NUM;
}
void LLCamera::setView(F32 vertical_fov_rads)
@@ -161,31 +171,33 @@ size_t LLCamera::readFrustumFromBuffer(const char *buffer)
// ---------------- test methods ----------------
-S32 LLCamera::AABBInFrustum(const LLVector4a &center, const LLVector4a& radius)
+static const LLVector4a sFrustumScaler[] =
{
- static const LLVector4a scaler[] = {
- LLVector4a(-1,-1,-1),
- LLVector4a( 1,-1,-1),
- LLVector4a(-1, 1,-1),
- LLVector4a( 1, 1,-1),
- LLVector4a(-1,-1, 1),
- LLVector4a( 1,-1, 1),
- LLVector4a(-1, 1, 1),
- LLVector4a( 1, 1, 1)
- };
+ LLVector4a(-1,-1,-1),
+ LLVector4a( 1,-1,-1),
+ LLVector4a(-1, 1,-1),
+ LLVector4a( 1, 1,-1),
+ LLVector4a(-1,-1, 1),
+ LLVector4a( 1,-1, 1),
+ LLVector4a(-1, 1, 1),
+ LLVector4a( 1, 1, 1) // 8 entries
+};
+S32 LLCamera::AABBInFrustum(const LLVector4a &center, const LLVector4a& radius)
+{
U8 mask = 0;
bool result = false;
LLVector4a rscale, maxp, minp;
LLSimdScalar d;
- for (U32 i = 0; i < mPlaneCount; i++)
+ U32 max_planes = llmin(mPlaneCount, (U32) AGENT_PLANE_USER_CLIP_NUM); // mAgentPlanes[] size is 7
+ for (U32 i = 0; i < max_planes; i++)
{
mask = mPlaneMask[i];
- if (mask != 0xff)
+ if (mask < PLANE_MASK_NUM)
{
const LLPlane& p(mAgentPlanes[i]);
p.getAt<3>(d);
- rscale.setMul(radius, scaler[mask]);
+ rscale.setMul(radius, sFrustumScaler[mask]);
minp.setSub(center, rscale);
d = -d;
if (p.dot3(minp).getF32() > d)
@@ -207,29 +219,19 @@ S32 LLCamera::AABBInFrustum(const LLVector4a &center, const LLVector4a& radius)
S32 LLCamera::AABBInFrustumNoFarClip(const LLVector4a& center, const LLVector4a& radius)
{
- static const LLVector4a scaler[] = {
- LLVector4a(-1,-1,-1),
- LLVector4a( 1,-1,-1),
- LLVector4a(-1, 1,-1),
- LLVector4a( 1, 1,-1),
- LLVector4a(-1,-1, 1),
- LLVector4a( 1,-1, 1),
- LLVector4a(-1, 1, 1),
- LLVector4a( 1, 1, 1)
- };
-
U8 mask = 0;
bool result = false;
LLVector4a rscale, maxp, minp;
LLSimdScalar d;
- for (U32 i = 0; i < mPlaneCount; i++)
+ U32 max_planes = llmin(mPlaneCount, (U32) AGENT_PLANE_USER_CLIP_NUM); // mAgentPlanes[] size is 7
+ for (U32 i = 0; i < max_planes; i++)
{
mask = mPlaneMask[i];
- if ((i != 5) && (mask != 0xff))
+ if ((i != 5) && (mask < PLANE_MASK_NUM))
{
const LLPlane& p(mAgentPlanes[i]);
p.getAt<3>(d);
- rscale.setMul(radius, scaler[mask]);
+ rscale.setMul(radius, sFrustumScaler[mask]);
minp.setSub(center, rscale);
d = -d;
if (p.dot3(minp).getF32() > d)
@@ -369,7 +371,7 @@ int LLCamera::sphereInFrustum(const LLVector3 &sphere_center, const F32 radius)
bool res = false;
for (int i = 0; i < 6; i++)
{
- if (mPlaneMask[i] != 0xff)
+ if (mPlaneMask[i] != PLANE_MASK_NONE)
{
float d = mAgentPlanes[i].dist(sphere_center);
@@ -541,14 +543,14 @@ void LLCamera::ignoreAgentFrustumPlane(S32 idx)
return;
}
- mPlaneMask[idx] = 0xff;
+ mPlaneMask[idx] = PLANE_MASK_NONE;
mAgentPlanes[idx].clear();
}
void LLCamera::calcAgentFrustumPlanes(LLVector3* frust)
{
- for (int i = 0; i < 8; i++)
+ for (int i = 0; i < AGENT_FRUSTRUM_NUM; i++)
{
mAgentFrustum[i] = frust[i];
}
@@ -560,22 +562,22 @@ void LLCamera::calcAgentFrustumPlanes(LLVector3* frust)
//order of planes is important, keep most likely to fail in the front of the list
//near - frust[0], frust[1], frust[2]
- mAgentPlanes[2] = planeFromPoints(frust[0], frust[1], frust[2]);
+ mAgentPlanes[AGENT_PLANE_NEAR] = planeFromPoints(frust[0], frust[1], frust[2]);
//far
- mAgentPlanes[5] = planeFromPoints(frust[5], frust[4], frust[6]);
+ mAgentPlanes[AGENT_PLANE_FAR] = planeFromPoints(frust[5], frust[4], frust[6]);
//left
- mAgentPlanes[0] = planeFromPoints(frust[4], frust[0], frust[7]);
+ mAgentPlanes[AGENT_PLANE_LEFT] = planeFromPoints(frust[4], frust[0], frust[7]);
//right
- mAgentPlanes[1] = planeFromPoints(frust[1], frust[5], frust[6]);
+ mAgentPlanes[AGENT_PLANE_RIGHT] = planeFromPoints(frust[1], frust[5], frust[6]);
//top
- mAgentPlanes[4] = planeFromPoints(frust[3], frust[2], frust[6]);
+ mAgentPlanes[AGENT_PLANE_TOP] = planeFromPoints(frust[3], frust[2], frust[6]);
//bottom
- mAgentPlanes[3] = planeFromPoints(frust[1], frust[0], frust[4]);
+ mAgentPlanes[AGENT_PLANE_BOTTOM] = planeFromPoints(frust[1], frust[0], frust[4]);
//cache plane octant facing mask for use in AABBInFrustum
for (U32 i = 0; i < mPlaneCount; i++)
@@ -635,7 +637,7 @@ void LLCamera::calculateWorldFrustumPlanes()
LLVector3 center = mOrigin - mXAxis*mNearPlane;
mWorldPlanePos = center;
LLVector3 pnorm;
- for (int p=0; p<4; p++)
+ for (int p = 0; p < PLANE_NUM; p++)
{
mLocalPlanes[p].getVector3(pnorm);
LLVector3 norm = rotateToAbsolute(pnorm);
diff --git a/indra/llmath/llcamera.h b/indra/llmath/llcamera.h
index 0b591be622..1283cfb16b 100755
--- a/indra/llmath/llcamera.h
+++ b/indra/llmath/llcamera.h
@@ -76,26 +76,39 @@ public:
PLANE_RIGHT = 1,
PLANE_BOTTOM = 2,
PLANE_TOP = 3,
- PLANE_NUM = 4
+ PLANE_NUM = 4,
+ PLANE_MASK_NONE = 0xff // Disable this plane
};
enum {
PLANE_LEFT_MASK = (1<<PLANE_LEFT),
PLANE_RIGHT_MASK = (1<<PLANE_RIGHT),
PLANE_BOTTOM_MASK = (1<<PLANE_BOTTOM),
PLANE_TOP_MASK = (1<<PLANE_TOP),
- PLANE_ALL_MASK = 0xf
+ PLANE_ALL_MASK = 0xf,
};
enum
- {
+ { // Indexes to mAgentPlanes[] and mPlaneMask[]
AGENT_PLANE_LEFT = 0,
- AGENT_PLANE_RIGHT,
- AGENT_PLANE_NEAR,
- AGENT_PLANE_BOTTOM,
- AGENT_PLANE_TOP,
- AGENT_PLANE_FAR,
+ AGENT_PLANE_RIGHT = 1,
+ AGENT_PLANE_NEAR = 2,
+ AGENT_PLANE_BOTTOM = 3,
+ AGENT_PLANE_TOP = 4,
+ AGENT_PLANE_FAR = 5,
+ AGENT_PLANE_USER_CLIP = 6
+ };
+ enum
+ { // Sizes for mAgentPlanes[]. 7th entry is special case for user clip
+ AGENT_PLANE_NO_USER_CLIP_NUM = 6,
+ AGENT_PLANE_USER_CLIP_NUM = 7,
+ PLANE_MASK_NUM = 8 // 7 actually used, 8 is for alignment
};
+ enum
+ {
+ AGENT_FRUSTRUM_NUM = 8
+ };
+
enum {
HORIZ_PLANE_LEFT = 0,
HORIZ_PLANE_RIGHT = 1,
@@ -108,15 +121,15 @@ public:
};
private:
- LL_ALIGN_16(LLPlane mAgentPlanes[7]); //frustum planes in agent space a la gluUnproject (I'm a bastard, I know) - DaveP
- U8 mPlaneMask[8]; // 8 for alignment
+ LL_ALIGN_16(LLPlane mAgentPlanes[AGENT_PLANE_USER_CLIP_NUM]); //frustum planes in agent space a la gluUnproject (I'm a bastard, I know) - DaveP
+ U8 mPlaneMask[PLANE_MASK_NUM]; // 8 for alignment
F32 mView; // angle between top and bottom frustum planes in radians.
F32 mAspect; // width/height
S32 mViewHeightInPixels; // for ViewHeightInPixels() only
F32 mNearPlane;
F32 mFarPlane;
- LL_ALIGN_16(LLPlane mLocalPlanes[4]);
+ LL_ALIGN_16(LLPlane mLocalPlanes[PLANE_NUM]);
F32 mFixedDistance; // Always return this distance, unless < 0
LLVector3 mFrustCenter; // center of frustum and radius squared for ultra-quick exclusion test
F32 mFrustRadiusSquared;
@@ -128,7 +141,7 @@ private:
LLVector3 mWorldPlanePos; // Position of World Planes (may be offset from camera)
public:
- LLVector3 mAgentFrustum[8]; //8 corners of 6-plane frustum
+ LLVector3 mAgentFrustum[AGENT_FRUSTRUM_NUM]; //8 corners of 6-plane frustum
F32 mFrustumCornerDist; //distance to corner of frustum against far clip plane
LLPlane& getAgentPlane(U32 idx) { return mAgentPlanes[idx]; }
diff --git a/indra/llmessage/llcurl.cpp b/indra/llmessage/llcurl.cpp
index 47041a2880..f2a3e059ef 100755
--- a/indra/llmessage/llcurl.cpp
+++ b/indra/llmessage/llcurl.cpp
@@ -72,7 +72,8 @@
static const U32 EASY_HANDLE_POOL_SIZE = 5;
static const S32 MULTI_PERFORM_CALL_REPEAT = 5;
-static const S32 CURL_REQUEST_TIMEOUT = 30; // seconds per operation
+static const S32 CURL_REQUEST_TIMEOUT = 120; // seconds per operation
+static const S32 CURL_CONNECT_TIMEOUT = 30; //seconds to wait for a connection
static const S32 MAX_ACTIVE_REQUEST_COUNT = 100;
// DEBUG //
@@ -517,6 +518,7 @@ void LLCurl::Easy::prepRequest(const std::string& url,
//don't verify host name so urls with scrubbed host names will work (improves DNS performance)
setopt(CURLOPT_SSL_VERIFYHOST, 0);
setopt(CURLOPT_TIMEOUT, llmax(time_out, CURL_REQUEST_TIMEOUT));
+ setopt(CURLOPT_CONNECTTIMEOUT, CURL_CONNECT_TIMEOUT);
setoptString(CURLOPT_URL, url);
diff --git a/indra/llprimitive/llmodel.cpp b/indra/llprimitive/llmodel.cpp
index 28ed051c55..5ed05e2201 100755
--- a/indra/llprimitive/llmodel.cpp
+++ b/indra/llprimitive/llmodel.cpp
@@ -628,25 +628,41 @@ LLModel::EModelStatus load_face_from_dom_polygons(std::vector<LLVolumeFace>& fac
if (v)
{
U32 v_idx = idx[j*stride+v_offset]*3;
+ v_idx = llclamp(v_idx, (U32) 0, (U32) v->getCount());
vert.getPosition().set(v->get(v_idx),
v->get(v_idx+1),
v->get(v_idx+2));
}
- if (n)
+ //bounds check n and t lookups because some FBX to DAE converters
+ //use negative indices and empty arrays to indicate data does not exist
+ //for a particular channel
+ if (n && n->getCount() > 0)
{
U32 n_idx = idx[j*stride+n_offset]*3;
+ n_idx = llclamp(n_idx, (U32) 0, (U32) n->getCount());
vert.getNormal().set(n->get(n_idx),
n->get(n_idx+1),
n->get(n_idx+2));
}
+ else
+ {
+ vert.getNormal().clear();
+ }
+
- if (t)
+ if (t && t->getCount() > 0)
{
U32 t_idx = idx[j*stride+t_offset]*2;
+ t_idx = llclamp(t_idx, (U32) 0, (U32) t->getCount());
vert.mTexCoord.setVec(t->get(t_idx),
t->get(t_idx+1));
}
+ else
+ {
+ vert.mTexCoord.clear();
+ }
+
verts.push_back(vert);
}
diff --git a/indra/llrender/llgl.cpp b/indra/llrender/llgl.cpp
index 088ba95b75..c3005f1722 100755
--- a/indra/llrender/llgl.cpp
+++ b/indra/llrender/llgl.cpp
@@ -1154,7 +1154,8 @@ void LLGLManager::initExtensions()
// Misc
glGetIntegerv(GL_MAX_ELEMENTS_VERTICES, (GLint*) &mGLMaxVertexRange);
glGetIntegerv(GL_MAX_ELEMENTS_INDICES, (GLint*) &mGLMaxIndexRange);
-
+ glGetIntegerv(GL_MAX_TEXTURE_SIZE, (GLint*) &mGLMaxTextureSize);
+
#if (LL_WINDOWS || LL_LINUX || LL_SOLARIS) && !LL_MESA_HEADLESS
LL_DEBUGS("RenderInit") << "GL Probe: Getting symbols" << LL_ENDL;
if (mHasVertexBufferObject)
diff --git a/indra/llrender/llgl.h b/indra/llrender/llgl.h
index 60597fd090..75e5fe86ec 100755
--- a/indra/llrender/llgl.h
+++ b/indra/llrender/llgl.h
@@ -155,6 +155,7 @@ public:
S32 mVRAM; // VRAM in MB
S32 mGLMaxVertexRange;
S32 mGLMaxIndexRange;
+ S32 mGLMaxTextureSize;
void getPixelFormat(); // Get the best pixel format
diff --git a/indra/llrender/llimagegl.cpp b/indra/llrender/llimagegl.cpp
index 38764eba23..38764eba23 100644..100755
--- a/indra/llrender/llimagegl.cpp
+++ b/indra/llrender/llimagegl.cpp
diff --git a/indra/llrender/llrendertarget.cpp b/indra/llrender/llrendertarget.cpp
index 6e22712b94..d53c37a847 100755
--- a/indra/llrender/llrendertarget.cpp
+++ b/indra/llrender/llrendertarget.cpp
@@ -117,8 +117,8 @@ void LLRenderTarget::resize(U32 resx, U32 resy, U32 color_fmt)
bool LLRenderTarget::allocate(U32 resx, U32 resy, U32 color_fmt, bool depth, bool stencil, LLTexUnit::eTextureType usage, bool use_fbo, S32 samples)
{
- resx = llmin(resx, (U32) 4096);
- resy = llmin(resy, (U32) 4096);
+ resx = llmin(resx, (U32) gGLManager.mGLMaxTextureSize);
+ resy = llmin(resy, (U32) gGLManager.mGLMaxTextureSize);
stop_glerror();
release();
diff --git a/indra/llui/llbutton.cpp b/indra/llui/llbutton.cpp
index a8149a9a1d..44f2c1efe9 100755
--- a/indra/llui/llbutton.cpp
+++ b/indra/llui/llbutton.cpp
@@ -644,7 +644,7 @@ void LLButton::draw()
// Cancel sticking of color, if the button is pressed,
// or when a flashing of the previously selected button is ended
if (mFlashingTimer
- && ((selected && !mFlashingTimer->isFlashingInProgress()) || pressed))
+ && ((selected && !mFlashingTimer->isFlashingInProgress() && !mForceFlashing) || pressed))
{
mFlashing = false;
}
@@ -971,8 +971,9 @@ void LLButton::setToggleState(BOOL b)
}
}
-void LLButton::setFlashing(bool b)
+void LLButton::setFlashing(bool b, bool force_flashing/* = false */)
{
+ mForceFlashing = force_flashing;
if (mFlashingTimer)
{
mFlashing = b;
diff --git a/indra/llui/llbutton.h b/indra/llui/llbutton.h
index 060db59a8a..7b4719866d 100755
--- a/indra/llui/llbutton.h
+++ b/indra/llui/llbutton.h
@@ -201,7 +201,7 @@ public:
void setToggleState(BOOL b);
void setHighlight(bool b);
- void setFlashing( bool b );
+ void setFlashing( bool b, bool force_flashing = false );
BOOL getFlashing() const { return mFlashing; }
LLFlashTimer* getFlashTimer() {return mFlashingTimer;}
@@ -378,7 +378,7 @@ protected:
LLFrameTimer mFrameTimer;
LLFlashTimer * mFlashingTimer;
-
+ bool mForceFlashing; // Stick flashing color even if button is pressed
bool mHandleRightMouse;
};
diff --git a/indra/llui/llchatentry.cpp b/indra/llui/llchatentry.cpp
index 6a1b48a08a..c04b70eb64 100755
--- a/indra/llui/llchatentry.cpp
+++ b/indra/llui/llchatentry.cpp
@@ -62,9 +62,9 @@ void LLChatEntry::draw()
{
if(mIsExpandable)
{
+ reflow();
expandText();
}
-
LLTextEditor::draw();
}
@@ -158,19 +158,21 @@ void LLChatEntry::onValueChange(S32 start, S32 end)
resetLabel();
}
-bool LLChatEntry::useLabel()
+bool LLChatEntry::useLabel() const
{
return !getLength() && !mLabel.empty();
}
void LLChatEntry::onFocusReceived()
{
-
+ LLUICtrl::onFocusReceived();
+ updateAllowingLanguageInput();
}
void LLChatEntry::onFocusLost()
{
-
+ LLTextEditor::focusLostHelper();
+ LLUICtrl::onFocusLost();
}
BOOL LLChatEntry::handleSpecialKey(const KEY key, const MASK mask)
diff --git a/indra/llui/llchatentry.h b/indra/llui/llchatentry.h
index 49c8d21450..e67f39b21b 100755
--- a/indra/llui/llchatentry.h
+++ b/indra/llui/llchatentry.h
@@ -56,14 +56,14 @@ protected:
LLChatEntry(const Params& p);
/*virtual*/ void beforeValueChange();
/*virtual*/ void onValueChange(S32 start, S32 end);
- /*virtual*/ bool useLabel();
+ /*virtual*/ bool useLabel() const;
public:
virtual void draw();
virtual void onCommit();
- /*virtual*/ void onFocusReceived();
- /*virtual*/ void onFocusLost();
+ /*virtual*/ void onFocusReceived();
+ /*virtual*/ void onFocusLost();
void enableSingleLineMode(bool single_line_mode);
boost::signals2::connection setTextExpandedCallback(const commit_signal_t::slot_type& cb);
diff --git a/indra/llui/llfloater.cpp b/indra/llui/llfloater.cpp
index 09e27a264a..273ceb4038 100755
--- a/indra/llui/llfloater.cpp
+++ b/indra/llui/llfloater.cpp
@@ -507,22 +507,11 @@ LLFloater::~LLFloater()
{
LLFloaterReg::removeInstance(mInstanceName, mKey);
-// delete mNotificationContext;
-// mNotificationContext = NULL;
-
- //// am I not hosted by another floater?
- //if (mHostHandle.isDead())
- //{
- // LLFloaterView* parent = (LLFloaterView*) getParent();
-
- // if( parent )
- // {
- // parent->removeChild( this );
- // }
- //}
-
- // Just in case we might still have focus here, release it.
- releaseFocus();
+ if( gFocusMgr.childHasKeyboardFocus(this))
+ {
+ // Just in case we might still have focus here, release it.
+ releaseFocus();
+ }
// This is important so that floaters with persistent rects (i.e., those
// created with rect control rather than an LLRect) are restored in their
@@ -1486,6 +1475,7 @@ void LLFloater::moveResizeHandlesToFront()
}
}
+/*virtual*/
BOOL LLFloater::isFrontmost()
{
LLFloaterView* floater_view = getParentByType<LLFloaterView>();
@@ -1504,7 +1494,7 @@ void LLFloater::addDependentFloater(LLFloater* floaterp, BOOL reposition)
floaterp->setRect(gFloaterView->findNeighboringPosition(this, floaterp));
floaterp->setSnapTarget(getHandle());
}
- gFloaterView->adjustToFitScreen(floaterp, FALSE);
+ gFloaterView->adjustToFitScreen(floaterp, FALSE, TRUE);
if (floaterp->isFrontmost())
{
// make sure to bring self and sibling floaters to front
@@ -2735,7 +2725,7 @@ void LLFloaterView::refresh()
const S32 FLOATER_MIN_VISIBLE_PIXELS = 16;
-void LLFloaterView::adjustToFitScreen(LLFloater* floater, BOOL allow_partial_outside)
+void LLFloaterView::adjustToFitScreen(LLFloater* floater, BOOL allow_partial_outside, BOOL snap_in_toolbars/* = false*/)
{
if (floater->getParent() != this)
{
@@ -2788,7 +2778,7 @@ void LLFloaterView::adjustToFitScreen(LLFloater* floater, BOOL allow_partial_out
}
// move window fully onscreen
- if (floater->translateIntoRect( getSnapRect(), allow_partial_outside ? FLOATER_MIN_VISIBLE_PIXELS : S32_MAX ))
+ if (floater->translateIntoRect( snap_in_toolbars ? getSnapRect() : gFloaterView->getRect(), allow_partial_outside ? FLOATER_MIN_VISIBLE_PIXELS : S32_MAX ))
{
floater->clearSnapTarget();
}
@@ -3258,6 +3248,11 @@ bool LLFloater::isShown() const
return ! isMinimized() && isInVisibleChain();
}
+bool LLFloater::isDetachedAndNotMinimized()
+{
+ return !getHost() && !isMinimized();
+}
+
/* static */
bool LLFloater::isShown(const LLFloater* floater)
{
diff --git a/indra/llui/llfloater.h b/indra/llui/llfloater.h
index 4dba1e645f..3482314698 100755
--- a/indra/llui/llfloater.h
+++ b/indra/llui/llfloater.h
@@ -238,6 +238,7 @@ public:
void center();
LLMultiFloater* getHost();
+ bool isDetachedAndNotMinimized();
void applyTitle();
std::string getCurrentTitle() const;
@@ -261,7 +262,7 @@ public:
static bool isVisible(const LLFloater* floater);
static bool isMinimized(const LLFloater* floater);
BOOL isFirstLook() { return mFirstLook; } // EXT-2653: This function is necessary to prevent overlapping for secondary showed toasts
- BOOL isFrontmost();
+ virtual BOOL isFrontmost();
BOOL isDependent() { return !mDependeeHandle.isDead(); }
void setCanMinimize(BOOL can_minimize);
void setCanClose(BOOL can_close);
@@ -528,7 +529,7 @@ public:
LLRect findNeighboringPosition( LLFloater* reference_floater, LLFloater* neighbor );
// Given a child of gFloaterView, make sure this view can fit entirely onscreen.
- void adjustToFitScreen(LLFloater* floater, BOOL allow_partial_outside);
+ void adjustToFitScreen(LLFloater* floater, BOOL allow_partial_outside, BOOL snap_in_toolbars = false);
void setMinimizePositionVerticalOffset(S32 offset) { mMinimizePositionVOffset = offset; }
void getMinimizePosition( S32 *left, S32 *bottom);
diff --git a/indra/llui/llfolderview.cpp b/indra/llui/llfolderview.cpp
index 8aa1eb7cd5..cf449217f5 100755
--- a/indra/llui/llfolderview.cpp
+++ b/indra/llui/llfolderview.cpp
@@ -323,9 +323,11 @@ static LLFastTimer::DeclareTimer FTM_FILTER("Filter Folder View");
void LLFolderView::filter( LLFolderViewFilter& filter )
{
+ // Entry point of inventory filtering (CHUI-849)
LLFastTimer t2(FTM_FILTER);
- filter.setFilterCount(llclamp(LLUI::sSettingGroups["config"]->getS32("FilterItemsPerFrame"), 1, 5000));
+ filter.resetTime(llclamp(LLUI::sSettingGroups["config"]->getS32(mParentPanel->getVisible() ? "FilterItemsMaxTimePerFrameVisible" : "FilterItemsMaxTimePerFrameUnvisible"), 1, 100));
+ // Note: we filter the model, not the view
getViewModelItem()->filter(filter);
}
@@ -661,7 +663,7 @@ void LLFolderView::draw()
// get preferable text height...
S32 pixel_height = mStatusTextBox->getTextPixelHeight();
- bool height_changed = local_rect.getHeight() != pixel_height;
+ bool height_changed = (local_rect.getHeight() < pixel_height);
if (height_changed)
{
// ... if it does not match current height, lets rearrange current view.
@@ -1601,15 +1603,17 @@ void LLFolderView::update()
{
mNeedsAutoSelect = TRUE;
}
- // filter to determine visibility before arranging
+
+ // Filter to determine visibility before arranging
filter(getFolderViewModel()->getFilter());
- // Clear the modified setting on the filter only if the filter count is non-zero after running the filter process
- // Note: if the filter count is zero, then the filter most likely halted before completing the entire set of items
- if (getFolderViewModel()->getFilter().isModified() && (getFolderViewModel()->getFilter().getFilterCount() > 0))
+
+ // Clear the modified setting on the filter only if the filter finished after running the filter process
+ // Note: if the filter count has timed out, that means the filter halted before completing the entire set of items
+ if (getFolderViewModel()->getFilter().isModified() && (!getFolderViewModel()->getFilter().isTimedOut()))
{
getFolderViewModel()->getFilter().clearModified();
}
-
+
// automatically show matching items, and select first one if we had a selection
if (mNeedsAutoSelect)
{
@@ -1649,11 +1653,13 @@ void LLFolderView::update()
BOOL is_visible = isInVisibleChain();
- //Puts folders/items in proper positions
- if ( is_visible )
+ // Puts folders/items in proper positions
+ // arrange() takes the model filter flag into account and call sort() if necessary (CHUI-849)
+ // It also handles the open/close folder animation
+ if (is_visible)
{
sanitizeSelection();
- if( needsArrange() )
+ if (needsArrange())
{
S32 height = 0;
S32 width = 0;
diff --git a/indra/llui/llfolderviewitem.cpp b/indra/llui/llfolderviewitem.cpp
index fdb4108afb..6c147ccc12 100755
--- a/indra/llui/llfolderviewitem.cpp
+++ b/indra/llui/llfolderviewitem.cpp
@@ -274,6 +274,7 @@ void LLFolderViewItem::refresh()
}
mLabelWidthDirty = true;
+ // Dirty the filter flag of the model from the view (CHUI-849)
vmi.dirtyFilter();
}
@@ -943,11 +944,17 @@ void LLFolderViewFolder::addToFolder(LLFolderViewFolder* folder)
static LLFastTimer::DeclareTimer FTM_ARRANGE("Arrange");
-// Finds width and height of this object and its children. Also
-// makes sure that this view and its children are the right size.
+// Make everything right and in the right place ready for drawing (CHUI-849)
+// * Sort everything correctly if necessary
+// * Turn widgets visible/invisible according to their model filtering state
+// * Takes animation state into account for opening/closing of folders (this makes widgets visible/invisible)
+// * Reposition visible widgets so that they line up correctly with no gap
+// * Compute the width and height of the current folder and its children
+// * Makes sure that this view and its children are the right size
S32 LLFolderViewFolder::arrange( S32* width, S32* height )
{
- // sort before laying out contents
+ // Sort before laying out contents
+ // Note that we sort from the root (CHUI-849)
getRoot()->getFolderViewModel()->sort(this);
LLFastTimer t2(FTM_ARRANGE);
@@ -1613,16 +1620,13 @@ void LLFolderViewFolder::addFolder(LLFolderViewFolder* folder)
}
void LLFolderViewFolder::requestArrange()
-{
- if ( mLastArrangeGeneration != -1)
- {
- mLastArrangeGeneration = -1;
- // flag all items up to root
- if (mParentFolder)
- {
- mParentFolder->requestArrange();
- }
- }
+{
+ mLastArrangeGeneration = -1;
+ // flag all items up to root
+ if (mParentFolder)
+ {
+ mParentFolder->requestArrange();
+ }
}
void LLFolderViewFolder::toggleOpen()
diff --git a/indra/llui/llfolderviewitem.h b/indra/llui/llfolderviewitem.h
index ca31931e19..a9b0201236 100755
--- a/indra/llui/llfolderviewitem.h
+++ b/indra/llui/llfolderviewitem.h
@@ -316,7 +316,6 @@ protected:
F32 mAutoOpenCountdown;
S32 mLastArrangeGeneration;
S32 mLastCalculatedWidth;
- S32 mMostFilteredDescendantGeneration;
bool mNeedsSort;
public:
diff --git a/indra/llui/llfolderviewmodel.cpp b/indra/llui/llfolderviewmodel.cpp
index 3593804554..3363dc5316 100755
--- a/indra/llui/llfolderviewmodel.cpp
+++ b/indra/llui/llfolderviewmodel.cpp
@@ -48,7 +48,7 @@ std::string LLFolderViewModelCommon::getStatusText()
void LLFolderViewModelCommon::filter()
{
- getFilter().setFilterCount(llclamp(LLUI::sSettingGroups["config"]->getS32("FilterItemsPerFrame"), 1, 5000));
+ getFilter().resetTime(llclamp(LLUI::sSettingGroups["config"]->getS32("FilterItemsMaxTimePerFrameVisible"), 1, 100));
mFolderView->getViewModelItem()->filter(getFilter());
}
diff --git a/indra/llui/llfolderviewmodel.h b/indra/llui/llfolderviewmodel.h
index 1b61212c0e..b1bcc8bbb4 100755
--- a/indra/llui/llfolderviewmodel.h
+++ b/indra/llui/llfolderviewmodel.h
@@ -87,12 +87,11 @@ public:
virtual void setModified(EFilterModified behavior = FILTER_RESTART) = 0;
// +-------------------------------------------------------------------+
- // + Count
+ // + Time
// +-------------------------------------------------------------------+
- virtual void setFilterCount(S32 count) = 0;
- virtual S32 getFilterCount() const = 0;
- virtual void decrementFilterCount() = 0;
-
+ virtual void resetTime(S32 timeout) = 0;
+ virtual bool isTimedOut() = 0;
+
// +-------------------------------------------------------------------+
// + Default
// +-------------------------------------------------------------------+
@@ -308,26 +307,28 @@ public:
virtual bool potentiallyVisible()
{
return passedFilter() // we've passed the filter
- || getLastFilterGeneration() < mRootViewModel.getFilter().getFirstSuccessGeneration() // or we don't know yet
+ || (getLastFilterGeneration() < mRootViewModel.getFilter().getFirstSuccessGeneration()) // or we don't know yet
|| descendantsPassedFilter();
}
virtual bool passedFilter(S32 filter_generation = -1)
{
- if (filter_generation < 0)
+ if (filter_generation < 0)
+ {
filter_generation = mRootViewModel.getFilter().getFirstSuccessGeneration();
-
- bool passed_folder_filter = mPassedFolderFilter && mLastFolderFilterGeneration >= filter_generation;
- bool passed_filter = mPassedFilter && mLastFilterGeneration >= filter_generation;
- return passed_folder_filter
- && (descendantsPassedFilter(filter_generation)
- || passed_filter);
+ }
+ bool passed_folder_filter = mPassedFolderFilter && (mLastFolderFilterGeneration >= filter_generation);
+ bool passed_filter = mPassedFilter && (mLastFilterGeneration >= filter_generation);
+ return passed_folder_filter && (passed_filter || descendantsPassedFilter(filter_generation));
}
virtual bool descendantsPassedFilter(S32 filter_generation = -1)
{
- if (filter_generation < 0) filter_generation = mRootViewModel.getFilter().getFirstSuccessGeneration();
- return mMostFilteredDescendantGeneration >= filter_generation;
+ if (filter_generation < 0)
+ {
+ filter_generation = mRootViewModel.getFilter().getFirstSuccessGeneration();
+ }
+ return mMostFilteredDescendantGeneration >= filter_generation;
}
diff --git a/indra/llui/lllayoutstack.cpp b/indra/llui/lllayoutstack.cpp
index e33ac1d5c2..c89c0203b4 100755
--- a/indra/llui/lllayoutstack.cpp
+++ b/indra/llui/lllayoutstack.cpp
@@ -214,8 +214,15 @@ LLLayoutStack::Params::Params()
open_time_constant("open_time_constant", 0.02f),
close_time_constant("close_time_constant", 0.03f),
resize_bar_overlap("resize_bar_overlap", 1),
- border_size("border_size", LLCachedControl<S32>(*LLUI::sSettingGroups["config"], "UIResizeBarHeight", 0))
-{}
+ border_size("border_size", LLCachedControl<S32>(*LLUI::sSettingGroups["config"], "UIResizeBarHeight", 0)),
+ show_drag_handle("show_drag_handle", false),
+ drag_handle_first_indent("drag_handle_first_indent", 0),
+ drag_handle_second_indent("drag_handle_second_indent", 0),
+ drag_handle_thickness("drag_handle_thickness", 5),
+ drag_handle_shift("drag_handle_shift", 2)
+{
+ addSynonym(border_size, "drag_handle_gap");
+}
LLLayoutStack::LLLayoutStack(const LLLayoutStack::Params& p)
: LLView(p),
@@ -227,8 +234,14 @@ LLLayoutStack::LLLayoutStack(const LLLayoutStack::Params& p)
mClip(p.clip),
mOpenTimeConstant(p.open_time_constant),
mCloseTimeConstant(p.close_time_constant),
- mResizeBarOverlap(p.resize_bar_overlap)
-{}
+ mResizeBarOverlap(p.resize_bar_overlap),
+ mShowDragHandle(p.show_drag_handle),
+ mDragHandleFirstIndent(p.drag_handle_first_indent),
+ mDragHandleSecondIndent(p.drag_handle_second_indent),
+ mDragHandleThickness(p.drag_handle_thickness),
+ mDragHandleShift(p.drag_handle_shift)
+{
+}
LLLayoutStack::~LLLayoutStack()
{
@@ -262,6 +275,26 @@ void LLLayoutStack::draw()
drawChild(panelp, 0, 0, !clip_rect.isEmpty());
}
}
+
+ const LLView::child_list_t * child_listp = getChildList();
+ BOOST_FOREACH(LLView * childp, * child_listp)
+ {
+ LLResizeBar * resize_barp = dynamic_cast<LLResizeBar*>(childp);
+ if (resize_barp && resize_barp->isShowDragHandle() && resize_barp->getVisible() && resize_barp->getRect().isValid())
+ {
+ LLRect screen_rect = resize_barp->calcScreenRect();
+ if (LLUI::getRootView()->getLocalRect().overlaps(screen_rect) && LLUI::sDirtyRect.overlaps(screen_rect))
+ {
+ LLUI::pushMatrix();
+ {
+ const LLRect& rb_rect(resize_barp->getRect());
+ LLUI::translate(rb_rect.mLeft, rb_rect.mBottom);
+ resize_barp->draw();
+ }
+ LLUI::popMatrix();
+ }
+ }
+ }
}
void LLLayoutStack::removeChild(LLView* view)
@@ -390,7 +423,6 @@ void LLLayoutStack::updateLayout()
BOOST_FOREACH(LLLayoutPanel* panelp, mPanels)
{
F32 panel_dim = llmax(panelp->getExpandedMinDim(), panelp->mTargetDim);
- F32 panel_visible_dim = panelp->getVisibleDim();
LLRect panel_rect;
if (mOrientation == HORIZONTAL)
@@ -407,27 +439,61 @@ void LLLayoutStack::updateLayout()
getRect().getWidth(),
llround(panel_dim));
}
- panelp->setIgnoreReshape(true);
- panelp->setShape(panel_rect);
- panelp->setIgnoreReshape(false);
LLRect resize_bar_rect(panel_rect);
-
+ LLResizeBar * resize_barp = panelp->getResizeBar();
+ bool show_drag_handle = resize_barp->isShowDragHandle();
F32 panel_spacing = (F32)mPanelSpacing * panelp->getVisibleAmount();
+ F32 panel_visible_dim = panelp->getVisibleDim();
+ S32 panel_spacing_round = (S32)(llround(panel_spacing));
+
if (mOrientation == HORIZONTAL)
{
- resize_bar_rect.mLeft = panel_rect.mRight - mResizeBarOverlap;
- resize_bar_rect.mRight = panel_rect.mRight + (S32)(llround(panel_spacing)) + mResizeBarOverlap;
-
cur_pos += panel_visible_dim + panel_spacing;
+
+ if (show_drag_handle && panel_spacing_round > mDragHandleThickness)
+ {
+ resize_bar_rect.mLeft = panel_rect.mRight + mDragHandleShift;
+ resize_bar_rect.mRight = resize_bar_rect.mLeft + mDragHandleThickness;
+ }
+ else
+ {
+ resize_bar_rect.mLeft = panel_rect.mRight - mResizeBarOverlap;
+ resize_bar_rect.mRight = panel_rect.mRight + panel_spacing_round + mResizeBarOverlap;
+ }
+
+ if (show_drag_handle)
+ {
+ resize_bar_rect.mBottom += mDragHandleSecondIndent;
+ resize_bar_rect.mTop -= mDragHandleFirstIndent;
+ }
+
}
else //VERTICAL
{
- resize_bar_rect.mTop = panel_rect.mBottom + mResizeBarOverlap;
- resize_bar_rect.mBottom = panel_rect.mBottom - (S32)(llround(panel_spacing)) - mResizeBarOverlap;
-
cur_pos -= panel_visible_dim + panel_spacing;
+
+ if (show_drag_handle && panel_spacing_round > mDragHandleThickness)
+ {
+ resize_bar_rect.mTop = panel_rect.mBottom - mDragHandleShift;
+ resize_bar_rect.mBottom = resize_bar_rect.mTop - mDragHandleThickness;
+ }
+ else
+ {
+ resize_bar_rect.mTop = panel_rect.mBottom + mResizeBarOverlap;
+ resize_bar_rect.mBottom = panel_rect.mBottom - panel_spacing_round - mResizeBarOverlap;
+ }
+
+ if (show_drag_handle)
+ {
+ resize_bar_rect.mLeft += mDragHandleFirstIndent;
+ resize_bar_rect.mRight -= mDragHandleSecondIndent;
+ }
}
+
+ panelp->setIgnoreReshape(true);
+ panelp->setShape(panel_rect);
+ panelp->setIgnoreReshape(false);
panelp->mResizeBar->setShape(resize_bar_rect);
}
@@ -475,14 +541,13 @@ void LLLayoutStack::createResizeBar(LLLayoutPanel* panelp)
{
if (lp->mResizeBar == NULL)
{
- LLResizeBar::Side side = (mOrientation == HORIZONTAL) ? LLResizeBar::RIGHT : LLResizeBar::BOTTOM;
-
LLResizeBar::Params resize_params;
resize_params.name("resize");
resize_params.resizing_view(lp);
resize_params.min_size(lp->getRelevantMinDim());
- resize_params.side(side);
+ resize_params.side((mOrientation == HORIZONTAL) ? LLResizeBar::RIGHT : LLResizeBar::BOTTOM);
resize_params.snapping_enabled(false);
+ resize_params.show_drag_handle(mShowDragHandle);
LLResizeBar* resize_bar = LLUICtrlFactory::create<LLResizeBar>(resize_params);
lp->mResizeBar = resize_bar;
LLView::addChild(resize_bar, 0);
@@ -864,3 +929,4 @@ void LLLayoutStack::updateResizeBarLimits()
previous_visible_panelp = visible_panelp;
}
}
+
diff --git a/indra/llui/lllayoutstack.h b/indra/llui/lllayoutstack.h
index 02c664f1a0..b570974bd6 100755
--- a/indra/llui/lllayoutstack.h
+++ b/indra/llui/lllayoutstack.h
@@ -62,6 +62,11 @@ public:
Optional<F32> open_time_constant,
close_time_constant;
Optional<S32> resize_bar_overlap;
+ Optional<bool> show_drag_handle;
+ Optional<S32> drag_handle_first_indent;
+ Optional<S32> drag_handle_second_indent;
+ Optional<S32> drag_handle_thickness;
+ Optional<S32> drag_handle_shift;
Params();
};
@@ -126,6 +131,11 @@ private:
F32 mCloseTimeConstant;
bool mNeedsLayout;
S32 mResizeBarOverlap;
+ bool mShowDragHandle;
+ S32 mDragHandleFirstIndent;
+ S32 mDragHandleSecondIndent;
+ S32 mDragHandleThickness;
+ S32 mDragHandleShift;
}; // end class LLLayoutStack
diff --git a/indra/llui/llmenugl.cpp b/indra/llui/llmenugl.cpp
index f7bf39c897..f854e1785d 100755
--- a/indra/llui/llmenugl.cpp
+++ b/indra/llui/llmenugl.cpp
@@ -3146,6 +3146,13 @@ void LLMenuGL::showPopup(LLView* spawning_view, LLMenuGL* menu, S32 x, S32 y)
const S32 CURSOR_HEIGHT = 22; // Approximate "normal" cursor size
const S32 CURSOR_WIDTH = 12;
+ if (menu->getChildList()->empty())
+ {
+ return;
+ }
+
+ menu->setVisible( TRUE );
+
//Do not show menu if all menu items are disabled
BOOL item_enabled = false;
for (LLView::child_list_t::const_iterator itor = menu->getChildList()->begin();
@@ -3156,8 +3163,9 @@ void LLMenuGL::showPopup(LLView* spawning_view, LLMenuGL* menu, S32 x, S32 y)
item_enabled = item_enabled || menu_item->getEnabled();
}
- if(menu->getChildList()->empty() || !item_enabled)
+ if(!item_enabled)
{
+ menu->setVisible( FALSE );
return;
}
@@ -3173,8 +3181,6 @@ void LLMenuGL::showPopup(LLView* spawning_view, LLMenuGL* menu, S32 x, S32 y)
menu->mFirstVisibleItem = NULL;
}
- menu->setVisible( TRUE );
-
// Fix menu rect if needed.
menu->needsArrange();
menu->arrangeAndClear();
diff --git a/indra/llui/llresizebar.cpp b/indra/llui/llresizebar.cpp
index 15e56cbfe5..e67b22c977 100755
--- a/indra/llui/llresizebar.cpp
+++ b/indra/llui/llresizebar.cpp
@@ -28,14 +28,53 @@
#include "llresizebar.h"
+#include "lllocalcliprect.h"
#include "llmath.h"
#include "llui.h"
#include "llmenugl.h"
#include "llfocusmgr.h"
#include "llwindow.h"
+class LLImagePanel : public LLPanel
+{
+public:
+ struct Params : public LLInitParam::Block<Params, LLPanel::Params>
+ {
+ Optional<bool> horizontal;
+ Params() : horizontal("horizontal", false) {}
+ };
+ LLImagePanel(const Params& p) : LLPanel(p), mHorizontal(p.horizontal) {}
+ virtual ~LLImagePanel() {}
+
+ void draw()
+ {
+ const LLRect& parent_rect = getParent()->getRect();
+ const LLRect& rect = getRect();
+ LLRect clip_rect( -rect.mLeft, parent_rect.getHeight() - rect.mBottom - 2
+ , parent_rect.getWidth() - rect.mLeft - (mHorizontal ? 2 : 0), -rect.mBottom);
+ LLLocalClipRect clip(clip_rect);
+ LLPanel::draw();
+ }
+
+private:
+ bool mHorizontal;
+};
+
+static LLDefaultChildRegistry::Register<LLImagePanel> t1("resize_bar_image_panel");
+
+LLResizeBar::Params::Params()
+: max_size("max_size", S32_MAX),
+ snapping_enabled("snapping_enabled", true),
+ resizing_view("resizing_view"),
+ side("side"),
+ allow_double_click_snapping("allow_double_click_snapping", true),
+ show_drag_handle("show_drag_handle", false)
+{
+ name = "resize_bar";
+}
+
LLResizeBar::LLResizeBar(const LLResizeBar::Params& p)
-: LLView(p),
+: LLPanel(p),
mDragLastScreenX( 0 ),
mDragLastScreenY( 0 ),
mLastMouseScreenX( 0 ),
@@ -46,7 +85,9 @@ LLResizeBar::LLResizeBar(const LLResizeBar::Params& p)
mSnappingEnabled(p.snapping_enabled),
mAllowDoubleClickSnapping(p.allow_double_click_snapping),
mResizingView(p.resizing_view),
- mResizeListener(NULL)
+ mResizeListener(NULL),
+ mShowDragHandle(p.show_drag_handle),
+ mImagePanel(NULL)
{
setFollowsNone();
// set up some generically good follow code.
@@ -75,8 +116,37 @@ LLResizeBar::LLResizeBar(const LLResizeBar::Params& p)
default:
break;
}
+
+ if (mShowDragHandle)
+ {
+ LLViewBorder::Params border_params;
+ border_params.border_thickness = 1;
+ border_params.highlight_light_color = LLUIColorTable::instance().getColor("ResizebarBorderLight");
+ border_params.shadow_dark_color = LLUIColorTable::instance().getColor("ResizebarBorderDark");
+
+ addBorder(border_params);
+ setBorderVisible(TRUE);
+
+ LLImagePanel::Params image_panel;
+ mDragHandleImage = LLUI::getUIImage(LLResizeBar::RIGHT == mSide ? "Vertical Drag Handle" : "Horizontal Drag Handle");
+ image_panel.bg_alpha_image = mDragHandleImage;
+ image_panel.background_visible = true;
+ image_panel.horizontal = (LLResizeBar::BOTTOM == mSide);
+ mImagePanel = LLUICtrlFactory::create<LLImagePanel>(image_panel);
+ setImagePanel(mImagePanel);
+ }
}
+BOOL LLResizeBar::postBuild()
+{
+ if (mShowDragHandle)
+ {
+ setBackgroundVisible(TRUE);
+ setTransparentColor(LLUIColorTable::instance().getColor("ResizebarBody"));
+ }
+
+ return LLPanel::postBuild();
+}
BOOL LLResizeBar::handleMouseDown(S32 x, S32 y, MASK mask)
{
@@ -342,3 +412,39 @@ BOOL LLResizeBar::handleDoubleClick(S32 x, S32 y, MASK mask)
return TRUE;
}
+void LLResizeBar::setImagePanel(LLPanel * panelp)
+{
+ const LLView::child_list_t * children = getChildList();
+ if (getChildCount() == 2)
+ {
+ LLPanel * image_panelp = dynamic_cast<LLPanel*>(children->back());
+ if (image_panelp)
+ {
+ removeChild(image_panelp);
+ delete image_panelp;
+ }
+ }
+
+ addChild(panelp);
+ sendChildToBack(panelp);
+}
+
+LLPanel * LLResizeBar::getImagePanel() const
+{
+ return getChildCount() > 0 ? (LLPanel *)getChildList()->back() : NULL;
+}
+
+void LLResizeBar::draw()
+{
+ if (mShowDragHandle)
+ {
+ S32 image_width = mDragHandleImage->getTextureWidth();
+ S32 image_height = mDragHandleImage->getTextureHeight();
+ const LLRect& panel_rect = getRect();
+ S32 image_left = (panel_rect.getWidth() - image_width) / 2 - 1;
+ S32 image_bottom = (panel_rect.getHeight() - image_height) / 2;
+ mImagePanel->setRect(LLRect(image_left, image_bottom + image_height, image_left + image_width, image_bottom));
+ }
+
+ LLPanel::draw();
+}
diff --git a/indra/llui/llresizebar.h b/indra/llui/llresizebar.h
index 8190a95a71..bcf8ea0b40 100755
--- a/indra/llui/llresizebar.h
+++ b/indra/llui/llresizebar.h
@@ -27,15 +27,14 @@
#ifndef LL_RESIZEBAR_H
#define LL_RESIZEBAR_H
-#include "llview.h"
-#include "llcoord.h"
+#include "llpanel.h"
-class LLResizeBar : public LLView
+class LLResizeBar : public LLPanel
{
public:
enum Side { LEFT, TOP, RIGHT, BOTTOM };
- struct Params : public LLInitParam::Block<Params, LLView::Params>
+ struct Params : public LLInitParam::Block<Params, LLPanel::Params>
{
Mandatory<LLView*> resizing_view;
Mandatory<Side> side;
@@ -44,24 +43,19 @@ public:
Optional<S32> max_size;
Optional<bool> snapping_enabled;
Optional<bool> allow_double_click_snapping;
+ Optional<bool> show_drag_handle;
- Params()
- : max_size("max_size", S32_MAX),
- snapping_enabled("snapping_enabled", true),
- resizing_view("resizing_view"),
- side("side"),
- allow_double_click_snapping("allow_double_click_snapping", true)
- {
- name = "resize_bar";
- }
+ Params();
};
protected:
LLResizeBar(const LLResizeBar::Params& p);
friend class LLUICtrlFactory;
+
+ /*virtual*/ BOOL postBuild();
public:
-// virtual void draw(); No appearance
+ virtual void draw();
virtual BOOL handleHover(S32 x, S32 y, MASK mask);
virtual BOOL handleMouseDown(S32 x, S32 y, MASK mask);
virtual BOOL handleMouseUp(S32 x, S32 y, MASK mask);
@@ -72,20 +66,26 @@ public:
void setAllowDoubleClickSnapping(BOOL allow) { mAllowDoubleClickSnapping = allow; }
bool canResize() { return getEnabled() && mMaxSize > mMinSize; }
void setResizeListener(boost::function<void(void*)> listener) {mResizeListener = listener;}
+ BOOL isShowDragHandle() const { return mShowDragHandle; }
+ void setImagePanel(LLPanel * panelp);
+ LLPanel * getImagePanel() const;
private:
- S32 mDragLastScreenX;
- S32 mDragLastScreenY;
- S32 mLastMouseScreenX;
- S32 mLastMouseScreenY;
- LLCoordGL mLastMouseDir;
- S32 mMinSize;
- S32 mMaxSize;
- const Side mSide;
- BOOL mSnappingEnabled;
- BOOL mAllowDoubleClickSnapping;
- LLView* mResizingView;
- boost::function<void(void*)> mResizeListener;
+ S32 mDragLastScreenX;
+ S32 mDragLastScreenY;
+ S32 mLastMouseScreenX;
+ S32 mLastMouseScreenY;
+ LLCoordGL mLastMouseDir;
+ S32 mMinSize;
+ S32 mMaxSize;
+ const Side mSide;
+ BOOL mSnappingEnabled;
+ BOOL mAllowDoubleClickSnapping;
+ BOOL mShowDragHandle;
+ LLView* mResizingView;
+ boost::function<void(void*)> mResizeListener;
+ LLPointer<LLUIImage> mDragHandleImage;
+ LLPanel * mImagePanel;
};
#endif // LL_RESIZEBAR_H
diff --git a/indra/llui/llscrolllistcolumn.cpp b/indra/llui/llscrolllistcolumn.cpp
index af124d9826..cc9ff7a487 100755
--- a/indra/llui/llscrolllistcolumn.cpp
+++ b/indra/llui/llscrolllistcolumn.cpp
@@ -236,7 +236,8 @@ void LLScrollColumnHeader::handleReshape(const LLRect& new_rect, bool by_user)
// tell scroll list to layout columns again
// do immediate update to get proper feedback to resize handle
// which needs to know how far the resize actually went
- mColumn->mParentCtrl->updateColumns();
+ const bool force_update = true;
+ mColumn->mParentCtrl->updateColumns(force_update);
}
}
diff --git a/indra/llui/llscrolllistctrl.cpp b/indra/llui/llscrolllistctrl.cpp
index 7f04c92b27..6e03f604a2 100755
--- a/indra/llui/llscrolllistctrl.cpp
+++ b/indra/llui/llscrolllistctrl.cpp
@@ -615,7 +615,6 @@ S32 LLScrollListCtrl::calcMaxContentWidth()
if (mColumnWidthsDirty)
{
- mColumnWidthsDirty = false;
// update max content width for this column, by looking at all items
column->mMaxContentWidth = column->mHeader ? LLFontGL::getFontSansSerifSmall()->getWidth(column->mLabel) + mColumnPadding + HEADING_TEXT_PADDING : 0;
item_list::iterator iter;
@@ -629,6 +628,7 @@ S32 LLScrollListCtrl::calcMaxContentWidth()
}
max_item_width += column->mMaxContentWidth;
}
+ mColumnWidthsDirty = false;
return max_item_width;
}
@@ -643,7 +643,7 @@ bool LLScrollListCtrl::updateColumnWidths()
if (!column) continue;
// update column width
- S32 new_width = column->getWidth();
+ S32 new_width = 0;
if (column->mRelWidth >= 0)
{
new_width = (S32)llround(column->mRelWidth*mItemListRect.getWidth());
@@ -652,6 +652,10 @@ bool LLScrollListCtrl::updateColumnWidths()
{
new_width = (mItemListRect.getWidth() - mTotalStaticColumnWidth - mTotalColumnPadding) / mNumDynamicWidthColumns;
}
+ else
+ {
+ new_width = column->getWidth();
+ }
if (column->getWidth() != new_width)
{
@@ -693,9 +697,9 @@ void LLScrollListCtrl::updateLineHeightInsert(LLScrollListItem* itemp)
}
-void LLScrollListCtrl::updateColumns()
+void LLScrollListCtrl::updateColumns(bool force_update)
{
- if (!mColumnsDirty)
+ if (!mColumnsDirty && !force_update)
return;
mColumnsDirty = false;
@@ -749,7 +753,7 @@ void LLScrollListCtrl::updateColumns()
}
// propagate column widths to individual cells
- if (columns_changed_width)
+ if (columns_changed_width || force_update)
{
item_list::iterator iter;
for (iter = mItemList.begin(); iter != mItemList.end(); iter++)
@@ -1179,10 +1183,10 @@ LLScrollListItem* LLScrollListCtrl::addSeparator(EAddPosition pos)
// Selects first enabled item of the given name.
// Returns false if item not found.
// Calls getItemByLabel in order to combine functionality
-BOOL LLScrollListCtrl::selectItemByLabel(const std::string& label, BOOL case_sensitive)
+BOOL LLScrollListCtrl::selectItemByLabel(const std::string& label, BOOL case_sensitive, S32 column/* = 0*/)
{
deselectAllItems(TRUE); // ensure that no stale items are selected, even if we don't find a match
- LLScrollListItem* item = getItemByLabel(label, case_sensitive);
+ LLScrollListItem* item = getItemByLabel(label, case_sensitive, column);
bool found = NULL != item;
if(found)
diff --git a/indra/llui/llscrolllistctrl.h b/indra/llui/llscrolllistctrl.h
index 8fa06cc499..c61e281a31 100755
--- a/indra/llui/llscrolllistctrl.h
+++ b/indra/llui/llscrolllistctrl.h
@@ -241,7 +241,7 @@ public:
// one of which can be selected at a time.
virtual LLScrollListItem* addSimpleElement(const std::string& value, EAddPosition pos = ADD_BOTTOM, const LLSD& id = LLSD());
- BOOL selectItemByLabel( const std::string& item, BOOL case_sensitive = TRUE ); // FALSE if item not found
+ BOOL selectItemByLabel( const std::string& item, BOOL case_sensitive = TRUE, S32 column = 0 ); // FALSE if item not found
BOOL selectItemByPrefix(const std::string& target, BOOL case_sensitive = TRUE);
BOOL selectItemByPrefix(const LLWString& target, BOOL case_sensitive = TRUE);
LLScrollListItem* getItemByLabel( const std::string& item, BOOL case_sensitive = TRUE, S32 column = 0 );
@@ -342,7 +342,7 @@ public:
static void onClickColumn(void *userdata);
- virtual void updateColumns();
+ virtual void updateColumns(bool force_update = false);
S32 calcMaxContentWidth();
bool updateColumnWidths();
diff --git a/indra/llui/lltextbase.cpp b/indra/llui/lltextbase.cpp
index a45c4ced2e..3c284b3f03 100755
--- a/indra/llui/lltextbase.cpp
+++ b/indra/llui/lltextbase.cpp
@@ -180,6 +180,7 @@ LLTextBase::Params::Params()
LLTextBase::LLTextBase(const LLTextBase::Params &p)
: LLUICtrl(p, LLTextViewModelPtr(new LLTextViewModel)),
mURLClickSignal(NULL),
+ mIsFriendSignal(NULL),
mMaxTextByteLength( p.max_text_length ),
mFont(p.font),
mFontShadow(p.font_shadow),
@@ -653,6 +654,10 @@ void LLTextBase::drawText()
mSpellCheckEnd = end;
}
}
+ else
+ {
+ mMisspellRanges.clear();
+ }
LLTextSegmentPtr cur_segment = *seg_iter;
@@ -1850,7 +1855,17 @@ LLTextBase::segment_set_t::iterator LLTextBase::getSegIterContaining(S32 index)
static LLPointer<LLIndexSegment> index_segment = new LLIndexSegment();
- if (index > getLength()) { return mSegments.end(); }
+ S32 text_len = 0;
+ if (!useLabel())
+ {
+ text_len = getLength();
+ }
+ else
+ {
+ text_len = mLabel.getWString().length();
+ }
+
+ if (index > text_len) { return mSegments.end(); }
// when there are no segments, we return the end iterator, which must be checked by caller
if (mSegments.size() <= 1) { return mSegments.begin(); }
@@ -1866,7 +1881,17 @@ LLTextBase::segment_set_t::const_iterator LLTextBase::getSegIterContaining(S32 i
{
static LLPointer<LLIndexSegment> index_segment = new LLIndexSegment();
- if (index > getLength()) { return mSegments.end(); }
+ S32 text_len = 0;
+ if (!useLabel())
+ {
+ text_len = getLength();
+ }
+ else
+ {
+ text_len = mLabel.getWString().length();
+ }
+
+ if (index > text_len) { return mSegments.end(); }
// when there are no segments, we return the end iterator, which must be checked by caller
if (mSegments.size() <= 1) { return mSegments.begin(); }
@@ -1916,9 +1941,12 @@ void LLTextBase::createUrlContextMenu(S32 x, S32 y, const std::string &in_url)
registrar.add("Url.OpenInternal", boost::bind(&LLUrlAction::openURLInternal, url));
registrar.add("Url.OpenExternal", boost::bind(&LLUrlAction::openURLExternal, url));
registrar.add("Url.Execute", boost::bind(&LLUrlAction::executeSLURL, url));
+ registrar.add("Url.Block", boost::bind(&LLUrlAction::blockObject, url));
registrar.add("Url.Teleport", boost::bind(&LLUrlAction::teleportToLocation, url));
registrar.add("Url.ShowProfile", boost::bind(&LLUrlAction::showProfile, url));
registrar.add("Url.AddFriend", boost::bind(&LLUrlAction::addFriend, url));
+ registrar.add("Url.RemoveFriend", boost::bind(&LLUrlAction::removeFriend, url));
+ registrar.add("Url.SendIM", boost::bind(&LLUrlAction::sendIM, url));
registrar.add("Url.ShowOnMap", boost::bind(&LLUrlAction::showLocationOnMap, url));
registrar.add("Url.CopyLabel", boost::bind(&LLUrlAction::copyLabelToClipboard, url));
registrar.add("Url.CopyUrl", boost::bind(&LLUrlAction::copyURLToClipboard, url));
@@ -1927,6 +1955,19 @@ void LLTextBase::createUrlContextMenu(S32 x, S32 y, const std::string &in_url)
delete mPopupMenu;
mPopupMenu = LLUICtrlFactory::getInstance()->createFromFile<LLContextMenu>(xui_file, LLMenuGL::sMenuContainer,
LLMenuHolderGL::child_registry_t::instance());
+ if (mIsFriendSignal)
+ {
+ bool isFriend = *(*mIsFriendSignal)(LLUUID(LLUrlAction::getUserID(url)));
+ LLView* addFriendButton = mPopupMenu->getChild<LLView>("add_friend");
+ LLView* removeFriendButton = mPopupMenu->getChild<LLView>("remove_friend");
+
+ if (addFriendButton && removeFriendButton)
+ {
+ addFriendButton->setEnabled(!isFriend);
+ removeFriendButton->setEnabled(isFriend);
+ }
+ }
+
if (mPopupMenu)
{
mPopupMenu->show(x, y);
@@ -2096,7 +2137,7 @@ void LLTextBase::resetLabel()
}
}
-bool LLTextBase::useLabel()
+bool LLTextBase::useLabel() const
{
return !getLength() && !mLabel.empty() && !hasFocus();
}
@@ -2602,21 +2643,18 @@ void LLTextBase::setCursorAtLocalPos( S32 local_x, S32 local_y, bool round, bool
void LLTextBase::changeLine( S32 delta )
{
S32 line = getLineNumFromDocIndex(mCursorPos);
+ S32 max_line_nb = getLineCount() - 1;
+ max_line_nb = (max_line_nb < 0 ? 0 : max_line_nb);
+
+ S32 new_line = llclamp(line + delta, 0, max_line_nb);
- S32 new_line = line;
- if( (delta < 0) && (line > 0 ) )
- {
- new_line = line - 1;
- }
- else if( (delta > 0) && (line < (getLineCount() - 1)) )
- {
- new_line = line + 1;
- }
-
- LLRect visible_region = getVisibleDocumentRect();
-
- S32 new_cursor_pos = getDocIndexFromLocalCoord(mDesiredXPixel, mLineInfoList[new_line].mRect.mBottom + mVisibleTextRect.mBottom - visible_region.mBottom, TRUE);
- setCursorPos(new_cursor_pos, true);
+ if (new_line != line)
+ {
+ LLRect visible_region = getVisibleDocumentRect();
+ S32 new_cursor_pos = getDocIndexFromLocalCoord(mDesiredXPixel,
+ mLineInfoList[new_line].mRect.mBottom + mVisibleTextRect.mBottom - visible_region.mBottom, TRUE);
+ setCursorPos(new_cursor_pos, true);
+ }
}
bool LLTextBase::scrolledToStart()
@@ -2910,6 +2948,15 @@ boost::signals2::connection LLTextBase::setURLClickedCallback(const commit_signa
return mURLClickSignal->connect(cb);
}
+boost::signals2::connection LLTextBase::setIsFriendCallback(const is_friend_signal_t::slot_type& cb)
+{
+ if (!mIsFriendSignal)
+ {
+ mIsFriendSignal = new is_friend_signal_t();
+ }
+ return mIsFriendSignal->connect(cb);
+}
+
//
// LLTextSegment
//
@@ -3203,7 +3250,7 @@ S32 LLNormalTextSegment::getNumChars(S32 num_pixels, S32 segment_offset, S32 lin
: LLFontGL::ONLY_WORD_BOUNDARIES;
- LLWString offsetString(text.c_str() + segment_offset + mStart);
+ S32 offsetLength = text.length() - (segment_offset + mStart);
if(getLength() < segment_offset + mStart)
{
@@ -3211,13 +3258,13 @@ S32 LLNormalTextSegment::getNumChars(S32 num_pixels, S32 segment_offset, S32 lin
<< segment_offset << "\tmStart:\t" << mStart << "\tsegments\t" << mEditor.mSegments.size() << "\tmax_chars\t" << max_chars << llendl;
}
- if(offsetString.length() + 1 < max_chars)
+ if( (offsetLength + 1) < max_chars)
{
- llinfos << "offsetString.length() + 1 < max_chars\t max_chars:\t" << max_chars << "\toffsetString.length():\t" << offsetString.length() << " getLength() : "
+ llinfos << "offsetString.length() + 1 < max_chars\t max_chars:\t" << max_chars << "\toffsetLength:\t" << offsetLength << " getLength() : "
<< getLength() << "\tsegment_offset:\t" << segment_offset << "\tmStart:\t" << mStart << "\tsegments\t" << mEditor.mSegments.size() << llendl;
}
- S32 num_chars = mStyle->getFont()->maxDrawableChars(offsetString.c_str(),
+ S32 num_chars = mStyle->getFont()->maxDrawableChars( text.c_str() + (segment_offset + mStart),
(F32)num_pixels,
max_chars,
word_wrap_style);
diff --git a/indra/llui/lltextbase.h b/indra/llui/lltextbase.h
index 20a73387b5..a74e97cac8 100755
--- a/indra/llui/lltextbase.h
+++ b/indra/llui/lltextbase.h
@@ -258,6 +258,8 @@ public:
friend class LLNormalTextSegment;
friend class LLUICtrlFactory;
+ typedef boost::signals2::signal<bool (const LLUUID& user_id)> is_friend_signal_t;
+
struct LineSpacingParams : public LLInitParam::ChoiceBlock<LineSpacingParams>
{
Alternative<F32> multiple;
@@ -434,6 +436,7 @@ public:
virtual void appendImageSegment(const LLStyle::Params& style_params);
virtual void appendWidget(const LLInlineViewSegment::Params& params, const std::string& text, bool allow_undo);
boost::signals2::connection setURLClickedCallback(const commit_signal_t::slot_type& cb);
+ boost::signals2::connection setIsFriendCallback(const is_friend_signal_t::slot_type& cb);
void setWordWrap(bool wrap);
LLScrollContainer* getScrollContainer() const { return mScroller; }
@@ -507,7 +510,7 @@ protected:
void initFromParams(const Params& p);
virtual void beforeValueChange();
virtual void onValueChange(S32 start, S32 end);
- virtual bool useLabel();
+ virtual bool useLabel() const;
// draw methods
void drawSelectionBackground(); // draws the black box behind the selected text
@@ -648,6 +651,9 @@ protected:
// Fired when a URL link is clicked
commit_signal_t* mURLClickSignal;
+ // Used to check if user with given ID is avatar's friend
+ is_friend_signal_t* mIsFriendSignal;
+
LLUIString mLabel; // text label that is visible when no user text provided
};
diff --git a/indra/llui/lltexteditor.cpp b/indra/llui/lltexteditor.cpp
index d6c5c5c48e..0c16e06109 100755
--- a/indra/llui/lltexteditor.cpp
+++ b/indra/llui/lltexteditor.cpp
@@ -1972,8 +1972,7 @@ void LLTextEditor::onFocusReceived()
updateAllowingLanguageInput();
}
-// virtual, from LLView
-void LLTextEditor::onFocusLost()
+void LLTextEditor::focusLostHelper()
{
updateAllowingLanguageInput();
@@ -1990,7 +1989,11 @@ void LLTextEditor::onFocusLost()
// Make sure cursor is shown again
getWindow()->showCursorFromMouseMove();
+}
+void LLTextEditor::onFocusLost()
+{
+ focusLostHelper();
LLTextBase::onFocusLost();
}
@@ -2136,12 +2139,17 @@ void LLTextEditor::drawPreeditMarker()
continue;
}
- S32 preedit_left = mVisibleTextRect.mLeft;
+ line_info& line = mLineInfoList[cur_line];
+ LLRect text_rect(line.mRect);
+ text_rect.mRight = mDocumentView->getRect().getWidth(); // clamp right edge to document extents
+ text_rect.translate(mDocumentView->getRect().mLeft, mDocumentView->getRect().mBottom); // adjust by scroll position
+
+ S32 preedit_left = text_rect.mLeft;
if (left > line_start)
{
preedit_left += mFont->getWidth(text, line_start, left - line_start);
}
- S32 preedit_right = mVisibleTextRect.mLeft;
+ S32 preedit_right = text_rect.mLeft;
if (right < line_end)
{
preedit_right += mFont->getWidth(text, line_start, right - line_start);
@@ -2154,18 +2162,18 @@ void LLTextEditor::drawPreeditMarker()
if (mPreeditStandouts[i])
{
gl_rect_2d(preedit_left + preedit_standout_gap,
- line_y + preedit_standout_position,
- preedit_right - preedit_standout_gap - 1,
- line_y + preedit_standout_position - preedit_standout_thickness,
- (mCursorColor.get() * preedit_standout_brightness + mWriteableBgColor.get() * (1 - preedit_standout_brightness)).setAlpha(1.0f));
+ text_rect.mBottom + mFont->getDescenderHeight() - 1,
+ preedit_right - preedit_standout_gap - 1,
+ text_rect.mBottom + mFont->getDescenderHeight() - 1 - preedit_standout_thickness,
+ (mCursorColor.get() * preedit_standout_brightness + mWriteableBgColor.get() * (1 - preedit_standout_brightness)).setAlpha(1.0f));
}
else
{
gl_rect_2d(preedit_left + preedit_marker_gap,
- line_y + preedit_marker_position,
- preedit_right - preedit_marker_gap - 1,
- line_y + preedit_marker_position - preedit_marker_thickness,
- (mCursorColor.get() * preedit_marker_brightness + mWriteableBgColor.get() * (1 - preedit_marker_brightness)).setAlpha(1.0f));
+ text_rect.mBottom + mFont->getDescenderHeight() - 1,
+ preedit_right - preedit_marker_gap - 1,
+ text_rect.mBottom + mFont->getDescenderHeight() - 1 - preedit_marker_thickness,
+ (mCursorColor.get() * preedit_marker_brightness + mWriteableBgColor.get() * (1 - preedit_marker_brightness)).setAlpha(1.0f));
}
}
}
@@ -2248,12 +2256,13 @@ void LLTextEditor::draw()
LLRect clip_rect(mVisibleTextRect);
clip_rect.stretch(1);
LLLocalClipRect clip(clip_rect);
- drawPreeditMarker();
}
LLTextBase::draw();
drawLineNumbers();
+ drawPreeditMarker();
+
//RN: the decision was made to always show the orange border for keyboard focus but do not put an insertion caret
// when in readonly mode
mBorder->setKeyboardFocusHighlight( hasFocus() );// && !mReadOnly);
@@ -2703,14 +2712,20 @@ BOOL LLTextEditor::hasPreeditString() const
void LLTextEditor::resetPreedit()
{
+ if (hasSelection())
+ {
+ if (hasPreeditString())
+ {
+ llwarns << "Preedit and selection!" << llendl;
+ deselect();
+ }
+ else
+ {
+ deleteSelection(TRUE);
+ }
+ }
if (hasPreeditString())
{
- if (hasSelection())
- {
- llwarns << "Preedit and selection!" << llendl;
- deselect();
- }
-
setCursorPos(mPreeditPositions.front());
removeStringNoUndo(mCursorPos, mPreeditPositions.back() - mCursorPos);
insertStringNoUndo(mCursorPos, mPreeditOverwrittenWString);
@@ -2758,7 +2773,10 @@ void LLTextEditor::updatePreedit(const LLWString &preedit_string,
{
mPreeditOverwrittenWString.clear();
}
- insertStringNoUndo(insert_preedit_at, mPreeditWString);
+
+ segment_vec_t segments;
+ //pass empty segments to let "insertStringNoUndo" make new LLNormalTextSegment and insert it, if needed.
+ insertStringNoUndo(insert_preedit_at, mPreeditWString, &segments);
mPreeditStandouts = preedit_standouts;
diff --git a/indra/llui/lltexteditor.h b/indra/llui/lltexteditor.h
index ad46ed45ec..32b543ec0e 100755
--- a/indra/llui/lltexteditor.h
+++ b/indra/llui/lltexteditor.h
@@ -255,6 +255,7 @@ protected:
S32 insert(S32 pos, const LLWString &wstr, bool group_with_next_op, LLTextSegmentPtr segment);
S32 remove(S32 pos, S32 length, bool group_with_next_op);
+ void focusLostHelper();
void updateAllowingLanguageInput();
BOOL hasPreeditString() const;
diff --git a/indra/llui/lltoolbar.cpp b/indra/llui/lltoolbar.cpp
index 3d9f5cbbc2..928e82cb8c 100755
--- a/indra/llui/lltoolbar.cpp
+++ b/indra/llui/lltoolbar.cpp
@@ -381,7 +381,7 @@ bool LLToolBar::stopCommandInProgress(const LLCommandId& commandId)
return (command_button != NULL);
}
-bool LLToolBar::flashCommand(const LLCommandId& commandId, bool flash)
+bool LLToolBar::flashCommand(const LLCommandId& commandId, bool flash, bool force_flashing/* = false */)
{
LLButton * command_button = NULL;
@@ -391,7 +391,7 @@ bool LLToolBar::flashCommand(const LLCommandId& commandId, bool flash)
if (it != mButtonMap.end())
{
command_button = it->second;
- command_button->setFlashing(flash ? TRUE : FALSE);
+ command_button->setFlashing((BOOL)(flash),(BOOL)(force_flashing));
}
}
diff --git a/indra/llui/lltoolbar.h b/indra/llui/lltoolbar.h
index 31424a36d4..743951a41f 100755
--- a/indra/llui/lltoolbar.h
+++ b/indra/llui/lltoolbar.h
@@ -192,7 +192,7 @@ public:
bool hasCommand(const LLCommandId& commandId) const; // is this command bound to a button in this toolbar
bool enableCommand(const LLCommandId& commandId, bool enabled); // enable/disable button bound to the specified command, if it exists in this toolbar
bool stopCommandInProgress(const LLCommandId& commandId); // stop command if it is currently active
- bool flashCommand(const LLCommandId& commandId, bool flash); // flash button associated with given command, if in this toolbar
+ bool flashCommand(const LLCommandId& commandId, bool flash, bool force_flashing = false); // flash button associated with given command, if in this toolbar
void setStartDragCallback(tool_startdrag_callback_t cb) { mStartDragItemCallback = cb; } // connects drag and drop behavior to external logic
void setHandleDragCallback(tool_handledrag_callback_t cb) { mHandleDragItemCallback = cb; }
diff --git a/indra/llui/llurlaction.cpp b/indra/llui/llurlaction.cpp
index f51aeaec13..23e574cb74 100755
--- a/indra/llui/llurlaction.cpp
+++ b/indra/llui/llurlaction.cpp
@@ -170,6 +170,30 @@ std::string LLUrlAction::getUserID(std::string url)
return id_str;
}
+std::string LLUrlAction::getObjectId(std::string url)
+{
+ LLURI uri(url);
+ LLSD path_array = uri.pathArray();
+ std::string id_str;
+ if (path_array.size() >= 3)
+ {
+ id_str = path_array.get(2).asString();
+ }
+ return id_str;
+}
+
+std::string LLUrlAction::getObjectName(std::string url)
+{
+ LLURI uri(url);
+ LLSD query_map = uri.queryMap();
+ std::string name;
+ if (query_map.has("name"))
+ {
+ name = query_map["name"].asString();
+ }
+ return name;
+}
+
void LLUrlAction::sendIM(std::string url)
{
std::string id_str = getUserID(url);
@@ -188,3 +212,21 @@ void LLUrlAction::addFriend(std::string url)
}
}
+void LLUrlAction::removeFriend(std::string url)
+{
+ std::string id_str = getUserID(url);
+ if (LLUUID::validate(id_str))
+ {
+ executeSLURL("secondlife:///app/agent/" + id_str + "/removefriend");
+ }
+}
+
+void LLUrlAction::blockObject(std::string url)
+{
+ std::string object_id = getObjectId(url);
+ std::string object_name = getObjectName(url);
+ if (LLUUID::validate(object_id))
+ {
+ executeSLURL("secondlife:///app/agent/" + object_id + "/block/" + object_name);
+ }
+}
diff --git a/indra/llui/llurlaction.h b/indra/llui/llurlaction.h
index e31cd71a20..e731376b95 100755
--- a/indra/llui/llurlaction.h
+++ b/indra/llui/llurlaction.h
@@ -77,8 +77,12 @@ public:
/// if the Url specifies an SL command in the form like 'app/{cmd}/{id}/*', show its profile
static void showProfile(std::string url);
static std::string getUserID(std::string url);
+ static std::string getObjectName(std::string url);
+ static std::string getObjectId(std::string url);
static void sendIM(std::string url);
static void addFriend(std::string url);
+ static void removeFriend(std::string url);
+ static void blockObject(std::string url);
/// specify the callbacks to enable this class's functionality
typedef boost::function<void (const std::string&)> url_callback_t;
diff --git a/indra/llui/llurlentry.cpp b/indra/llui/llurlentry.cpp
index 99ee688888..b1cc502c4b 100755
--- a/indra/llui/llurlentry.cpp
+++ b/indra/llui/llurlentry.cpp
@@ -504,6 +504,10 @@ std::string localize_slapp_label(const std::string& url, const std::string& full
{
return LLTrans::getString("SLappAgentRequestFriend") + " " + full_name;
}
+ if (LLStringUtil::endsWith(url, "/removefriend"))
+ {
+ return LLTrans::getString("SLappAgentRemoveFriend") + " " + full_name;
+ }
return full_name;
}
diff --git a/indra/llwindow/llwindowwin32.cpp b/indra/llwindow/llwindowwin32.cpp
index 43c0090993..30f5526500 100755
--- a/indra/llwindow/llwindowwin32.cpp
+++ b/indra/llwindow/llwindowwin32.cpp
@@ -159,9 +159,8 @@ LLWinImm LLWinImm::sTheInstance;
LLWinImm::LLWinImm() : mHImmDll(NULL)
{
// Check system metrics
- if ( !GetSystemMetrics( SM_DBCSENABLED ) )
+ if ( !GetSystemMetrics( SM_IMMENABLED ) )
return;
-
mHImmDll = LoadLibraryA("Imm32");
if (mHImmDll != NULL)
@@ -3500,19 +3499,11 @@ void LLWindowWin32::updateLanguageTextInputArea()
void LLWindowWin32::interruptLanguageTextInput()
{
- if (mPreeditor)
+ if (mPreeditor && LLWinImm::isAvailable())
{
- if (LLWinImm::isAvailable())
- {
- HIMC himc = LLWinImm::getContext(mWindowHandle);
- LLWinImm::notifyIME(himc, NI_COMPOSITIONSTR, CPS_COMPLETE, 0);
- LLWinImm::releaseContext(mWindowHandle, himc);
- }
-
- // Win32 document says there will be no composition string
- // after NI_COMPOSITIONSTR returns. The following call to
- // resetPreedit should be a NOP unless IME goes mad...
- mPreeditor->resetPreedit();
+ HIMC himc = LLWinImm::getContext(mWindowHandle);
+ LLWinImm::notifyIME(himc, NI_COMPOSITIONSTR, CPS_COMPLETE, 0);
+ LLWinImm::releaseContext(mWindowHandle, himc);
}
}
diff --git a/indra/lscript/lscript_compile/indra.l b/indra/lscript/lscript_compile/indra.l
index 1bb38bbf65..1c9f50202d 100755
--- a/indra/lscript/lscript_compile/indra.l
+++ b/indra/lscript/lscript_compile/indra.l
@@ -336,6 +336,8 @@ int yyerror(const char *fmt, ...);
"ATTACH_HUD_BOTTOM_LEFT" { count(); yylval.ival = 36; return(INTEGER_CONSTANT); }
"ATTACH_HUD_BOTTOM" { count(); yylval.ival = 37; return(INTEGER_CONSTANT); }
"ATTACH_HUD_BOTTOM_RIGHT" { count(); yylval.ival = 38; return(INTEGER_CONSTANT); }
+"ATTACH_NECK" { count(); yylval.ival = 39; return(INTEGER_CONSTANT); }
+"ATTACH_AVATAR_CENTER" { count(); yylval.ival = 40; return(INTEGER_CONSTANT); }
"LAND_LEVEL" { count(); yylval.ival = E_LANDBRUSH_LEVEL; return(INTEGER_CONSTANT); }
"LAND_RAISE" { count(); yylval.ival = E_LANDBRUSH_RAISE; return(INTEGER_CONSTANT); }
diff --git a/indra/newview/VIEWER_VERSION.txt b/indra/newview/VIEWER_VERSION.txt
index 4a788a01da..0f44168a4d 100644
--- a/indra/newview/VIEWER_VERSION.txt
+++ b/indra/newview/VIEWER_VERSION.txt
@@ -1 +1 @@
-3.6.3
+3.6.4
diff --git a/indra/newview/app_settings/keywords.ini b/indra/newview/app_settings/keywords.ini
index f0d8b77afd..a87310955f 100755
--- a/indra/newview/app_settings/keywords.ini
+++ b/indra/newview/app_settings/keywords.ini
@@ -274,7 +274,8 @@ ATTACH_LLLEG Passed to llAttachToAvatar to attach task to left lower leg
ATTACH_BELLY Passed to llAttachToAvatar to attach task to belly
ATTACH_LEFT_PEC Passed to llAttachToAvatar to attach task to left pectoral
ATTACH_RIGHT_PEC Passed to llAttachToAvatar to attach task to right pectoral
-
+ATTACH_NECK Passed to llAttachToAvatar to attach task to neck
+ATTACH_AVATAR_CENTER Passed to llAttachToAvatar to attach task to avatar center
LAND_LEVEL Passed to llModifyLand to level terrain
LAND_RAISE Passed to llModifyLand to raise terrain
LAND_LOWER Passed to llModifyLand to lower terrain
diff --git a/indra/newview/app_settings/settings.xml b/indra/newview/app_settings/settings.xml
index 9239059c10..72fe21cf14 100755
--- a/indra/newview/app_settings/settings.xml
+++ b/indra/newview/app_settings/settings.xml
@@ -3566,16 +3566,27 @@
<key>Value</key>
<real>10.0</real>
</map>
- <key>FilterItemsPerFrame</key>
+ <key>FilterItemsMaxTimePerFrameVisible</key>
<map>
- <key>Comment</key>
- <string>Maximum number of inventory items to match against search filter every frame (lower to increase framerate while searching, higher to improve search speed)</string>
- <key>Persist</key>
- <integer>1</integer>
- <key>Type</key>
- <string>S32</string>
- <key>Value</key>
- <integer>500</integer>
+ <key>Comment</key>
+ <string>Max time devoted to items filtering per frame for visible inventory listings (in milliseconds)</string>
+ <key>Persist</key>
+ <integer>1</integer>
+ <key>Type</key>
+ <string>S32</string>
+ <key>Value</key>
+ <integer>10</integer>
+ </map>
+ <key>FilterItemsMaxTimePerFrameUnvisible</key>
+ <map>
+ <key>Comment</key>
+ <string>Max time devoted to items filtering per frame for non visible inventory listings (in milliseconds)</string>
+ <key>Persist</key>
+ <integer>1</integer>
+ <key>Type</key>
+ <string>S32</string>
+ <key>Value</key>
+ <integer>1</integer>
</map>
<key>FindLandArea</key>
<map>
@@ -6540,7 +6551,10 @@
<key>NotificationConferenceIMOptions</key>
<map>
<key>Comment</key>
- <string>Specifies how the UI responds to Conference IM Notifications.</string>
+ <string>
+ Specifies how the UI responds to Conference IM Notifications.
+ Allowed values: [openconversations,toast,flash,noaction]
+ </string>
<key>Persist</key>
<integer>1</integer>
<key>Type</key>
@@ -6551,7 +6565,10 @@
<key>NotificationFriendIMOptions</key>
<map>
<key>Comment</key>
- <string>Specifies how the UI responds to Friend IM Notifications.</string>
+ <string>
+ Specifies how the UI responds to Friend IM Notifications.
+ Allowed values: [openconversations,toast,flash,noaction]
+ </string>
<key>Persist</key>
<integer>1</integer>
<key>Type</key>
@@ -6562,7 +6579,10 @@
<key>NotificationGroupChatOptions</key>
<map>
<key>Comment</key>
- <string>Specifies how the UI responds to Group Chat Notifications.</string>
+ <string>
+ Specifies how the UI responds to Group Chat Notifications.
+ Allowed values: [openconversations,toast,flash,noaction]
+ </string>
<key>Persist</key>
<integer>1</integer>
<key>Type</key>
@@ -6573,7 +6593,10 @@
<key>NotificationNearbyChatOptions</key>
<map>
<key>Comment</key>
- <string>Specifies how the UI responds to Nearby Chat Notifications.</string>
+ <string>
+ Specifies how the UI responds to Nearby Chat Notifications.
+ Allowed values: [openconversations,toast,flash,noaction]
+ </string>
<key>Persist</key>
<integer>1</integer>
<key>Type</key>
@@ -6584,7 +6607,24 @@
<key>NotificationNonFriendIMOptions</key>
<map>
<key>Comment</key>
- <string>Specifies how the UI responds to Non Friend IM Notifications.</string>
+ <string>
+ Specifies how the UI responds to Non Friend IM Notifications.
+ Allowed values: [openconversations,toast,flash,noaction]
+ </string>
+ <key>Persist</key>
+ <integer>1</integer>
+ <key>Type</key>
+ <string>String</string>
+ <key>Value</key>
+ <string>toast</string>
+ </map>
+ <key>NotificationObjectIMOptions</key>
+ <map>
+ <key>Comment</key>
+ <string>
+ Specifies how the UI responds to Object IM Notifications.
+ Allowed values: [openconversations,toast,flash,noaction]
+ </string>
<key>Persist</key>
<integer>1</integer>
<key>Type</key>
@@ -7141,6 +7181,72 @@
<key>Value</key>
<integer>0</integer>
</map>
+ <key>PlaySoundFriendIM</key>
+ <map>
+ <key>Comment</key>
+ <string>Plays a sound when friend's IM received.</string>
+ <key>Persist</key>
+ <integer>1</integer>
+ <key>Type</key>
+ <string>Boolean</string>
+ <key>Value</key>
+ <integer>0</integer>
+ </map>
+ <key>PlaySoundNonFriendIM</key>
+ <map>
+ <key>Comment</key>
+ <string>Plays a sound when non-friend's IM received.</string>
+ <key>Persist</key>
+ <integer>1</integer>
+ <key>Type</key>
+ <string>Boolean</string>
+ <key>Value</key>
+ <integer>0</integer>
+ </map>
+ <key>PlaySoundConferenceIM</key>
+ <map>
+ <key>Comment</key>
+ <string>Plays a sound when conference IM received.</string>
+ <key>Persist</key>
+ <integer>1</integer>
+ <key>Type</key>
+ <string>Boolean</string>
+ <key>Value</key>
+ <integer>0</integer>
+ </map>
+ <key>PlaySoundGroupChatIM</key>
+ <map>
+ <key>Comment</key>
+ <string>Plays a sound when group chat IM received.</string>
+ <key>Persist</key>
+ <integer>1</integer>
+ <key>Type</key>
+ <string>Boolean</string>
+ <key>Value</key>
+ <integer>0</integer>
+ </map>
+ <key>PlaySoundNearbyChatIM</key>
+ <map>
+ <key>Comment</key>
+ <string>Plays a sound when nearby chat IM received.</string>
+ <key>Persist</key>
+ <integer>1</integer>
+ <key>Type</key>
+ <string>Boolean</string>
+ <key>Value</key>
+ <integer>0</integer>
+ </map>
+ <key>PlaySoundObjectIM</key>
+ <map>
+ <key>Comment</key>
+ <string>Plays a sound when IM fom an object received.</string>
+ <key>Persist</key>
+ <integer>1</integer>
+ <key>Type</key>
+ <string>Boolean</string>
+ <key>Value</key>
+ <integer>0</integer>
+ </map>
<key>PlaySoundNewConversation</key>
<map>
<key>Comment</key>
@@ -8567,6 +8673,18 @@
<integer>0</integer>
</map>
+ <key>RenderDepthOfFieldInEditMode</key>
+ <map>
+ <key>Comment</key>
+ <string>Whether to use depth of field effect when in edit mode</string>
+ <key>Persist</key>
+ <integer>1</integer>
+ <key>Type</key>
+ <string>Boolean</string>
+ <key>Value</key>
+ <integer>0</integer>
+ </map>
+
<key>CameraDoFResScale</key>
<map>
<key>Comment</key>
diff --git a/indra/newview/app_settings/settings_per_account.xml b/indra/newview/app_settings/settings_per_account.xml
index 590f41283b..636caf5ef3 100755
--- a/indra/newview/app_settings/settings_per_account.xml
+++ b/indra/newview/app_settings/settings_per_account.xml
@@ -109,18 +109,7 @@
<string>Boolean</string>
<key>Value</key>
<integer>0</integer>
- </map>
- <key>DisplayDestinationsOnInitialRun</key>
- <map>
- <key>Comment</key>
- <string>Display the destinations guide when a user first launches Second Life.</string>
- <key>Persist</key>
- <integer>1</integer>
- <key>Type</key>
- <string>Boolean</string>
- <key>Value</key>
- <integer>1</integer>
- </map>
+ </map>
<key>LastInventoryInboxActivity</key>
<map>
<key>Comment</key>
diff --git a/indra/newview/app_settings/shaders/class1/avatar/objectSkinV.glsl b/indra/newview/app_settings/shaders/class1/avatar/objectSkinV.glsl
index 43ed41a205..efd0d03965 100755
--- a/indra/newview/app_settings/shaders/class1/avatar/objectSkinV.glsl
+++ b/indra/newview/app_settings/shaders/class1/avatar/objectSkinV.glsl
@@ -45,3 +45,4 @@ mat4 getObjectSkinnedTransform()
return mat;
}
+
diff --git a/indra/newview/gpu_table.txt b/indra/newview/gpu_table.txt
index c64e11929d..122577b132 100755
--- a/indra/newview/gpu_table.txt
+++ b/indra/newview/gpu_table.txt
@@ -38,7 +38,7 @@ ATI 3D-Analyze .*ATI.*3D-Analyze.* 0 0 0 0
ATI All-in-Wonder 7500 .*ATI.*All-in-Wonder 75.* 0 1 0 0
ATI All-in-Wonder 8500 .*ATI.*All-in-Wonder 85.* 0 1 0 0
ATI All-in-Wonder 9200 .*ATI.*All-in-Wonder 92.* 0 1 0 0
-ATI All-in-Wonder 9xxx .*ATI.*All-in-Wonder 9.* 1 1 0 0
+ATI All-in-Wonder 9xxx .*ATI.*All-in-Wonder 9.* 1 1 0 2.1
ATI All-in-Wonder HD .*ATI.*All-in-Wonder HD.* 1 1 1 3.3
ATI All-in-Wonder X600 .*ATI.*All-in-Wonder X6.* 1 1 0 0
ATI All-in-Wonder X800 .*ATI.*All-in-Wonder X8.* 1 1 1 2.1
@@ -46,162 +46,132 @@ ATI All-in-Wonder X1800 .*ATI.*All-in-Wonder X18.* 3 1 0 0
ATI All-in-Wonder X1900 .*ATI.*All-in-Wonder X19.* 3 1 0 0
ATI All-in-Wonder PCI-E .*ATI.*All-in-Wonder.*PCI-E.* 1 1 0 0
ATI All-in-Wonder Radeon .*ATI.*All-in-Wonder Radeon.* 0 1 0 0
-ATI ASUS ARES .*ATI.*ASUS.*ARES.* 3 1 0 0
-ATI ASUS A9xxx .*ATI.*ASUS.*A9.* 1 1 0 0
-ATI ASUS AH24xx .*ATI.*ASUS.*AH24.* 1 1 1 3.3
-ATI ASUS AH26xx .*ATI.*ASUS.*AH26.* 1 1 1 3.3
-ATI ASUS AH34xx .*ATI.*ASUS.*AH34.* 1 1 1 3.3
-ATI ASUS AH36xx .*ATI.*ASUS.*AH36.* 1 1 1 3.3
-ATI ASUS AH46xx .*ATI.*ASUS.*AH46.* 2 1 1 3.3
-ATI ASUS AX3xx .*ATI.*ASUS.*AX3.* 1 1 0 0
-ATI ASUS AX5xx .*ATI.*ASUS.*AX5.* 1 1 0 0
-ATI ASUS AX8xx .*ATI.*ASUS.*AX8.* 2 1 0 0
-ATI ASUS EAH24xx .*ATI.*ASUS.*EAH24.* 2 1 0 0
-ATI ASUS EAH26xx .*ATI.*ASUS.*EAH26.* 3 1 0 0
-ATI ASUS EAH29xx .*ATI.*ASUS.*EAH29.* 3 1 0 0
-ATI ASUS EAH34xx .*ATI.*ASUS.*EAH34.* 1 1 0 0
-ATI ASUS EAH36xx .*ATI.*ASUS.*EAH36.* 2 1 0 0
-ATI ASUS EAH38xx .*ATI.*ASUS.*EAH38.* 2 1 1 3.3
-ATI ASUS EAH43xx .*ATI.*ASUS.*EAH43.* 2 1 1 3.3
-ATI ASUS EAH45xx .*ATI.*ASUS.*EAH45.* 2 1 0 0
-ATI ASUS EAH48xx .*ATI.*ASUS.*EAH48.* 3 1 1 3.3
-ATI ASUS EAH57xx .*ATI.*ASUS.*EAH57.* 3 1 1 4.1
-ATI ASUS EAH58xx .*ATI.*ASUS.*EAH58.* 5 1 1 4.1
-ATI ASUS EAH62xx .*ATI.*ASUS.*EAH62.* 2 1 0 0
-ATI ASUS EAH63xx .*ATI.*ASUS.*EAH63.* 2 1 0 0
-ATI ASUS EAH64xx .*ATI.*ASUS.*EAH64.* 2 1 0 0
-ATI ASUS EAH65xx .*ATI.*ASUS.*EAH65.* 2 1 0 4.1
-ATI ASUS EAH66xx .*ATI.*ASUS.*EAH66.* 3 1 0 4.1
-ATI ASUS EAH67xx .*ATI.*ASUS.*EAH67.* 3 1 0 0
-ATI ASUS EAH68xx .*ATI.*ASUS.*EAH68.* 5 1 0 4
-ATI ASUS EAH69xx .*ATI.*ASUS.*EAH69.* 5 1 0 4.1
-ATI ASUS Radeon X1xxx .*ATI.*ASUS.*X1.* 2 1 1 2.1
-ATI Radeon X7xx .*ATI.*ASUS.*X7.* 1 1 0 0
-ATI Radeon X19xx .*ATI.*(Radeon|Diamond) X19.* ?.* 2 1 1 2.1
-ATI Radeon X18xx .*ATI.*(Radeon|Diamond) X18.* ?.* 3 1 1 2.1
+ATI Radeon X1300 .*ATI.*(ASUS|Radeon).*X13.* 2 1 1 2.1
+ATI Radeon X1500 .*ATI.*(ASUS|Radeon).*X15.* 2 1 1 2.1
+ATI Radeon X1600 .*ATI.*(ASUS|Radeon).*X16.* 2 1 1 2.1
+ATI Radeon X1700 .*ATI.*(ASUS|Radeon).*X17.* 2 1 1 2.1
+ATI Radeon X1800 .*ATI.*(Radeon|Diamond) X18.* ?.* 3 1 1 2.1
+ATI Radeon X1900 .*ATI.*(Radeon|Diamond|ASUS) X19.* ?.* 2 1 1 2.1
ATI Radeon X17xx .*ATI.*(Radeon|Diamond) X17.* ?.* 1 1 1 2.1
-ATI Radeon X16xx .*ATI.*(Radeon|Diamond) X16.* ?.* 1 1 1 2.1
-ATI Radeon X15xx .*ATI.*(Radeon|Diamond) X15.* ?.* 1 1 1 2.1
-ATI Radeon X13xx .*ATI.*(Radeon|Diamond) X13.* ?.* 1 1 1 2.1
-ATI Radeon X1xxx .*ATI.*(Radeon|Diamond) X1.. ?.* 0 1 1 2.1
-ATI Radeon X2xxx .*ATI.*(Radeon|Diamond) X2.. ?.* 1 1 1 2.1
+ATI Radeon X16xx .*ATI.*(Radeon|Diamond) X17.* ?.* 1 1 1 2.1
+ATI Radeon X28xx .*ATI.*(Radeon|Diamond) X28.. ?.* 1 1 1 2.1
ATI Display Adapter .*ATI.*display adapter.* 1 1 1 4.1
ATI FireGL 5200 .*ATI.*FireGL V52.* 1 1 1 2.1
ATI FireGL 5xxx .*ATI.*FireGL V5.* 2 1 1 3.3
ATI FireGL .*ATI.*Fire.*GL.* 4 1 1 4.2
-ATI FirePro M3900 .*ATI.*FirePro.*M39.* 2 1 0 0
+ATI FirePro M3900 .*ATI.*FirePro.*M39.* 2 1 0 4.1
ATI FirePro M5800 .*ATI.*FirePro.*M58.* 3 1 0 0
ATI FirePro M7740 .*ATI.*FirePro.*M77.* 3 1 0 0
ATI FirePro M7820 .*ATI.*FirePro.*M78.* 5 1 1 4.2
-ATI FireMV .*ATI.*FireMV.* 0 1 1 1.3
+ATI FireMV .*ATI.*FireMV.* 0 1 1 3.2
ATI Generic .*ATI.*Generic.* 0 0 0 0
ATI Hercules 9800 .*ATI.*Hercules.* 9800.* 1 1 0 0
-ATI IGP 340M .*ATI.*IGP.*340M.* 0 0 0 0
+ATI IGP 340M .*ATI.*IGP.* 34[0-9]M.* 0 0 0 1.3
ATI M52 .*ATI.*M52.* 1 1 0 0
ATI M54 .*ATI.*M54.* 1 1 0 0
ATI M56 .*ATI.*M56.* 1 1 0 0
ATI M71 .*ATI.*M71.* 1 1 0 0
ATI M72 .*ATI.*M72.* 1 1 0 0
ATI M76 .*ATI.*M76.* 3 1 0 0
-ATI Radeon HD 64xx .*ATI.*AMD Radeon.* HD [67]4..[MG] 2 1 1 4.2
-ATI Radeon HD 65xx .*ATI.*AMD Radeon.* HD [67]5..[MG] 2 1 1 4.2
-ATI Radeon HD 66xx .*ATI.*AMD Radeon.* HD [67]6..[MG] 3 1 1 4.2
-ATI Radeon HD 7100 .*ATI.*AMD Radeon.* HD 71.* 2 1 0 0
-ATI Radeon HD 7200 .*ATI.*AMD Radeon.* HD 72.* 2 1 0 0
-ATI Radeon HD 7300 .*ATI.*AMD Radeon.* HD 73.* 2 1 0 4.2
-ATI Radeon HD 7400 .*ATI.*AMD Radeon.* HD 74.* 2 1 0 4.2
-ATI Radeon HD 7500 .*ATI.*AMD Radeon.* HD 75.* 3 1 1 4.2
-ATI Radeon HD 7600 .*ATI.*AMD Radeon.* HD 76.* 3 1 0 4.2
-ATI Radeon HD 7700 .*ATI.*AMD Radeon.* HD 77.* 4 1 1 4.2
-ATI Radeon HD 7800 .*ATI.*AMD Radeon.* HD 78.* 5 1 1 4.2
-ATI Radeon HD 7900 .*ATI.*AMD Radeon.* HD 79.* 5 1 1 4.2
-ATI ASUS HD7100 .*ATI.*ASUS.* HD71.* 2 1 0 0
-ATI ASUS HD7200 .*ATI.*ASUS.* HD72.* 2 1 0 0
-ATI ASUS HD7300 .*ATI.*ASUS.* HD73.* 2 1 0 0
-ATI ASUS HD7400 .*ATI.*ASUS.* HD74.* 2 1 0 0
-ATI ASUS HD7500 .*ATI.*ASUS.* HD75.* 3 1 1 4.2
-ATI ASUS HD7600 .*ATI.*ASUS.* HD76.* 3 1 0 0
-ATI ASUS HD7700 .*ATI.*ASUS.* HD77.* 4 1 1 4.2
-ATI ASUS HD7800 .*ATI.*ASUS.* HD78.* 5 1 1 4.2
-ATI ASUS HD7900 .*ATI.*ASUS.* HD79.* 5 1 1 4.2
+ATI Radeon HD 6300M .*ATI.*AMD Radeon.* (HD|HD )63..M 2 1 1 4.2
+ATI Radeon HD 6400M .*ATI.*AMD Radeon.* (HD|HD )64..M 2 1 1 4.2
+ATI Radeon HD 6500M .*ATI.*AMD Radeon.* (HD|HD )65..M 2 1 1 4.2
+ATI Radeon HD 6600M .*ATI.*AMD Radeon.* (HD 6|6)6..M 3 1 1 4.2
+ATI Radeon HD 6700M .*ATI.*AMD Radeon.* (HD|HD )67..M 3 1 1 4.2
+ATI Radeon HD 6800M .*ATI.*AMD Radeon.* (HD|HD )68..M 3 1 1 4.2
+ATI Radeon HD 6300G .*ATI.*AMD Radeon.* (HD|HD )63..G 2 1 1 4.2
+ATI Radeon HD 6400G .*ATI.*AMD Radeon.* (HD|HD )64..G 2 1 1 4.2
+ATI Radeon HD 6500G .*ATI.*AMD Radeon.* (HD|HD )65..G 2 1 1 4.2
+ATI Radeon HD 6600G .*ATI.*AMD Radeon.* (HD|HD )66..G 3 1 1 4.2
+ATI Radeon HD 7100 .*ATI.*(Radeon|ASUS).* (HD|HD )71.* 2 1 0 0
+ATI Radeon HD 7200 .*ATI.*(Radeon|ASUS).* (HD|HD )72.* 2 1 0 4.2
+ATI Radeon HD 7300 .*ATI.*(Radeon|ASUS).* (HD|HD )73.* 2 1 0 4.2
+ATI Radeon HD 7400 .*ATI.*(Radeon|ASUS).* (HD|HD )74.* 2 1 0 4.2
+ATI Radeon HD 7500 .*ATI.*(Radeon|ASUS).* (HD|HD )75.* 3 1 1 4.2
+ATI Radeon HD 7600 .*ATI.*(Radeon|ASUS).* (HD|HD )76.* 3 1 0 4.2
+ATI Radeon HD 7700 .*ATI.*(Radeon|ASUS).* (HD|HD )77.* 4 1 1 4.2
+ATI Radeon HD 7800 .*ATI.*(Radeon|ASUS).* (HD|HD )78.* 5 1 1 4.2
+ATI Radeon HD 7900 .*ATI.*(Radeon|ASUS).* (HD|HD )79.* 5 1 1 4.2
+ATI Radeon HD 7000 Series .*ATI.*(Radeon|ASUS).* (HD|HD )7000 Series.* 3 1 1 4.2
ATI Mobility Radeon 4100 .*ATI.*Mobility.* 41.. 1 1 1 3.3
+ATI Mobility Radeon 5000 .*ATI.*Mobility.* 50.. 1 1 1 4.2
ATI Mobility Radeon 7xxx .*ATI.*Mobility.*Radeon 7.* 0 1 1 1.3
ATI Mobility Radeon 8xxx .*ATI.*Mobility.*Radeon 8.* 0 1 0 0
ATI Mobility Radeon 9800 .*ATI.*Mobility.* 98.* 1 1 0 0
ATI Mobility Radeon 9700 .*ATI.*Mobility.* 97.* 0 1 1 2.1
ATI Mobility Radeon 9600 .*ATI.*Mobility.* 96.* 1 1 1 2.1
-ATI Mobility Radeon HD 530v .*ATI.*Mobility.*HD *530v.* 1 1 1 3.3
-ATI Mobility Radeon HD 540v .*ATI.*Mobility.*HD *540v.* 1 1 1 3.3
-ATI Mobility Radeon HD 545v .*ATI.*Mobility.*HD *545v.* 2 1 1 4
-ATI Mobility Radeon HD 550v .*ATI.*Mobility.*HD *550v.* 3 1 1 4
-ATI Mobility Radeon HD 560v .*ATI.*Mobility.*HD *560v.* 3 1 1 3.2
-ATI Mobility Radeon HD 565v .*ATI.*Mobility.*HD *565v.* 3 1 1 3.3
-ATI Mobility Radeon HD 2300 .*ATI.*Mobility.*HD *23.* 0 1 1 2.1
-ATI Mobility Radeon HD 2400 .*ATI.*Mobility.*HD *24.* 1 1 1 3.3
-ATI Mobility Radeon HD 2600 .*ATI.*Mobility.*HD *26.* 1 1 1 3.3
-ATI Mobility Radeon HD 2700 .*ATI.*Mobility.*HD *27.* 3 1 0 0
-ATI Mobility Radeon HD 3100 .*ATI.*Mobility.*HD *31.* 0 1 0 0
-ATI Mobility Radeon HD 3200 .*ATI.*Mobility.*HD *32.* 0 1 0 0
-ATI Mobility Radeon HD 3400 .*ATI.*Mobility.*HD *34.* 1 1 1 3.3
-ATI Mobility Radeon HD 3600 .*ATI.*Mobility.*HD *36.* 1 1 1 4
-ATI Mobility Radeon HD 3800 .*ATI.*Mobility.*HD *38.* 3 1 1 3.3
-ATI Mobility Radeon HD 4200 .*ATI.*Mobility.*HD *42.* 1 1 1 4
-ATI Mobility Radeon HD 4300 .*ATI.*Mobility.*HD *43.* 1 1 1 4
-ATI Mobility Radeon HD 4500 .*ATI.*Mobility.*HD *45.* 1 1 1 4
-ATI Mobility Radeon HD 4600 .*ATI.*Mobility.*HD *46.* 2 1 1 3.3
-ATI Mobility Radeon HD 4800 .*ATI.*Mobility.*HD *48.* 3 1 1 3.3
-ATI Mobility Radeon HD 5100 .*ATI.*Mobility.*HD *51.* 3 1 1 3.2
-ATI Mobility Radeon HD 5300 .*ATI.*Mobility.*HD *53.* 3 1 0 0
-ATI Mobility Radeon HD 5400 .*ATI.*Mobility.*HD *54.* 2 1 1 4.2
-ATI Mobility Radeon HD 5500 .*ATI.*Mobility.*HD *55.* 3 1 0 0
-ATI Mobility Radeon HD 5600 .*ATI.*Mobility.*HD *56.* 3 1 1 4.2
-ATI Mobility Radeon HD 5700 .*ATI.*Mobility.*HD *57.* 3 1 1 4.1
-ATI Mobility Radeon HD 6200 .*ATI.*Mobility.*HD *62.* 3 1 0 0
-ATI Mobility Radeon HD 6300 .*ATI.*Mobility.*HD *63.* 3 1 1 4.2
-ATI Mobility Radeon HD 6400M .*ATI.*Mobility.*HD *64.* 3 1 0 0
-ATI Mobility Radeon HD 6500M .*ATI.*Mobility.*HD *65.* 5 1 1 4.2
-ATI Mobility Radeon HD 6600M .*ATI.*Mobility.*HD *66.* 5 1 0 0
-ATI Mobility Radeon HD 6700M .*ATI.*Mobility.*HD *67.* 5 1 0 0
-ATI Mobility Radeon HD 6800M .*ATI.*Mobility.*HD *68.* 5 1 0 0
-ATI Mobility Radeon HD 6900M .*ATI.*Mobility.*HD *69.* 5 1 0 0
-ATI Radeon HD 2300 .*ATI.*Radeon HD *23.. 0 1 1 3.3
-ATI Radeon HD 2400 .*ATI.*Radeon HD *24.. 1 1 1 4
-ATI Radeon HD 2600 .*ATI.*Radeon HD *26.. 2 1 1 3.3
-ATI Radeon HD 2900 .*ATI.*Radeon HD *29.. 3 1 1 3.3
-ATI Radeon HD 3000 .*ATI.*Radeon HD *30.. 0 1 0 0
-ATI Radeon HD 3100 .*ATI.*Radeon HD *31.. 1 1 0 0
-ATI Radeon HD 3200 .*ATI.*Radeon HD *32.. 1 1 1 4
-ATI Radeon HD 3300 .*ATI.*Radeon HD *33.. 1 1 1 3.3
-ATI Radeon HD 3400 .*ATI.*Radeon HD *34.. 1 1 1 4
-ATI Radeon HD 3500 .*ATI.*Radeon HD *35.. 2 1 0 0
-ATI Radeon HD 3600 .*ATI.*Radeon HD *36.. 3 1 1 3.3
-ATI Radeon HD 3700 .*ATI.*Radeon HD *37.. 3 1 0 0
+ATI Mobility Radeon HD 530v .*ATI.*Mobility.*HD 530v.* 1 1 1 3.3
+ATI Mobility Radeon HD 540v .*ATI.*Mobility.*HD 540v.* 1 1 1 3.3
+ATI Mobility Radeon HD 545v .*ATI.*Mobility.*HD 545v.* 2 1 1 4
+ATI Mobility Radeon HD 550v .*ATI.*Mobility.*HD 550v.* 3 1 1 4
+ATI Mobility Radeon HD 560v .*ATI.*Mobility.*HD 560v.* 3 1 1 3.2
+ATI Mobility Radeon HD 565v .*ATI.*Mobility.*HD 565v.* 3 1 1 3.3
+ATI Mobility Radeon HD 2300 .*ATI.*Mobility.*HD 23.* 0 1 1 2.1
+ATI Mobility Radeon HD 2400 .*ATI.*Mobility.*HD 24.* 1 1 1 3.3
+ATI Mobility Radeon HD 2600 .*ATI.*Mobility.*HD 26.* 1 1 1 3.3
+ATI Mobility Radeon HD 2700 .*ATI.*Mobility.*HD 27.* 3 1 0 0
+ATI Mobility Radeon HD 3100 .*ATI.*Mobility.*HD 31.* 0 1 0 0
+ATI Mobility Radeon HD 3200 .*ATI.*Mobility.*HD 32.* 0 1 0 0
+ATI Mobility Radeon HD 3400 .*ATI.*Mobility.*HD 34.* 1 1 1 4
+ATI Mobility Radeon HD 3600 .*ATI.*Mobility.*HD 36.* 1 1 1 4
+ATI Mobility Radeon HD 3800 .*ATI.*Mobility.*HD 38.* 3 1 1 3.3
+ATI Mobility Radeon HD 4200 .*ATI.*Mobility.*HD 42.* 1 1 1 4
+ATI Mobility Radeon HD 4300 .*ATI.*Mobility.*(HD |HD)43.* 1 1 1 4
+ATI Mobility Radeon HD 4500 .*ATI.*Mobility.*HD 45.* 1 1 1 4
+ATI Mobility Radeon HD 4600 .*ATI.*Mobility.*HD 46.* 2 1 1 3.3
+ATI Mobility Radeon HD 4800 .*ATI.*Mobility.*HD 48.* 3 1 1 3.3
+ATI Mobility Radeon HD 5000 Series .*ATI.*Mobility.*HD 50.* 3 1 1 3.2
+ATI Mobility Radeon HD 5100 .*ATI.*Mobility.*HD 51.* 3 1 1 3.2
+ATI Mobility Radeon HD 5300 .*ATI.*Mobility.*HD 53.* 3 1 0 0
+ATI Mobility Radeon HD 5400 .*ATI.*Mobility.*HD 54.* 2 1 1 4.2
+ATI Mobility Radeon HD 5500 .*ATI.*Mobility.*HD 55.* 3 1 0 4.2
+ATI Mobility Radeon HD 5600 .*ATI.*Mobility.*HD 56.* 3 1 1 4.2
+ATI Mobility Radeon HD 5700 .*ATI.*Mobility.*HD 57.* 3 1 1 4.1
+ATI Mobility Radeon HD 6200 .*ATI.*Mobility.*HD 62.* 3 1 0 0
+ATI Mobility Radeon HD 6300 .*ATI.*Mobility.*HD 63.* 3 1 1 4.2
+ATI Mobility Radeon HD 6400M .*ATI.*Mobility.*HD 64.* 3 1 0 0
+ATI Mobility Radeon HD 6500M .*ATI.*Mobility.*HD 65.* 5 1 1 4.2
+ATI Mobility Radeon HD 6600M .*ATI.*Mobility.*HD 66.* 5 1 0 0
+ATI Mobility Radeon HD 6700M .*ATI.*Mobility.*HD 67.* 5 1 0 0
+ATI Mobility Radeon HD 6800M .*ATI.*Mobility.*HD 68.* 5 1 0 0
+ATI Mobility Radeon HD 6900M .*ATI.*Mobility.*HD 69.* 5 1 0 0
+ATI Mobility Radeon Graphics .*ATI Mobility Radeon Graphics.* 1 1 0 4
+ATI Radeon HD 2300 .*ATI.*Radeon.* (HD|HD )23.. 0 1 1 3.3
+ATI Radeon HD 2400 .*ATI.*(Radeon|ASUS).* (HD|HD |EAH)24.. 1 1 1 4
+ATI Radeon HD 2600 .*ATI.*(Radeon|ASUS).* (HD|HD |EAH)26.. 2 1 1 4
+ATI Radeon HD 2900 .*ATI.*Radeon.* (HD|HD )29.. 3 1 1 3.3
+ATI Radeon HD 3000 .*ATI.*Radeon.* (HD|HD )30.. 0 1 0 0
+ATI Radeon HD 3100 .*ATI.*Radeon.* (HD|HD )31.. 1 1 0 0
+ATI Radeon HD 3200 .*ATI.*Radeon.* (HD|HD )32.. 1 1 1 4
+ATI Radeon HD 3300 .*ATI.*Radeon.* (HD|HD )33.. 1 1 1 3.3
+ATI Radeon HD 3400 .*ATI.*(Radeon|ASUS).* (HD|HD |AH|EAH)34.. 1 1 1 4
+ATI Radeon HD 3500 .*ATI.*Radeon.* (HD|HD )35.. 2 1 0 0
+ATI Radeon HD 3600 .*ATI.*(Radeon|ASUS).* (HD|HD |AH|EAH)36.. 3 1 1 4
+ATI Radeon HD 3700 .*ATI.*Radeon.* (HD|HD )37.. 3 1 0 3.3
ATI HD3700 .*ATI.* HD37.. 3 1 0 3.3
-ATI Radeon HD 3800 .*ATI.*Radeon HD *38.. 3 1 1 4
-ATI Radeon HD 4100 .*ATI.*Radeon HD *41.. 1 1 0 0
-ATI Radeon HD 4200 .*ATI.*Radeon HD *42.. 1 1 1 4
-ATI Radeon HD 4300 .*ATI.*Radeon HD *43.. 2 1 1 4
-ATI Radeon HD 4400 .*ATI.*Radeon HD *44.. 2 1 0 0
-ATI Radeon HD 4500 .*ATI.*Radeon HD *45.. 2 1 1 3.3
-ATI Radeon HD 4600 .*ATI.*Radeon HD *46.. 3 1 1 4
-ATI Radeon HD 4700 .*ATI.*Radeon HD *47.. 3 1 1 3.3
-ATI Radeon HD 4800 .*ATI.*Radeon HD *48.. 3 1 1 4
-ATI ASUS EAH5400 .*ATI.*ASUS EAH54.. 3 1 1 4.2
-ATI Radeon HD 5400 .*ATI.*Radeon HD *54.. 3 1 1 4.2
-ATI Radeon HD 5500 .*ATI.*Radeon HD *55.. 3 1 1 4.2
-ATI ASUS EAH5500 .*ATI.*ASUS EAH55.. 3 1 1 4.2
-ATI Radeon HD 5600 .*ATI.*Radeon HD *56.. 3 1 1 4.2
-ATI Radeon HD 5700 .*ATI.*Radeon HD *57.. 3 1 1 4.2
-ATI Radeon HD 5800 .*ATI.*Radeon HD *58.. 4 1 1 4.2
-ATI Radeon HD 5900 .*ATI.*Radeon HD *59.. 4 1 1 4.2
-ATI Radeon HD 6200 .*ATI.*Radeon HD *62.. 0 1 1 4.2
-ATI Radeon HD 6300 .*ATI.*Radeon HD *63.. 1 1 1 4.2
-ATI Radeon HD 6400 .*ATI.*Radeon HD *64.. 3 1 1 4.2
-ATI Radeon HD 6500 .*ATI.*Radeon HD *65.. 3 1 1 4.2
-ATI Radeon HD 6600 .*ATI.*Radeon HD *66.. 3 1 1 4.2
-ATI Radeon HD 6700 .*ATI.*Radeon HD *67.. 3 1 1 4.2
-ATI Radeon HD 6800 .*ATI.*Radeon HD *68.. 4 1 1 4.2
-ATI Radeon HD 6900 .*ATI.*Radeon HD *69.. 5 1 1 4.2
+ATI Radeon HD 3800 .*ATI.*(Radeon|ASUS).* (HD|HD |EAH)38.. 3 1 1 4
+ATI Radeon HD 4100 .*ATI.*Radeon.* (HD|HD )41.. 1 1 0 0
+ATI Radeon HD 4200 .*ATI.*Radeon.* (HD|HD )42.. 1 1 1 4
+ATI Radeon HD 4300 .*ATI.*(Radeon|ASUS).* (HD4|HD 4|EAH4|4)3.. 2 1 1 4
+ATI Radeon HD 4400 .*ATI.*Radeon.* (HD|HD )44.. 2 1 0 0
+ATI Radeon HD 4500 .*ATI.*(Radeon|ASUS).* (HD|HD |EAH)45.. 2 1 1 3.3
+ATI Radeon HD 4600 .*ATI.*(Radeon|ASUS).* (HD|HD |EAH)46.. 3 1 1 4
+ATI Radeon HD 4700 .*ATI.*(Radeon|ASUS).* (HD|HD |EAH)47.. 3 1 1 3.3
+ATI Radeon HD 4800 .*ATI.*(Radeon|ASUS).* (HD|HD |EAH)48.. 3 1 1 4
+ATI Radeon HD 5400 .*ATI.*(Radeon|ASUS).* (HD|HD |EAH)54.. 3 1 1 4.2
+ATI Radeon HD 5500 .*ATI.*(Radeon|ASUS).* (HD|HD |EAH)55.. 3 1 1 4.2
+ATI Radeon HD 5600 .*ATI.*(Radeon|ASUS).* (HD|HD |EAH)56.. 3 1 1 4.2
+ATI Radeon HD 5700 .*ATI.*(Radeon|ASUS).* (HD|HD |EAH)57.. 3 1 1 4.2
+ATI Radeon HD 5800 .*ATI.*(Radeon|ASUS).* (HD|HD |EAH)58.. 4 1 1 4.2
+ATI Radeon HD 5900 .*ATI.*Radeon.* (HD|HD )59.. 4 1 1 4.2
+ATI Radeon HD 6200 .*ATI.*Radeon.* (HD|HD )62.. 0 1 1 4.2
+ATI Radeon HD 6300 .*ATI.*Radeon.* (HD|HD )63.. 1 1 1 4.2
+ATI Radeon HD 6400 .*ATI.*(Radeon|ASUS).* (HD|HD |EAH)64.. 3 1 1 4.2
+ATI Radeon HD 6500 .*ATI.*(Radeon|ASUS).* (HD|HD |EAH)65.. 3 1 1 4.2
+ATI Radeon HD 6600 .*ATI.*(Radeon|ASUS).* (HD|HD |EAH)66.. 3 1 1 4.2
+ATI Radeon HD 6700 .*ATI.*(Radeon|ASUS).* (HD|HD |EAH)67.. 3 1 1 4.2
+ATI Radeon HD 6800 .*ATI.*(Radeon|ASUS).* (HD|HD |EAH)68.. 4 1 1 4.2
+ATI Radeon HD 6900 .*ATI.*(Radeon|ASUS).* (HD|HD |EAH)69.. 5 1 1 4.2
ATI Radeon OpenGL .*ATI.*Radeon OpenGL.* 0 0 0 0
ATI Radeon 2100 .*ATI.*Radeon 21.. 0 1 1 2.1
ATI Radeon 3000 .*ATI.*Radeon 30.. 1 1 1 4
@@ -219,17 +189,21 @@ ATI Radeon 9800 .*ATI.*Radeon 98.. 1 1 1 2.1
ATI Radeon RV250 .*ATI.*RV250.* 0 1 0 0
ATI Radeon RV600 .*ATI.*RV6.* 1 1 0 0
ATI Radeon RX700 .*ATI.*RX70.* 1 1 0 0
-ATI Radeon RX800 .*ATI.*Radeon *RX80.* 2 1 0 0
+ATI Radeon RX800 .*ATI.*Radeon RX80.* 2 1 0 0
ATI RS880M .*ATI.*RS880M 1 1 0 0
ATI Radeon RX9550 .*ATI.*RX9550.* 1 1 0 0
ATI Radeon VE .*ATI.*Radeon.*VE.* 0 0 0 0
-ATI Radeon X300 .*ATI.*Radeon *X3.* 1 1 1 2.1
+ATI Radeon X300 .*ATI.*Radeon X3.* 1 1 1 2.1
ATI Radeon X400 .*ATI.*Radeon ?X4.* 0 1 0 0
ATI Radeon X500 .*ATI.*Radeon ?X5.* 1 1 1 2.1
-ATI Radeon X600 .*ATI.*Radeon ?X6.* 1 1 1 2.1
+ATI Radeon X600 .*ATI.*(Radeon |ASUS Extreme A)X6.* 1 1 1 2.1
ATI Radeon X700 .*ATI.*Radeon ?X7.* 2 1 1 2.1
ATI Radeon X800 .*ATI.*Radeon ?X8.* 1 1 1 2.1
ATI Radeon X900 .*ATI.*Radeon ?X9.* 2 1 0 0
+ATI Radeon X1000 .*ATI.*Radeon ?X10.* 2 1 0 2.1
+ATI Radeon X1200 .*ATI.*Radeon ?X12.* 2 1 0 2.1
+ATI Radeon X1400 .*ATI.*Radeon ?X14.* 2 1 0 2.1
+ATI Radeon X2300 .*ATI.*Radeon ?X23.* 2 1 0 2.1
ATI Radeon Xpress .*ATI.*Radeon Xpress.* 0 1 1 2.1
ATI Rage 128 .*ATI.*Rage 128.* 0 1 0 0
ATI R300 (9700) .*R300.* 0 1 1 2.1
@@ -248,41 +222,43 @@ ATI RV530 .*RV530.* 1 1 0 0
ATI RX480 (Xpress 200P) .*RX480.* 0 1 0 0
ATI RX700 .*RX700.* 1 1 0 0
AMD ANTILLES (HD 6990) .*(AMD|ATI).*Antilles.* 3 1 0 0
+ATI ROBSON .*(AMD|ATI).*ROBSON.* 3 1 0 4
AMD BARTS (HD 6800) .*(AMD|ATI).*Barts.* 3 1 1 2.1
+AMD WRESTLER .*(AMD|ATI).*WRESTLER.* 3 1 1 4
+AMD SUMO .*(AMD|ATI).*SUMO.* 3 1 1 4.1
AMD CAICOS (HD 6400) .*(AMD|ATI).*Caicos.* 3 1 0 0
AMD CAYMAN (HD 6900) .*(AMD|ATI).*(Cayman|CAYMAM).* 3 1 0 0
-AMD CEDAR (HD 5450) .*(AMD|ATI).*Cedar.* 2 1 0 0
+AMD CEDAR (HD 5450) .*(AMD|ATI).*Cedar.* 2 1 0 2.1
AMD CYPRESS (HD 5800) .*(AMD|ATI).*Cypress.* 3 1 0 0
AMD HEMLOCK (HD 5970) .*(AMD|ATI).*Hemlock.* 3 1 0 0
AMD JUNIPER (HD 5700) .*(AMD|ATI).*Juniper.* 3 1 0 0
AMD PARK .*(AMD|ATI).*Park.* 3 1 0 0
-AMD REDWOOD (HD 5500/5600) .*(AMD|ATI).*Redwood.* 3 1 0 0
-AMD TURKS (HD 6500/6600) .*(AMD|ATI).*Turks.* 3 1 0 0
+AMD REDWOOD (HD 5500/5600) .*(AMD|ATI).*Redwood.* 3 1 0 1.4
+AMD TURKS (HD 6500/6600) .*(AMD|ATI).*Turks.* 3 1 0 2.1
AMD RS780 (HD 3200) .*RS780.* 0 1 1 2.1
AMD RS880 (HD 4200) .*RS880.* 0 1 1 3.2
AMD RV610 (HD 2400) .*RV610.* 1 1 0 0
AMD RV620 (HD 3400) .*RV620.* 1 1 0 0
AMD RV630 (HD 2600) .*RV630.* 2 1 0 0
-AMD RV635 (HD 3600) .*RV635.* 3 1 0 0
+AMD RV635 (HD 3600) .*RV635.* 3 1 0 1.4
AMD RV670 (HD 3800) .*RV670.* 3 1 0 0
AMD R680 (HD 3870 X2) .*R680.* 3 1 0 0
AMD R700 (HD 4800 X2) .*R700.* 3 1 0 0
AMD RV710 (HD 4300) .*RV710.* 0 1 1 1.4
-AMD RV730 (HD 4600) .*RV730.* 3 1 0 0
+AMD RV730 (HD 4600) .*RV730.* 3 1 0 1.4
AMD RV740 (HD 4700) .*RV740.* 3 1 0 0
AMD RV770 (HD 4800) .*RV770.* 3 1 0 0
AMD RV790 (HD 4800) .*RV790.* 3 1 0 0
ATI 760G/Radeon 3000 .*ATI.*AMD 760G.* 1 1 1 3.3
ATI 780L/Radeon 3000 .*ATI.*AMD 780L.* 1 1 0 0
ATI Radeon DDR .*ATI.*Radeon ?DDR.* 0 1 0 0
-ATI FirePro 2000 .*ATI.*FirePro 2.* 2 1 1 4.1
+ATI FirePro 2000 .*ATI.*FirePro 2.* 2 1 1 4.2
ATI FirePro 3000 .*ATI.*FirePro V3.* 2 1 0 0
-ATI FirePro 4000 .*ATI.*FirePro V4.* 2 1 0 0
+ATI FirePro 4000 .*ATI.*FirePro V4.* 2 1 0 4.1
ATI FirePro 5000 .*ATI.*FirePro V5.* 3 1 0 0
ATI FirePro 7000 .*ATI.*FirePro V7.* 3 1 0 0
ATI FirePro M .*ATI.*FirePro M.* 3 1 1 4.2
ATI R300 (9700) .*R300.* 0 1 1 2.1
-ATI Radeon .*ATI.*(Diamond|Radeon).* 0 1 0 4.2
Intel X3100 .*Intel.*X3100.* 1 1 1 2.1
Intel GMA 3600 .*Intel.* 3600.* 0 1 1 3
Intel 830M .*Intel.*830M 0 0 0 0
@@ -308,8 +284,6 @@ Intel Graphics Media HD .*Intel.*Graphics Media.*HD.* 1 1 1 2.1
Intel HD Graphics 2000 .*Intel.*HD Graphics 2.* 2 1 0 4
Intel HD Graphics 3000 .*Intel.*HD Graphics 3.* 3 1 1 3.1
Intel HD Graphics 4000 .*Intel.*HD Graphics 4.* 3 1 1 4
-Intel HD2000 .*Intel.*HD2000.* 2 1 0 0
-Intel HD3000 .*Intel.*HD3000.* 3 1 0 0
Intel HD Graphics .*Intel.*HD Graphics.* 2 1 1 4
Intel Mobile 4 Series .*Intel.*Mobile.* 4 Series.* 0 1 1 2.1
Intel 4 Series Internal .*Intel.* 4 Series Internal.* 1 1 1 2.1
@@ -322,113 +296,109 @@ Intel Q45/Q43 .*Intel.*Q4.* 1 1 1 2.1
Intel B45/B43 .*Intel.*B4.* 1 1 1 2.1
Intel 3D-Analyze .*Intel.*3D-Analyze.* 2 1 0 0
Matrox .*Matrox.* 0 0 0 0
-Mesa .*Mesa.* 1 0 1 2.1
+Mesa .*Mesa.* 1 0 1 3
Gallium .*Gallium.* 1 1 1 2.1
-NVIDIA G100M .*NVIDIA .*100M.* 4 1 1 3.3
-NVIDIA G102M .*NVIDIA .*102M.* 1 1 1 3.3
-NVIDIA G103M .*NVIDIA .*103M.* 2 1 1 3.3
-NVIDIA G105M .*NVIDIA .*105M.* 2 1 1 3.3
-NVIDIA G 110M .*NVIDIA .*110M.* 1 1 1 3.3
-NVIDIA G 120M .*NVIDIA .*120M.* 1 1 1 3.3
-NVIDIA G 205M .*NVIDIA .*205M.* 1 1 0 0
-NVIDIA G 410M .*NVIDIA .*410M.* 3 1 1 4.2
-NVIDIA GT 120M .*NVIDIA .*GT *12*M.* 3 1 1 3.3
-NVIDIA GT 130M .*NVIDIA .*GT *13*M.* 3 1 1 3.3
-NVIDIA GT 140M .*NVIDIA .*GT *14*M.* 3 1 1 3.3
-NVIDIA GT 150M .*NVIDIA .*GTS *15*M.* 2 1 0 0
-NVIDIA GTS 160M .*NVIDIA .*GTS *16*M.* 2 1 0 0
-NVIDIA G210M .*NVIDIA .*G21*M.* 3 1 0 0
-NVIDIA GT 220M .*NVIDIA .*GT *22*M.* 3 1 1 3.3
-NVIDIA GT 230M .*NVIDIA .*GT *23*M.* 3 1 1 3.3
-NVIDIA GT 240M .*NVIDIA .*GT *24*M.* 3 1 1 3.3
-NVIDIA GTS 250M .*NVIDIA .*GTS *25*M.* 3 1 0 0
-NVIDIA GTS 260M .*NVIDIA .*GTS *26*M.* 3 1 0 0
-NVIDIA GTX 260M .*NVIDIA .*GTX *26*M.* 3 1 0 0
-NVIDIA GTX 270M .*NVIDIA .*GTX *27*M.* 3 1 0 0
-NVIDIA GTX 280M .*NVIDIA .*GTX *28*M.* 3 1 0 0
-NVIDIA 300M .*NVIDIA .*30*M.* 3 1 1 4.2
-NVIDIA G 310M .*NVIDIA .*31*M.* 2 1 0 0
-NVIDIA GT 320M .*NVIDIA .*GT *32*M.* 3 1 0 0
-NVIDIA GT 325M .*NVIDIA .*GT *32*M.* 3 1 1 3.3
-NVIDIA GT 330M .*NVIDIA .*GT *33*M.* 3 1 1 3.3
-NVIDIA GT 340M .*NVIDIA .*GT *34*M.* 4 1 1 3.3
-NVIDIA GTS 350M .*NVIDIA .*GTS *35*M.* 4 1 1 3.3
-NVIDIA GTS 360M .*NVIDIA .*GTS *360M.* 5 1 1 3.3
-NVIDIA 405M .*NVIDIA .* 40*M.* 2 1 0 4.2
-NVIDIA 410M .*NVIDIA .* 41*M.* 3 1 0 0
-NVIDIA GT 415M .*NVIDIA .*GT *41*M.* 3 1 1 4.2
-NVIDIA GT 420M .*NVIDIA .*GT *42*M.* 3 1 1 4.2
-NVIDIA GT 430M .*NVIDIA .*GT *43*M.* 3 1 1 4.2
-NVIDIA GT 440M .*NVIDIA .*GT *44*M.* 3 1 1 4.2
-NVIDIA GT 450M .*NVIDIA .*GT *45*M.* 3 1 0 0
-NVIDIA GTX 460M .*NVIDIA .*GTX *46*M.* 4 1 1 4.2
-NVIDIA GTX 470M .*NVIDIA .*GTX *47*M.* 3 1 0 0
-NVIDIA GTX 480M .*NVIDIA .*GTX *48*M.* 3 1 1 4.2
-NVIDIA GT 520M .*NVIDIA .*GT *52*M.* 3 1 1 4.2
-NVIDIA GT 530M .*NVIDIA .*GT *53*M.* 3 1 1 4.2
-NVIDIA GT 540M .*NVIDIA .*GT *54*M.* 3 1 1 4.2
-NVIDIA GT 550M .*NVIDIA .*GT *55*M.* 3 1 1 4.2
-NVIDIA GTX 560M .*NVIDIA .*GTX *56*M.* 3 1 0 0
-NVIDIA GTX 570M .*NVIDIA .*GTX *57*M.* 5 1 0 0
-NVIDIA GTX 580M .*NVIDIA .*GTX *58*M.* 5 1 1 4.2
-NVIDIA 610M .*NVIDIA.* 61*M.* 3 1 1 4.2
-NVIDIA GT 620M .*NVIDIA .*GT *62*M.* 3 1 0 0
-NVIDIA GT 630M .*NVIDIA .*GT *63*M.* 3 1 0 0
-NVIDIA GT 640M .*NVIDIA .*GT *64*M.* 3 1 0 0
-NVIDIA GT 650M .*NVIDIA .*GT *65*M.* 3 1 0 0
-NVIDIA GTX 660M .*NVIDIA .*GTX *66*M.* 5 1 0 0
-NVIDIA GTX 670M .*NVIDIA .*GTX *67*M.* 5 1 1 4.2
-NVIDIA GTX 680M .*NVIDIA .*GTX *68*M.* 5 1 0 0
-NVIDIA GTX 690M .*NVIDIA .*GTX *69*M.* 5 1 0 0
+NVIDIA G100M .*NVIDIA .* 10[0-9]M.* 4 1 1 3.3
+NVIDIA G 110M .*NVIDIA .* 11[0-9]M.* 1 1 1 3.3
+NVIDIA G 120M .*NVIDIA .* 12[0-9]M.* 1 1 1 3.3
+NVIDIA G 200M .*NVIDIA .* 20[0-9]M.* 1 1 0 0
+NVIDIA G 410M .*NVIDIA .* 41[0-9]M.* 3 1 1 4.2
+NVIDIA GT 130M .*NVIDIA .*GT 13[0-9]M.* 3 1 1 3.3
+NVIDIA GT 140M .*NVIDIA .*GT 14[0-9]M.* 3 1 1 3.3
+NVIDIA GT 150M .*NVIDIA .*GTS 15[0-9]M.* 2 1 0 0
+NVIDIA GTS 160M .*NVIDIA .*GTS 16[0-9]M.* 2 1 0 0
+NVIDIA G210M .*NVIDIA .*G21[0-9]M.* 3 1 0 3.3
+NVIDIA GT 220M .*NVIDIA .*GT 22[0-9]M.* 3 1 1 3.3
+NVIDIA GT 230M .*NVIDIA .*GT 23[0-9]M.* 3 1 1 3.3
+NVIDIA GT 240M .*NVIDIA .*GT 24[0-9]M.* 3 1 1 3.3
+NVIDIA GTS 250M .*NVIDIA .*GTS 25[0-9]M.* 3 1 0 3.3
+NVIDIA GTS 260M .*NVIDIA .*GTS 26[0-9]M.* 3 1 0 0
+NVIDIA GTX 260M .*NVIDIA .*GTX 26[0-9]M.* 3 1 0 3.3
+NVIDIA GTX 270M .*NVIDIA .*GTX 27[0-9]M.* 3 1 0 0
+NVIDIA GTX 280M .*NVIDIA .*GTX 28[0-9]M.* 3 1 0 3.3
+NVIDIA 300M .*NVIDIA .*GT 30[0-9]M.* 3 1 1 4.2
+NVIDIA G 310M .*NVIDIA .* 31[0-9]M.* 2 1 0 3.3
+NVIDIA GT 320M .*NVIDIA .* 32[0-9]M.* 3 1 0 3.3
+NVIDIA GT 330M .*NVIDIA .*GT 33[0-9]M.* 3 1 1 3.3
+NVIDIA GT 340M .*NVIDIA .*GT 34[0-9]M.* 4 1 1 3.3
+NVIDIA GTS 350M .*NVIDIA .*GTS 35[0-9]M.* 4 1 1 3.3
+NVIDIA GTS 360M .*NVIDIA .*GTS 36[0-9]M.* 5 1 1 3.3
+NVIDIA 400M .*NVIDIA .* 40[0-9]M.* 2 1 0 0
+NVIDIA 410M .*NVIDIA .* 41[0-9]M.* 3 1 0 0
+NVIDIA GT 420M .*NVIDIA .*GT 42[0-9]M.* 3 1 1 4.2
+NVIDIA GT 430M .*NVIDIA .*GT 43[0-9]M.* 3 1 1 4.2
+NVIDIA GT 440M .*NVIDIA .*GT 44[0-9]M.* 3 1 1 4.2
+NVIDIA GT 450M .*NVIDIA .*GT 45[0-9]M.* 3 1 0 0
+NVIDIA GTX 460M .*NVIDIA .*GTX 46[0-9]M.* 4 1 1 4.3
+NVIDIA GTX 470M .*NVIDIA .*GTX 47[0-9]M.* 3 1 0 4.2
+NVIDIA GTX 480M .*NVIDIA .*GTX 48[0-9]M.* 3 1 1 4.2
+NVIDIA GT 520M .*NVIDIA .*GT 52[0-9]M.* 3 1 1 4.2
+NVIDIA GT 530M .*NVIDIA .*GT 53[0-9]M.* 3 1 1 4.2
+NVIDIA GT 540M .*NVIDIA .*GT 54[0-9]M.* 3 1 1 4.2
+NVIDIA GT 550M .*GeForce GT 55[0-9]M.* 3 1 1 4.2
+NVIDIA GTX 560M .*NVIDIA .*GTX 56[0-9]M.* 3 1 0 4.2
+NVIDIA GTX 570M .*NVIDIA .*GTX 57[0-9]M.* 5 1 0 4.2
+NVIDIA GTX 580M .*NVIDIA .*GTX 58[0-9]M.* 5 1 1 4.2
+NVIDIA 610M .*NVIDIA.* 61[0-9]M.* 3 1 1 4.2
+NVIDIA GT 620M .*NVIDIA .*GT 62[0-9]M.* 3 1 0 4.2
+NVIDIA GT 630M .*NVIDIA .*GT 63[0-9]M.* 3 1 0 4.2
+NVIDIA GT 640M .*NVIDIA .*GT 64[0-9]M.* 3 1 0 4.2
+NVIDIA GT 650M .*NVIDIA .*GT 65[0-9]M.* 3 1 0 4.2
+NVIDIA GTX 660M .*NVIDIA .*GTX 66[0-9]M.* 5 1 0 4.3
+NVIDIA GTX 670M .*NVIDIA .*GTX 67[0-9]M.* 5 1 1 4.2
+NVIDIA GTX 680M .*NVIDIA .*GTX 68[0-9]M.* 5 1 0 4.2
+NVIDIA GTX 690M .*NVIDIA .*GTX 69[0-9]M.* 5 1 0 0
NVIDIA G100 .*NVIDIA .*G10.* 3 1 1 4.2
-NVIDIA GT 120 .*NVIDIA .*GT *12.* 2 1 0 3
-NVIDIA GT 130 .*NVIDIA .*GT *13.* 2 1 0 3.3
-NVIDIA GTS 150 .*NVIDIA .*GTS *15.* 2 1 0 0
+NVIDIA GT 120 .*NVIDIA .*GT 12.* 2 1 0 3.3
+NVIDIA GT 130 .*NVIDIA .*GT 13.* 2 1 0 3.3
+NVIDIA GT 140 .*NVIDIA .*GT 14.* 2 1 0 3.3
+NVIDIA GTS 150 .*NVIDIA .*GTS 15.* 2 1 0 0
NVIDIA 200 .*NVIDIA .*GeForce 20.* 2 1 1 3.3
NVIDIA G200 .*NVIDIA .*GeForce G20.* 2 1 1 3.3
NVIDIA G210 .*NVIDIA .*GeForce G210.* 3 1 1 3.3
NVIDIA 210 .*NVIDIA .*GeForce 210.* 3 1 1 3.3
-NVIDIA GT 220 .*NVIDIA .*GT *22.* 2 1 1 3.3
-NVIDIA GT 230 .*NVIDIA .*GT *23.* 2 1 1 3.3
-NVIDIA GT 240 .*NVIDIA .*GT *24.* 4 1 1 3.3
-NVIDIA GTS 240 .*NVIDIA .*GTS *24.* 4 1 1 3.3
-NVIDIA GTS 250 .*NVIDIA .*GTS *25.* 4 1 1 3.3
-NVIDIA GTX 260 .*NVIDIA .*GTX *26.* 4 1 1 3.3
-NVIDIA GTX 270 .*NVIDIA .*GTX *27.* 4 1 0 3.3
-NVIDIA GTX 280 .*NVIDIA .*GTX *28.* 4 1 1 3.3
-NVIDIA GTX 290 .*NVIDIA .*GTX *29.* 5 1 0 3.3
+NVIDIA GT 220 .*NVIDIA .*GT 22.* 2 1 1 3.3
+NVIDIA GT 230 .*NVIDIA .*GT 23.* 2 1 1 3.3
+NVIDIA GT 240 .*NVIDIA .*GT 24.* 4 1 1 3.3
+NVIDIA GTS 240 .*NVIDIA .*GTS 24.* 4 1 1 3.3
+NVIDIA GTS 250 .*NVIDIA .*GTS 25.* 4 1 1 3.3
+NVIDIA GTX 260 .*NVIDIA .*GTX 26.* 4 1 1 3.3
+NVIDIA GTX 270 .*NVIDIA .*GTX 27.* 4 1 0 3.3
+NVIDIA GTX 280 .*NVIDIA .*GTX 28.* 4 1 1 3.3
+NVIDIA GTX 290 .*NVIDIA .*GTX 29.* 5 1 0 3.3
NVIDIA 310 .*NVIDIA .*GeForce 310.* 3 1 1 3.3
NVIDIA 315 .*NVIDIA .*GeForce 315.* 3 1 1 3.3
-NVIDIA GT 320 .*NVIDIA .*GT *32.* 3 1 0 3.3
-NVIDIA GT 330 .*NVIDIA .*GT *33.* 3 1 0 3.3
-NVIDIA GT 340 .*NVIDIA .*GT *34.* 3 1 0 0
+NVIDIA GT 320 .*NVIDIA .*GT 32.* 3 1 0 3.3
+NVIDIA GT 330 .*NVIDIA .*GT 33.* 3 1 0 3.3
+NVIDIA GT 340 .*NVIDIA .*GT 34.* 3 1 0 3.3
NVIDIA 405 .*NVIDIA .* 405.* 3 1 0 3.3
-NVIDIA GT 420 .*NVIDIA .*GT *42.* 3 1 1 4.2
-NVIDIA GT 430 .*NVIDIA .*GT *43.* 3 1 1 4.2
-NVIDIA GT 440 .*NVIDIA .*GT *44.* 4 1 0 4.2
-NVIDIA GTS 450 .*NVIDIA .*GTS *45.* 4 1 1 4.2
-NVIDIA GTX 460 .*NVIDIA .*GTX *46.* 5 1 1 4.3
-NVIDIA GTX 470 .*NVIDIA .*GTX *47.* 5 1 1 4.2
-NVIDIA GTX 480 .*NVIDIA .*GTX *48.* 5 1 1 4.2
-NVIDIA 510 .*NVIDIA .* 510.* 3 1 0 0
-NVIDIA GT 520 .*NVIDIA .*GT *52.* 3 1 1 4.2
-NVIDIA GT 530 .*NVIDIA .*GT *53.* 3 1 1 4.2
-NVIDIA GT 540 .*NVIDIA .*GT *54.* 3 1 1 4.2
-NVIDIA GTX 550 .*NVIDIA .*GTX *55.* 5 1 1 4.3
-NVIDIA GTX 560 .*NVIDIA .*GTX *56.* 5 1 1 4.2
-NVIDIA GTX 570 .*NVIDIA .*GTX *57.* 5 1 1 4.2
-NVIDIA GTX 580 .*NVIDIA .*GTX *58.* 5 1 1 4.3
-NVIDIA GTX 590 .*NVIDIA .*GTX *59.* 5 1 1 4.2
-NVIDIA GT 610 .*NVIDIA .*GT *61.* 3 1 1 4.2
-NVIDIA GT 620 .*NVIDIA .*GT *62.* 3 1 0 4.2
-NVIDIA GT 630 .*NVIDIA .*GT *63.* 3 1 0 4.2
-NVIDIA GT 640 .*NVIDIA .*GT *64.* 3 1 0 4.3
-NVIDIA GT 650 .*NVIDIA .*GT *65.* 3 1 1 4.2
-NVIDIA GTX 650 .*NVIDIA .*GTX *65.* 3 1 1 4.2
-NVIDIA GTX 660 .*NVIDIA .*GTX *66.* 5 1 0 4.3
-NVIDIA GTX 670 .*NVIDIA .*GTX *67.* 5 1 1 4.2
-NVIDIA GTX 680 .*NVIDIA .*GTX *68.* 5 1 1 4.2
-NVIDIA GTX 690 .*NVIDIA .*GTX *69.* 5 1 1 4.2
+NVIDIA GT 420 .*NVIDIA .*GT 42.* 3 1 1 4.2
+NVIDIA GT 430 .*NVIDIA .*GT 43.* 3 1 1 4.3
+NVIDIA GT 440 .*NVIDIA .*GT 44.* 4 1 0 4.3
+NVIDIA GTS 450 .*NVIDIA .*GTS 45.* 4 1 1 4.2
+NVIDIA GTX 460 .*NVIDIA .*GTX 46.* 5 1 1 4.3
+NVIDIA GTX 470 .*NVIDIA .*GTX 47.* 5 1 1 4.2
+NVIDIA GTX 480 .*NVIDIA .*GTX 48.* 5 1 1 4.2
+NVIDIA 510 .*NVIDIA .* 510.* 3 1 0 4.2
+NVIDIA GT 520 .*NVIDIA .*GT 52.* 3 1 1 4.2
+NVIDIA GT 530 .*NVIDIA .*GT 53.* 3 1 1 4.2
+NVIDIA GT 540 .*NVIDIA .*GT 54.* 3 1 1 4.2
+NVIDIA GTX 550 .*NVIDIA .*GTX 55.* 5 1 1 4.3
+NVIDIA GTX 560 .*NVIDIA .*GTX 56.* 5 1 1 4.3
+NVIDIA GTX 570 .*NVIDIA .*GTX 57.* 5 1 1 4.2
+NVIDIA GTX 580 .*NVIDIA .*GTX 58.* 5 1 1 4.3
+NVIDIA GTX 590 .*NVIDIA .*GTX 59.* 5 1 1 4.2
+NVIDIA 605 .*NVIDIA .* 605.* 3 1 1 4.2
+NVIDIA GT 610 .*NVIDIA .*GT 61.* 3 1 1 4.2
+NVIDIA GT 620 .*NVIDIA .*GT 62.* 3 1 0 4.2
+NVIDIA GT 630 .*NVIDIA .*GT 63.* 3 1 0 4.2
+NVIDIA GT 640 .*NVIDIA .*GT 64.* 3 1 0 4.2
+NVIDIA GT 650 .*NVIDIA .*GT 65.* 3 1 1 4.2
+NVIDIA GTX 650 .*NVIDIA .*GTX 65.* 3 1 1 4.2
+NVIDIA GTX 660 .*NVIDIA .*GTX 66.* 5 1 0 4.3
+NVIDIA GTX 670 .*NVIDIA .*GTX 67.* 5 1 1 4.2
+NVIDIA GTX 680 .*NVIDIA .*GTX 68.* 5 1 1 4.2
+NVIDIA GTX 690 .*NVIDIA .*GTX 69.* 5 1 1 4.2
NVIDIA C51 .*NVIDIA .*C51.* 0 1 1 2
NVIDIA G72 .*NVIDIA .*G72.* 1 1 0 0
NVIDIA G73 .*NVIDIA .*G73.* 1 1 0 0
@@ -437,13 +407,7 @@ NVIDIA G86 .*NVIDIA .*G86.* 3 1 0 0
NVIDIA G92 .*NVIDIA .*G92.* 3 1 0 0
NVIDIA GeForce .*GeForce 256.* 0 0 0 0
NVIDIA GeForce 2 .*GeForce ?2 ?.* 0 1 1 1.5
-NVIDIA GeForce 3 .*GeForce ?3 ?.* 2 1 1 2.1
-NVIDIA GeForce 3 Ti .*GeForce ?3 Ti.* 0 1 0 0
NVIDIA GeForce 4 .*NVIDIA .*GeForce ?4.* 0 1 1 1.5
-NVIDIA GeForce 4 Go .*NVIDIA .*GeForce ?4.*Go.* 0 1 0 0
-NVIDIA GeForce 4 MX .*NVIDIA .*GeForce ?4 MX.* 0 1 0 0
-NVIDIA GeForce 4 PCX .*NVIDIA .*GeForce ?4 PCX.* 0 1 0 0
-NVIDIA GeForce 4 Ti .*NVIDIA .*GeForce ?4 Ti.* 0 1 0 0
NVIDIA GeForce 6100 .*NVIDIA .*GeForce 61.* 3 1 1 4.2
NVIDIA GeForce 6200 .*NVIDIA .*GeForce 62.* 0 1 1 2.1
NVIDIA GeForce 6500 .*NVIDIA .*GeForce 65.* 1 1 1 2.1
@@ -458,33 +422,33 @@ NVIDIA GeForce 7500 .*NVIDIA .*GeForce 75.* 2 1 1 2.1
NVIDIA GeForce 7600 .*NVIDIA .*GeForce 76.* 2 1 1 2.1
NVIDIA GeForce 7800 .*NVIDIA .*GeForce 78.* 2 1 1 2.1
NVIDIA GeForce 7900 .*NVIDIA .*GeForce 79.* 3 1 1 2.1
-NVIDIA GeForce 8100 .*NVIDIA .*GeForce 81.* 1 1 0 0
-NVIDIA GeForce 8200M .*NVIDIA .*GeForce 8200M.* 1 1 0 3.3
-NVIDIA GeForce 8200 .*NVIDIA .*GeForce 82.* 1 1 0 2.1
+NVIDIA GeForce 8100 .*NVIDIA .*GeForce 81.* 1 1 0 3.3
+NVIDIA GeForce 8200M .*NVIDIA .*GeForce 820[0-9]M.* 1 1 0 3.3
+NVIDIA GeForce 8200 .*NVIDIA .*GeForce 82.* 1 1 0 3.3
NVIDIA GeForce 8300 .*NVIDIA .*GeForce 83.* 3 1 1 3.3
-NVIDIA GeForce 8400M .*NVIDIA .*GeForce 8400M.* 1 1 1 3.3
+NVIDIA GeForce 8400M .*NVIDIA .*GeForce 840[0-9]M.* 1 1 1 3.3
NVIDIA GeForce 8400 .*NVIDIA .*GeForce 84.* 2 1 1 3.3
NVIDIA GeForce 8500 .*NVIDIA .*GeForce 85.* 2 1 1 3.3
-NVIDIA GeForce 8600M .*NVIDIA .*GeForce 8600M.* 2 1 1 3.3
+NVIDIA GeForce 8600M .*NVIDIA .*GeForce 860[0-9]M.* 2 1 1 3.3
NVIDIA GeForce 8600 .*NVIDIA .*GeForce 86.* 3 1 1 3.3
-NVIDIA GeForce 8700M .*NVIDIA .*GeForce 8700M.* 2 1 1 3.3
+NVIDIA GeForce 8700M .*NVIDIA .*GeForce 870[0-9]M.* 2 1 1 3.3
NVIDIA GeForce 8700 .*NVIDIA .*GeForce 87.* 3 1 0 0
-NVIDIA GeForce 8800M .*NVIDIA .*GeForce 8800M.* 2 1 1 3.3
+NVIDIA GeForce 8800M .*NVIDIA .*GeForce 880[0-9]M.* 2 1 1 3.3
NVIDIA GeForce 8800 .*NVIDIA .*GeForce 88.* 3 1 1 3.3
-NVIDIA GeForce 9100M .*NVIDIA .*GeForce 9100M.* 0 1 0 0
+NVIDIA GeForce 9100M .*NVIDIA .*GeForce 910[0-9]M.* 0 1 0 3.3
NVIDIA GeForce 9100 .*NVIDIA .*GeForce 91.* 0 1 0 3.3
-NVIDIA GeForce 9200M .*NVIDIA .*GeForce 9200M.* 1 1 0 3.1
+NVIDIA GeForce 9200M .*NVIDIA .*GeForce 920[0-9]M.* 1 1 0 3.3
NVIDIA GeForce 9200 .*NVIDIA .*GeForce 92.* 1 1 0 3.3
-NVIDIA GeForce 9300M .*NVIDIA .*GeForce 9300M.* 1 1 1 3.3
+NVIDIA GeForce 9300M .*NVIDIA .*GeForce 930[0-9]M.* 1 1 1 3.3
NVIDIA GeForce 9300 .*NVIDIA .*GeForce 93.* 1 1 1 3.3
-NVIDIA GeForce 9400M .*NVIDIA .*GeForce 9400M.* 2 1 1 3.3
+NVIDIA GeForce 9400M .*NVIDIA .*GeForce 940[0-9]M.* 2 1 1 3.3
NVIDIA GeForce 9400 .*NVIDIA .*GeForce 94.* 3 1 1 3.3
-NVIDIA GeForce 9500M .*NVIDIA .*GeForce 9500M.* 1 1 1 3.3
+NVIDIA GeForce 9500M .*NVIDIA .*GeForce 950[0-9]M.* 1 1 1 3.3
NVIDIA GeForce 9500 .*NVIDIA .*GeForce 95.* 3 1 1 3.3
-NVIDIA GeForce 9600M .*NVIDIA .*GeForce 9600M.* 2 1 1 3.3
+NVIDIA GeForce 9600M .*NVIDIA .*GeForce 960[0-9]M.* 2 1 1 3.3
NVIDIA GeForce 9600 .*NVIDIA .*GeForce 96.* 3 1 1 3.3
-NVIDIA GeForce 9700M .*NVIDIA .*GeForce 9700M.* 0 1 1 3.3
-NVIDIA GeForce 9800M .*NVIDIA .*GeForce 9800M.* 2 1 1 3.3
+NVIDIA GeForce 9700M .*NVIDIA .*GeForce 970[0-9]M.* 0 1 1 3.3
+NVIDIA GeForce 9800M .*NVIDIA .*GeForce 980[0-9]M.* 2 1 1 3.3
NVIDIA GeForce 9800 .*NVIDIA .*GeForce 98.* 3 1 1 3.3
NVIDIA GeForce FX 5100 .*NVIDIA .*GeForce FX 51.* 0 1 0 0
NVIDIA GeForce FX 5200 .*NVIDIA .*GeForce FX 52.* 0 1 0 2.1
@@ -495,7 +459,7 @@ NVIDIA GeForce FX 5700 .*NVIDIA .*GeForce FX 57.* 0 1 1 2.1
NVIDIA GeForce FX 5800 .*NVIDIA .*GeForce FX 58.* 1 1 0 0
NVIDIA GeForce FX 5900 .*NVIDIA .*GeForce FX 59.* 1 1 1 2.1
NVIDIA GeForce FX Go5100 .*NVIDIA .*GeForce FX Go51.* 0 1 0 0
-NVIDIA GeForce FX Go5200 .*NVIDIA .*GeForce FX Go52.* 0 1 0 0
+NVIDIA GeForce FX Go5200 .*NVIDIA .*GeForce FX Go52.* 0 1 0 1.5
NVIDIA GeForce FX Go5300 .*NVIDIA .*GeForce FX Go53.* 0 1 0 0
NVIDIA GeForce FX Go5500 .*NVIDIA .*GeForce FX Go55.* 0 1 0 0
NVIDIA GeForce FX Go5600 .*NVIDIA .*GeForce FX Go56.* 0 1 1 2.1
@@ -504,13 +468,13 @@ NVIDIA GeForce FX Go5800 .*NVIDIA .*GeForce FX Go58.* 1 1 0 0
NVIDIA GeForce FX Go5900 .*NVIDIA .*GeForce FX Go59.* 1 1 0 0
NVIDIA GeForce FX Go5xxx .*NVIDIA .*GeForce FX Go.* 0 1 0 0
NVIDIA GeForce Go 6100 .*NVIDIA .*GeForce Go 61.* 0 1 1 2.1
-NVIDIA GeForce Go 6200 .*NVIDIA .*GeForce Go 62.* 0 1 0 0
-NVIDIA GeForce Go 6400 .*NVIDIA .*GeForce Go 64.* 1 1 1 2
+NVIDIA GeForce Go 6200 .*NVIDIA .*GeForce Go 62.* 0 1 0 1.5
+NVIDIA GeForce Go 6400 .*NVIDIA .*GeForce Go 64.* 1 1 1 2.1
NVIDIA GeForce Go 6500 .*NVIDIA .*GeForce Go 65.* 1 1 0 0
NVIDIA GeForce Go 6600 .*NVIDIA .*GeForce Go 66.* 0 1 1 2.1
NVIDIA GeForce Go 6700 .*NVIDIA .*GeForce Go 67.* 1 1 0 0
NVIDIA GeForce Go 6800 .*NVIDIA .*GeForce Go 68.* 0 1 1 2.1
-NVIDIA GeForce Go 7200 .*NVIDIA .*GeForce Go 72.* 1 1 0 0
+NVIDIA GeForce Go 7200 .*NVIDIA .*GeForce Go 72.* 1 1 0 2.1
NVIDIA GeForce Go 7300 LE .*NVIDIA .*GeForce Go 73.*LE.* 1 1 0 0
NVIDIA GeForce Go 7300 .*NVIDIA .*GeForce Go 73.* 1 1 1 2.1
NVIDIA GeForce Go 7400 .*NVIDIA .*GeForce Go 74.* 1 1 1 2.1
@@ -528,9 +492,9 @@ NVIDIA NB8P .*NVIDIA .*NB8P.* 2 1 0 0
NVIDIA NB9E .*NVIDIA .*NB9E.* 3 1 0 0
NVIDIA NB9M .*NVIDIA .*NB9M.* 1 1 0 0
NVIDIA NB9P .*NVIDIA .*NB9P.* 2 1 0 0
-NVIDIA N10 .*NVIDIA .*N10.* 1 1 0 0
-NVIDIA GeForce PCX .*GeForce PCX.* 0 1 0 0
-NVIDIA Generic .*NVIDIA .*Unknown.* 0 0 0 3
+NVIDIA N10 .*NVIDIA .*N10.* 1 1 0 2.1
+NVIDIA GeForce PCX .*GeForce PCX.* 0 1 0 1.5
+NVIDIA Generic .*NVIDIA .*Unknown.* 0 0 0 2.1
NVIDIA NV17 .*NVIDIA .*NV17.* 0 1 0 0
NVIDIA NV34 .*NVIDIA .*NV34.* 0 1 0 0
NVIDIA NV35 .*NVIDIA .*NV35.* 0 1 0 0
@@ -540,7 +504,7 @@ NVIDIA NV43 .*NVIDIA .*NV43.* 1 1 0 0
NVIDIA NV44 .*NVIDIA .*NV44.* 1 1 0 0
NVIDIA nForce .*NVIDIA .*nForce.* 0 0 0 3.3
NVIDIA MCP51 .*NVIDIA .*MCP51.* 1 1 0 0
-NVIDIA MCP61 .*NVIDIA .*MCP61.* 1 1 0 0
+NVIDIA MCP61 .*NVIDIA .*MCP61.* 1 1 0 2.1
NVIDIA MCP67 .*NVIDIA .*MCP67.* 1 1 0 0
NVIDIA MCP68 .*NVIDIA .*MCP68.* 1 1 0 0
NVIDIA MCP73 .*NVIDIA .*MCP73.* 1 1 0 0
@@ -548,44 +512,44 @@ NVIDIA MCP77 .*NVIDIA .*MCP77.* 1 1 0 0
NVIDIA MCP78 .*NVIDIA .*MCP78.* 1 1 0 0
NVIDIA MCP79 .*NVIDIA .*MCP79.* 1 1 0 0
NVIDIA MCP7A .*NVIDIA .*MCP7A.* 1 1 0 0
-NVIDIA Quadro2 .*Quadro2.* 0 1 0 0
-NVIDIA Quadro 1000M .*Quadro.*1000M.* 2 1 0 4.2
-NVIDIA Quadro 2000 M/D .*Quadro.*2000.* 3 1 0 4.2
-NVIDIA Quadro 3000M .*Quadro.*3000M.* 3 1 0 0
-NVIDIA Quadro 4000M .*Quadro.*4000M.* 3 1 0 0
-NVIDIA Quadro 4000 .*Quadro *4000.* 3 1 0 4.2
-NVIDIA Quadro 50x0 M .*Quadro.*50.0.* 3 1 0 0
+NVIDIA Quadro2 .*Quadro2.* 0 1 0 1.5
+NVIDIA Quadro 1000M .*Quadro.* (K1|1)00[0-9]M.* 2 1 0 4.2
+NVIDIA Quadro 2000 M/D .*Quadro.* (K2|2)000.* 3 1 0 4.2
+NVIDIA Quadro 3000M .*Quadro.* (K3|3)00[0-9]M.* 3 1 0 4.2
+NVIDIA Quadro 4000M .*Quadro.* (K4|4)00[0-9]M.* 3 1 0 4.2
+NVIDIA Quadro 4000 .*Quadro 4000.* 3 1 0 4.2
+NVIDIA Quadro 50x0 M .*Quadro.* 50.0.* 3 1 0 4.2
NVIDIA Quadro 6000 .*Quadro.* 6000.* 3 1 0 0
NVIDIA Quadro 400 .*Quadro.* 400.* 2 1 0 3.3
-NVIDIA Quadro 600 .*Quadro.*600.* 2 1 0 3.3
-NVIDIA Quadro4 .*Quadro4.* 0 1 0 0
+NVIDIA Quadro 600 .*Quadro.* 600.* 2 1 0 4.2
+NVIDIA Quadro4 .*Quadro4.* 0 1 0 1.5
NVIDIA Quadro DCC .*Quadro DCC.* 0 1 0 0
NVIDIA Quadro CX .*Quadro.*CX.* 3 1 0 0
-NVIDIA Quadro FX 770M .*Quadro.*FX *770M.* 2 1 0 0
-NVIDIA Quadro FX 1500M .*Quadro.*FX *1500M.* 1 1 0 2.1
-NVIDIA Quadro FX 1600M .*Quadro.*FX *1600M.* 2 1 0 0
-NVIDIA Quadro FX 2500M .*Quadro.*FX *2500M.* 2 1 0 0
-NVIDIA Quadro FX 2700M .*Quadro.*FX *2700M.* 3 1 0 0
-NVIDIA Quadro FX 2800M .*Quadro.*FX *2800M.* 3 1 0 3.3
-NVIDIA Quadro FX 3500 .*Quadro.*FX *3500.* 2 1 0 2.1
-NVIDIA Quadro FX 3600 .*Quadro.*FX *3600.* 3 1 0 0
-NVIDIA Quadro FX 3700 .*Quadro.*FX *3700.* 3 1 0 3.3
-NVIDIA Quadro FX 3800 .*Quadro.*FX *3800.* 3 1 0 3.2
-NVIDIA Quadro FX 4500 .*Quadro.*FX *45.* 3 1 0 0
-NVIDIA Quadro FX 880M .*Quadro.*FX *880M.* 3 1 0 3.3
-NVIDIA Quadro FX 4800 .*NVIDIA .*Quadro *FX *4800.* 3 1 0 0
+NVIDIA Quadro FX 770M .*Quadro.*FX 77[0-9]M.* 2 1 0 3.3
+NVIDIA Quadro FX 1500M .*Quadro.*FX 150[0-9]M.* 1 1 0 2.1
+NVIDIA Quadro FX 1600M .*Quadro.*FX 160[0-9]M.* 2 1 0 3.3
+NVIDIA Quadro FX 2500M .*Quadro.*FX 250[0-9]M.* 2 1 0 2.1
+NVIDIA Quadro FX 2700M .*Quadro.*FX 270[0-9]M.* 3 1 0 3.3
+NVIDIA Quadro FX 2800M .*Quadro.*FX 280[0-9]M.* 3 1 0 3.3
+NVIDIA Quadro FX 3500 .*Quadro.*FX 3500.* 2 1 0 2.1
+NVIDIA Quadro FX 3600 .*Quadro.*FX 3600.* 3 1 0 3.3
+NVIDIA Quadro FX 3700 .*Quadro.*FX 3700.* 3 1 0 3.3
+NVIDIA Quadro FX 3800 .*Quadro.*FX 3800.* 3 1 0 3.3
+NVIDIA Quadro FX 4500 .*Quadro.*FX 45.* 3 1 0 2.1
+NVIDIA Quadro FX 880M .*Quadro.*FX 88[0-9]M.* 3 1 0 3.3
+NVIDIA Quadro FX 4800 .*NVIDIA .*Quadro FX 4800.* 3 1 0 3.1
NVIDIA Quadro FX .*Quadro FX.* 1 1 0 3.3
-NVIDIA Quadro NVS 1xxM .*Quadro NVS *1.[05]M.* 0 1 1 3.3
-NVIDIA Quadro NVS 300M .*NVIDIA .*NVS *300M.* 2 1 0 0
-NVIDIA Quadro NVS 320M .*NVIDIA .*NVS *320M.* 2 1 0 0
-NVIDIA Quadro NVS 2100M .*NVIDIA .*NVS *2100M.* 2 1 0 0
-NVIDIA Quadro NVS 3100M .*NVIDIA .*NVS *3100M.* 2 1 0 0
-NVIDIA Quadro NVS 4200M .*NVIDIA .*NVS *4200M.* 2 1 0 4.1
-NVIDIA Quadro NVS 5100M .*NVIDIA .*NVS *5100M.* 2 1 0 0
-NVIDIA Quadro NVS .*NVIDIA .*NVS 0 1 0 3.2
+NVIDIA Quadro NVS 1xxM .*Quadro NVS 1.[05]M.* 0 1 1 3.3
+NVIDIA Quadro NVS 300M .*NVIDIA .*NVS 30[0-9]M.* 2 1 0 0
+NVIDIA Quadro NVS 320M .*NVIDIA .*NVS 32[0-9]M.* 2 1 0 0
+NVIDIA Quadro NVS 2100M .*NVIDIA .*NVS 210[0-9]M.* 2 1 0 3.3
+NVIDIA Quadro NVS 3100M .*NVIDIA .*NVS 310[0-9]M.* 2 1 0 3.3
+NVIDIA Quadro NVS 4200M .*NVIDIA .*NVS 420[0-9]M.* 2 1 0 4.2
+NVIDIA Quadro NVS 5100M .*NVIDIA .*NVS 510[0-9]M.* 2 1 0 0
+NVIDIA Quadro NVS .*NVIDIA .*NVS 0 1 0 4.2
NVIDIA Corporation N12P .*NVIDIA .*N12P.* 1 1 1 4.1
-NVIDIA Corporation N11M .*NVIDIA .*N11M.* 2 1 0 0
-NVIDIA RIVA TNT .*RIVA TNT.* 0 0 0 0
+NVIDIA Corporation N11M .*NVIDIA .*N11M.* 2 1 0 3.1
+NVIDIA RIVA TNT .*RIVA TNT.* 0 0 0 1.5
S3 .*S3 Graphics.* 0 0 1 1.4
SiS SiS.* 0 0 1 1.5
Trident Trident.* 0 0 0 0
diff --git a/indra/newview/llagent.cpp b/indra/newview/llagent.cpp
index 05f3824485..f4ce3c9118 100755
--- a/indra/newview/llagent.cpp
+++ b/indra/newview/llagent.cpp
@@ -46,6 +46,7 @@
#include "llenvmanager.h"
#include "llfirstuse.h"
#include "llfloatercamera.h"
+#include "llfloaterimcontainer.h"
#include "llfloaterreg.h"
#include "llfloatertools.h"
#include "llgroupactions.h"
@@ -91,6 +92,7 @@
#include "llworld.h"
#include "llworldmap.h"
#include "stringize.h"
+#include "boost/foreach.hpp"
using namespace LLAvatarAppearanceDefines;
@@ -2037,7 +2039,16 @@ void LLAgent::endAnimationUpdateUI()
{
skip_list.insert(LLFloaterReg::findInstance("mini_map"));
}
-
+
+ LLFloaterIMContainer* im_box = LLFloaterReg::getTypedInstance<LLFloaterIMContainer>("im_container");
+ LLFloaterIMContainer::floater_list_t conversations;
+ im_box->getDetachedConversationFloaters(conversations);
+ BOOST_FOREACH(LLFloater* conversation, conversations)
+ {
+ llinfos << "skip_list.insert(session_floater): " << conversation->getTitle() << llendl;
+ skip_list.insert(conversation);
+ }
+
gFloaterView->popVisibleAll(skip_list);
#endif
mViewsPushed = FALSE;
diff --git a/indra/newview/llappviewer.cpp b/indra/newview/llappviewer.cpp
index ad2d0e1145..003d82dd0e 100755
--- a/indra/newview/llappviewer.cpp
+++ b/indra/newview/llappviewer.cpp
@@ -4562,11 +4562,6 @@ void LLAppViewer::idle()
llinfos << "Dead object updates: " << gObjectList.mNumDeadObjectUpdates << llendl;
gObjectList.mNumDeadObjectUpdates = 0;
}
- if (gObjectList.mNumUnknownKills)
- {
- llinfos << "Kills on unknown objects: " << gObjectList.mNumUnknownKills << llendl;
- gObjectList.mNumUnknownKills = 0;
- }
if (gObjectList.mNumUnknownUpdates)
{
llinfos << "Unknown object updates: " << gObjectList.mNumUnknownUpdates << llendl;
diff --git a/indra/newview/llchannelmanager.cpp b/indra/newview/llchannelmanager.cpp
index 43757d0174..8b2d9e639f 100755
--- a/indra/newview/llchannelmanager.cpp
+++ b/indra/newview/llchannelmanager.cpp
@@ -139,8 +139,6 @@ void LLChannelManager::onLoginCompleted()
}
LLPersistentNotificationStorage::getInstance()->loadNotifications();
-
- LLDoNotDisturbNotificationStorage::getInstance()->initialize();
LLDoNotDisturbNotificationStorage::getInstance()->loadNotifications();
}
diff --git a/indra/newview/llchathistory.cpp b/indra/newview/llchathistory.cpp
index 0f138873ac..af3c6eff11 100755
--- a/indra/newview/llchathistory.cpp
+++ b/indra/newview/llchathistory.cpp
@@ -628,6 +628,7 @@ LLChatHistory::LLChatHistory(const LLChatHistory::Params& p)
editor_params.enabled = false; // read only
editor_params.show_context_menu = "true";
mEditor = LLUICtrlFactory::create<LLTextEditor>(editor_params, this);
+ mEditor->setIsFriendCallback(LLAvatarActions::isFriend);
}
LLSD LLChatHistory::getValue() const
diff --git a/indra/newview/llchatitemscontainerctrl.cpp b/indra/newview/llchatitemscontainerctrl.cpp
index a1a9463d43..fd4f17b694 100755
--- a/indra/newview/llchatitemscontainerctrl.cpp
+++ b/indra/newview/llchatitemscontainerctrl.cpp
@@ -323,12 +323,11 @@ BOOL LLFloaterIMNearbyChatToastPanel::handleMouseUp (S32 x, S32 y, MASK mask)
return TRUE;
else
{
- (LLFloaterReg::getTypedInstance<LLFloaterIMNearbyChat>("nearby_chat"))->showHistory();
+ LLFloaterReg::getTypedInstance<LLFloaterIMNearbyChat>("nearby_chat")->showHistory();
return FALSE;
}
}
-
- (LLFloaterReg::getTypedInstance<LLFloaterIMNearbyChat>("nearby_chat"))->showHistory();
+ LLFloaterReg::getTypedInstance<LLFloaterIMNearbyChat>("nearby_chat")->showHistory();
return LLPanel::handleMouseUp(x,y,mask);
}
diff --git a/indra/newview/llconversationmodel.cpp b/indra/newview/llconversationmodel.cpp
index c74ce24872..192a594c9d 100755
--- a/indra/newview/llconversationmodel.cpp
+++ b/indra/newview/llconversationmodel.cpp
@@ -363,7 +363,10 @@ void LLConversationItemSession::buildContextMenu(LLMenuGL& menu, U32 flags)
lldebugs << "LLConversationItemParticipant::buildContextMenu()" << llendl;
menuentry_vec_t items;
menuentry_vec_t disabled_items;
-
+ if((flags & ITEM_IN_MULTI_SELECTION) && (this->getType() != CONV_SESSION_NEARBY))
+ {
+ items.push_back(std::string("close_selected_conversations"));
+ }
if(this->getType() == CONV_SESSION_1_ON_1)
{
items.push_back(std::string("close_conversation"));
@@ -386,6 +389,10 @@ void LLConversationItemSession::buildContextMenu(LLMenuGL& menu, U32 flags)
addVoiceOptions(items);
items.push_back(std::string("chat_history"));
}
+ else if(this->getType() == CONV_SESSION_NEARBY)
+ {
+ items.push_back(std::string("chat_history"));
+ }
hide_context_entries(menu, items, disabled_items);
}
diff --git a/indra/newview/llconversationmodel.h b/indra/newview/llconversationmodel.h
index 8766585049..d8cdcdfc97 100755
--- a/indra/newview/llconversationmodel.h
+++ b/indra/newview/llconversationmodel.h
@@ -252,11 +252,10 @@ public:
const std::string& getName() const { return mEmpty; }
const std::string& getFilterText() { return mEmpty; }
void setModified(EFilterModified behavior = FILTER_RESTART) { }
-
- void setFilterCount(S32 count) { }
- S32 getFilterCount() const { return 0; }
- void decrementFilterCount() { }
-
+
+ void resetTime(S32 timeout) { }
+ bool isTimedOut() { return false; }
+
bool isDefault() const { return true; }
bool isNotDefault() const { return false; }
void markDefault() { }
diff --git a/indra/newview/llconversationview.cpp b/indra/newview/llconversationview.cpp
index b6c53e5e30..9faa12b2ee 100755
--- a/indra/newview/llconversationview.cpp
+++ b/indra/newview/llconversationview.cpp
@@ -118,9 +118,19 @@ void LLConversationViewSession::setFlashState(bool flash_state)
mFlashTimer->stopFlashing();
}
+void LLConversationViewSession::setHighlightState(bool hihglight_state)
+{
+ mFlashStateOn = hihglight_state;
+ mFlashStarted = true;
+ mFlashTimer->stopFlashing();
+}
+
void LLConversationViewSession::startFlashing()
{
- if (isInVisibleChain() && mFlashStateOn && !mFlashStarted)
+ LLFloaterIMContainer* im_box = LLFloaterReg::getTypedInstance<LLFloaterIMContainer>("im_container");
+
+ // Need to start flashing only when "Conversations" is opened or brought on top
+ if (isInVisibleChain() && !im_box->isMinimized() && mFlashStateOn && !mFlashStarted)
{
mFlashStarted = true;
mFlashTimer->startFlashing();
@@ -263,6 +273,29 @@ BOOL LLConversationViewSession::handleMouseDown( S32 x, S32 y, MASK mask )
return result;
}
+BOOL LLConversationViewSession::handleMouseUp( S32 x, S32 y, MASK mask )
+{
+ BOOL result = LLFolderViewFolder::handleMouseUp(x, y, mask);
+
+ LLFloater* volume_floater = LLFloaterReg::findInstance("floater_voice_volume");
+ LLFloater* chat_volume_floater = LLFloaterReg::findInstance("chat_voice");
+ if (result
+ && getRoot()
+ && !(volume_floater && volume_floater->isShown() && volume_floater->hasFocus())
+ && !(chat_volume_floater && chat_volume_floater->isShown() && chat_volume_floater->hasFocus()))
+ {
+ LLConversationItem* item = dynamic_cast<LLConversationItem *>(getViewModelItem());
+ LLUUID session_id = item? item->getUUID() : LLUUID();
+ LLFloaterIMSessionTab* session_floater = LLFloaterIMSessionTab::findConversation(session_id);
+ if(!session_floater->hasFocus())
+ {
+ session_floater->setFocus(true);
+ }
+ }
+
+ return result;
+}
+
BOOL LLConversationViewSession::handleRightMouseDown( S32 x, S32 y, MASK mask )
{
BOOL result = LLFolderViewFolder::handleRightMouseDown(x, y, mask);
@@ -340,16 +373,20 @@ void LLConversationViewSession::setVisibleIfDetached(BOOL visible)
{
// Do this only if the conversation floater has been torn off (i.e. no multi floater host) and is not minimized
// Note: minimized dockable floaters are brought to front hence unminimized when made visible and we don't want that here
- LLFolderViewModelItem* item = mViewModelItem;
- LLUUID session_uuid = dynamic_cast<LLConversationItem*>(item)->getUUID();
- LLFloater* session_floater = LLFloaterIMSessionTab::getConversation(session_uuid);
-
- if (session_floater && !session_floater->getHost() && !session_floater->isMinimized())
+ LLFloater* session_floater = getSessionFloater();
+ if (session_floater && session_floater->isDetachedAndNotMinimized())
{
session_floater->setVisible(visible);
}
}
+LLFloater* LLConversationViewSession::getSessionFloater()
+{
+ LLFolderViewModelItem* item = mViewModelItem;
+ LLUUID session_uuid = dynamic_cast<LLConversationItem*>(item)->getUUID();
+ return LLFloaterIMSessionTab::getConversation(session_uuid);
+}
+
LLConversationViewParticipant* LLConversationViewSession::findParticipant(const LLUUID& participant_id)
{
// This is *not* a general tree parsing algorithm. We search only in the mItems list
diff --git a/indra/newview/llconversationview.h b/indra/newview/llconversationview.h
index 3eb2e63792..5a74974302 100755
--- a/indra/newview/llconversationview.h
+++ b/indra/newview/llconversationview.h
@@ -69,6 +69,7 @@ public:
/*virtual*/ void draw();
/*virtual*/ BOOL handleMouseDown( S32 x, S32 y, MASK mask );
/*virtual*/ BOOL handleRightMouseDown( S32 x, S32 y, MASK mask );
+ /*virtual*/ BOOL handleMouseUp( S32 x, S32 y, MASK mask );
/*virtual*/ S32 arrange(S32* width, S32* height);
@@ -86,6 +87,9 @@ public:
virtual void refresh();
/*virtual*/ void setFlashState(bool flash_state);
+ void setHighlightState(bool hihglight_state);
+
+ LLFloater* getSessionFloater();
private:
diff --git a/indra/newview/lldonotdisturbnotificationstorage.cpp b/indra/newview/lldonotdisturbnotificationstorage.cpp
index 82affcf068..495cd01349 100755
--- a/indra/newview/lldonotdisturbnotificationstorage.cpp
+++ b/indra/newview/lldonotdisturbnotificationstorage.cpp
@@ -70,7 +70,7 @@ BOOL LLDoNotDisturbNotificationStorageTimer::tick()
LLDoNotDisturbNotificationStorage::LLDoNotDisturbNotificationStorage()
: LLSingleton<LLDoNotDisturbNotificationStorage>()
- , LLNotificationStorage(gDirUtilp->getExpandedFilename(LL_PATH_PER_SL_ACCOUNT, "dnd_notifications.xml"))
+ , LLNotificationStorage("")
, mDirty(false)
{
nameToPayloadParameterMap[toastName] = "SESSION_ID";
@@ -83,6 +83,7 @@ LLDoNotDisturbNotificationStorage::~LLDoNotDisturbNotificationStorage()
void LLDoNotDisturbNotificationStorage::initialize()
{
+ setFileName(gDirUtilp->getExpandedFilename(LL_PATH_PER_SL_ACCOUNT, "dnd_notifications.xml"));
getCommunicationChannel()->connectFailedFilter(boost::bind(&LLDoNotDisturbNotificationStorage::onChannelChanged, this, _1));
}
@@ -115,7 +116,8 @@ void LLDoNotDisturbNotificationStorage::saveNotifications()
{
LLNotificationPtr notificationPtr = historyIter->second;
- if (!notificationPtr->isRespondedTo() && !notificationPtr->isCancelled() && !notificationPtr->isExpired())
+ if (!notificationPtr->isRespondedTo() && !notificationPtr->isCancelled() &&
+ !notificationPtr->isExpired() && !notificationPtr->isPersistent())
{
data.append(notificationPtr->asLLSD(true));
}
@@ -210,12 +212,8 @@ void LLDoNotDisturbNotificationStorage::loadNotifications()
}
- if(imToastExists)
- {
- LLFloaterReg::showInstance("im_container");
- }
-
- if(group_ad_hoc_toast_exists)
+ bool isConversationLoggingAllowed = gSavedPerAccountSettings.getS32("KeepConversationLogTranscripts") > 0;
+ if(group_ad_hoc_toast_exists && isConversationLoggingAllowed)
{
LLFloaterReg::showInstance("conversation");
}
@@ -266,11 +264,6 @@ void LLDoNotDisturbNotificationStorage::updateNotifications()
}
}
- if(imToastExists)
- {
- LLFloaterReg::showInstance("im_container");
- }
-
if(imToastExists || offerExists)
{
make_ui_sound("UISndNewIncomingIMSession");
diff --git a/indra/newview/lldrawpoolavatar.cpp b/indra/newview/lldrawpoolavatar.cpp
index 075299386e..a0024a231c 100755
--- a/indra/newview/lldrawpoolavatar.cpp
+++ b/indra/newview/lldrawpoolavatar.cpp
@@ -135,6 +135,16 @@ void LLDrawPoolAvatar::prerender()
{
sBufferUsage = GL_STREAM_DRAW_ARB;
}
+
+ if (!mDrawFace.empty())
+ {
+ const LLFace *facep = mDrawFace[0];
+ if (facep && facep->getDrawable())
+ {
+ LLVOAvatar* avatarp = (LLVOAvatar *)facep->getDrawable()->getVObj().get();
+ updateRiggedVertexBuffers(avatarp);
+ }
+ }
}
LLMatrix4& LLDrawPoolAvatar::getModelView()
@@ -1434,6 +1444,65 @@ void LLDrawPoolAvatar::renderAvatars(LLVOAvatar* single_avatar, S32 pass)
}
}
+void LLDrawPoolAvatar::getRiggedGeometry(LLFace* face, LLPointer<LLVertexBuffer>& buffer, U32 data_mask, const LLMeshSkinInfo* skin, LLVolume* volume, const LLVolumeFace& vol_face)
+{
+ face->setGeomIndex(0);
+ face->setIndicesIndex(0);
+
+ //rigged faces do not batch textures
+ face->setTextureIndex(255);
+
+ if (buffer.isNull() || buffer->getTypeMask() != data_mask || !buffer->isWriteable())
+ { //make a new buffer
+ if (sShaderLevel > 0)
+ {
+ buffer = new LLVertexBuffer(data_mask, GL_DYNAMIC_DRAW_ARB);
+ }
+ else
+ {
+ buffer = new LLVertexBuffer(data_mask, GL_STREAM_DRAW_ARB);
+ }
+ buffer->allocateBuffer(vol_face.mNumVertices, vol_face.mNumIndices, true);
+ }
+ else
+ { //resize existing buffer
+ buffer->resizeBuffer(vol_face.mNumVertices, vol_face.mNumIndices);
+ }
+
+ face->setSize(vol_face.mNumVertices, vol_face.mNumIndices);
+ face->setVertexBuffer(buffer);
+
+ U16 offset = 0;
+
+ LLMatrix4 mat_vert = skin->mBindShapeMatrix;
+ glh::matrix4f m((F32*) mat_vert.mMatrix);
+ m = m.inverse().transpose();
+
+ F32 mat3[] =
+ { m.m[0], m.m[1], m.m[2],
+ m.m[4], m.m[5], m.m[6],
+ m.m[8], m.m[9], m.m[10] };
+
+ LLMatrix3 mat_normal(mat3);
+
+ //let getGeometryVolume know if alpha should override shiny
+ U32 type = gPipeline.getPoolTypeFromTE(face->getTextureEntry(), face->getTexture());
+
+ if (type == LLDrawPool::POOL_ALPHA)
+ {
+ face->setPoolType(LLDrawPool::POOL_ALPHA);
+ }
+ else
+ {
+ face->setPoolType(LLDrawPool::POOL_AVATAR);
+ }
+
+ //llinfos << "Rebuilt face " << face->getTEOffset() << " of " << face->getDrawable() << " at " << gFrameTimeSeconds << llendl;
+ face->getGeometryVolume(*volume, face->getTEOffset(), mat_vert, mat_normal, offset, true);
+
+ buffer->flush();
+}
+
void LLDrawPoolAvatar::updateRiggedFaceVertexBuffer(LLVOAvatar* avatar, LLFace* face, const LLMeshSkinInfo* skin, LLVolume* volume, const LLVolumeFace& vol_face)
{
LLVector4a* weight = vol_face.mWeights;
@@ -1453,60 +1522,27 @@ void LLDrawPoolAvatar::updateRiggedFaceVertexBuffer(LLVOAvatar* avatar, LLFace*
buffer->getNumIndices() != vol_face.mNumIndices ||
(drawable && drawable->isState(LLDrawable::REBUILD_ALL)))
{
- face->setGeomIndex(0);
- face->setIndicesIndex(0);
-
- //rigged faces do not batch textures
- face->setTextureIndex(255);
-
- if (buffer.isNull() || buffer->getTypeMask() != data_mask || !buffer->isWriteable())
- { //make a new buffer
- if (sShaderLevel > 0)
+ if (drawable && drawable->isState(LLDrawable::REBUILD_ALL))
+ { //rebuild EVERY face in the drawable, not just this one, to avoid missing drawable wide rebuild issues
+ for (S32 i = 0; i < drawable->getNumFaces(); ++i)
{
- buffer = new LLVertexBuffer(data_mask, GL_DYNAMIC_DRAW_ARB);
- }
- else
- {
- buffer = new LLVertexBuffer(data_mask, GL_STREAM_DRAW_ARB);
+ LLFace* facep = drawable->getFace(i);
+ U32 face_data_mask = facep->getRiggedVertexBufferDataMask();
+ if (face_data_mask)
+ {
+ LLPointer<LLVertexBuffer> cur_buffer = facep->getVertexBuffer();
+ const LLVolumeFace& cur_vol_face = volume->getVolumeFace(i);
+ getRiggedGeometry(facep, cur_buffer, face_data_mask, skin, volume, cur_vol_face);
+ }
}
- buffer->allocateBuffer(vol_face.mNumVertices, vol_face.mNumIndices, true);
- }
- else
- { //resize existing buffer
- buffer->resizeBuffer(vol_face.mNumVertices, vol_face.mNumIndices);
- }
-
- face->setSize(vol_face.mNumVertices, vol_face.mNumIndices);
- face->setVertexBuffer(buffer);
-
- U16 offset = 0;
-
- LLMatrix4 mat_vert = skin->mBindShapeMatrix;
- glh::matrix4f m((F32*) mat_vert.mMatrix);
- m = m.inverse().transpose();
-
- F32 mat3[] =
- { m.m[0], m.m[1], m.m[2],
- m.m[4], m.m[5], m.m[6],
- m.m[8], m.m[9], m.m[10] };
-
- LLMatrix3 mat_normal(mat3);
-
- //let getGeometryVolume know if alpha should override shiny
- U32 type = gPipeline.getPoolTypeFromTE(face->getTextureEntry(), face->getTexture());
+ drawable->clearState(LLDrawable::REBUILD_ALL);
- if (type == LLDrawPool::POOL_ALPHA)
- {
- face->setPoolType(LLDrawPool::POOL_ALPHA);
+ buffer = face->getVertexBuffer();
}
else
- {
- face->setPoolType(LLDrawPool::POOL_AVATAR);
+ { //just rebuild this face
+ getRiggedGeometry(face, buffer, data_mask, skin, volume, vol_face);
}
-
- face->getGeometryVolume(*volume, face->getTEOffset(), mat_vert, mat_normal, offset, true);
-
- buffer->flush();
}
if (sShaderLevel <= 0 && face->mLastSkinTime < avatar->getLastSkinTime())
@@ -1591,11 +1627,6 @@ void LLDrawPoolAvatar::updateRiggedFaceVertexBuffer(LLVOAvatar* avatar, LLFace*
}
}
}
-
- if (drawable && (face->getTEOffset() == drawable->getNumFaces()-1))
- {
- drawable->clearState(LLDrawable::REBUILD_ALL);
- }
}
void LLDrawPoolAvatar::renderRigged(LLVOAvatar* avatar, U32 type, bool glow)
@@ -1771,7 +1802,6 @@ void LLDrawPoolAvatar::renderRigged(LLVOAvatar* avatar, U32 type, bool glow)
void LLDrawPoolAvatar::renderDeferredRiggedSimple(LLVOAvatar* avatar)
{
- updateRiggedVertexBuffers(avatar);
renderRigged(avatar, RIGGED_DEFERRED_SIMPLE);
}
@@ -1840,7 +1870,6 @@ void LLDrawPoolAvatar::updateRiggedVertexBuffers(LLVOAvatar* avatar)
void LLDrawPoolAvatar::renderRiggedSimple(LLVOAvatar* avatar)
{
- updateRiggedVertexBuffers(avatar);
renderRigged(avatar, RIGGED_SIMPLE);
}
diff --git a/indra/newview/lldrawpoolavatar.h b/indra/newview/lldrawpoolavatar.h
index 7d0368a945..4fbda1f862 100755
--- a/indra/newview/lldrawpoolavatar.h
+++ b/indra/newview/lldrawpoolavatar.h
@@ -133,6 +133,7 @@ public:
void endDeferredRiggedSimple();
void endDeferredRiggedBump();
+ void getRiggedGeometry(LLFace* face, LLPointer<LLVertexBuffer>& buffer, U32 data_mask, const LLMeshSkinInfo* skin, LLVolume* volume, const LLVolumeFace& vol_face);
void updateRiggedFaceVertexBuffer(LLVOAvatar* avatar,
LLFace* facep,
const LLMeshSkinInfo* skin,
diff --git a/indra/newview/llface.cpp b/indra/newview/llface.cpp
index f021f4ed0f..9b2b778677 100755
--- a/indra/newview/llface.cpp
+++ b/indra/newview/llface.cpp
@@ -768,7 +768,7 @@ bool less_than_max_mag(const LLVector4a& vec)
}
BOOL LLFace::genVolumeBBoxes(const LLVolume &volume, S32 f,
- const LLMatrix4& mat_vert_in, const LLMatrix3& mat_normal_in, BOOL global_volume)
+ const LLMatrix4& mat_vert_in, BOOL global_volume)
{
//get bounding box
if (mDrawablep->isState(LLDrawable::REBUILD_VOLUME | LLDrawable::REBUILD_POSITION | LLDrawable::REBUILD_RIGGED))
@@ -777,10 +777,6 @@ BOOL LLFace::genVolumeBBoxes(const LLVolume &volume, S32 f,
LLMatrix4a mat_vert;
mat_vert.loadu(mat_vert_in);
- LLMatrix4a mat_normal;
- mat_normal.loadu(mat_normal_in);
-
- //VECTORIZE THIS
LLVector4a min,max;
if (f >= volume.getNumVolumeFaces())
@@ -797,100 +793,68 @@ BOOL LLFace::genVolumeBBoxes(const LLVolume &volume, S32 f,
llassert(less_than_max_mag(max));
//min, max are in volume space, convert to drawable render space
- LLVector4a center;
- LLVector4a t;
- t.setAdd(min, max);
- t.mul(0.5f);
- mat_vert.affineTransform(t, center);
- LLVector4a size;
- size.setSub(max, min);
- size.mul(0.5f);
- llassert(less_than_max_mag(min));
- llassert(less_than_max_mag(max));
+ //get 8 corners of bounding box
+ LLVector4Logical mask[6];
- if (!global_volume)
+ for (U32 i = 0; i < 6; ++i)
{
- //VECTORIZE THIS
- LLVector4a scale;
- scale.load3(mDrawablep->getVObj()->getScale().mV);
- size.mul(scale);
+ mask[i].clear();
}
- // Catch potential badness from normalization before it happens
- //
- llassert(mat_normal.mMatrix[0].isFinite3() && (mat_normal.mMatrix[0].dot3(mat_normal.mMatrix[0]).getF32() > F_APPROXIMATELY_ZERO));
- llassert(mat_normal.mMatrix[1].isFinite3() && (mat_normal.mMatrix[1].dot3(mat_normal.mMatrix[1]).getF32() > F_APPROXIMATELY_ZERO));
- llassert(mat_normal.mMatrix[2].isFinite3() && (mat_normal.mMatrix[2].dot3(mat_normal.mMatrix[2]).getF32() > F_APPROXIMATELY_ZERO));
-
- mat_normal.mMatrix[0].normalize3fast();
- mat_normal.mMatrix[1].normalize3fast();
- mat_normal.mMatrix[2].normalize3fast();
+ mask[0].setElement<2>(); //001
+ mask[1].setElement<1>(); //010
+ mask[2].setElement<1>(); //011
+ mask[2].setElement<2>();
+ mask[3].setElement<0>(); //100
+ mask[4].setElement<0>(); //101
+ mask[4].setElement<2>();
+ mask[5].setElement<0>(); //110
+ mask[5].setElement<1>();
- LLVector4a v[4];
+ LLVector4a v[8];
- //get 4 corners of bounding box
- mat_normal.rotate(size,v[0]);
+ v[6] = min;
+ v[7] = max;
- //VECTORIZE THIS
- LLVector4a scale;
-
- scale.set(-1.f, -1.f, 1.f);
- scale.mul(size);
- mat_normal.rotate(scale, v[1]);
-
- scale.set(1.f, -1.f, -1.f);
- scale.mul(size);
- mat_normal.rotate(scale, v[2]);
-
- scale.set(-1.f, 1.f, -1.f);
- scale.mul(size);
- mat_normal.rotate(scale, v[3]);
+ for (U32 i = 0; i < 6; ++i)
+ {
+ v[i].setSelectWithMask(mask[i], min, max);
+ }
+
+ LLVector4a tv[8];
+ //transform bounding box into drawable space
+ for (U32 i = 0; i < 8; ++i)
+ {
+ mat_vert.affineTransform(v[i], tv[i]);
+ }
+
+ //find bounding box
LLVector4a& newMin = mExtents[0];
LLVector4a& newMax = mExtents[1];
-
- newMin = newMax = center;
-
- llassert(less_than_max_mag(center));
-
- for (U32 i = 0; i < 4; i++)
- {
- LLVector4a delta;
- delta.setAbs(v[i]);
- LLVector4a min;
- min.setSub(center, delta);
- LLVector4a max;
- max.setAdd(center, delta);
- newMin.setMin(newMin,min);
- newMax.setMax(newMax,max);
+ newMin = newMax = tv[0];
- llassert(less_than_max_mag(newMin));
- llassert(less_than_max_mag(newMax));
+ for (U32 i = 1; i < 8; ++i)
+ {
+ newMin.setMin(newMin, tv[i]);
+ newMax.setMax(newMax, tv[i]);
}
if (!mDrawablep->isActive())
- {
+ { // Shift position for region
LLVector4a offset;
offset.load3(mDrawablep->getRegion()->getOriginAgent().mV);
newMin.add(offset);
newMax.add(offset);
-
- llassert(less_than_max_mag(newMin));
- llassert(less_than_max_mag(newMax));
}
- t.setAdd(newMin, newMax);
+ LLVector4a t;
+ t.setAdd(newMin,newMax);
t.mul(0.5f);
- llassert(less_than_max_mag(t));
-
- //VECTORIZE THIS
mCenterLocal.set(t.getF32ptr());
-
- llassert(less_than_max_mag(newMin));
- llassert(less_than_max_mag(newMax));
t.setSub(newMax,newMin);
mBoundingSphereRadius = t.getLength3().getF32()*0.5f;
diff --git a/indra/newview/llface.h b/indra/newview/llface.h
index 0687544d53..763634a3ab 100755
--- a/indra/newview/llface.h
+++ b/indra/newview/llface.h
@@ -195,7 +195,7 @@ public:
void setSize(S32 numVertices, S32 num_indices = 0, bool align = false);
BOOL genVolumeBBoxes(const LLVolume &volume, S32 f,
- const LLMatrix4& mat, const LLMatrix3& inv_trans_mat, BOOL global_volume = FALSE);
+ const LLMatrix4& mat, BOOL global_volume = FALSE);
void init(LLDrawable* drawablep, LLViewerObject* objp);
void destroy();
diff --git a/indra/newview/llfavoritesbar.cpp b/indra/newview/llfavoritesbar.cpp
index 6d90667194..b35ef3a961 100755
--- a/indra/newview/llfavoritesbar.cpp
+++ b/indra/newview/llfavoritesbar.cpp
@@ -400,6 +400,8 @@ LLFavoritesBarCtrl::LLFavoritesBarCtrl(const LLFavoritesBarCtrl::Params& p)
mMoreTextBox->setClickedCallback(boost::bind(&LLFavoritesBarCtrl::showDropDownMenu, this));
addChild(mMoreTextBox);
+ mDropDownItemsCount = 0;
+
LLTextBox::Params label_param(p.label);
mBarLabel = LLUICtrlFactory::create<LLTextBox> (label_param);
addChild(mBarLabel);
@@ -820,11 +822,13 @@ void LLFavoritesBarCtrl::updateButtons()
}
// Update overflow menu
LLToggleableMenu* overflow_menu = static_cast <LLToggleableMenu*> (mOverflowMenuHandle.get());
- if (overflow_menu && overflow_menu->getVisible())
+ if (overflow_menu && overflow_menu->getVisible() && (overflow_menu->getItemCount() != mDropDownItemsCount))
{
overflow_menu->setVisible(FALSE);
if (mUpdateDropDownItems)
+ {
showDropDownMenu();
+ }
}
}
else
@@ -940,6 +944,7 @@ void LLFavoritesBarCtrl::showDropDownMenu()
menu->updateParent(LLMenuGL::sMenuContainer);
menu->setButtonRect(mMoreTextBox->getRect(), this);
positionAndShowMenu(menu);
+ mDropDownItemsCount = menu->getItemCount();
}
}
diff --git a/indra/newview/llfavoritesbar.h b/indra/newview/llfavoritesbar.h
index f06e9b9b64..211d3c4ce3 100755
--- a/indra/newview/llfavoritesbar.h
+++ b/indra/newview/llfavoritesbar.h
@@ -101,6 +101,7 @@ protected:
LLUUID mFavoriteFolderId;
const LLFontGL *mFont;
S32 mFirstDropDownItem;
+ S32 mDropDownItemsCount;
bool mUpdateDropDownItems;
bool mRestoreOverflowMenu;
diff --git a/indra/newview/llfloateravatarpicker.cpp b/indra/newview/llfloateravatarpicker.cpp
index 113aa9a8f2..c0afb72cff 100755
--- a/indra/newview/llfloateravatarpicker.cpp
+++ b/indra/newview/llfloateravatarpicker.cpp
@@ -513,6 +513,7 @@ void LLFloaterAvatarPicker::find()
url += "/";
}
url += "?page_size=100&names=";
+ std::replace(text.begin(), text.end(), '.', ' ');
url += LLURI::escape(text);
llinfos << "avatar picker " << url << llendl;
LLHTTPClient::get(url, new LLAvatarPickerResponder(mQueryID, getKey().asString()));
@@ -748,7 +749,12 @@ void LLFloaterAvatarPicker::processResponse(const LLUUID& query_id, const LLSD&
{
getChildView("ok_btn")->setEnabled(true);
search_results->setEnabled(true);
- search_results->selectFirstItem();
+ search_results->sortByColumnIndex(1, TRUE);
+ std::string text = getChild<LLUICtrl>("Edit")->getValue().asString();
+ if (!search_results->selectItemByLabel(text, TRUE, 1))
+ {
+ search_results->selectFirstItem();
+ }
onList();
search_results->setFocus(TRUE);
}
diff --git a/indra/newview/llfloaterconversationpreview.cpp b/indra/newview/llfloaterconversationpreview.cpp
index a3d715530d..b570de14aa 100755
--- a/indra/newview/llfloaterconversationpreview.cpp
+++ b/indra/newview/llfloaterconversationpreview.cpp
@@ -50,6 +50,7 @@ LLFloaterConversationPreview::LLFloaterConversationPreview(const LLSD& session_i
BOOL LLFloaterConversationPreview::postBuild()
{
mChatHistory = getChild<LLChatHistory>("chat_history");
+ LLLoadHistoryThread::setLoadEndSignal(boost::bind(&LLFloaterConversationPreview::SetPages, this, _1, _2));
const LLConversation* conv = LLConversationLog::instance().getConversation(mSessionID);
std::string name;
@@ -70,7 +71,7 @@ BOOL LLFloaterConversationPreview::postBuild()
name = LLTrans::getString("NearbyChatTitle");
file = "chat";
}
-
+ mChatHistoryFileName = file;
LLStringUtil::format_map_t args;
args["[NAME]"] = name;
std::string title = getString("Title", args);
@@ -80,23 +81,46 @@ BOOL LLFloaterConversationPreview::postBuild()
load_params["load_all_history"] = true;
load_params["cut_off_todays_date"] = false;
- LLLogChat::loadChatHistory(file, mMessages, load_params);
- mCurrentPage = mMessages.size() / mPageSize;
+ LLSD loading;
+ loading[LL_IM_TEXT] = LLTrans::getString("loading_chat_logs");
+ mMessages.push_back(loading);
mPageSpinner = getChild<LLSpinCtrl>("history_page_spin");
mPageSpinner->setCommitCallback(boost::bind(&LLFloaterConversationPreview::onMoreHistoryBtnClick, this));
mPageSpinner->setMinValue(1);
- mPageSpinner->setMaxValue(mCurrentPage + 1);
- mPageSpinner->set(mCurrentPage + 1);
-
- std::string total_page_num = llformat("/ %d", mCurrentPage + 1);
- getChild<LLTextBox>("page_num_label")->setValue(total_page_num);
-
+ mPageSpinner->set(1);
+ mPageSpinner->setEnabled(false);
+ mChatHistoryLoaded = false;
+ LLLogChat::startChatHistoryThread(file, load_params);
return LLFloater::postBuild();
}
+void LLFloaterConversationPreview::SetPages(std::list<LLSD>& messages, const std::string& file_name)
+{
+ if(file_name == mChatHistoryFileName)
+ {
+ mMessages = messages;
+
+
+ mCurrentPage = mMessages.size() / mPageSize;
+ mPageSpinner->setEnabled(true);
+ mPageSpinner->setMaxValue(mCurrentPage+1);
+ mPageSpinner->set(mCurrentPage+1);
+
+ std::string total_page_num = llformat("/ %d", mCurrentPage+1);
+ getChild<LLTextBox>("page_num_label")->setValue(total_page_num);
+ mChatHistoryLoaded = true;
+
+ }
+
+}
void LLFloaterConversationPreview::draw()
{
+ if(mChatHistoryLoaded)
+ {
+ showHistory();
+ mChatHistoryLoaded = false;
+ }
LLFloater::draw();
}
@@ -128,6 +152,11 @@ void LLFloaterConversationPreview::showHistory()
for (int msg_num = 0; (iter != mMessages.end() && msg_num < mPageSize); ++iter, ++msg_num)
{
+ if (iter->size() == 0)
+ {
+ continue;
+ }
+
LLSD msg = *iter;
LLUUID from_id = LLUUID::null;
diff --git a/indra/newview/llfloaterconversationpreview.h b/indra/newview/llfloaterconversationpreview.h
index b17ae84b63..389f3dfd09 100755
--- a/indra/newview/llfloaterconversationpreview.h
+++ b/indra/newview/llfloaterconversationpreview.h
@@ -42,6 +42,7 @@ public:
virtual ~LLFloaterConversationPreview(){};
virtual BOOL postBuild();
+ void SetPages(std::list<LLSD>& messages,const std::string& file_name);
virtual void draw();
virtual void onOpen(const LLSD& key);
@@ -59,6 +60,8 @@ private:
std::list<LLSD> mMessages;
std::string mAccountName;
std::string mCompleteName;
+ std::string mChatHistoryFileName;
+ bool mChatHistoryLoaded;
};
#endif /* LLFLOATERCONVERSATIONPREVIEW_H_ */
diff --git a/indra/newview/llfloaterimcontainer.cpp b/indra/newview/llfloaterimcontainer.cpp
index b40789db9c..4591b80ac4 100755
--- a/indra/newview/llfloaterimcontainer.cpp
+++ b/indra/newview/llfloaterimcontainer.cpp
@@ -47,6 +47,7 @@
#include "llfloaterpreference.h"
#include "llimview.h"
#include "llnotificationsutil.h"
+#include "lltoolbarview.h"
#include "lltransientfloatermgr.h"
#include "llviewercontrol.h"
#include "llconversationview.h"
@@ -54,6 +55,7 @@
#include "llworld.h"
#include "llsdserialize.h"
#include "llviewerobjectlist.h"
+#include "boost/foreach.hpp"
//
// LLFloaterIMContainer
@@ -63,7 +65,8 @@ LLFloaterIMContainer::LLFloaterIMContainer(const LLSD& seed, const Params& param
mExpandCollapseBtn(NULL),
mConversationsRoot(NULL),
mConversationsEventStream("ConversationsEvents"),
- mInitialized(false)
+ mInitialized(false),
+ mIsFirstLaunch(true)
{
mEnableCallbackRegistrar.add("IMFloaterContainer.Check", boost::bind(&LLFloaterIMContainer::isActionChecked, this, _2));
mCommitCallbackRegistrar.add("IMFloaterContainer.Action", boost::bind(&LLFloaterIMContainer::onCustomAction, this, _2));
@@ -113,6 +116,10 @@ void LLFloaterIMContainer::sessionAdded(const LLUUID& session_id, const std::str
void LLFloaterIMContainer::sessionActivated(const LLUUID& session_id, const std::string& name, const LLUUID& other_participant_id)
{
+ if(!isInVisibleChain())
+ {
+ setVisibleAndFrontmost(false);
+ }
selectConversationPair(session_id, true);
collapseMessagesPane(false);
}
@@ -204,6 +211,7 @@ BOOL LLFloaterIMContainer::postBuild()
// a scroller for folder view
LLRect scroller_view_rect = mConversationsListPanel->getRect();
scroller_view_rect.translate(-scroller_view_rect.mLeft, -scroller_view_rect.mBottom);
+ scroller_view_rect.mBottom += getChild<LLLayoutStack>("conversations_pane_buttons_stack")->getRect().getHeight();
LLScrollContainer::Params scroller_params(LLUICtrlFactory::getDefaultParams<LLFolderViewScrollContainer>());
scroller_params.rect(scroller_view_rect);
@@ -221,7 +229,8 @@ BOOL LLFloaterIMContainer::postBuild()
mExpandCollapseBtn->setClickedCallback(boost::bind(&LLFloaterIMContainer::onExpandCollapseButtonClicked, this));
mStubCollapseBtn = getChild<LLButton>("stub_collapse_btn");
mStubCollapseBtn->setClickedCallback(boost::bind(&LLFloaterIMContainer::onStubCollapseButtonClicked, this));
- getChild<LLButton>("speak_btn")->setClickedCallback(boost::bind(&LLFloaterIMContainer::onSpeakButtonClicked, this));
+ mSpeakBtn = getChild<LLButton>("speak_btn");
+ mSpeakBtn->setClickedCallback(boost::bind(&LLFloaterIMContainer::onSpeakButtonClicked, this));
childSetAction("add_btn", boost::bind(&LLFloaterIMContainer::onAddButtonClicked, this));
@@ -258,7 +267,6 @@ BOOL LLFloaterIMContainer::postBuild()
void LLFloaterIMContainer::onOpen(const LLSD& key)
{
LLMultiFloater::onOpen(key);
- openNearbyChat();
reSelectConversation();
assignResizeLimits();
}
@@ -593,6 +601,7 @@ void LLFloaterIMContainer::setMinimized(BOOL b)
//Switching from minimized to un-minimized
if(was_minimized && !b)
{
+ gToolBarView->flashCommand(LLCommandId("chat"), false);
LLFloaterIMSessionTab* session_floater = LLFloaterIMSessionTab::findConversation(mSelectedSession);
if(session_floater && !session_floater->isTornOff())
@@ -621,7 +630,6 @@ void LLFloaterIMContainer::setVisible(BOOL visible)
LLFloaterReg::toggleInstanceOrBringToFront(name);
selectConversationPair(LLUUID(NULL), false, false);
}
- openNearbyChat();
flashConversationItemWidget(mSelectedSession,false);
LLFloaterIMSessionTab* session_floater = LLFloaterIMSessionTab::findConversation(mSelectedSession);
@@ -651,7 +659,11 @@ void LLFloaterIMContainer::setVisible(BOOL visible)
LLConversationViewSession* widget = dynamic_cast<LLConversationViewSession*>(widget_it->second);
if (widget)
{
- widget->setVisibleIfDetached(visible);
+ LLFloater* session_floater = widget->getSessionFloater();
+ if (session_floater != nearby_chat)
+ {
+ widget->setVisibleIfDetached(visible);
+ }
}
}
@@ -659,10 +671,37 @@ void LLFloaterIMContainer::setVisible(BOOL visible)
LLMultiFloater::setVisible(visible);
}
+void LLFloaterIMContainer::getDetachedConversationFloaters(floater_list_t& floaters)
+{
+ typedef conversations_widgets_map::value_type conv_pair;
+ BOOST_FOREACH(conv_pair item, mConversationsWidgets)
+ {
+ LLConversationViewSession* widget = dynamic_cast<LLConversationViewSession*>(item.second);
+ if (widget)
+ {
+ LLFloater* session_floater = widget->getSessionFloater();
+ if (session_floater && session_floater->isDetachedAndNotMinimized())
+ {
+ floaters.push_back(session_floater);
+ }
+ }
+ }
+}
+
void LLFloaterIMContainer::setVisibleAndFrontmost(BOOL take_focus, const LLSD& key)
{
LLMultiFloater::setVisibleAndFrontmost(take_focus, key);
- selectConversationPair(getSelectedSession(), false, take_focus);
+ // Do not select "Nearby Chat" conversation, since it will bring its window to front
+ // Only select other sessions
+ if (!getSelectedSession().isNull())
+ {
+ selectConversationPair(getSelectedSession(), false, take_focus);
+ }
+ if (mInitialized && mIsFirstLaunch)
+ {
+ collapseMessagesPane(gSavedPerAccountSettings.getBOOL("ConversationsMessagePaneCollapsed"));
+ mIsFirstLaunch = false;
+ }
}
void LLFloaterIMContainer::updateResizeLimits()
@@ -779,13 +818,6 @@ void LLFloaterIMContainer::reshapeFloaterAndSetResizeLimits(bool collapse, S32 d
setCanMinimize(at_least_one_panel_is_expanded);
assignResizeLimits();
-
- // force set correct size for the title after show/hide minimize button
- LLRect cur_rect = getRect();
- LLRect force_rect = cur_rect;
- force_rect.mRight = cur_rect.mRight + 1;
- setRect(force_rect);
- setRect(cur_rect);
}
void LLFloaterIMContainer::assignResizeLimits()
@@ -793,15 +825,12 @@ void LLFloaterIMContainer::assignResizeLimits()
bool is_conv_pane_expanded = !mConversationsPane->isCollapsed();
bool is_msg_pane_expanded = !mMessagesPane->isCollapsed();
- // With two panels visible number of borders is three, because the borders
- // between the panels are merged into one
- S32 number_of_visible_borders = llmin((is_conv_pane_expanded? 2 : 0) + (is_msg_pane_expanded? 2 : 0), 3);
- S32 summary_width_of_visible_borders = number_of_visible_borders * LLPANEL_BORDER_WIDTH;
- S32 conv_pane_target_width = is_conv_pane_expanded?
- (is_msg_pane_expanded?
- mConversationsPane->getRect().getWidth()
- : mConversationsPane->getExpandedMinDim())
- : mConversationsPane->getMinDim();
+ S32 summary_width_of_visible_borders = (is_msg_pane_expanded ? mConversationsStack->getPanelSpacing() : 0) + 1;
+
+ S32 conv_pane_target_width = is_conv_pane_expanded
+ ? ( is_msg_pane_expanded?mConversationsPane->getRect().getWidth():mConversationsPane->getExpandedMinDim() )
+ : mConversationsPane->getMinDim();
+
S32 msg_pane_min_width = is_msg_pane_expanded ? mMessagesPane->getExpandedMinDim() : 0;
S32 new_min_width = conv_pane_target_width + msg_pane_min_width + summary_width_of_visible_borders;
@@ -961,11 +990,11 @@ void LLFloaterIMContainer::setSortOrder(const LLConversationSort& order)
conversation_floater->setSortOrder(order);
}
}
-
+
gSavedSettings.setU32("ConversationSortOrder", (U32)order);
}
-void LLFloaterIMContainer::getSelectedUUIDs(uuid_vec_t& selected_uuids)
+void LLFloaterIMContainer::getSelectedUUIDs(uuid_vec_t& selected_uuids, bool participant_uuids/* = true*/)
{
const std::set<LLFolderViewItem*> selectedItems = mConversationsRoot->getSelectionList();
@@ -978,7 +1007,7 @@ void LLFloaterIMContainer::getSelectedUUIDs(uuid_vec_t& selected_uuids)
conversationItem = static_cast<LLConversationItem *>((*it)->getViewModelItem());
//When a one-on-one conversation exists, retrieve the participant id from the conversation floater
- if(conversationItem->getType() == LLConversationItem::CONV_SESSION_1_ON_1)
+ if(conversationItem->getType() == LLConversationItem::CONV_SESSION_1_ON_1 && participant_uuids)
{
LLFloaterIMSession * conversation_floaterp = LLFloaterIMSession::findInstance(conversationItem->getUUID());
LLUUID participant_id = conversation_floaterp->getOtherParticipantUUID();
@@ -1133,6 +1162,11 @@ void LLFloaterIMContainer::doToSelectedConversation(const std::string& command,
{
LLFloater::onClickClose(conversationFloater);
}
+ else if("close_selected_conversations" == command)
+ {
+ getSelectedUUIDs(selectedIDS,false);
+ closeSelectedConversations(selectedIDS);
+ }
else if("open_voice_conversation" == command)
{
gIMMgr->startCall(conversationItem->getUUID());
@@ -1143,7 +1177,7 @@ void LLFloaterIMContainer::doToSelectedConversation(const std::string& command,
}
else if("chat_history" == command)
{
- if (selectedIDS.size() > 0)
+ if (selectedIDS.size() > 0)
{
LLAvatarActions::viewChatHistory(selectedIDS.front());
}
@@ -1156,6 +1190,17 @@ void LLFloaterIMContainer::doToSelectedConversation(const std::string& command,
}
}
}
+ //if there is no LLFloaterIMSession* instance for selected conversation it might be Nearby chat
+ else
+ {
+ if(conversationItem->getType() == LLConversationItem::CONV_SESSION_NEARBY)
+ {
+ if("chat_history" == command)
+ {
+ LLFloaterReg::showInstance("preview_conversation", LLSD(LLUUID::null), true);
+ }
+ }
+ }
}
void LLFloaterIMContainer::doToSelected(const LLSD& userdata)
@@ -1185,7 +1230,7 @@ void LLFloaterIMContainer::doToSelectedGroup(const LLSD& userdata)
if (action == "group_profile")
{
- LLGroupActions::show(mSelectedSession);
+ LLGroupActions::show(mSelectedSession);
}
else if (action == "activate_group")
{
@@ -1211,7 +1256,19 @@ bool LLFloaterIMContainer::enableContextMenuItem(const LLSD& userdata)
//Enable Chat history item for ad-hoc and group conversations
if ("can_chat_history" == item && uuids.size() > 0)
{
- return LLLogChat::isTranscriptExist(uuids.front());
+ //Disable menu item if selected participant is user agent
+ if(uuids.front() != gAgentID)
+ {
+ if (getCurSelectedViewModelItem()->getType() == LLConversationItem::CONV_SESSION_NEARBY)
+ {
+ return LLLogChat::isNearbyTranscriptExist();
+ }
+ else
+ {
+ bool is_group = (getCurSelectedViewModelItem()->getType() == LLConversationItem::CONV_SESSION_GROUP);
+ return LLLogChat::isTranscriptExist(uuids.front(),is_group);
+ }
+ }
}
// If nothing is selected(and selected item is not group chat), everything needs to be disabled
@@ -1886,13 +1943,6 @@ void LLFloaterIMContainer::openNearbyChat()
}
}
-void LLFloaterIMContainer::onNearbyChatClosed()
-{
- // If nearby chat is the only remaining conversation and it is closed, close whole conversation floater as well
- if (mConversationsItems.size() == 1)
- closeFloater();
-}
-
void LLFloaterIMContainer::reSelectConversation()
{
LLFloaterIMSessionTab* session_floater = LLFloaterIMSessionTab::getConversation(mSelectedSession);
@@ -1904,7 +1954,6 @@ void LLFloaterIMContainer::reSelectConversation()
void LLFloaterIMContainer::updateSpeakBtnState()
{
- LLButton* mSpeakBtn = getChild<LLButton>("speak_btn");
mSpeakBtn->setToggleState(LLVoiceClient::getInstance()->getUserPTTState());
mSpeakBtn->setEnabled(LLAgent::isActionAllowed("speak"));
}
@@ -1925,6 +1974,17 @@ void LLFloaterIMContainer::flashConversationItemWidget(const LLUUID& session_id,
}
}
+void LLFloaterIMContainer::highlightConversationItemWidget(const LLUUID& session_id, bool is_highlighted)
+{
+ //Finds the conversation line item to highlight using the session_id
+ LLConversationViewSession * widget = dynamic_cast<LLConversationViewSession *>(get_ptr_in_map(mConversationsWidgets,session_id));
+
+ if (widget)
+ {
+ widget->setHighlightState(is_highlighted);
+ }
+}
+
bool LLFloaterIMContainer::isScrolledOutOfSight(LLConversationViewSession* conversation_item_widget)
{
llassert(conversation_item_widget != NULL);
@@ -1940,23 +2000,28 @@ bool LLFloaterIMContainer::isScrolledOutOfSight(LLConversationViewSession* conve
BOOL LLFloaterIMContainer::handleKeyHere(KEY key, MASK mask )
{
+ BOOL handled = FALSE;
+
if(mask == MASK_ALT)
{
if (KEY_RETURN == key )
{
expandConversation();
+ handled = TRUE;
}
if ((KEY_DOWN == key ) || (KEY_RIGHT == key))
{
selectNextorPreviousConversation(true);
+ handled = TRUE;
}
if ((KEY_UP == key) || (KEY_LEFT == key))
{
selectNextorPreviousConversation(false);
+ handled = TRUE;
}
}
- return TRUE;
+ return handled;
}
bool LLFloaterIMContainer::selectAdjacentConversation(bool focus_selected)
@@ -2013,7 +2078,22 @@ void LLFloaterIMContainer::expandConversation()
}
}
-void LLFloaterIMContainer::closeFloater(bool app_quitting/* = false*/)
+// By default, if torn off session is currently frontmost, LLFloater::isFrontmost() will return FALSE, which can lead to some bugs
+// So LLFloater::isFrontmost() is overriden here to check both selected session and the IM floater itself
+// Exclude "Nearby Chat" session from the check, as "Nearby Chat" window and "Conversations" floater can be brought
+// to front independently
+/*virtual*/
+BOOL LLFloaterIMContainer::isFrontmost()
+{
+ LLFloaterIMSessionTab* selected_session = LLFloaterIMSessionTab::getConversation(mSelectedSession);
+ LLFloaterIMNearbyChat* nearby_chat = LLFloaterReg::findTypedInstance<LLFloaterIMNearbyChat>("nearby_chat");
+ return (selected_session && selected_session->isFrontmost() && (selected_session != nearby_chat))
+ || LLFloater::isFrontmost();
+}
+
+// For conversations, closeFloater() (linked to Ctrl-W) does not actually close the floater but the active conversation.
+// This is intentional so it doesn't confuse the user. onClickCloseBtn() closes the whole floater.
+void LLFloaterIMContainer::onClickCloseBtn()
{
// Always unminimize before trying to close.
// Most of the time the user will never see this state.
@@ -2022,7 +2102,80 @@ void LLFloaterIMContainer::closeFloater(bool app_quitting/* = false*/)
LLMultiFloater::setMinimized(FALSE);
}
- LLFloater::closeFloater(app_quitting);
+ LLFloater::closeFloater();
+}
+
+void LLFloaterIMContainer::closeHostedFloater()
+{
+ onClickCloseBtn();
+}
+
+void LLFloaterIMContainer::closeAllConversations()
+{
+ LLDynamicArray<LLUUID> ids;
+ for (conversations_items_map::iterator it_session = mConversationsItems.begin(); it_session != mConversationsItems.end(); it_session++)
+ {
+ LLUUID session_id = it_session->first;
+ if (session_id != LLUUID())
+ {
+ ids.push_back(session_id);
+ }
+ }
+
+ for (LLDynamicArray<LLUUID>::const_iterator it = ids.begin(); it != ids.end(); ++it)
+ {
+ LLFloaterIMSession *conversationFloater = LLFloaterIMSession::findInstance(*it);
+ LLFloater::onClickClose(conversationFloater);
+ }
+}
+
+void LLFloaterIMContainer::closeSelectedConversations(const uuid_vec_t& ids)
+{
+ for (uuid_vec_t::const_iterator it = ids.begin(); it != ids.end(); ++it)
+ {
+ //We don't need to close Nearby chat, so skip it
+ if (*it != LLUUID())
+ {
+ LLFloaterIMSession *conversationFloater = LLFloaterIMSession::findInstance(*it);
+ if(conversationFloater)
+ {
+ LLFloater::onClickClose(conversationFloater);
+ }
+ }
+ }
+}
+void LLFloaterIMContainer::closeFloater(bool app_quitting/* = false*/)
+{
+ if(app_quitting)
+ {
+ closeAllConversations();
+ onClickCloseBtn();
+ }
+ else
+ {
+ // Check for currently active session
+ LLUUID session_id = getSelectedSession();
+ // If current session is Nearby Chat or there is only one session remaining, close the floater
+ if (mConversationsItems.size() == 1 || session_id == LLUUID() || app_quitting)
+ {
+ onClickCloseBtn();
+ }
+ else
+ {
+ // Otherwise, close current conversation
+ LLFloaterIMSessionTab* active_conversation = LLFloaterIMSessionTab::getConversation(session_id);
+ if (active_conversation)
+ {
+ active_conversation->closeFloater();
+ }
+ }
+ }
+}
+
+void LLFloaterIMContainer::handleReshape(const LLRect& rect, bool by_user)
+{
+ LLMultiFloater::handleReshape(rect, by_user);
+ storeRectControl();
}
// EOF
diff --git a/indra/newview/llfloaterimcontainer.h b/indra/newview/llfloaterimcontainer.h
index e39d20ec35..36da457cac 100755
--- a/indra/newview/llfloaterimcontainer.h
+++ b/indra/newview/llfloaterimcontainer.h
@@ -63,6 +63,8 @@ public:
/*virtual*/ void setVisible(BOOL visible);
/*virtual*/ void setVisibleAndFrontmost(BOOL take_focus=TRUE, const LLSD& key = LLSD());
/*virtual*/ void updateResizeLimits();
+ /*virtual*/ void handleReshape(const LLRect& rect, bool by_user);
+
void onCloseFloater(LLUUID& id);
/*virtual*/ void addFloater(LLFloater* floaterp,
@@ -105,8 +107,6 @@ public:
LLConversationItem* getSessionModel(const LLUUID& session_id) { return get_ptr_in_map(mConversationsItems,session_id); }
LLConversationSort& getSortOrder() { return mConversationViewModel.getSorter(); }
- void onNearbyChatClosed();
-
// Handling of lists of participants is public so to be common with llfloatersessiontab
// *TODO : Find a better place for this.
bool checkContextMenuItem(const std::string& item, uuid_vec_t& selectedIDS);
@@ -116,6 +116,10 @@ public:
void assignResizeLimits();
virtual BOOL handleKeyHere(KEY key, MASK mask );
/*virtual*/ void closeFloater(bool app_quitting = false);
+ void closeAllConversations();
+ void closeSelectedConversations(const uuid_vec_t& ids);
+ /*virtual*/ BOOL isFrontmost();
+
private:
typedef std::map<LLUUID,LLFloater*> avatarID_panel_map_t;
@@ -130,6 +134,8 @@ private:
void onStubCollapseButtonClicked();
void processParticipantsStyleUpdate();
void onSpeakButtonClicked();
+ /*virtual*/ void onClickCloseBtn();
+ /*virtual*/ void closeHostedFloater();
void collapseConversationsPane(bool collapse, bool save_is_allowed=true);
@@ -144,7 +150,7 @@ private:
void setSortOrderParticipants(const LLConversationFilter::ESortOrderType order);
void setSortOrder(const LLConversationSort& order);
- void getSelectedUUIDs(uuid_vec_t& selected_uuids);
+ void getSelectedUUIDs(uuid_vec_t& selected_uuids, bool participant_uuids = true);
const LLConversationItem * getCurSelectedViewModelItem();
void getParticipantUUIDs(uuid_vec_t& selected_uuids);
void doToSelected(const LLSD& userdata);
@@ -169,6 +175,7 @@ private:
LLButton* mExpandCollapseBtn;
LLButton* mStubCollapseBtn;
+ LLButton* mSpeakBtn;
LLPanel* mStubPanel;
LLTextBox* mStubTextBox;
LLLayoutPanel* mMessagesPane;
@@ -176,6 +183,7 @@ private:
LLLayoutStack* mConversationsStack;
bool mInitialized;
+ bool mIsFirstLaunch;
LLUUID mSelectedSession;
std::string mGeneralTitle;
@@ -190,9 +198,12 @@ public:
void updateSpeakBtnState();
static bool isConversationLoggingAllowed();
void flashConversationItemWidget(const LLUUID& session_id, bool is_flashes);
+ void highlightConversationItemWidget(const LLUUID& session_id, bool is_highlighted);
bool isScrolledOutOfSight(LLConversationViewSession* conversation_item_widget);
boost::signals2::connection mMicroChangedSignal;
S32 getConversationListItemSize() { return mConversationsWidgets.size(); }
+ typedef std::list<LLFloater*> floater_list_t;
+ void getDetachedConversationFloaters(floater_list_t& floaters);
private:
LLConversationViewSession* createConversationItemWidget(LLConversationItem* item);
diff --git a/indra/newview/llfloaterimnearbychat.cpp b/indra/newview/llfloaterimnearbychat.cpp
index 30320fc5d7..3d77ea4f0b 100755
--- a/indra/newview/llfloaterimnearbychat.cpp
+++ b/indra/newview/llfloaterimnearbychat.cpp
@@ -138,19 +138,28 @@ BOOL LLFloaterIMNearbyChat::postBuild()
// virtual
void LLFloaterIMNearbyChat::closeHostedFloater()
{
- // Should check how many conversations are ongoing. Close all if 1 only (the Nearby Chat), select next one otherwise
+ // If detached from conversations window close anyway
+ if (!getHost())
+ {
+ setVisible(FALSE);
+ }
+
+ // Should check how many conversations are ongoing. Select next to "Nearby Chat" in case there are some other besides.
+ // Close conversations window in case "Nearby Chat" is attached and the only conversation
LLFloaterIMContainer* floater_container = LLFloaterIMContainer::getInstance();
if (floater_container->getConversationListItemSize() == 1)
{
- floater_container->closeFloater();
+ if (getHost())
+ {
+ floater_container->closeFloater();
+ }
}
else
{
if (!getHost())
{
- setVisible(FALSE);
+ floater_container->selectNextConversationByID(LLUUID());
}
- floater_container->selectNextConversationByID(LLUUID());
}
}
@@ -262,7 +271,7 @@ void LLFloaterIMNearbyChat::setVisibleAndFrontmost(BOOL take_focus, const LLSD&
{
LLFloaterIMSessionTab::setVisibleAndFrontmost(take_focus, key);
- if(!isTornOff() && matchesKey(key))
+ if(matchesKey(key))
{
LLFloaterIMContainer::getInstance()->selectConversationPair(mSessionID, true, take_focus);
}
@@ -296,7 +305,6 @@ void LLFloaterIMNearbyChat::onClose(bool app_quitting)
{
// Override LLFloaterIMSessionTab::onClose() so that Nearby Chat is not removed from the conversation floater
LLFloaterIMSessionTab::restoreFloater();
- onClickCloseBtn();
}
// virtual
@@ -306,13 +314,7 @@ void LLFloaterIMNearbyChat::onClickCloseBtn()
{
return;
}
- LLFloaterIMSessionTab::onTearOffClicked();
-
- LLFloaterIMContainer *im_box = LLFloaterIMContainer::findInstance();
- if (im_box)
- {
- im_box->onNearbyChatClosed();
- }
+ closeHostedFloater();
}
void LLFloaterIMNearbyChat::onChatFontChange(LLFontGL* fontp)
@@ -350,11 +352,17 @@ bool LLFloaterIMNearbyChat::isChatVisible() const
void LLFloaterIMNearbyChat::showHistory()
{
openFloater();
+ LLFloaterIMContainer::getInstance()->selectConversation(LLUUID(NULL));
+
if(!isMessagePaneExpanded())
{
restoreFloater();
setFocus(true);
}
+ else
+ {
+ LLFloaterIMContainer::getInstance()->setFocus(TRUE);
+ }
setResizeLimits(getMinWidth(), EXPANDED_MIN_HEIGHT);
}
@@ -568,7 +576,10 @@ void LLFloaterIMNearbyChat::sendChat( EChatType type )
if (0 == channel)
{
// discard returned "found" boolean
- LLGestureMgr::instance().triggerAndReviseString(utf8text, &utf8_revised_text);
+ if(!LLGestureMgr::instance().triggerAndReviseString(utf8text, &utf8_revised_text))
+ {
+ utf8_revised_text = utf8text;
+ }
}
else
{
@@ -636,10 +647,7 @@ void LLFloaterIMNearbyChat::addMessage(const LLChat& chat,bool archive,const LLS
void LLFloaterIMNearbyChat::onChatBoxCommit()
{
- if (mInputEditor->getText().length() > 0)
- {
- sendChat(CHAT_TYPE_NORMAL);
- }
+ sendChat(CHAT_TYPE_NORMAL);
gAgent.stopTyping();
}
diff --git a/indra/newview/llfloaterimnearbychathandler.cpp b/indra/newview/llfloaterimnearbychathandler.cpp
index 9ce5e12897..cc00b6fd10 100755
--- a/indra/newview/llfloaterimnearbychathandler.cpp
+++ b/indra/newview/llfloaterimnearbychathandler.cpp
@@ -606,6 +606,7 @@ void LLFloaterIMNearbyChatHandler::processChat(const LLChat& chat_msg,
//Don't show nearby toast, if conversation is visible and selected
if ((nearby_chat->hasFocus()) ||
+ (LLFloater::isVisible(nearby_chat) && nearby_chat->isTornOff() && !nearby_chat->isMinimized()) ||
((im_box->getSelectedSession().isNull() &&
((LLFloater::isVisible(im_box) && !im_box->isMinimized() && im_box->isFrontmost())
|| (LLFloater::isVisible(nearby_chat) && !nearby_chat->isMinimized() && nearby_chat->isFrontmost())))))
diff --git a/indra/newview/llfloaterimsession.cpp b/indra/newview/llfloaterimsession.cpp
index 8ec85e1160..5cb9df5625 100755
--- a/indra/newview/llfloaterimsession.cpp
+++ b/indra/newview/llfloaterimsession.cpp
@@ -109,18 +109,6 @@ void LLFloaterIMSession::refresh()
void LLFloaterIMSession::onTearOffClicked()
{
LLFloaterIMSessionTab::onTearOffClicked();
-
- if(mIsP2PChat)
- {
- if(isTornOff())
- {
- mSpeakingIndicator->setSpeakerId(mOtherParticipantUUID, mSessionID);
- }
- else
- {
- mSpeakingIndicator->setSpeakerId(LLUUID::null);
- }
- }
}
// virtual
@@ -442,8 +430,11 @@ void LLFloaterIMSession::addSessionParticipants(const uuid_vec_t& uuids)
}
else
{
- // remember whom we have invited, to notify others later, when the invited ones actually join
- mInvitedParticipants.insert(mInvitedParticipants.end(), uuids.begin(), uuids.end());
+ if(findInstance(mSessionID))
+ {
+ // remember whom we have invited, to notify others later, when the invited ones actually join
+ mInvitedParticipants.insert(mInvitedParticipants.end(), uuids.begin(), uuids.end());
+ }
inviteToSession(uuids);
}
@@ -469,13 +460,18 @@ void LLFloaterIMSession::addP2PSessionParticipants(const LLSD& notification, con
temp_ids.insert(temp_ids.end(), uuids.begin(), uuids.end());
// then we can close the current session
- onClose(false);
+ if(findInstance(mSessionID))
+ {
+ onClose(false);
+
+ // remember whom we have invited, to notify others later, when the invited ones actually join
+ mInvitedParticipants.insert(mInvitedParticipants.end(), uuids.begin(), uuids.end());
+ }
// we start a new session so reset the initialization flag
mSessionInitialized = false;
- // remember whom we have invited, to notify others later, when the invited ones actually join
- mInvitedParticipants.insert(mInvitedParticipants.end(), uuids.begin(), uuids.end());
+
// Start a new ad hoc voice call if we invite new participants to a P2P call,
// or start a text chat otherwise.
diff --git a/indra/newview/llfloaterimsessiontab.cpp b/indra/newview/llfloaterimsessiontab.cpp
index ce6e639305..0ccfdb9a7b 100755
--- a/indra/newview/llfloaterimsessiontab.cpp
+++ b/indra/newview/llfloaterimsessiontab.cpp
@@ -55,7 +55,6 @@ LLFloaterIMSessionTab::LLFloaterIMSessionTab(const LLSD& session_id)
, mSessionID(session_id.asUUID())
, mConversationsRoot(NULL)
, mScroller(NULL)
- , mSpeakingIndicator(NULL)
, mChatHistory(NULL)
, mInputEditor(NULL)
, mInputEditorPad(0)
@@ -212,7 +211,7 @@ void LLFloaterIMSessionTab::assignResizeLimits()
mRightPartPanel->setIgnoreReshape(is_participants_pane_collapsed);
S32 participants_pane_target_width = is_participants_pane_collapsed?
- 0 : (mParticipantListPanel->getRect().getWidth() + LLPANEL_BORDER_WIDTH);
+ 0 : (mParticipantListPanel->getRect().getWidth() + mParticipantListAndHistoryStack->getPanelSpacing());
S32 new_min_width = participants_pane_target_width + mRightPartPanel->getExpandedMinDim() + mFloaterExtraWidth;
@@ -241,7 +240,10 @@ BOOL LLFloaterIMSessionTab::postBuild()
mTearOffBtn->setCommitCallback(boost::bind(&LLFloaterIMSessionTab::onTearOffClicked, this));
mGearBtn = getChild<LLButton>("gear_btn");
-
+ mAddBtn = getChild<LLButton>("add_btn");
+ mVoiceButton = getChild<LLButton>("voice_call_btn");
+ mTranslationCheckBox = getChild<LLUICtrl>("translate_chat_checkbox_lp");
+
mParticipantListPanel = getChild<LLLayoutPanel>("speakers_list_panel");
mRightPartPanel = getChild<LLLayoutPanel>("right_part_holder");
@@ -256,8 +258,6 @@ BOOL LLFloaterIMSessionTab::postBuild()
scroller_params.rect(scroller_view_rect);
mScroller = LLUICtrlFactory::create<LLFolderViewScrollContainer>(scroller_params);
mScroller->setFollowsAll();
-
- mSpeakingIndicator = getChild<LLOutputMonitorCtrl>("speaking_indicator");
// Insert that scroller into the panel widgets hierarchy
mParticipantListPanel->addChild(mScroller);
@@ -270,6 +270,7 @@ BOOL LLFloaterIMSessionTab::postBuild()
mInputPanels = getChild<LLLayoutStack>("input_panels");
mInputEditor->setTextExpandedCallback(boost::bind(&LLFloaterIMSessionTab::reshapeChatLayoutPanel, this));
+ mInputEditor->setMouseUpCallback(boost::bind(&LLFloaterIMSessionTab::onInputEditorClicked, this));
mInputEditor->setCommitOnFocusLost( FALSE );
mInputEditor->setPassDelete(TRUE);
mInputEditor->setFont(LLViewerChat::getChatFont());
@@ -372,7 +373,7 @@ void LLFloaterIMSessionTab::draw()
void LLFloaterIMSessionTab::enableDisableCallBtn()
{
- getChildView("voice_call_btn")->setEnabled(
+ mVoiceButton->setEnabled(
mSessionID.notNull()
&& mSession
&& mSession->mSessionInitialized
@@ -399,6 +400,16 @@ void LLFloaterIMSessionTab::onFocusLost()
LLTransientDockableFloater::onFocusLost();
}
+void LLFloaterIMSessionTab::onInputEditorClicked()
+{
+ LLFloaterIMContainer* im_box = LLFloaterIMContainer::findInstance();
+ if (im_box)
+ {
+ im_box->flashConversationItemWidget(mSessionID,false);
+ }
+ gToolBarView->flashCommand(LLCommandId("chat"), false);
+}
+
std::string LLFloaterIMSessionTab::appendTime()
{
time_t utc_time;
@@ -758,7 +769,7 @@ void LLFloaterIMSessionTab::reshapeChatLayoutPanel()
void LLFloaterIMSessionTab::showTranslationCheckbox(BOOL show)
{
- getChild<LLUICtrl>("translate_chat_checkbox_lp")->setVisible(mIsNearbyChat? show : FALSE);
+ mTranslationCheckBox->setVisible(mIsNearbyChat && show);
}
// static
@@ -805,15 +816,10 @@ void LLFloaterIMSessionTab::reloadEmptyFloaters()
void LLFloaterIMSessionTab::updateCallBtnState(bool callIsActive)
{
- LLButton* voiceButton = getChild<LLButton>("voice_call_btn");
- voiceButton->setImageOverlay(
- callIsActive? getString("call_btn_stop") : getString("call_btn_start"));
-
- voiceButton->setToolTip(
- callIsActive? getString("end_call_button_tooltip") : getString("start_call_button_tooltip"));
+ mVoiceButton->setImageOverlay(callIsActive? getString("call_btn_stop") : getString("call_btn_start"));
+ mVoiceButton->setToolTip(callIsActive? getString("end_call_button_tooltip") : getString("start_call_button_tooltip"));
enableDisableCallBtn();
-
}
void LLFloaterIMSessionTab::onSlide(LLFloaterIMSessionTab* self)
@@ -898,6 +904,7 @@ void LLFloaterIMSessionTab::restoreFloater()
mExpandCollapseLineBtn->setImageOverlay(getString("expandline_icon"));
setMessagePaneExpanded(true);
saveCollapsedState();
+ mInputEditor->enableSingleLineMode(false);
enableResizeCtrls(true, true, true);
}
}
@@ -953,8 +960,8 @@ void LLFloaterIMSessionTab::updateGearBtn()
if(prevVisibility != mGearBtn->getVisible())
{
LLRect gear_btn_rect = mGearBtn->getRect();
- LLRect add_btn_rect = getChild<LLButton>("add_btn")->getRect();
- LLRect call_btn_rect = getChild<LLButton>("voice_call_btn")->getRect();
+ LLRect add_btn_rect = mAddBtn->getRect();
+ LLRect call_btn_rect = mVoiceButton->getRect();
S32 gap_width = call_btn_rect.mLeft - add_btn_rect.mRight;
S32 right_shift = gear_btn_rect.getWidth() + gap_width;
if(mGearBtn->getVisible())
@@ -968,24 +975,24 @@ void LLFloaterIMSessionTab::updateGearBtn()
add_btn_rect.translate(-right_shift,0);
call_btn_rect.translate(-right_shift,0);
}
- getChild<LLButton>("add_btn")->setRect(add_btn_rect);
- getChild<LLButton>("voice_call_btn")->setRect(call_btn_rect);
+ mAddBtn->setRect(add_btn_rect);
+ mVoiceButton->setRect(call_btn_rect);
}
}
void LLFloaterIMSessionTab::initBtns()
{
LLRect gear_btn_rect = mGearBtn->getRect();
- LLRect add_btn_rect = getChild<LLButton>("add_btn")->getRect();
- LLRect call_btn_rect = getChild<LLButton>("voice_call_btn")->getRect();
+ LLRect add_btn_rect = mAddBtn->getRect();
+ LLRect call_btn_rect = mVoiceButton->getRect();
S32 gap_width = call_btn_rect.mLeft - add_btn_rect.mRight;
S32 right_shift = gear_btn_rect.getWidth() + gap_width;
add_btn_rect.translate(-right_shift,0);
call_btn_rect.translate(-right_shift,0);
- getChild<LLButton>("add_btn")->setRect(add_btn_rect);
- getChild<LLButton>("voice_call_btn")->setRect(call_btn_rect);
+ mAddBtn->setRect(add_btn_rect);
+ mVoiceButton->setRect(call_btn_rect);
}
// static
@@ -1083,21 +1090,26 @@ void LLFloaterIMSessionTab::saveCollapsedState()
}
BOOL LLFloaterIMSessionTab::handleKeyHere(KEY key, MASK mask )
{
+ BOOL handled = FALSE;
+
if(mask == MASK_ALT)
{
LLFloaterIMContainer* floater_container = LLFloaterIMContainer::getInstance();
if (KEY_RETURN == key && !isTornOff())
{
floater_container->expandConversation();
+ handled = TRUE;
}
if ((KEY_UP == key) || (KEY_LEFT == key))
{
floater_container->selectNextorPreviousConversation(false);
+ handled = TRUE;
}
if ((KEY_DOWN == key ) || (KEY_RIGHT == key))
{
floater_container->selectNextorPreviousConversation(true);
+ handled = TRUE;
}
}
- return TRUE;
+ return handled;
}
diff --git a/indra/newview/llfloaterimsessiontab.h b/indra/newview/llfloaterimsessiontab.h
index 302d5a8066..e7b05a584b 100755
--- a/indra/newview/llfloaterimsessiontab.h
+++ b/indra/newview/llfloaterimsessiontab.h
@@ -171,8 +171,7 @@ protected:
LLFolderView* mConversationsRoot;
LLScrollContainer* mScroller;
- LLOutputMonitorCtrl* mSpeakingIndicator;
- LLChatHistory* mChatHistory;
+ LLChatHistory* mChatHistory;
LLChatEntry* mInputEditor;
LLLayoutPanel * mChatLayoutPanel;
LLLayoutStack * mInputPanels;
@@ -182,6 +181,9 @@ protected:
LLButton* mTearOffBtn;
LLButton* mCloseBtn;
LLButton* mGearBtn;
+ LLButton* mAddBtn;
+ LLButton* mVoiceButton;
+ LLUICtrl* mTranslationCheckBox;
private:
// Handling selection and contextual menu
@@ -201,6 +203,8 @@ private:
*/
void reshapeChatLayoutPanel();
+ void onInputEditorClicked();
+
bool checkIfTornOff();
bool mIsHostAttached;
bool mHasVisibleBeenInitialized;
diff --git a/indra/newview/llfloaterland.cpp b/indra/newview/llfloaterland.cpp
index 8290494c22..d4355007c1 100755
--- a/indra/newview/llfloaterland.cpp
+++ b/indra/newview/llfloaterland.cpp
@@ -2118,7 +2118,7 @@ void LLPanelLandOptions::refreshSearch()
bool can_change =
LLViewerParcelMgr::isParcelModifiableByAgent(
- parcel, GP_LAND_CHANGE_IDENTITY)
+ parcel, GP_LAND_FIND_PLACES)
&& region
&& !(region->getRegionFlag(REGION_FLAGS_BLOCK_PARCEL_SEARCH));
diff --git a/indra/newview/llfloaterpreference.cpp b/indra/newview/llfloaterpreference.cpp
index 55b03986d0..4ebe813be6 100755
--- a/indra/newview/llfloaterpreference.cpp
+++ b/indra/newview/llfloaterpreference.cpp
@@ -452,6 +452,7 @@ BOOL LLFloaterPreference::postBuild()
getChild<LLComboBox>("ConferenceIMOptions")->setCommitCallback(boost::bind(&LLFloaterPreference::onNotificationsChange, this,"ConferenceIMOptions"));
getChild<LLComboBox>("GroupChatOptions")->setCommitCallback(boost::bind(&LLFloaterPreference::onNotificationsChange, this,"GroupChatOptions"));
getChild<LLComboBox>("NearbyChatOptions")->setCommitCallback(boost::bind(&LLFloaterPreference::onNotificationsChange, this,"NearbyChatOptions"));
+ getChild<LLComboBox>("ObjectIMOptions")->setCommitCallback(boost::bind(&LLFloaterPreference::onNotificationsChange, this,"ObjectIMOptions"));
// if floater is opened before login set default localized do not disturb message
if (LLStartUp::getStartupState() < STATE_STARTED)
@@ -721,6 +722,7 @@ void LLFloaterPreference::onOpen(const LLSD& key)
onNotificationsChange("ConferenceIMOptions");
onNotificationsChange("GroupChatOptions");
onNotificationsChange("NearbyChatOptions");
+ onNotificationsChange("ObjectIMOptions");
LLPanelLogin::setAlwaysRefresh(true);
refresh();
@@ -928,7 +930,7 @@ void LLFloaterPreference::onNotificationsChange(const std::string& OptionName)
bool show_notifications_alert = true;
for (notifications_map::iterator it_notification = mNotificationOptions.begin(); it_notification != mNotificationOptions.end(); it_notification++)
{
- if(it_notification->second != "None")
+ if(it_notification->second != "No action")
{
show_notifications_alert = false;
break;
diff --git a/indra/newview/llfolderviewmodelinventory.cpp b/indra/newview/llfolderviewmodelinventory.cpp
index 586965e5a0..c28657dbcd 100755
--- a/indra/newview/llfolderviewmodelinventory.cpp
+++ b/indra/newview/llfolderviewmodelinventory.cpp
@@ -74,6 +74,7 @@ void LLFolderViewModelInventory::sort( LLFolderViewFolder* folder )
it != end_it;
++it)
{
+ // Recursive call to sort() on child (CHUI-849)
LLFolderViewFolder* child_folderp = *it;
sort(child_folderp);
@@ -129,12 +130,12 @@ void LLFolderViewModelItemInventory::requestSort()
void LLFolderViewModelItemInventory::setPassedFilter(bool passed, S32 filter_generation, std::string::size_type string_offset, std::string::size_type string_size)
{
LLFolderViewModelItemCommon::setPassedFilter(passed, filter_generation, string_offset, string_size);
-
- bool passed_filter_before = mPrevPassedAllFilters;
+ bool before = mPrevPassedAllFilters;
mPrevPassedAllFilters = passedFilter(filter_generation);
- if (passed_filter_before != mPrevPassedAllFilters)
+ if (before != mPrevPassedAllFilters)
{
+ // Need to rearrange the folder if the filtered state of the item changed
LLFolderViewFolder* parent_folder = mFolderViewItem->getParentFolder();
if (parent_folder)
{
@@ -150,11 +151,11 @@ bool LLFolderViewModelItemInventory::filterChildItem( LLFolderViewModelItem* ite
bool continue_filtering = true;
if (item->getLastFilterGeneration() < filter_generation)
{
- // recursive application of the filter for child items
+ // Recursive application of the filter for child items (CHUI-849)
continue_filtering = item->filter( filter );
}
- // track latest generation to pass any child items, for each folder up to root
+ // Update latest generation to pass filter in parent and propagate up to root
if (item->passedFilter())
{
LLFolderViewModelItemInventory* view_model = this;
@@ -174,53 +175,61 @@ bool LLFolderViewModelItemInventory::filter( LLFolderViewFilter& filter)
const S32 filter_generation = filter.getCurrentGeneration();
const S32 must_pass_generation = filter.getFirstRequiredGeneration();
- if (getLastFilterGeneration() >= must_pass_generation
+ if (getLastFilterGeneration() >= must_pass_generation
&& getLastFolderFilterGeneration() >= must_pass_generation
&& !passedFilter(must_pass_generation))
{
// failed to pass an earlier filter that was a subset of the current one
- // go ahead and flag this item as done
+ // go ahead and flag this item as not pass
setPassedFilter(false, filter_generation);
setPassedFolderFilter(false, filter_generation);
return true;
}
- const bool passed_filter_folder = (getInventoryType() == LLInventoryType::IT_CATEGORY)
- ? filter.checkFolder(this)
- : true;
+ // *TODO : Revise the logic for fast pass on less restrictive filter case
+ /*
+ const S32 sufficient_pass_generation = filter.getFirstSuccessGeneration();
+ if (getLastFilterGeneration() >= sufficient_pass_generation
+ && getLastFolderFilterGeneration() >= sufficient_pass_generation
+ && passedFilter(sufficient_pass_generation))
+ {
+ // passed an earlier filter that was a superset of the current one
+ // go ahead and flag this item as pass
+ setPassedFilter(true, filter_generation);
+ setPassedFolderFilter(true, filter_generation);
+ return true;
+ }
+ */
+
+ const bool passed_filter_folder = (getInventoryType() == LLInventoryType::IT_CATEGORY) ? filter.checkFolder(this) : true;
setPassedFolderFilter(passed_filter_folder, filter_generation);
- if(!mChildren.empty()
+ bool continue_filtering = true;
+
+ if (!mChildren.empty()
&& (getLastFilterGeneration() < must_pass_generation // haven't checked descendants against minimum required generation to pass
- || descendantsPassedFilter(must_pass_generation))) // or at least one descendant has passed the minimum requirement
+ || descendantsPassedFilter(must_pass_generation))) // or at least one descendant has passed the minimum requirement
{
// now query children
- for (child_list_t::iterator iter = mChildren.begin(), end_iter = mChildren.end();
- iter != end_iter && filter.getFilterCount() > 0;
- ++iter)
+ for (child_list_t::iterator iter = mChildren.begin(), end_iter = mChildren.end(); iter != end_iter; ++iter)
{
- if (!filterChildItem((*iter), filter))
+ continue_filtering = filterChildItem((*iter), filter);
+ if (!continue_filtering)
{
break;
}
}
}
- // if we didn't use all filter iterations
- // that means we filtered all of our descendants
- // so filter ourselves now
- if (filter.getFilterCount() > 0)
+ // If we didn't use all the filter time that means we filtered all of our descendants so we can filter ourselves now
+ if (continue_filtering)
{
- filter.decrementFilterCount();
-
+ // This is where filter check on the item done (CHUI-849)
const bool passed_filter = filter.check(this);
setPassedFilter(passed_filter, filter_generation, filter.getStringMatchOffset(this), filter.getFilterStringSize());
- return true;
- }
- else
- {
- return false;
+ continue_filtering = !filter.isTimedOut();
}
+ return continue_filtering;
}
LLFolderViewModelInventory* LLInventoryPanel::getFolderViewModel()
@@ -307,8 +316,8 @@ bool LLInventorySort::operator()(const LLFolderViewModelItemInventory* const& a,
}
}
-LLFolderViewModelItemInventory::LLFolderViewModelItemInventory( class LLFolderViewModelInventory& root_view_model )
- : LLFolderViewModelItemCommon(root_view_model),
- mPrevPassedAllFilters(false)
+LLFolderViewModelItemInventory::LLFolderViewModelItemInventory( class LLFolderViewModelInventory& root_view_model ) :
+ LLFolderViewModelItemCommon(root_view_model),
+ mPrevPassedAllFilters(false)
{
}
diff --git a/indra/newview/llfolderviewmodelinventory.h b/indra/newview/llfolderviewmodelinventory.h
index 890d03d1c9..9dcfdfa185 100755
--- a/indra/newview/llfolderviewmodelinventory.h
+++ b/indra/newview/llfolderviewmodelinventory.h
@@ -59,9 +59,8 @@ public:
virtual BOOL startDrag(EDragAndDropType* type, LLUUID* id) const = 0;
virtual LLToolDragAndDrop::ESource getDragSource() const = 0;
-
protected:
- bool mPrevPassedAllFilters;
+ bool mPrevPassedAllFilters;
};
class LLInventorySort
diff --git a/indra/newview/llgroupactions.cpp b/indra/newview/llgroupactions.cpp
index a0f2918bd7..302d21c2e4 100755
--- a/indra/newview/llgroupactions.cpp
+++ b/indra/newview/llgroupactions.cpp
@@ -116,6 +116,80 @@ public:
};
LLGroupHandler gGroupHandler;
+// This object represents a pending request for specified group member information
+// which is needed to check whether avatar can leave group
+class LLFetchGroupMemberData : public LLGroupMgrObserver
+{
+public:
+ LLFetchGroupMemberData(const LLUUID& group_id) :
+ mGroupId(group_id),
+ mRequestProcessed(false),
+ LLGroupMgrObserver(group_id)
+ {
+ llinfos << "Sending new group member request for group_id: "<< group_id << llendl;
+ LLGroupMgr* mgr = LLGroupMgr::getInstance();
+ // register ourselves as an observer
+ mgr->addObserver(this);
+ // send a request
+ mgr->sendGroupPropertiesRequest(group_id);
+ mgr->sendCapGroupMembersRequest(group_id);
+ }
+
+ ~LLFetchGroupMemberData()
+ {
+ if (!mRequestProcessed)
+ {
+ // Request is pending
+ llwarns << "Destroying pending group member request for group_id: "
+ << mGroupId << llendl;
+ }
+ // Remove ourselves as an observer
+ LLGroupMgr::getInstance()->removeObserver(this);
+ }
+
+ void changed(LLGroupChange gc)
+ {
+ if (gc == GC_MEMBER_DATA && !mRequestProcessed)
+ {
+ LLGroupMgrGroupData* gdatap = LLGroupMgr::getInstance()->getGroupData(mGroupId);
+ if (!gdatap)
+ {
+ llwarns << "LLGroupMgr::getInstance()->getGroupData() was NULL" << llendl;
+ }
+ else if (!gdatap->isMemberDataComplete())
+ {
+ llwarns << "LLGroupMgr::getInstance()->getGroupData()->isMemberDataComplete() was FALSE" << llendl;
+ }
+ else
+ {
+ processGroupData();
+ mRequestProcessed = true;
+ }
+ }
+ }
+
+ LLUUID getGroupId() { return mGroupId; }
+ virtual void processGroupData() = 0;
+protected:
+ LLUUID mGroupId;
+private:
+ bool mRequestProcessed;
+};
+
+class LLFetchLeaveGroupData: public LLFetchGroupMemberData
+{
+public:
+ LLFetchLeaveGroupData(const LLUUID& group_id)
+ : LLFetchGroupMemberData(group_id)
+ {}
+ void processGroupData()
+ {
+ LLGroupActions::processLeaveGroupDataResponse(mGroupId);
+ }
+};
+
+LLFetchLeaveGroupData* gFetchLeaveGroupData = NULL;
+
// static
void LLGroupActions::search()
{
@@ -208,23 +282,52 @@ bool LLGroupActions::onJoinGroup(const LLSD& notification, const LLSD& response)
void LLGroupActions::leave(const LLUUID& group_id)
{
if (group_id.isNull())
+ {
return;
+ }
- S32 count = gAgent.mGroups.count();
- S32 i;
- for (i = 0; i < count; ++i)
+ LLGroupData group_data;
+ if (gAgent.getGroupData(group_id, group_data))
{
- if(gAgent.mGroups.get(i).mID == group_id)
- break;
+ LLGroupMgrGroupData* gdatap = LLGroupMgr::getInstance()->getGroupData(group_id);
+ if (!gdatap || !gdatap->isMemberDataComplete())
+ {
+ if (gFetchLeaveGroupData != NULL)
+ {
+ delete gFetchLeaveGroupData;
+ gFetchLeaveGroupData = NULL;
+ }
+ gFetchLeaveGroupData = new LLFetchLeaveGroupData(group_id);
+ }
+ else
+ {
+ processLeaveGroupDataResponse(group_id);
+ }
}
- if (i < count)
+}
+
+//static
+void LLGroupActions::processLeaveGroupDataResponse(const LLUUID group_id)
+{
+ LLGroupMgrGroupData* gdatap = LLGroupMgr::getInstance()->getGroupData(group_id);
+ LLUUID agent_id = gAgent.getID();
+ LLGroupMgrGroupData::member_list_t::iterator mit = gdatap->mMembers.find(agent_id);
+ //get the member data for the group
+ if ( mit != gdatap->mMembers.end() )
{
- LLSD args;
- args["GROUP"] = gAgent.mGroups.get(i).mName;
- LLSD payload;
- payload["group_id"] = group_id;
- LLNotificationsUtil::add("GroupLeaveConfirmMember", args, payload, onLeaveGroup);
+ LLGroupMemberData* member_data = (*mit).second;
+
+ if ( member_data && member_data->isOwner() && gdatap->mMemberCount == 1)
+ {
+ LLNotificationsUtil::add("OwnerCannotLeaveGroup");
+ return;
+ }
}
+ LLSD args;
+ args["GROUP"] = gdatap->mName;
+ LLSD payload;
+ payload["group_id"] = group_id;
+ LLNotificationsUtil::add("GroupLeaveConfirmMember", args, payload, onLeaveGroup);
}
// static
diff --git a/indra/newview/llgroupactions.h b/indra/newview/llgroupactions.h
index 3f9852f194..afc4686dd7 100755
--- a/indra/newview/llgroupactions.h
+++ b/indra/newview/llgroupactions.h
@@ -114,6 +114,14 @@ public:
private:
static bool onJoinGroup(const LLSD& notification, const LLSD& response);
static bool onLeaveGroup(const LLSD& notification, const LLSD& response);
+
+ /**
+ * This function is called by LLFetchLeaveGroupData upon receiving a response to a group
+ * members data request.
+ */
+ static void processLeaveGroupDataResponse(const LLUUID group_id);
+
+ friend class LLFetchLeaveGroupData;
};
#endif // LL_LLGROUPACTIONS_H
diff --git a/indra/newview/llimview.cpp b/indra/newview/llimview.cpp
index 3b72ad3cd9..9e23755d73 100755
--- a/indra/newview/llimview.cpp
+++ b/indra/newview/llimview.cpp
@@ -103,6 +103,7 @@ BOOL LLSessionTimeoutTimer::tick()
}
+void notify_of_message(const LLSD& msg, bool is_dnd_msg);
void process_dnd_im(const LLSD& notification)
{
@@ -129,15 +130,9 @@ void process_dnd_im(const LLSD& notification)
fromID,
false,
false); //will need slight refactor to retrieve whether offline message or not (assume online for now)
+ }
- LLFloaterIMContainer* im_box = LLFloaterReg::getTypedInstance<LLFloaterIMContainer>("im_container");
-
- if (im_box)
- {
- im_box->flashConversationItemWidget(sessionID, true);
- }
-
- }
+ notify_of_message(data, true);
}
@@ -158,75 +153,106 @@ static void on_avatar_name_cache_toast(const LLUUID& agent_id,
LLNotificationsUtil::add("IMToast", args, args, boost::bind(&LLFloaterIMContainer::showConversation, LLFloaterIMContainer::getInstance(), msg["session_id"].asUUID()));
}
-void on_new_message(const LLSD& msg)
+void notify_of_message(const LLSD& msg, bool is_dnd_msg)
{
- std::string user_preferences;
- LLUUID participant_id = msg["from_id"].asUUID();
- LLUUID session_id = msg["session_id"].asUUID();
- LLIMModel::LLIMSession* session = LLIMModel::instance().findIMSession(session_id);
-
- // do not show notification which goes from agent
- if (gAgent.getID() == participant_id)
- {
- return;
- }
+ std::string user_preferences;
+ LLUUID participant_id = msg[is_dnd_msg ? "FROM_ID" : "from_id"].asUUID();
+ LLUUID session_id = msg[is_dnd_msg ? "SESSION_ID" : "session_id"].asUUID();
+ LLIMModel::LLIMSession* session = LLIMModel::instance().findIMSession(session_id);
- // determine state of conversations floater
- enum {CLOSED, NOT_ON_TOP, ON_TOP, ON_TOP_AND_ITEM_IS_SELECTED} conversations_floater_status;
+ // do not show notification which goes from agent
+ if (gAgent.getID() == participant_id)
+ {
+ return;
+ }
+ // determine state of conversations floater
+ enum {CLOSED, NOT_ON_TOP, ON_TOP, ON_TOP_AND_ITEM_IS_SELECTED} conversations_floater_status;
- LLFloaterIMContainer* im_box = LLFloaterReg::getTypedInstance<LLFloaterIMContainer>("im_container");
+ LLFloaterIMContainer* im_box = LLFloaterReg::getTypedInstance<LLFloaterIMContainer>("im_container");
LLFloaterIMSessionTab* session_floater = LLFloaterIMSessionTab::getConversation(session_id);
-
+ bool store_dnd_message = false; // flag storage of a dnd message
+ bool is_session_focused = session_floater->isTornOff() && session_floater->hasFocus();
if (!LLFloater::isVisible(im_box) || im_box->isMinimized())
{
conversations_floater_status = CLOSED;
}
else if (!im_box->hasFocus() &&
- !(session_floater && LLFloater::isVisible(session_floater)
- && !session_floater->isMinimized() && session_floater->hasFocus()))
+ !(session_floater && LLFloater::isVisible(session_floater)
+ && !session_floater->isMinimized() && session_floater->hasFocus()))
{
conversations_floater_status = NOT_ON_TOP;
}
else if (im_box->getSelectedSession() != session_id)
{
conversations_floater_status = ON_TOP;
- }
+ }
else
{
conversations_floater_status = ON_TOP_AND_ITEM_IS_SELECTED;
}
- // determine user prefs for this session
- if (session_id.isNull())
- {
- user_preferences = gSavedSettings.getString("NotificationNearbyChatOptions");
- }
- else if(session->isP2PSessionType())
- {
- if (LLAvatarTracker::instance().isBuddy(participant_id))
- {
- user_preferences = gSavedSettings.getString("NotificationFriendIMOptions");
- }
- else
- {
- user_preferences = gSavedSettings.getString("NotificationNonFriendIMOptions");
- }
- }
- else if(session->isAdHocSessionType())
- {
- user_preferences = gSavedSettings.getString("NotificationConferenceIMOptions");
- }
- else if(session->isGroupSessionType())
- {
- user_preferences = gSavedSettings.getString("NotificationGroupChatOptions");
- }
+ // determine user prefs for this session
+ if (session_id.isNull())
+ {
+ if (msg["source_type"].asInteger() == CHAT_SOURCE_OBJECT)
+ {
+ user_preferences = gSavedSettings.getString("NotificationObjectIMOptions");
+ if (!gAgent.isDoNotDisturb() && (gSavedSettings.getBOOL("PlaySoundObjectIM") == TRUE))
+ {
+ make_ui_sound("UISndNewIncomingIMSession");
+ }
+ }
+ else
+ {
+ user_preferences = gSavedSettings.getString("NotificationNearbyChatOptions");
+ if (!gAgent.isDoNotDisturb() && (gSavedSettings.getBOOL("PlaySoundNearbyChatIM") == TRUE))
+ {
+ make_ui_sound("UISndNewIncomingIMSession");
+ }
+ }
+ }
+ else if(session->isP2PSessionType())
+ {
+ if (LLAvatarTracker::instance().isBuddy(participant_id))
+ {
+ user_preferences = gSavedSettings.getString("NotificationFriendIMOptions");
+ if (!gAgent.isDoNotDisturb() && (gSavedSettings.getBOOL("PlaySoundFriendIM") == TRUE))
+ {
+ make_ui_sound("UISndNewIncomingIMSession");
+ }
+ }
+ else
+ {
+ user_preferences = gSavedSettings.getString("NotificationNonFriendIMOptions");
+ if (!gAgent.isDoNotDisturb() && (gSavedSettings.getBOOL("PlaySoundNonFriendIM") == TRUE))
+ {
+ make_ui_sound("UISndNewIncomingIMSession");
+ }
+ }
+ }
+ else if(session->isAdHocSessionType())
+ {
+ user_preferences = gSavedSettings.getString("NotificationConferenceIMOptions");
+ if (!gAgent.isDoNotDisturb() && (gSavedSettings.getBOOL("PlaySoundConferenceIM") == TRUE))
+ {
+ make_ui_sound("UISndNewIncomingIMSession");
+ }
+ }
+ else if(session->isGroupSessionType())
+ {
+ user_preferences = gSavedSettings.getString("NotificationGroupChatOptions");
+ if (!gAgent.isDoNotDisturb() && (gSavedSettings.getBOOL("PlaySoundGroupChatIM") == TRUE))
+ {
+ make_ui_sound("UISndNewIncomingIMSession");
+ }
+ }
- // actions:
+ // actions:
// 0. nothing - exit
- if (("none" == user_preferences ||
+ if (("noaction" == user_preferences ||
ON_TOP_AND_ITEM_IS_SELECTED == conversations_floater_status)
&& session_floater->isMessagePaneExpanded())
{
@@ -261,57 +287,103 @@ void on_new_message(const LLSD& msg)
}
}
}
- else
- {
- //If in DND mode, allow notification to be stored so upon DND exit
- //useMostItrusiveIMNotification will be called to notify user a message exists
- if(session_id.notNull()
- && participant_id.notNull()
- && !session_floater->isShown())
- {
- LLAvatarNameCache::get(participant_id, boost::bind(&on_avatar_name_cache_toast, _1, _2, msg));
- }
- }
- }
+ else
+ {
+ store_dnd_message = true;
+ }
- // 2. Flash line item
- if ("openconversations" == user_preferences
- || ON_TOP == conversations_floater_status
- || ("toast" == user_preferences && ON_TOP != conversations_floater_status)
- || ("flash" == user_preferences && CLOSED == conversations_floater_status))
- {
- if(!LLMuteList::getInstance()->isMuted(participant_id))
- {
- im_box->flashConversationItemWidget(session_id, true);
- }
- }
+ }
- // 3. Flash FUI button
- if (("toast" == user_preferences || "flash" == user_preferences) &&
- (CLOSED == conversations_floater_status
- || NOT_ON_TOP == conversations_floater_status))
- {
- if(!LLMuteList::getInstance()->isMuted(participant_id)
- && !gAgent.isDoNotDisturb())
- {
- gToolBarView->flashCommand(LLCommandId("chat"), true);
- }
- }
+ // 2. Flash line item
+ if ("openconversations" == user_preferences
+ || ON_TOP == conversations_floater_status
+ || ("toast" == user_preferences && ON_TOP != conversations_floater_status)
+ || ("flash" == user_preferences && (CLOSED == conversations_floater_status
+ || NOT_ON_TOP == conversations_floater_status))
+ || is_dnd_msg)
+ {
+ if(!LLMuteList::getInstance()->isMuted(participant_id))
+ {
+ if(gAgent.isDoNotDisturb())
+ {
+ store_dnd_message = true;
+ }
+ else
+ {
+ if (is_dnd_msg && (ON_TOP == conversations_floater_status ||
+ NOT_ON_TOP == conversations_floater_status ||
+ CLOSED == conversations_floater_status))
+ {
+ im_box->highlightConversationItemWidget(session_id, true);
+ }
+ else
+ {
+ im_box->flashConversationItemWidget(session_id, true);
+ }
+ }
+ }
+ }
- // 4. Toast
- if ((("toast" == user_preferences) &&
- (CLOSED == conversations_floater_status
- || NOT_ON_TOP == conversations_floater_status))
- || !session_floater->isMessagePaneExpanded())
+ // 3. Flash FUI button
+ if (("toast" == user_preferences || "flash" == user_preferences) &&
+ (CLOSED == conversations_floater_status
+ || NOT_ON_TOP == conversations_floater_status)
+ && !is_session_focused
+ && !is_dnd_msg) //prevent flashing FUI button because the conversation floater will have already opened
+ {
+ if(!LLMuteList::getInstance()->isMuted(participant_id))
+ {
+ if(!gAgent.isDoNotDisturb())
+ {
+ gToolBarView->flashCommand(LLCommandId("chat"), true, im_box->isMinimized());
+ }
+ else
+ {
+ store_dnd_message = true;
+ }
+ }
+ }
- {
- //Show IM toasts (upper right toasts)
- // Skip toasting for system messages and for nearby chat
- if(session_id.notNull() && participant_id.notNull())
- {
- LLAvatarNameCache::get(participant_id, boost::bind(&on_avatar_name_cache_toast, _1, _2, msg));
- }
- }
+ // 4. Toast
+ if ((("toast" == user_preferences) &&
+ (ON_TOP_AND_ITEM_IS_SELECTED != conversations_floater_status) &&
+ (!session_floater->isTornOff() || !LLFloater::isVisible(session_floater)))
+ || !session_floater->isMessagePaneExpanded())
+
+ {
+ //Show IM toasts (upper right toasts)
+ // Skip toasting for system messages and for nearby chat
+ if(session_id.notNull() && participant_id.notNull())
+ {
+ if(!is_dnd_msg)
+ {
+ if(gAgent.isDoNotDisturb())
+ {
+ store_dnd_message = true;
+ }
+ else
+ {
+ LLAvatarNameCache::get(participant_id, boost::bind(&on_avatar_name_cache_toast, _1, _2, msg));
+ }
+ }
+ }
+ }
+ if (store_dnd_message)
+ {
+ // If in DND mode, allow notification to be stored so upon DND exit
+ // the user will be notified with some limitations (see 'is_dnd_msg' flag checks)
+ if(session_id.notNull()
+ && participant_id.notNull()
+ && !session_floater->isShown())
+ {
+ LLAvatarNameCache::get(participant_id, boost::bind(&on_avatar_name_cache_toast, _1, _2, msg));
+ }
+ }
+}
+
+void on_new_message(const LLSD& msg)
+{
+ notify_of_message(msg, false);
}
LLIMModel::LLIMModel()
@@ -2597,6 +2669,13 @@ void LLIMMgr::addMessage(
fixed_session_name = session_name;
name_is_setted = true;
}
+ bool skip_message = false;
+ if (gSavedSettings.getBOOL("VoiceCallsFriendsOnly"))
+ {
+ // Evaluate if we need to skip this message when that setting is true (default is false)
+ skip_message = (LLAvatarTracker::instance().getBuddyInfo(other_participant_id) == NULL); // Skip non friends...
+ skip_message &= !(other_participant_id == gAgentID); // You are your best friend... Don't skip yourself
+ }
bool new_session = !hasSession(new_session_id);
if (new_session)
@@ -2608,6 +2687,12 @@ void LLIMMgr::addMessage(
}
LLIMModel::getInstance()->newSession(new_session_id, fixed_session_name, dialog, other_participant_id, false, is_offline_msg);
+ LLIMModel::LLIMSession* session = LLIMModel::instance().findIMSession(new_session_id);
+ skip_message &= !session->isGroupSessionType(); // Do not skip group chats...
+ if(skip_message)
+ {
+ gIMMgr->leaveSession(new_session_id);
+ }
// When we get a new IM, and if you are a god, display a bit
// of information about the source. This is to help liaisons
// when answering questions.
@@ -2648,23 +2733,13 @@ void LLIMMgr::addMessage(
}
}
- bool skip_message = false;
- if (gSavedSettings.getBOOL("VoiceCallsFriendsOnly"))
- {
- // Evaluate if we need to skip this message when that setting is true (default is false)
- LLIMModel::LLIMSession* session = LLIMModel::instance().findIMSession(new_session_id);
- skip_message = (LLAvatarTracker::instance().getBuddyInfo(other_participant_id) == NULL); // Skip non friends...
- skip_message &= !session->isGroupSessionType(); // Do not skip group chats...
- skip_message &= !(other_participant_id == gAgentID); // You are your best friend... Don't skip yourself
- }
-
if (!LLMuteList::getInstance()->isMuted(other_participant_id, LLMute::flagTextChat) && !skip_message)
{
LLIMModel::instance().addMessage(new_session_id, from, other_participant_id, msg);
}
// Open conversation floater if offline messages are present
- if (is_offline_msg)
+ if (is_offline_msg && !skip_message)
{
LLFloaterReg::showInstance("im_container");
LLFloaterReg::getTypedInstance<LLFloaterIMContainer>("im_container")->
@@ -2971,10 +3046,9 @@ void LLIMMgr::inviteToSession(
{
bool isRejectGroupCall = (gSavedSettings.getBOOL("VoiceCallsRejectGroup") && (notify_box_type == "VoiceInviteGroup"));
bool isRejectNonFriendCall = (gSavedSettings.getBOOL("VoiceCallsFriendsOnly") && (LLAvatarTracker::instance().getBuddyInfo(caller_id) == NULL));
- bool isRejectDoNotDisturb = (gAgent.isDoNotDisturb() && !hasSession(session_id));
- if (isRejectGroupCall || isRejectNonFriendCall || isRejectDoNotDisturb)
+ if (isRejectGroupCall || isRejectNonFriendCall || gAgent.isDoNotDisturb())
{
- if (isRejectDoNotDisturb && !isRejectGroupCall && !isRejectNonFriendCall)
+ if (gAgent.isDoNotDisturb() && !isRejectGroupCall && !isRejectNonFriendCall)
{
LLSD args;
addSystemMessage(session_id, "you_auto_rejected_call", args);
diff --git a/indra/newview/llinventoryfilter.cpp b/indra/newview/llinventoryfilter.cpp
index 92f2d33073..3c6974cf6d 100755
--- a/indra/newview/llinventoryfilter.cpp
+++ b/indra/newview/llinventoryfilter.cpp
@@ -70,11 +70,8 @@ LLInventoryFilter::LLInventoryFilter(const Params& p)
mFilterSubString(p.substring),
mCurrentGeneration(0),
mFirstRequiredGeneration(0),
- mFirstSuccessGeneration(0),
- mFilterCount(0)
+ mFirstSuccessGeneration(0)
{
- mNextFilterGeneration = mCurrentGeneration + 1;
-
// copy mFilterOps into mDefaultFilterOps
markDefault();
}
@@ -92,9 +89,7 @@ bool LLInventoryFilter::check(const LLFolderViewModelItem* item)
return passed_clipboard;
}
- std::string::size_type string_offset = mFilterSubString.size() ? listener->getSearchableName().find(mFilterSubString) : std::string::npos;
-
- BOOL passed = (mFilterSubString.size() == 0 || string_offset != std::string::npos);
+ bool passed = (mFilterSubString.size() ? listener->getSearchableName().find(mFilterSubString) != std::string::npos : true);
passed = passed && checkAgainstFilterType(listener);
passed = passed && checkAgainstPermissions(listener);
passed = passed && checkAgainstFilterLinks(listener);
@@ -105,17 +100,12 @@ bool LLInventoryFilter::check(const LLFolderViewModelItem* item)
bool LLInventoryFilter::check(const LLInventoryItem* item)
{
- std::string::size_type string_offset = mFilterSubString.size() ? item->getName().find(mFilterSubString) : std::string::npos;
-
+ const bool passed_string = (mFilterSubString.size() ? item->getName().find(mFilterSubString) != std::string::npos : true);
const bool passed_filtertype = checkAgainstFilterType(item);
const bool passed_permissions = checkAgainstPermissions(item);
- const BOOL passed_clipboard = checkAgainstClipboard(item->getUUID());
- const bool passed = (passed_filtertype
- && passed_permissions
- && passed_clipboard
- && (mFilterSubString.size() == 0 || string_offset != std::string::npos));
+ const bool passed_clipboard = checkAgainstClipboard(item->getUUID());
- return passed;
+ return passed_filtertype && passed_permissions && passed_clipboard && passed_string;
}
bool LLInventoryFilter::checkFolder(const LLFolderViewModelItem* item) const
@@ -439,7 +429,7 @@ void LLInventoryFilter::updateFilterTypes(U64 types, U64& current_types)
current_types = types;
if (more_bits_set && fewer_bits_set)
{
- // neither less or more restrive, both simultaneously
+ // neither less or more restrictive, both simultaneously
// so we need to filter from scratch
setModified(FILTER_RESTART);
}
@@ -714,7 +704,7 @@ void LLInventoryFilter::resetDefault()
void LLInventoryFilter::setModified(EFilterModified behavior)
{
mFilterText.clear();
- mCurrentGeneration = mNextFilterGeneration++;
+ mCurrentGeneration++;
if (mFilterModified == FILTER_NONE)
{
@@ -1021,21 +1011,19 @@ LLInventoryFilter::EFolderShow LLInventoryFilter::getShowFolderState() const
return mFilterOps.mShowFolderState;
}
-void LLInventoryFilter::setFilterCount(S32 count)
-{
- mFilterCount = count;
-}
-S32 LLInventoryFilter::getFilterCount() const
+bool LLInventoryFilter::isTimedOut()
{
- return mFilterCount;
+ return mFilterTime.hasExpired();
}
-void LLInventoryFilter::decrementFilterCount()
-{
- mFilterCount--;
+void LLInventoryFilter::resetTime(S32 timeout)
+{
+ mFilterTime.reset();
+ F32 time_in_sec = (F32)(timeout)/1000.0;
+ mFilterTime.setTimerExpirySec(time_in_sec);
}
-S32 LLInventoryFilter::getCurrentGeneration() const
+S32 LLInventoryFilter::getCurrentGeneration() const
{
return mCurrentGeneration;
}
diff --git a/indra/newview/llinventoryfilter.h b/indra/newview/llinventoryfilter.h
index 4912b5ca91..ce516af0b9 100755
--- a/indra/newview/llinventoryfilter.h
+++ b/indra/newview/llinventoryfilter.h
@@ -215,12 +215,11 @@ public:
void setModified(EFilterModified behavior = FILTER_RESTART);
// +-------------------------------------------------------------------+
- // + Count
+ // + Time
// +-------------------------------------------------------------------+
- void setFilterCount(S32 count);
- S32 getFilterCount() const;
- void decrementFilterCount();
-
+ void resetTime(S32 timeout);
+ bool isTimedOut();
+
// +-------------------------------------------------------------------+
// + Default
// +-------------------------------------------------------------------+
@@ -262,13 +261,15 @@ private:
const std::string mName;
S32 mCurrentGeneration;
+ // The following makes checking for pass/no pass possible even if the item is not checked against the current generation
+ // Any item that *did not pass* the "required generation" will *not pass* the current one
+ // Any item that *passes* the "success generation" will *pass* the current one
S32 mFirstRequiredGeneration;
S32 mFirstSuccessGeneration;
- S32 mNextFilterGeneration;
- S32 mFilterCount;
EFilterModified mFilterModified;
-
+ LLTimer mFilterTime;
+
std::string mFilterText;
std::string mEmptyLookupMessage;
};
diff --git a/indra/newview/llinventorypanel.cpp b/indra/newview/llinventorypanel.cpp
index cf1fd4c0d0..e5b9e11d48 100755
--- a/indra/newview/llinventorypanel.cpp
+++ b/indra/newview/llinventorypanel.cpp
@@ -192,7 +192,7 @@ LLFolderView * LLInventoryPanel::createFolderRoot(LLUUID root_id )
p.show_item_link_overlays = mShowItemLinkOverlays;
p.root = NULL;
p.options_menu = "menu_inventory.xml";
-
+
return LLUICtrlFactory::create<LLFolderView>(p);
}
@@ -396,6 +396,7 @@ LLInventoryFilter::EFolderShow LLInventoryPanel::getShowFolderState()
return getFilter().getShowFolderState();
}
+// Called when something changed in the global model (new item, item coming through the wire, rename, move, etc...) (CHUI-849)
void LLInventoryPanel::modelChanged(U32 mask)
{
static LLFastTimer::DeclareTimer FTM_REFRESH("Inventory Refresh");
diff --git a/indra/newview/lllogchat.cpp b/indra/newview/lllogchat.cpp
index 2d7454b636..90b169ecd3 100755
--- a/indra/newview/lllogchat.cpp
+++ b/indra/newview/lllogchat.cpp
@@ -25,7 +25,7 @@
*/
#include "llviewerprecompiledheaders.h"
-
+#include "llfloaterconversationpreview.h"
#include "llagent.h"
#include "llagentui.h"
#include "llavatarnamecache.h"
@@ -206,6 +206,7 @@ private:
};
LLLogChat::save_history_signal_t * LLLogChat::sSaveHistorySignal = NULL;
+LLLoadHistoryThread::load_end_signal_t * LLLoadHistoryThread::mLoadEndSignal = NULL;
//static
std::string LLLogChat::makeLogFileName(std::string filename)
@@ -336,75 +337,83 @@ void LLLogChat::saveHistory(const std::string& filename,
void LLLogChat::loadChatHistory(const std::string& file_name, std::list<LLSD>& messages, const LLSD& load_params)
{
if (file_name.empty())
- {
- llwarns << "Session name is Empty!" << llendl;
- return ;
- }
-
- bool load_all_history = load_params.has("load_all_history") ? load_params["load_all_history"].asBoolean() : false;
+ {
+ LL_WARNS("LLLogChat::loadChatHistory") << "Session name is Empty!" << LL_ENDL;
+ return ;
+ }
- LLFILE* fptr = LLFile::fopen(makeLogFileName(file_name), "r");/*Flawfinder: ignore*/
- if (!fptr)
- {
- fptr = LLFile::fopen(oldLogFileName(file_name), "r");/*Flawfinder: ignore*/
- if (!fptr)
- {
- return; //No previous conversation with this name.
- }
- }
-
- char buffer[LOG_RECALL_SIZE]; /*Flawfinder: ignore*/
- char *bptr;
- S32 len;
- bool firstline = TRUE;
+ bool load_all_history = load_params.has("load_all_history") ? load_params["load_all_history"].asBoolean() : false;
- if (load_all_history || fseek(fptr, (LOG_RECALL_SIZE - 1) * -1 , SEEK_END))
- { //We need to load the whole historyFile or it's smaller than recall size, so get it all.
- firstline = FALSE;
- if (fseek(fptr, 0, SEEK_SET))
- {
- fclose(fptr);
- return;
- }
- }
+ LLFILE* fptr = LLFile::fopen(LLLogChat::makeLogFileName(file_name), "r");/*Flawfinder: ignore*/
+ if (!fptr)
+ {
+ fptr = LLFile::fopen(LLLogChat::oldLogFileName(file_name), "r");/*Flawfinder: ignore*/
+ if (!fptr)
+ {
+ return; //No previous conversation with this name.
+ }
+ }
- while (fgets(buffer, LOG_RECALL_SIZE, fptr) && !feof(fptr))
- {
- len = strlen(buffer) - 1; /*Flawfinder: ignore*/
- for (bptr = (buffer + len); (*bptr == '\n' || *bptr == '\r') && bptr>buffer; bptr--) *bptr='\0';
-
- if (firstline)
- {
- firstline = FALSE;
- continue;
- }
+ char buffer[LOG_RECALL_SIZE]; /*Flawfinder: ignore*/
+ char *bptr;
+ S32 len;
+ bool firstline = TRUE;
+
+ if (load_all_history || fseek(fptr, (LOG_RECALL_SIZE - 1) * -1 , SEEK_END))
+ { //We need to load the whole historyFile or it's smaller than recall size, so get it all.
+ firstline = FALSE;
+ if (fseek(fptr, 0, SEEK_SET))
+ {
+ fclose(fptr);
+ return;
+ }
+ }
+ while (fgets(buffer, LOG_RECALL_SIZE, fptr) && !feof(fptr))
+ {
+ len = strlen(buffer) - 1; /*Flawfinder: ignore*/
+ for (bptr = (buffer + len); (*bptr == '\n' || *bptr == '\r') && bptr>buffer; bptr--) *bptr='\0';
+
+ if (firstline)
+ {
+ firstline = FALSE;
+ continue;
+ }
+
+ std::string line(buffer);
+
+ //updated 1.23 plain text log format requires a space added before subsequent lines in a multilined message
+ if (' ' == line[0])
+ {
+ line.erase(0, MULTI_LINE_PREFIX.length());
+ append_to_last_message(messages, '\n' + line);
+ }
+ else if (0 == len && ('\n' == line[0] || '\r' == line[0]))
+ {
+ //to support old format's multilined messages with new lines used to divide paragraphs
+ append_to_last_message(messages, line);
+ }
+ else
+ {
+ LLSD item;
+ if (!LLChatLogParser::parse(line, item, load_params))
+ {
+ item[LL_IM_TEXT] = line;
+ }
+ messages.push_back(item);
+ }
+ }
+ fclose(fptr);
- std::string line(buffer);
- //updated 1.23 plaint text log format requires a space added before subsequent lines in a multilined message
- if (' ' == line[0])
- {
- line.erase(0, MULTI_LINE_PREFIX.length());
- append_to_last_message(messages, '\n' + line);
- }
- else if (0 == len && ('\n' == line[0] || '\r' == line[0]))
- {
- //to support old format's multilined messages with new lines used to divide paragraphs
- append_to_last_message(messages, line);
- }
- else
- {
- LLSD item;
- if (!LLChatLogParser::parse(line, item, load_params))
- {
- item[LL_IM_TEXT] = line;
- }
- messages.push_back(item);
- }
- }
- fclose(fptr);
}
+void LLLogChat::startChatHistoryThread(const std::string& file_name, const LLSD& load_params)
+{
+
+ LLLoadHistoryThread* mThread = new LLLoadHistoryThread();
+ mThread->start();
+ mThread->setHistoryParams(file_name, load_params);
+}
// static
std::string LLLogChat::oldLogFileName(std::string filename)
{
@@ -461,6 +470,13 @@ void LLLogChat::findTranscriptFiles(std::string pattern, std::vector<std::string
LLFILE * filep = LLFile::fopen(fullname, "rb");
if (NULL != filep)
{
+ if(makeLogFileName("chat")== fullname)
+ {
+ //Add Nearby chat history to the list of transcriptions
+ list_of_transcriptions.push_back(gDirUtilp->add(dirname, filename));
+ LLFile::close(filep);
+ return;
+ }
char buffer[LOG_RECALL_SIZE];
fseek(filep, 0, SEEK_END); // seek to end of file
@@ -631,7 +647,7 @@ void LLLogChat::deleteTranscripts()
}
// static
-bool LLLogChat::isTranscriptExist(const LLUUID& avatar_id)
+bool LLLogChat::isTranscriptExist(const LLUUID& avatar_id, bool is_group)
{
std::vector<std::string> list_of_transcriptions;
LLLogChat::getListOfTranscriptFiles(list_of_transcriptions);
@@ -641,20 +657,53 @@ bool LLLogChat::isTranscriptExist(const LLUUID& avatar_id)
LLAvatarName avatar_name;
LLAvatarNameCache::get(avatar_id, &avatar_name);
std::string avatar_user_name = avatar_name.getAccountName();
- std::replace(avatar_user_name.begin(), avatar_user_name.end(), '.', '_');
-
- BOOST_FOREACH(std::string& transcript_file_name, list_of_transcriptions)
+ if(!is_group)
{
- if (std::string::npos != transcript_file_name.find(avatar_user_name))
+ std::replace(avatar_user_name.begin(), avatar_user_name.end(), '.', '_');
+ BOOST_FOREACH(std::string& transcript_file_name, list_of_transcriptions)
{
- return true;
+ if (std::string::npos != transcript_file_name.find(avatar_user_name))
+ {
+ return true;
+ }
}
}
+ else
+ {
+ std::string file_name;
+ gCacheName->getGroupName(avatar_id, file_name);
+ file_name = makeLogFileName(file_name);
+ BOOST_FOREACH(std::string& transcript_file_name, list_of_transcriptions)
+ {
+ if (transcript_file_name == file_name)
+ {
+ return true;
+ }
+ }
+ }
+
}
return false;
}
+bool LLLogChat::isNearbyTranscriptExist()
+{
+ std::vector<std::string> list_of_transcriptions;
+ LLLogChat::getListOfTranscriptFiles(list_of_transcriptions);
+
+ std::string file_name;
+ file_name = makeLogFileName("chat");
+ BOOST_FOREACH(std::string& transcript_file_name, list_of_transcriptions)
+ {
+ if (transcript_file_name == file_name)
+ {
+ return true;
+ }
+ }
+ return false;
+}
+
//*TODO mark object's names in a special way so that they will be distinguishable form avatar name
//which are more strict by its nature (only firstname and secondname)
//Example, an object's name can be written like "Object <actual_object's_name>"
@@ -795,3 +844,116 @@ bool LLChatLogParser::parse(std::string& raw, LLSD& im, const LLSD& parse_params
im[LL_IM_TEXT] = name_and_text[IDX_TEXT];
return true; //parsed name and message text, maybe have a timestamp too
}
+
+
+
+ LLLoadHistoryThread::LLLoadHistoryThread() : LLThread("load chat history")
+ {
+ mNewLoad = false;
+ }
+
+ void LLLoadHistoryThread::run()
+ {
+ while (!LLApp::isQuitting())
+ {
+ if(mNewLoad)
+ {
+ loadHistory(mFileName,mMessages,mLoadParams);
+ shutdown();
+ }
+ }
+ }
+ void LLLoadHistoryThread::setHistoryParams(const std::string& file_name, const LLSD& load_params)
+ {
+ mFileName = file_name;
+ mLoadParams = load_params;
+ mNewLoad = true;
+ }
+ void LLLoadHistoryThread::loadHistory(const std::string& file_name, std::list<LLSD>& messages, const LLSD& load_params)
+ {
+
+ if (file_name.empty())
+ {
+ LL_WARNS("LLLogChat::loadHistory") << "Session name is Empty!" << LL_ENDL;
+ return ;
+ }
+
+ bool load_all_history = load_params.has("load_all_history") ? load_params["load_all_history"].asBoolean() : false;
+
+ LLFILE* fptr = LLFile::fopen(LLLogChat::makeLogFileName(file_name), "r");/*Flawfinder: ignore*/
+ if (!fptr)
+ {
+ fptr = LLFile::fopen(LLLogChat::oldLogFileName(file_name), "r");/*Flawfinder: ignore*/
+ if (!fptr)
+ {
+ mNewLoad = false;
+ (*mLoadEndSignal)(messages, file_name);
+ return; //No previous conversation with this name.
+ }
+ }
+
+ char buffer[LOG_RECALL_SIZE]; /*Flawfinder: ignore*/
+ char *bptr;
+ S32 len;
+ bool firstline = TRUE;
+
+ if (load_all_history || fseek(fptr, (LOG_RECALL_SIZE - 1) * -1 , SEEK_END))
+ { //We need to load the whole historyFile or it's smaller than recall size, so get it all.
+ firstline = FALSE;
+ if (fseek(fptr, 0, SEEK_SET))
+ {
+ fclose(fptr);
+ mNewLoad = false;
+ (*mLoadEndSignal)(messages, file_name);
+ return;
+ }
+ }
+ while (fgets(buffer, LOG_RECALL_SIZE, fptr) && !feof(fptr))
+ {
+ len = strlen(buffer) - 1; /*Flawfinder: ignore*/
+ for (bptr = (buffer + len); (*bptr == '\n' || *bptr == '\r') && bptr>buffer; bptr--) *bptr='\0';
+
+ if (firstline)
+ {
+ firstline = FALSE;
+ continue;
+ }
+
+ std::string line(buffer);
+
+ //updated 1.23 plaint text log format requires a space added before subsequent lines in a multilined message
+ if (' ' == line[0])
+ {
+ line.erase(0, MULTI_LINE_PREFIX.length());
+ append_to_last_message(messages, '\n' + line);
+ }
+ else if (0 == len && ('\n' == line[0] || '\r' == line[0]))
+ {
+ //to support old format's multilined messages with new lines used to divide paragraphs
+ append_to_last_message(messages, line);
+ }
+ else
+ {
+ LLSD item;
+ if (!LLChatLogParser::parse(line, item, load_params))
+ {
+ item[LL_IM_TEXT] = line;
+ }
+ messages.push_back(item);
+ }
+ }
+ fclose(fptr);
+ mNewLoad = false;
+ (*mLoadEndSignal)(messages, file_name);
+ }
+
+ //static
+ boost::signals2::connection LLLoadHistoryThread::setLoadEndSignal(const load_end_signal_t::slot_type& cb)
+ {
+ if (NULL == mLoadEndSignal)
+ {
+ mLoadEndSignal = new load_end_signal_t();
+ }
+
+ return mLoadEndSignal->connect(cb);
+ }
diff --git a/indra/newview/lllogchat.h b/indra/newview/lllogchat.h
index e819f00dd9..acee99afa2 100755
--- a/indra/newview/lllogchat.h
+++ b/indra/newview/lllogchat.h
@@ -28,6 +28,24 @@
#define LL_LLLOGCHAT_H
class LLChat;
+class LLLoadHistoryThread : public LLThread
+{
+private:
+ std::string mFileName;
+ std::list<LLSD> mMessages;
+ LLSD mLoadParams;
+ bool mNewLoad;
+public:
+ LLLoadHistoryThread();
+
+ void setHistoryParams(const std::string& file_name, const LLSD& load_params);
+ virtual void loadHistory(const std::string& file_name, std::list<LLSD>& messages, const LLSD& load_params);
+ virtual void run();
+
+ typedef boost::signals2::signal<void (std::list<LLSD>& messages,const std::string& file_name)> load_end_signal_t;
+ static load_end_signal_t * mLoadEndSignal;
+ static boost::signals2::connection setLoadEndSignal(const load_end_signal_t::slot_type& cb);
+};
class LLLogChat
{
@@ -39,6 +57,7 @@ public:
LOG_LLSD,
LOG_END
};
+
static std::string timestamp(bool withdate = false);
static std::string makeLogFileName(std::string(filename));
/**
@@ -54,6 +73,7 @@ public:
static void getListOfTranscriptBackupFiles(std::vector<std::string>& list_of_transcriptions);
static void loadChatHistory(const std::string& file_name, std::list<LLSD>& messages, const LLSD& load_params = LLSD());
+ static void startChatHistoryThread(const std::string& file_name, const LLSD& load_params);
typedef boost::signals2::signal<void ()> save_history_signal_t;
static boost::signals2::connection setSaveHistorySignal(const save_history_signal_t::slot_type& cb);
@@ -67,7 +87,8 @@ public:
std::vector<std::string>& listOfFilesToMove);
static void deleteTranscripts();
- static bool isTranscriptExist(const LLUUID& avatar_id);
+ static bool isTranscriptExist(const LLUUID& avatar_id, bool is_group=false);
+ static bool isNearbyTranscriptExist();
private:
static std::string cleanFileName(std::string filename);
@@ -126,6 +147,7 @@ protected:
virtual ~LLChatLogParser() {};
};
+
// LLSD map lookup constants
extern const std::string LL_IM_TIME; //("time");
extern const std::string LL_IM_TEXT; //("message");
diff --git a/indra/newview/llmenuoptionpathfindingrebakenavmesh.cpp b/indra/newview/llmenuoptionpathfindingrebakenavmesh.cpp
index 2b92b0b3d1..a567d1217a 100755
--- a/indra/newview/llmenuoptionpathfindingrebakenavmesh.cpp
+++ b/indra/newview/llmenuoptionpathfindingrebakenavmesh.cpp
@@ -92,7 +92,7 @@ void LLMenuOptionPathfindingRebakeNavmesh::initialize()
void LLMenuOptionPathfindingRebakeNavmesh::quit()
{
- if (mIsInitialized)
+ if (mIsInitialized) // Quitting from the login screen leaves this uninitialized
{
if (mNavMeshSlot.connected())
{
diff --git a/indra/newview/llmeshrepository.h b/indra/newview/llmeshrepository.h
index 8602271f84..8eaf691d6f 100755
--- a/indra/newview/llmeshrepository.h
+++ b/indra/newview/llmeshrepository.h
@@ -413,7 +413,7 @@ public:
void startRequest() { ++mPendingUploads; }
void stopRequest() { --mPendingUploads; }
-
+
bool finished() { return mFinished; }
virtual void run();
void preStart();
diff --git a/indra/newview/llnamelistctrl.cpp b/indra/newview/llnamelistctrl.cpp
index 7f396b7b7e..7ddd04fed0 100755
--- a/indra/newview/llnamelistctrl.cpp
+++ b/indra/newview/llnamelistctrl.cpp
@@ -416,9 +416,9 @@ void LLNameListCtrl::onAvatarNameCache(const LLUUID& agent_id,
}
-void LLNameListCtrl::updateColumns()
+void LLNameListCtrl::updateColumns(bool force_update)
{
- LLScrollListCtrl::updateColumns();
+ LLScrollListCtrl::updateColumns(force_update);
if (!mNameColumn.empty())
{
diff --git a/indra/newview/llnamelistctrl.h b/indra/newview/llnamelistctrl.h
index 271802d48a..5aa1e1c458 100755
--- a/indra/newview/llnamelistctrl.h
+++ b/indra/newview/llnamelistctrl.h
@@ -149,7 +149,7 @@ public:
void sortByName(BOOL ascending);
- /*virtual*/ void updateColumns();
+ /*virtual*/ void updateColumns(bool force_update);
/*virtual*/ void mouseOverHighlightNthItem( S32 index );
private:
diff --git a/indra/newview/llnotificationstorage.h b/indra/newview/llnotificationstorage.h
index 7aabf7d09e..53fd898ea4 100755
--- a/indra/newview/llnotificationstorage.h
+++ b/indra/newview/llnotificationstorage.h
@@ -44,6 +44,7 @@ public:
protected:
bool writeNotifications(const LLSD& pNotificationData) const;
bool readNotifications(LLSD& pNotificationData) const;
+ void setFileName(std::string pFileName) {mFileName = pFileName;}
LLNotificationResponderInterface* createResponder(const std::string& pNotificationName, const LLSD& pParams) const;
diff --git a/indra/newview/llnotificationtiphandler.cpp b/indra/newview/llnotificationtiphandler.cpp
index a85335f1ba..4ca961c1f9 100755
--- a/indra/newview/llnotificationtiphandler.cpp
+++ b/indra/newview/llnotificationtiphandler.cpp
@@ -83,13 +83,6 @@ bool LLTipHandler::processNotification(const LLNotificationPtr& notification)
if (notification->canLogToChat())
{
LLHandlerUtil::logToNearbyChat(notification, CHAT_SOURCE_SYSTEM);
-
- // don't show toast if Nearby Chat is opened
- LLFloaterIMNearbyChat* nearby_chat = LLFloaterReg::getTypedInstance<LLFloaterIMNearbyChat>("nearby_chat");
- if (nearby_chat->isChatVisible())
- {
- return false;
- }
}
std::string session_name = notification->getPayload()["SESSION_NAME"];
diff --git a/indra/newview/llpanelgroupinvite.cpp b/indra/newview/llpanelgroupinvite.cpp
index 133b269c11..a9a3c686a6 100755
--- a/indra/newview/llpanelgroupinvite.cpp
+++ b/indra/newview/llpanelgroupinvite.cpp
@@ -85,6 +85,7 @@ public:
std::string mAlreadyInGroup;
std::string mTooManySelected;
bool mConfirmedOwnerInvite;
+ std::set<LLUUID> mInviteeIDs;
void (*mCloseCallback)(void* data);
@@ -117,31 +118,30 @@ LLPanelGroupInvite::impl::~impl()
}
}
+const S32 MAX_GROUP_INVITES = 100; // Max invites per request. 100 to match server cap.
+
void LLPanelGroupInvite::impl::addUsers(const std::vector<std::string>& names,
const uuid_vec_t& agent_ids)
{
std::string name;
LLUUID id;
+ if (names.size() + mInviteeIDs.size() > MAX_GROUP_INVITES)
+ {
+ // Fail! Show a warning and don't add any names.
+ LLSD msg;
+ msg["MESSAGE"] = mTooManySelected;
+ LLNotificationsUtil::add("GenericAlert", msg);
+ return;
+ }
+
for (S32 i = 0; i < (S32)names.size(); i++)
{
name = names[i];
id = agent_ids[i];
// Make sure this agent isn't already in the list.
- bool already_in_list = false;
- std::vector<LLScrollListItem*> items = mInvitees->getAllData();
- for (std::vector<LLScrollListItem*>::iterator iter = items.begin();
- iter != items.end(); ++iter)
- {
- LLScrollListItem* item = *iter;
- if (item->getUUID() == id)
- {
- already_in_list = true;
- break;
- }
- }
- if (already_in_list)
+ if (mInviteeIDs.find(id) != mInviteeIDs.end())
{
continue;
}
@@ -152,6 +152,7 @@ void LLPanelGroupInvite::impl::addUsers(const std::vector<std::string>& names,
row["columns"][0]["value"] = name;
mInvitees->addElement(row);
+ mInviteeIDs.insert(id);
}
}
@@ -193,7 +194,6 @@ void LLPanelGroupInvite::impl::submitInvitations()
role_member_pairs[item->getUUID()] = role_id;
}
- const S32 MAX_GROUP_INVITES = 100; // Max invites per request. 100 to match server cap.
if (role_member_pairs.size() > MAX_GROUP_INVITES)
{
// Fail!
@@ -334,6 +334,12 @@ void LLPanelGroupInvite::impl::handleRemove()
mInvitees->getAllSelected();
if (selection.empty()) return;
+ std::vector<LLScrollListItem*>::iterator iter;
+ for(iter = selection.begin(); iter != selection.end(); ++iter)
+ {
+ mInviteeIDs.erase( (*iter)->getUUID() );
+ }
+
// Remove all selected invitees.
mInvitees->deleteSelectedItems();
mRemoveButton->setEnabled(FALSE);
@@ -459,6 +465,7 @@ void LLPanelGroupInvite::clear()
mImplementation->mRoleNames->clear();
mImplementation->mRoleNames->removeall();
mImplementation->mOKButton->setEnabled(FALSE);
+ mImplementation->mInviteeIDs.clear();
}
void LLPanelGroupInvite::addUsers(uuid_vec_t& agent_ids)
diff --git a/indra/newview/llpanellogin.cpp b/indra/newview/llpanellogin.cpp
index bcb90bcb56..911ecaad9d 100755
--- a/indra/newview/llpanellogin.cpp
+++ b/indra/newview/llpanellogin.cpp
@@ -82,10 +82,6 @@ const S32 MAX_PASSWORD = 16;
LLPanelLogin *LLPanelLogin::sInstance = NULL;
BOOL LLPanelLogin::sCapslockDidNotification = FALSE;
-// Helper for converting a user name into the canonical "Firstname Lastname" form.
-// For new accounts without a last name "Resident" is added as a last name.
-static std::string canonicalize_username(const std::string& name);
-
class LLLoginRefreshHandler : public LLCommandHandler
{
public:
@@ -266,7 +262,6 @@ void LLPanelLogin::addFavoritesToStartLocation()
// Load favorites into the combo.
std::string user_defined_name = getChild<LLComboBox>("username_combo")->getSimple();
- std::string canonical_user_name = canonicalize_username(user_defined_name);
std::string filename = gDirUtilp->getExpandedFilename(LL_PATH_USER_SETTINGS, "stored_favorites.xml");
LLSD fav_llsd;
llifstream file;
@@ -279,7 +274,7 @@ void LLPanelLogin::addFavoritesToStartLocation()
// The account name in stored_favorites.xml has Resident last name even if user has
// a single word account name, so it can be compared case-insensitive with the
// user defined "firstname lastname".
- S32 res = LLStringUtil::compareInsensitive(canonical_user_name, iter->first);
+ S32 res = LLStringUtil::compareInsensitive(user_defined_name, iter->first);
if (res != 0)
{
lldebugs << "Skipping favorites for " << iter->first << llendl;
@@ -1012,29 +1007,3 @@ void LLPanelLogin::onLocationSLURL()
LLStartUp::setStartSLURL(location); // calls onUpdateStartSLURL, above
}
-
-
-std::string canonicalize_username(const std::string& name)
-{
- std::string cname = name;
- LLStringUtil::trim(cname);
-
- // determine if the username is a first/last form or not.
- size_t separator_index = cname.find_first_of(" ._");
- std::string first = cname.substr(0, separator_index);
- std::string last;
- if (separator_index != cname.npos)
- {
- last = cname.substr(separator_index+1, cname.npos);
- LLStringUtil::trim(last);
- }
- else
- {
- // ...on Linden grids, single username users as considered to have
- // last name "Resident"
- last = "Resident";
- }
-
- // Username in traditional "firstname lastname" form.
- return first + ' ' + last;
-}
diff --git a/indra/newview/llpanelmaininventory.cpp b/indra/newview/llpanelmaininventory.cpp
index d6535c88e9..53deded2f2 100755
--- a/indra/newview/llpanelmaininventory.cpp
+++ b/indra/newview/llpanelmaininventory.cpp
@@ -130,6 +130,8 @@ BOOL LLPanelMainInventory::postBuild()
mFilterTabs = getChild<LLTabContainer>("inventory filter tabs");
mFilterTabs->setCommitCallback(boost::bind(&LLPanelMainInventory::onFilterSelected, this));
+ mCounterCtrl = getChild<LLUICtrl>("ItemcountText");
+
//panel->getFilter().markDefault();
// Set up the default inv. panel/filter settings.
@@ -566,7 +568,7 @@ void LLPanelMainInventory::draw()
void LLPanelMainInventory::updateItemcountText()
{
// *TODO: Calling setlocale() on each frame may be inefficient.
- LLLocale locale(LLStringUtil::getLocale());
+ //LLLocale locale(LLStringUtil::getLocale());
std::string item_count_string;
LLResMgr::getInstance()->getIntegerString(item_count_string, gInventory.getItemCount());
@@ -589,8 +591,7 @@ void LLPanelMainInventory::updateItemcountText()
text = getString("ItemcountUnknown");
}
- // *TODO: Cache the LLUICtrl* for the ItemcountText control
- getChild<LLUICtrl>("ItemcountText")->setValue(text);
+ mCounterCtrl->setValue(text);
}
void LLPanelMainInventory::onFocusReceived()
diff --git a/indra/newview/llpanelmaininventory.h b/indra/newview/llpanelmaininventory.h
index 899931aa89..394b004e20 100755
--- a/indra/newview/llpanelmaininventory.h
+++ b/indra/newview/llpanelmaininventory.h
@@ -121,6 +121,7 @@ private:
LLFilterEditor* mFilterEditor;
LLTabContainer* mFilterTabs;
+ LLUICtrl* mCounterCtrl;
LLHandle<LLFloater> mFinderHandle;
LLInventoryPanel* mActivePanel;
bool mResortActivePanel;
diff --git a/indra/newview/llpanelprofile.cpp b/indra/newview/llpanelprofile.cpp
index e2e7006773..5acc98904b 100755
--- a/indra/newview/llpanelprofile.cpp
+++ b/indra/newview/llpanelprofile.cpp
@@ -36,6 +36,8 @@
#include "lltabcontainer.h"
#include "llviewercontrol.h"
#include "llviewernetwork.h"
+#include "llmutelist.h"
+#include "llpanelblockedlist.h"
static const std::string PANEL_PICKS = "panel_picks";
@@ -137,6 +139,12 @@ public:
return true;
}
+ if (verb == "removefriend")
+ {
+ LLAvatarActions::removeFriendDialog(avatar_id);
+ return true;
+ }
+
if (verb == "mute")
{
if (! LLAvatarActions::isBlocked(avatar_id))
@@ -155,6 +163,18 @@ public:
return true;
}
+ if (verb == "block")
+ {
+ if (params.size() > 2)
+ {
+ const std::string object_name = params[2].asString();
+ LLMute mute(avatar_id, object_name, LLMute::OBJECT);
+ LLMuteList::getInstance()->add(mute);
+ LLPanelBlockedList::showPanelAndSelect(mute.mID);
+ }
+ return true;
+ }
+
return false;
}
};
diff --git a/indra/newview/llpersistentnotificationstorage.cpp b/indra/newview/llpersistentnotificationstorage.cpp
index 666f10df96..076c3e0235 100755
--- a/indra/newview/llpersistentnotificationstorage.cpp
+++ b/indra/newview/llpersistentnotificationstorage.cpp
@@ -38,7 +38,8 @@
LLPersistentNotificationStorage::LLPersistentNotificationStorage()
: LLSingleton<LLPersistentNotificationStorage>()
- , LLNotificationStorage(gDirUtilp->getExpandedFilename(LL_PATH_PER_SL_ACCOUNT, "open_notifications.xml"))
+ , LLNotificationStorage("")
+ , mLoaded(false)
{
}
@@ -89,8 +90,13 @@ void LLPersistentNotificationStorage::loadNotifications()
LL_INFOS("LLPersistentNotificationStorage") << "start loading notifications" << LL_ENDL;
- LLNotifications::instance().getChannel("Persistent")->
- connectChanged(boost::bind(&LLPersistentNotificationStorage::onPersistentChannelChanged, this, _1));
+ if (mLoaded)
+ {
+ LL_INFOS("LLPersistentNotificationStorage") << "notifications already loaded, exiting" << LL_ENDL;
+ return;
+ }
+
+ mLoaded = true;
LLSD input;
if (!readNotifications(input) ||input.isUndefined())
@@ -135,8 +141,20 @@ void LLPersistentNotificationStorage::loadNotifications()
LL_INFOS("LLPersistentNotificationStorage") << "finished loading notifications" << LL_ENDL;
}
+void LLPersistentNotificationStorage::initialize()
+{
+ setFileName(gDirUtilp->getExpandedFilename(LL_PATH_PER_SL_ACCOUNT, "open_notifications.xml"));
+ LLNotifications::instance().getChannel("Persistent")->
+ connectChanged(boost::bind(&LLPersistentNotificationStorage::onPersistentChannelChanged, this, _1));
+}
+
bool LLPersistentNotificationStorage::onPersistentChannelChanged(const LLSD& payload)
{
+ // In case we received channel changed signal but haven't yet loaded notifications, do it
+ if (!mLoaded)
+ {
+ loadNotifications();
+ }
// we ignore "load" messages, but rewrite the persistence file on any other
const std::string sigtype = payload["sigtype"].asString();
if ("load" != sigtype)
diff --git a/indra/newview/llpersistentnotificationstorage.h b/indra/newview/llpersistentnotificationstorage.h
index 98a825d2c1..bf0306380e 100755
--- a/indra/newview/llpersistentnotificationstorage.h
+++ b/indra/newview/llpersistentnotificationstorage.h
@@ -53,10 +53,13 @@ public:
void saveNotifications();
void loadNotifications();
+ void initialize();
+
protected:
private:
bool onPersistentChannelChanged(const LLSD& payload);
+ bool mLoaded;
};
#endif // LL_LLPERSISTENTNOTIFICATIONSTORAGE_H
diff --git a/indra/newview/llspatialpartition.cpp b/indra/newview/llspatialpartition.cpp
index 941c578783..9e97790df8 100755
--- a/indra/newview/llspatialpartition.cpp
+++ b/indra/newview/llspatialpartition.cpp
@@ -3457,7 +3457,7 @@ void renderPhysicsShape(LLDrawable* drawable, LLVOVolume* volume)
}
else if (type == LLPhysicsShapeBuilderUtil::PhysicsShapeSpecification::SPHERE)
{
- /*LLVolumeParams volume_params;
+ LLVolumeParams volume_params;
volume_params.setType( LL_PCODE_PROFILE_CIRCLE_HALF, LL_PCODE_PATH_CIRCLE );
volume_params.setBeginAndEndS( 0.f, 1.f );
volume_params.setBeginAndEndT( 0.f, 1.f );
@@ -3467,7 +3467,7 @@ void renderPhysicsShape(LLDrawable* drawable, LLVOVolume* volume)
gGL.diffuseColor4fv(color.mV);
pushVerts(sphere);
- LLPrimitive::sVolumeManager->unrefVolume(sphere);*/
+ LLPrimitive::sVolumeManager->unrefVolume(sphere);
}
else if (type == LLPhysicsShapeBuilderUtil::PhysicsShapeSpecification::CYLINDER)
{
@@ -3545,51 +3545,67 @@ void renderPhysicsShapes(LLSpatialGroup* group)
for (LLSpatialGroup::OctreeNode::const_element_iter i = group->getDataBegin(); i != group->getDataEnd(); ++i)
{
LLDrawable* drawable = *i;
- LLVOVolume* volume = drawable->getVOVolume();
- if (volume && !volume->isAttachment() && volume->getPhysicsShapeType() != LLViewerObject::PHYSICS_SHAPE_NONE )
+
+ if (drawable->isSpatialBridge())
{
- if (!group->mSpatialPartition->isBridge())
+ LLSpatialBridge* bridge = drawable->asPartition()->asBridge();
+
+ if (bridge)
{
gGL.pushMatrix();
- LLVector3 trans = drawable->getRegion()->getOriginAgent();
- gGL.translatef(trans.mV[0], trans.mV[1], trans.mV[2]);
- renderPhysicsShape(drawable, volume);
+ gGL.multMatrix((F32*)bridge->mDrawable->getRenderMatrix().mMatrix);
+ bridge->renderPhysicsShapes();
gGL.popMatrix();
}
- else
- {
- renderPhysicsShape(drawable, volume);
- }
}
else
{
- LLViewerObject* object = drawable->getVObj();
- if (object && object->getPCode() == LLViewerObject::LL_VO_SURFACE_PATCH)
+ LLVOVolume* volume = drawable->getVOVolume();
+ if (volume && !volume->isAttachment() && volume->getPhysicsShapeType() != LLViewerObject::PHYSICS_SHAPE_NONE )
{
- gGL.pushMatrix();
- gGL.multMatrix((F32*) object->getRegion()->mRenderMatrix.mMatrix);
- //push face vertices for terrain
- for (S32 i = 0; i < drawable->getNumFaces(); ++i)
+ if (!group->mSpatialPartition->isBridge())
{
- LLFace* face = drawable->getFace(i);
- if (face)
+ gGL.pushMatrix();
+ LLVector3 trans = drawable->getRegion()->getOriginAgent();
+ gGL.translatef(trans.mV[0], trans.mV[1], trans.mV[2]);
+ renderPhysicsShape(drawable, volume);
+ gGL.popMatrix();
+ }
+ else
+ {
+ renderPhysicsShape(drawable, volume);
+ }
+ }
+ else
+ {
+ LLViewerObject* object = drawable->getVObj();
+ if (object && object->getPCode() == LLViewerObject::LL_VO_SURFACE_PATCH)
+ {
+ gGL.pushMatrix();
+ gGL.multMatrix((F32*) object->getRegion()->mRenderMatrix.mMatrix);
+ //push face vertices for terrain
+ for (S32 i = 0; i < drawable->getNumFaces(); ++i)
{
- LLVertexBuffer* buff = face->getVertexBuffer();
- if (buff)
+ LLFace* face = drawable->getFace(i);
+ if (face)
{
- glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
+ LLVertexBuffer* buff = face->getVertexBuffer();
+ if (buff)
+ {
+ glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
- buff->setBuffer(LLVertexBuffer::MAP_VERTEX);
- gGL.diffuseColor3f(0.2f, 0.5f, 0.3f);
- buff->draw(LLRender::TRIANGLES, buff->getNumIndices(), 0);
+ buff->setBuffer(LLVertexBuffer::MAP_VERTEX);
+ gGL.diffuseColor3f(0.2f, 0.5f, 0.3f);
+ buff->draw(LLRender::TRIANGLES, buff->getNumIndices(), 0);
- gGL.diffuseColor3f(0.2f, 1.f, 0.3f);
- glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
- buff->draw(LLRender::TRIANGLES, buff->getNumIndices(), 0);
+ gGL.diffuseColor3f(0.2f, 1.f, 0.3f);
+ glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
+ buff->draw(LLRender::TRIANGLES, buff->getNumIndices(), 0);
+ }
}
}
+ gGL.popMatrix();
}
- gGL.popMatrix();
}
}
}
diff --git a/indra/newview/llstartup.cpp b/indra/newview/llstartup.cpp
index cff3a7e02a..67a76460a7 100755
--- a/indra/newview/llstartup.cpp
+++ b/indra/newview/llstartup.cpp
@@ -51,6 +51,7 @@
#include "lllandmark.h"
#include "llcachename.h"
#include "lldir.h"
+#include "lldonotdisturbnotificationstorage.h"
#include "llerrorcontrol.h"
#include "llfloaterreg.h"
#include "llfocusmgr.h"
@@ -68,6 +69,7 @@
#include "llfloaterimnearbychat.h"
#include "llnotifications.h"
#include "llnotificationsutil.h"
+#include "llpersistentnotificationstorage.h"
#include "llteleporthistory.h"
#include "llregionhandle.h"
#include "llsd.h"
@@ -900,6 +902,10 @@ bool idle_startup()
gDirUtilp->setLindenUserDir(userid);
LLFile::mkdir(gDirUtilp->getLindenUserDir());
+ // As soon as directories are ready initialize notification storages
+ LLPersistentNotificationStorage::getInstance()->initialize();
+ LLDoNotDisturbNotificationStorage::getInstance()->initialize();
+
// Set PerAccountSettingsFile to the default value.
gSavedSettings.setString("PerAccountSettingsFile",
gDirUtilp->getExpandedFilename(LL_PATH_PER_SL_ACCOUNT,
diff --git a/indra/newview/llsyswellwindow.cpp b/indra/newview/llsyswellwindow.cpp
index e92bd766ca..1a3add2bfb 100755
--- a/indra/newview/llsyswellwindow.cpp
+++ b/indra/newview/llsyswellwindow.cpp
@@ -423,9 +423,18 @@ void LLNotificationWellWindow::onItemClick(LLSysWellItem* item)
void LLNotificationWellWindow::onItemClose(LLSysWellItem* item)
{
LLUUID id = item->getID();
- removeItemByID(id);
+
if(mChannel)
+ {
+ // removeItemByID() is invoked from killToastByNotificationID() and item will removed;
mChannel->killToastByNotificationID(id);
+ }
+ else
+ {
+ // removeItemByID() should be called one time for each item to remove it from notification well
+ removeItemByID(id);
+ }
+
}
void LLNotificationWellWindow::onAdd( LLNotificationPtr notify )
diff --git a/indra/newview/lltexturecache.cpp b/indra/newview/lltexturecache.cpp
index 36a7aeb590..5bc2e971eb 100755
--- a/indra/newview/lltexturecache.cpp
+++ b/indra/newview/lltexturecache.cpp
@@ -1922,10 +1922,10 @@ bool LLTextureCache::writeToFastCache(S32 id, LLPointer<LLImageRaw> raw, S32 dis
h >>= i;
if(w * h *c > 0) //valid
{
- LLPointer<LLImageRaw> newraw = new LLImageRaw(raw->getData(), raw->getWidth(), raw->getHeight(), raw->getComponents());
- newraw->scale(w, h) ;
- raw = newraw;
-
+ //make a duplicate to keep the original raw image untouched.
+ raw = raw->duplicate();
+ raw->scale(w, h) ;
+
discardlevel += i ;
}
}
@@ -1935,9 +1935,12 @@ bool LLTextureCache::writeToFastCache(S32 id, LLPointer<LLImageRaw> raw, S32 dis
memcpy(mFastCachePadBuffer + sizeof(S32), &h, sizeof(S32));
memcpy(mFastCachePadBuffer + sizeof(S32) * 2, &c, sizeof(S32));
memcpy(mFastCachePadBuffer + sizeof(S32) * 3, &discardlevel, sizeof(S32));
- if(w * h * c > 0) //valid
+
+ S32 copy_size = w * h * c;
+ if(copy_size > 0) //valid
{
- memcpy(mFastCachePadBuffer + TEXTURE_FAST_CACHE_ENTRY_OVERHEAD, raw->getData(), w * h * c);
+ copy_size = llmin(copy_size, TEXTURE_FAST_CACHE_ENTRY_SIZE - TEXTURE_FAST_CACHE_ENTRY_OVERHEAD);
+ memcpy(mFastCachePadBuffer + TEXTURE_FAST_CACHE_ENTRY_OVERHEAD, raw->getData(), copy_size);
}
S32 offset = id * TEXTURE_FAST_CACHE_ENTRY_SIZE;
diff --git a/indra/newview/lltexturefetch.cpp b/indra/newview/lltexturefetch.cpp
index 6173e76a35..6173e76a35 100755..100644
--- a/indra/newview/lltexturefetch.cpp
+++ b/indra/newview/lltexturefetch.cpp
diff --git a/indra/newview/lltoastimpanel.cpp b/indra/newview/lltoastimpanel.cpp
index 75e6e3d13a..09ab31df36 100755
--- a/indra/newview/lltoastimpanel.cpp
+++ b/indra/newview/lltoastimpanel.cpp
@@ -28,6 +28,7 @@
#include "lltoastimpanel.h"
#include "llagent.h"
+#include "llavatarnamecache.h"
#include "llfloaterreg.h"
#include "llgroupactions.h"
#include "llgroupiconctrl.h"
@@ -61,6 +62,15 @@ LLToastIMPanel::LLToastIMPanel(LLToastIMPanel::Params &p) : LLToastPanel(p.notif
style_params.font.name(font_name);
style_params.font.size(font_size);
+ LLIMModel::LLIMSession* im_session = LLIMModel::getInstance()->findIMSession(p.session_id);
+ mIsGroupMsg = (im_session && im_session->mSessionType == LLIMModel::LLIMSession::GROUP_SESSION);
+ if(mIsGroupMsg)
+ {
+ mAvatarName->setValue(im_session->mName);
+ LLAvatarName avatar_name;
+ LLAvatarNameCache::get(p.avatar_id, &avatar_name);
+ p.message = "[From " + avatar_name.getDisplayName() + "]\n" + p.message;
+ }
//Handle IRC styled /me messages.
std::string prefix = p.message.substr(0, 4);
@@ -81,12 +91,17 @@ LLToastIMPanel::LLToastIMPanel(LLToastIMPanel::Params &p) : LLToastPanel(p.notif
mMessage->setText(p.message, style_params);
}
- mAvatarName->setValue(p.from);
+ if(!mIsGroupMsg)
+ {
+ mAvatarName->setValue(p.from);
+ }
mTime->setValue(p.time);
mSessionID = p.session_id;
mAvatarID = p.avatar_id;
mNotification = p.notification;
+
+
initIcon();
S32 maxLinesCount;
@@ -147,7 +162,14 @@ void LLToastIMPanel::spawnNameToolTip()
LLToolTip::Params params;
params.background_visible(false);
- params.click_callback(boost::bind(&LLFloaterReg::showInstance, "inspect_avatar", LLSD().with("avatar_id", mAvatarID), FALSE));
+ if(!mIsGroupMsg)
+ {
+ params.click_callback(boost::bind(&LLFloaterReg::showInstance, "inspect_avatar", LLSD().with("avatar_id", mAvatarID), FALSE));
+ }
+ else
+ {
+ params.click_callback(boost::bind(&LLFloaterReg::showInstance, "inspect_group", LLSD().with("group_id", mSessionID), FALSE));
+ }
params.delay_time(0.0f); // spawn instantly on hover
params.image(LLUI::getUIImage("Info_Small"));
params.message("");
diff --git a/indra/newview/lltoastimpanel.h b/indra/newview/lltoastimpanel.h
index 3eb11fb3bc..767617dabc 100755
--- a/indra/newview/lltoastimpanel.h
+++ b/indra/newview/lltoastimpanel.h
@@ -73,6 +73,8 @@ private:
LLTextBox* mAvatarName;
LLTextBox* mTime;
LLTextBox* mMessage;
+
+ bool mIsGroupMsg;
};
#endif // LLTOASTIMPANEL_H_
diff --git a/indra/newview/lltoolbarview.cpp b/indra/newview/lltoolbarview.cpp
index b2318f9158..78a555d67d 100755
--- a/indra/newview/lltoolbarview.cpp
+++ b/indra/newview/lltoolbarview.cpp
@@ -51,8 +51,6 @@ LLToolBarView* gToolBarView = NULL;
static LLDefaultChildRegistry::Register<LLToolBarView> r("toolbar_view");
-void handleLoginToolbarSetup();
-
bool isToolDragged()
{
return (LLToolDragAndDrop::getInstance()->getSource() == LLToolDragAndDrop::SOURCE_VIEWER);
@@ -111,8 +109,6 @@ BOOL LLToolBarView::postBuild()
mToolbars[i]->setButtonAddCallback(boost::bind(LLToolBarView::onToolBarButtonAdded,_1));
mToolbars[i]->setButtonRemoveCallback(boost::bind(LLToolBarView::onToolBarButtonRemoved,_1));
}
-
- LLAppViewer::instance()->setOnLoginCompletedCallback(boost::bind(&handleLoginToolbarSetup));
return TRUE;
}
@@ -180,13 +176,13 @@ S32 LLToolBarView::stopCommandInProgress(const LLCommandId& commandId)
return command_location;
}
-S32 LLToolBarView::flashCommand(const LLCommandId& commandId, bool flash)
+S32 LLToolBarView::flashCommand(const LLCommandId& commandId, bool flash, bool force_flashing/* = false */)
{
S32 command_location = hasCommand(commandId);
if (command_location != TOOLBAR_NONE)
{
- mToolbars[command_location]->flashCommand(commandId, flash);
+ mToolbars[command_location]->flashCommand(commandId, flash, force_flashing);
}
return command_location;
@@ -696,18 +692,3 @@ bool LLToolBarView::isModified() const
}
-//
-// HACK to bring up destinations guide at startup
-//
-
-void handleLoginToolbarSetup()
-{
- // Open the destinations guide by default on first login, per Rhett
- if (gSavedPerAccountSettings.getBOOL("DisplayDestinationsOnInitialRun") || gAgent.isFirstLogin())
- {
- LLFloaterReg::showInstance("destinations");
-
- gSavedPerAccountSettings.setBOOL("DisplayDestinationsOnInitialRun", FALSE);
- }
-}
-
diff --git a/indra/newview/lltoolbarview.h b/indra/newview/lltoolbarview.h
index 7125dd9990..dcc3862074 100755
--- a/indra/newview/lltoolbarview.h
+++ b/indra/newview/lltoolbarview.h
@@ -90,7 +90,7 @@ public:
S32 removeCommand(const LLCommandId& commandId, int& rank); // Sets the rank the removed command was at, RANK_NONE if not found
S32 enableCommand(const LLCommandId& commandId, bool enabled);
S32 stopCommandInProgress(const LLCommandId& commandId);
- S32 flashCommand(const LLCommandId& commandId, bool flash);
+ S32 flashCommand(const LLCommandId& commandId, bool flash, bool force_flashing = false);
// Loads the toolbars from the existing user or default settings
bool loadToolbars(bool force_default = false); // return false if load fails
diff --git a/indra/newview/lltoolpie.cpp b/indra/newview/lltoolpie.cpp
index fc9a316759..1c362c18e0 100755
--- a/indra/newview/lltoolpie.cpp
+++ b/indra/newview/lltoolpie.cpp
@@ -121,7 +121,7 @@ BOOL LLToolPie::handleMouseDown(S32 x, S32 y, MASK mask)
BOOL LLToolPie::handleRightMouseDown(S32 x, S32 y, MASK mask)
{
// don't pick transparent so users can't "pay" transparent objects
- mPick = gViewerWindow->pickImmediate(x, y, FALSE);
+ mPick = gViewerWindow->pickImmediate(x, y, FALSE, TRUE);
mPick.mKeyMask = mask;
// claim not handled so UI focus stays same
@@ -1687,6 +1687,13 @@ BOOL LLToolPie::handleRightClickPick()
showVisualContextMenuEffect();
}
}
+ else if (mPick.mParticleOwnerID.notNull())
+ {
+ if (gMenuMuteParticle && mPick.mParticleOwnerID != gAgent.getID())
+ {
+ gMenuMuteParticle->show(x,y);
+ }
+ }
LLTool::handleRightMouseDown(x, y, mask);
// We handled the event.
diff --git a/indra/newview/llviewermenu.cpp b/indra/newview/llviewermenu.cpp
index 5e2f05f468..49eb7dc94a 100755
--- a/indra/newview/llviewermenu.cpp
+++ b/indra/newview/llviewermenu.cpp
@@ -169,6 +169,7 @@ LLContextMenu *gMenuObject = NULL;
LLContextMenu *gMenuAttachmentSelf = NULL;
LLContextMenu *gMenuAttachmentOther = NULL;
LLContextMenu *gMenuLand = NULL;
+LLContextMenu *gMenuMuteParticle = NULL;
const std::string SAVE_INTO_TASK_INVENTORY("Save Object Back to Object Contents");
@@ -425,6 +426,9 @@ void init_menus()
gMenuLand = LLUICtrlFactory::createFromFile<LLContextMenu>(
"menu_land.xml", gMenuHolder, registry);
+ gMenuMuteParticle = LLUICtrlFactory::createFromFile<LLContextMenu>(
+ "menu_mute_particle.xml", gMenuHolder, registry);
+
///
/// set up the colors
///
@@ -2450,6 +2454,9 @@ void cleanup_menus()
delete gMenuLand;
gMenuLand = NULL;
+ delete gMenuMuteParticle;
+ gMenuMuteParticle = NULL;
+
delete gMenuBarView;
gMenuBarView = NULL;
@@ -2803,6 +2810,13 @@ bool enable_object_edit()
return enable;
}
+bool enable_mute_particle()
+{
+ const LLPickInfo& pick = LLToolPie::getInstance()->getPick();
+
+ return pick.mParticleOwnerID != LLUUID::null && pick.mParticleOwnerID != gAgent.getID();
+}
+
// mutually exclusive - show either edit option or build in menu
bool enable_object_build()
{
@@ -6220,6 +6234,33 @@ class LLLandEdit : public view_listener_t
}
};
+class LLMuteParticle : public view_listener_t
+{
+ bool handleEvent(const LLSD& userdata)
+ {
+ LLUUID id = LLToolPie::getInstance()->getPick().mParticleOwnerID;
+
+ if (id.notNull())
+ {
+ std::string name;
+ gCacheName->getFullName(id, name);
+
+ LLMute mute(id, name, LLMute::AGENT);
+ if (LLMuteList::getInstance()->isMuted(mute.mID))
+ {
+ LLMuteList::getInstance()->remove(mute);
+ }
+ else
+ {
+ LLMuteList::getInstance()->add(mute);
+ LLPanelBlockedList::showPanelAndSelect(mute.mID);
+ }
+ }
+
+ return true;
+ }
+};
+
class LLWorldEnableBuyLand : public view_listener_t
{
bool handleEvent(const LLSD& userdata)
@@ -8713,6 +8754,9 @@ void initialize_menus()
view_listener_t::addMenu(new LLLandBuyPass(), "Land.BuyPass");
view_listener_t::addMenu(new LLLandEdit(), "Land.Edit");
+ // Particle muting
+ view_listener_t::addMenu(new LLMuteParticle(), "Particle.Mute");
+
view_listener_t::addMenu(new LLLandEnableBuyPass(), "Land.EnableBuyPass");
commit.add("Land.Buy", boost::bind(&handle_buy_land));
@@ -8735,6 +8779,7 @@ void initialize_menus()
enable.add("EnablePayObject", boost::bind(&enable_pay_object));
enable.add("EnablePayAvatar", boost::bind(&enable_pay_avatar));
enable.add("EnableEdit", boost::bind(&enable_object_edit));
+ enable.add("EnableMuteParticle", boost::bind(&enable_mute_particle));
enable.add("VisibleBuild", boost::bind(&enable_object_build));
commit.add("Pathfinding.Linksets.Select", boost::bind(&LLFloaterPathfindingLinksets::openLinksetsWithSelectedObjects));
enable.add("EnableSelectInPathfindingLinksets", boost::bind(&enable_object_select_in_pathfinding_linksets));
diff --git a/indra/newview/llviewermenu.h b/indra/newview/llviewermenu.h
index 143420e227..7f09fc2d8f 100755
--- a/indra/newview/llviewermenu.h
+++ b/indra/newview/llviewermenu.h
@@ -177,6 +177,7 @@ extern LLContextMenu *gMenuObject;
extern LLContextMenu *gMenuAttachmentSelf;
extern LLContextMenu *gMenuAttachmentOther;
extern LLContextMenu *gMenuLand;
+extern LLContextMenu *gMenuMuteParticle;
// Needed to build menus when attachment site list available
extern LLMenuGL* gAttachSubMenu;
diff --git a/indra/newview/llviewermessage.cpp b/indra/newview/llviewermessage.cpp
index c7901f0bd8..e3335c9cd8 100755
--- a/indra/newview/llviewermessage.cpp
+++ b/indra/newview/llviewermessage.cpp
@@ -259,11 +259,15 @@ bool friendship_offer_callback(const LLSD& notification, const LLSD& response)
break;
}
- LLNotificationFormPtr modified_form(new LLNotificationForm(*notification_ptr->getForm()));
- modified_form->setElementEnabled("Accept", false);
- modified_form->setElementEnabled("Decline", false);
- notification_ptr->updateForm(modified_form);
- notification_ptr->repost();
+ // TODO: this set of calls has undesirable behavior under Windows OS (CHUI-985):
+ // here appears three additional toasts instead one modified
+ // need investigation and fix
+
+ // LLNotificationFormPtr modified_form(new LLNotificationForm(*notification_ptr->getForm()));
+ // modified_form->setElementEnabled("Accept", false);
+ // modified_form->setElementEnabled("Decline", false);
+ // notification_ptr->updateForm(modified_form);
+ // notification_ptr->repost();
}
return false;
@@ -2649,7 +2653,8 @@ void process_improved_im(LLMessageSystem *msg, void **user_data)
{
send_do_not_disturb_message(msg, from_id);
}
- else
+
+ if (!is_muted)
{
LL_INFOS("Messaging") << "Received IM_GROUP_INVITATION message." << LL_ENDL;
// Read the binary bucket for more information.
@@ -3673,6 +3678,7 @@ void process_chat_from_simulator(LLMessageSystem *msg, void **user_data)
LLSD msg_notify = LLSD(LLSD::emptyMap());
msg_notify["session_id"] = LLUUID();
msg_notify["from_id"] = chat.mFromID;
+ msg_notify["source_type"] = chat.mSourceType;
on_new_message(msg_notify);
}
}
@@ -4570,7 +4576,6 @@ void process_kill_object(LLMessageSystem *mesgsys, void **user_data)
if (id == LLUUID::null)
{
LL_DEBUGS("Messaging") << "Unknown kill for local " << local_id << LL_ENDL;
- gObjectList.mNumUnknownKills++;
continue;
}
else
@@ -4594,18 +4599,12 @@ void process_kill_object(LLMessageSystem *mesgsys, void **user_data)
// Do the kill
gObjectList.killObject(objectp);
}
- else
- {
- LL_WARNS("Messaging") << "Object in UUID lookup, but not on object list in kill!" << LL_ENDL;
- gObjectList.mNumUnknownKills++;
- }
}
// We should remove the object from selection after it is marked dead by gObjectList to make LLToolGrab,
// which is using the object, release the mouse capture correctly when the object dies.
// See LLToolGrab::handleHoverActive() and LLToolGrab::handleHoverNonPhysical().
LLSelectMgr::getInstance()->removeObjectFromSelections(id);
-
}
}
@@ -7327,8 +7326,12 @@ void process_script_teleport_request(LLMessageSystem* msg, void**)
LLFloaterWorldMap* instance = LLFloaterWorldMap::getInstance();
if(instance)
{
- instance->trackURL(
- sim_name, (S32)pos.mV[VX], (S32)pos.mV[VY], (S32)pos.mV[VZ]);
+ llinfos << "Object named " << object_name
+ << " is offering TP to region "
+ << sim_name << " position " << pos
+ << llendl;
+
+ instance->trackURL(sim_name, (S32)pos.mV[VX], (S32)pos.mV[VY], (S32)pos.mV[VZ]);
LLFloaterReg::showInstance("world_map", "center");
}
diff --git a/indra/newview/llviewerobjectlist.cpp b/indra/newview/llviewerobjectlist.cpp
index caacf26cb3..66615657d8 100755
--- a/indra/newview/llviewerobjectlist.cpp
+++ b/indra/newview/llviewerobjectlist.cpp
@@ -106,7 +106,6 @@ LLViewerObjectList::LLViewerObjectList()
mNumNewObjects = 0;
mWasPaused = FALSE;
mNumDeadObjectUpdates = 0;
- mNumUnknownKills = 0;
mNumUnknownUpdates = 0;
}
diff --git a/indra/newview/llviewerobjectlist.h b/indra/newview/llviewerobjectlist.h
index 449a4633ff..6518c25d09 100755
--- a/indra/newview/llviewerobjectlist.h
+++ b/indra/newview/llviewerobjectlist.h
@@ -188,7 +188,6 @@ public:
S32 mNumUnknownUpdates;
S32 mNumDeadObjectUpdates;
- S32 mNumUnknownKills;
S32 mNumDeadObjects;
protected:
std::vector<U64> mOrphanParents; // LocalID/ip,port of orphaned objects
diff --git a/indra/newview/llviewerpartsim.cpp b/indra/newview/llviewerpartsim.cpp
index 6bd9f66b9c..61cdfd7818 100755
--- a/indra/newview/llviewerpartsim.cpp
+++ b/indra/newview/llviewerpartsim.cpp
@@ -488,9 +488,13 @@ void LLViewerPartSim::destroyClass()
//static
BOOL LLViewerPartSim::shouldAddPart()
{
- if (sParticleCount > PART_THROTTLE_THRESHOLD*sMaxParticleCount)
+ if (sParticleCount >= MAX_PART_COUNT)
{
+ return FALSE;
+ }
+ if (sParticleCount > PART_THROTTLE_THRESHOLD*sMaxParticleCount)
+ {
F32 frac = (F32)sParticleCount/(F32)sMaxParticleCount;
frac -= PART_THROTTLE_THRESHOLD;
frac *= PART_THROTTLE_RESCALE;
@@ -500,7 +504,10 @@ BOOL LLViewerPartSim::shouldAddPart()
return FALSE;
}
}
- if (sParticleCount >= MAX_PART_COUNT)
+
+ // Check frame rate, and don't add more if the viewer is really slow
+ const F32 MIN_FRAME_RATE_FOR_NEW_PARTICLES = 4.f;
+ if (gFPSClamped < MIN_FRAME_RATE_FOR_NEW_PARTICLES)
{
return FALSE;
}
diff --git a/indra/newview/llviewertexture.cpp b/indra/newview/llviewertexture.cpp
index 6cc9f4ace1..84f66c359f 100755
--- a/indra/newview/llviewertexture.cpp
+++ b/indra/newview/llviewertexture.cpp
@@ -1199,10 +1199,10 @@ void LLViewerFetchedTexture::dump()
// ONLY called from LLViewerFetchedTextureList
void LLViewerFetchedTexture::destroyTexture()
{
- //if(LLImageGL::sGlobalTextureMemoryInBytes < sMaxDesiredTextureMemInBytes)//not ready to release unused memory.
- //{
- // return ;
- //}
+ if(LLImageGL::sGlobalTextureMemoryInBytes < sMaxDesiredTextureMemInBytes * 0.95f)//not ready to release unused memory.
+ {
+ return ;
+ }
if (mNeedsCreateTexture)//return if in the process of generating a new texture.
{
return ;
@@ -1290,7 +1290,12 @@ void LLViewerFetchedTexture::addToCreateTexture()
destroyRawImage();
return ;
}
- mRawImage->scale(w >> i, h >> i) ;
+
+ {
+ //make a duplicate in case somebody else is using this raw image
+ mRawImage = mRawImage->duplicate();
+ mRawImage->scale(w >> i, h >> i) ;
+ }
}
}
}
@@ -1521,7 +1526,7 @@ F32 LLViewerFetchedTexture::calcDecodePriority()
else if (pixel_priority < 0.001f && !have_all_data)
{
// Not on screen but we might want some data
- if (mBoostLevel > BOOST_HIGH)
+ if (mBoostLevel > BOOST_SELECTED)
{
// Always want high boosted images
priority = 1.f;
@@ -2669,7 +2674,11 @@ void LLViewerFetchedTexture::setCachedRawImage()
--i ;
}
- mRawImage->scale(w >> i, h >> i) ;
+ {
+ //make a duplicate in case somebody else is using this raw image
+ mRawImage = mRawImage->duplicate();
+ mRawImage->scale(w >> i, h >> i) ;
+ }
}
mCachedRawImage = mRawImage ;
mRawDiscardLevel += i ;
diff --git a/indra/newview/llviewertexture.h b/indra/newview/llviewertexture.h
index c96f89017f..10101a4b9b 100755
--- a/indra/newview/llviewertexture.h
+++ b/indra/newview/llviewertexture.h
@@ -101,6 +101,7 @@ public:
INVALID_TEXTURE_TYPE
};
+
typedef std::vector<LLFace*> ll_face_list_t;
typedef std::vector<LLVOVolume*> ll_volume_list_t;
diff --git a/indra/newview/llviewerwindow.cpp b/indra/newview/llviewerwindow.cpp
index 65a906d3c0..40b8560071 100755
--- a/indra/newview/llviewerwindow.cpp
+++ b/indra/newview/llviewerwindow.cpp
@@ -229,7 +229,9 @@ LLFrameTimer gAwayTriggerTimer;
BOOL gShowOverlayTitle = FALSE;
LLViewerObject* gDebugRaycastObject = NULL;
+LLVOPartGroup* gDebugRaycastParticle = NULL;
LLVector4a gDebugRaycastIntersection;
+LLVector4a gDebugRaycastParticleIntersection;
LLVector2 gDebugRaycastTexCoord;
LLVector4a gDebugRaycastNormal;
LLVector4a gDebugRaycastTangent;
@@ -1811,7 +1813,6 @@ void LLViewerWindow::initBase()
gFloaterView = main_view->getChild<LLFloaterView>("Floater View");
gFloaterView->setFloaterSnapView(main_view->getChild<LLView>("floater_snap_region")->getHandle());
gSnapshotFloaterView = main_view->getChild<LLSnapshotFloaterView>("Snapshot Floater View");
-
// Console
llassert( !gConsole );
@@ -2844,6 +2845,8 @@ void LLViewerWindow::updateUI()
&gDebugRaycastTangent,
&gDebugRaycastStart,
&gDebugRaycastEnd);
+
+ gDebugRaycastParticle = gPipeline.lineSegmentIntersectParticle(gDebugRaycastStart, gDebugRaycastEnd, &gDebugRaycastParticleIntersection, NULL);
}
updateMouseDelta();
@@ -3664,7 +3667,7 @@ void LLViewerWindow::pickAsync(S32 x, S32 y_from_bot, MASK mask, void (*callback
pick_transparent = TRUE;
}
- LLPickInfo pick_info(LLCoordGL(x, y_from_bot), mask, pick_transparent, TRUE, callback);
+ LLPickInfo pick_info(LLCoordGL(x, y_from_bot), mask, pick_transparent, FALSE, TRUE, callback);
schedulePick(pick_info);
}
@@ -3720,7 +3723,7 @@ void LLViewerWindow::returnEmptyPicks()
}
// Performs the GL object/land pick.
-LLPickInfo LLViewerWindow::pickImmediate(S32 x, S32 y_from_bot, BOOL pick_transparent)
+LLPickInfo LLViewerWindow::pickImmediate(S32 x, S32 y_from_bot, BOOL pick_transparent, BOOL pick_particle)
{
BOOL in_build_mode = LLFloaterReg::instanceVisible("build");
if (in_build_mode || LLDrawPoolAlpha::sShowDebugAlpha)
@@ -3729,10 +3732,10 @@ LLPickInfo LLViewerWindow::pickImmediate(S32 x, S32 y_from_bot, BOOL pick_trans
// "Show Debug Alpha" means no object actually transparent
pick_transparent = TRUE;
}
-
+
// shortcut queueing in mPicks and just update mLastPick in place
MASK key_mask = gKeyboard->currentMask(TRUE);
- mLastPick = LLPickInfo(LLCoordGL(x, y_from_bot), key_mask, pick_transparent, TRUE, NULL);
+ mLastPick = LLPickInfo(LLCoordGL(x, y_from_bot), key_mask, pick_transparent, pick_particle, TRUE, NULL);
mLastPick.fetchResults();
return mLastPick;
@@ -4291,7 +4294,8 @@ BOOL LLViewerWindow::rawSnapshot(LLImageRaw *raw, S32 image_width, S32 image_hei
F32 scale_factor = 1.0f ;
if (!keep_window_aspect || (image_width > window_width) || (image_height > window_height))
{
- if ((image_width > window_width || image_height > window_height) && LLPipeline::sRenderDeferred && !show_ui)
+ if ((image_width <= gGLManager.mGLMaxTextureSize && image_height <= gGLManager.mGLMaxTextureSize) &&
+ (image_width > window_width || image_height > window_height) && LLPipeline::sRenderDeferred && !show_ui)
{
if (scratch_space.allocate(image_width, image_height, GL_RGBA, true, true))
{
@@ -4306,6 +4310,8 @@ BOOL LLViewerWindow::rawSnapshot(LLImageRaw *raw, S32 image_width, S32 image_hei
snapshot_height = image_height;
reset_deferred = true;
mWorldViewRectRaw.set(0, image_height, image_width, 0);
+ LLViewerCamera::getInstance()->setViewHeightInPixels( mWorldViewRectRaw.getHeight() );
+ LLViewerCamera::getInstance()->setAspect( getWorldViewAspectRatio() );
scratch_space.bindTarget();
}
else
@@ -4515,6 +4521,8 @@ BOOL LLViewerWindow::rawSnapshot(LLImageRaw *raw, S32 image_width, S32 image_hei
if (reset_deferred)
{
mWorldViewRectRaw = window_rect;
+ LLViewerCamera::getInstance()->setViewHeightInPixels( mWorldViewRectRaw.getHeight() );
+ LLViewerCamera::getInstance()->setAspect( getWorldViewAspectRatio() );
scratch_space.flush();
scratch_space.release();
gPipeline.allocateScreenBuffer(original_width, original_height);
@@ -5128,13 +5136,15 @@ LLPickInfo::LLPickInfo()
mTangent(),
mBinormal(),
mHUDIcon(NULL),
- mPickTransparent(FALSE)
+ mPickTransparent(FALSE),
+ mPickParticle(FALSE)
{
}
LLPickInfo::LLPickInfo(const LLCoordGL& mouse_pos,
MASK keyboard_mask,
BOOL pick_transparent,
+ BOOL pick_particle,
BOOL pick_uv_coords,
void (*pick_callback)(const LLPickInfo& pick_info))
: mMousePt(mouse_pos),
@@ -5150,7 +5160,8 @@ LLPickInfo::LLPickInfo(const LLCoordGL& mouse_pos,
mTangent(),
mBinormal(),
mHUDIcon(NULL),
- mPickTransparent(pick_transparent)
+ mPickTransparent(pick_transparent),
+ mPickParticle(pick_particle)
{
}
@@ -5168,6 +5179,10 @@ void LLPickInfo::fetchResults()
LLVector4a origin;
origin.load3(LLViewerCamera::getInstance()->getOrigin().mV);
F32 icon_dist = 0.f;
+ LLVector4a start;
+ LLVector4a end;
+ LLVector4a particle_end;
+
if (hit_icon)
{
LLVector4a delta;
@@ -5177,14 +5192,24 @@ void LLPickInfo::fetchResults()
LLViewerObject* hit_object = gViewerWindow->cursorIntersect(mMousePt.mX, mMousePt.mY, 512.f,
NULL, -1, mPickTransparent, &face_hit,
- &intersection, &uv, &normal, &tangent);
+ &intersection, &uv, &normal, &tangent, &start, &end);
mPickPt = mMousePt;
U32 te_offset = face_hit > -1 ? face_hit : 0;
- //unproject relative clicked coordinate from window coordinate using GL
-
+ if (mPickParticle)
+ { //get the end point of line segement to use for particle raycast
+ if (hit_object)
+ {
+ particle_end = intersection;
+ }
+ else
+ {
+ particle_end = end;
+ }
+ }
+
LLViewerObject* objectp = hit_object;
@@ -5199,6 +5224,7 @@ void LLPickInfo::fetchResults()
mHUDIcon = hit_icon;
mPickType = PICK_ICON;
mPosGlobal = mHUDIcon->getPositionGlobal();
+
}
else if (objectp)
{
@@ -5248,6 +5274,18 @@ void LLPickInfo::fetchResults()
}
}
+ if (mPickParticle)
+ { //search for closest particle to click origin out to intersection point
+ S32 part_face = -1;
+
+ LLVOPartGroup* group = gPipeline.lineSegmentIntersectParticle(start, particle_end, NULL, &part_face);
+ if (group)
+ {
+ mParticleOwnerID = group->getPartOwner(part_face);
+ mParticleSourceID = group->getPartSource(part_face);
+ }
+ }
+
if (mPickCallback)
{
mPickCallback(*this);
diff --git a/indra/newview/llviewerwindow.h b/indra/newview/llviewerwindow.h
index 89f6e3bc26..c16b80b214 100755
--- a/indra/newview/llviewerwindow.h
+++ b/indra/newview/llviewerwindow.h
@@ -65,6 +65,7 @@ class LLWindow;
class LLRootView;
class LLWindowListener;
class LLViewerWindowListener;
+class LLVOPartGroup;
class LLPopupView;
#define PICK_HALF_WIDTH 5
@@ -87,7 +88,8 @@ public:
LLPickInfo();
LLPickInfo(const LLCoordGL& mouse_pos,
MASK keyboard_mask,
- BOOL pick_transparent,
+ BOOL pick_transparent,
+ BOOL pick_particle,
BOOL pick_surface_info,
void (*pick_callback)(const LLPickInfo& pick_info));
@@ -108,6 +110,8 @@ public:
LLVector3d mPosGlobal;
LLVector3 mObjectOffset;
LLUUID mObjectID;
+ LLUUID mParticleOwnerID;
+ LLUUID mParticleSourceID;
S32 mObjectFace;
LLHUDIcon* mHUDIcon;
LLVector3 mIntersection;
@@ -118,6 +122,7 @@ public:
LLVector4 mTangent;
LLVector3 mBinormal;
BOOL mPickTransparent;
+ BOOL mPickParticle;
void getSurfaceInfo();
private:
@@ -356,7 +361,7 @@ public:
void returnEmptyPicks();
void pickAsync(S32 x, S32 y_from_bot, MASK mask, void (*callback)(const LLPickInfo& pick_info), BOOL pick_transparent = FALSE);
- LLPickInfo pickImmediate(S32 x, S32 y, BOOL pick_transparent);
+ LLPickInfo pickImmediate(S32 x, S32 y, BOOL pick_transparent, BOOL pick_particle = FALSE);
LLHUDIcon* cursorIntersectIcon(S32 mouse_x, S32 mouse_y, F32 depth,
LLVector4a* intersection);
@@ -501,6 +506,8 @@ extern LLFrameTimer gAwayTriggerTimer; // how long the avatar has been away
extern LLViewerObject* gDebugRaycastObject;
extern LLVector4a gDebugRaycastIntersection;
+extern LLVOPartGroup* gDebugRaycastParticle;
+extern LLVector4a gDebugRaycastParticleIntersection;
extern LLVector2 gDebugRaycastTexCoord;
extern LLVector4a gDebugRaycastNormal;
extern LLVector4a gDebugRaycastTangent;
diff --git a/indra/newview/llvopartgroup.cpp b/indra/newview/llvopartgroup.cpp
index 43a5ddba42..8ed86b4fd5 100755
--- a/indra/newview/llvopartgroup.cpp
+++ b/indra/newview/llvopartgroup.cpp
@@ -193,8 +193,14 @@ void LLVOPartGroup::updateSpatialExtents(LLVector4a& newMin, LLVector4a& newMax)
const LLVector3& pos_agent = getPositionAgent();
newMin.load3( (pos_agent - mScale).mV);
newMax.load3( (pos_agent + mScale).mV);
+
+ llassert(newMin.isFinite3());
+ llassert(newMax.isFinite3());
+
LLVector4a pos;
pos.load3(pos_agent.mV);
+
+ llassert(pos.isFinite3());
mDrawable->setPositionGroup(pos);
}
@@ -234,6 +240,37 @@ LLDrawable* LLVOPartGroup::createDrawable(LLPipeline *pipeline)
const F32 MAX_PARTICLE_AREA_SCALE = 0.02f; // some tuned constant, limits on how much particle area to draw
+ LLUUID LLVOPartGroup::getPartOwner(S32 idx)
+ {
+ LLUUID ret = LLUUID::null;
+
+ if (idx < (S32) mViewerPartGroupp->mParticles.size())
+ {
+ ret = mViewerPartGroupp->mParticles[idx]->mPartSourcep->getOwnerUUID();
+ }
+
+ return ret;
+ }
+
+ LLUUID LLVOPartGroup::getPartSource(S32 idx)
+ {
+ LLUUID ret = LLUUID::null;
+
+ if (idx < (S32) mViewerPartGroupp->mParticles.size())
+ {
+ LLViewerPart* part = mViewerPartGroupp->mParticles[idx];
+ if (part && part->mPartSourcep.notNull() &&
+ part->mPartSourcep->mSourceObjectp.notNull())
+ {
+ LLViewerObject* source = part->mPartSourcep->mSourceObjectp;
+ ret = source->getID();
+ }
+ }
+
+ return ret;
+ }
+
+
F32 LLVOPartGroup::getPartSize(S32 idx)
{
if (idx < (S32) mViewerPartGroupp->mParticles.size())
@@ -316,6 +353,10 @@ BOOL LLVOPartGroup::updateGeometry(LLDrawable *drawable)
inv_camera_dist_squared = 1.f / camera_dist_squared;
else
inv_camera_dist_squared = 1.f;
+
+ llassert(llfinite(inv_camera_dist_squared));
+ llassert(!llisnan(inv_camera_dist_squared));
+
F32 area = part->mScale.mV[0] * part->mScale.mV[1] * inv_camera_dist_squared;
tot_area = llmax(tot_area, area);
@@ -387,20 +428,63 @@ BOOL LLVOPartGroup::updateGeometry(LLDrawable *drawable)
return TRUE;
}
-void LLVOPartGroup::getGeometry(S32 idx,
- LLStrider<LLVector4a>& verticesp,
- LLStrider<LLVector3>& normalsp,
- LLStrider<LLVector2>& texcoordsp,
- LLStrider<LLColor4U>& colorsp,
- LLStrider<U16>& indicesp)
+
+BOOL LLVOPartGroup::lineSegmentIntersect(const LLVector4a& start, const LLVector4a& end,
+ S32 face,
+ BOOL pick_transparent,
+ S32* face_hit,
+ LLVector4a* intersection,
+ LLVector2* tex_coord,
+ LLVector4a* normal,
+ LLVector4a* bi_normal)
{
- if (idx >= (S32) mViewerPartGroupp->mParticles.size())
+ LLVector4a dir;
+ dir.setSub(end, start);
+
+ F32 closest_t = 2.f;
+ BOOL ret = FALSE;
+
+ for (U32 idx = 0; idx < mViewerPartGroupp->mParticles.size(); ++idx)
{
- return;
+ const LLViewerPart &part = *((LLViewerPart*) (mViewerPartGroupp->mParticles[idx]));
+
+ LLVector4a v[4];
+ LLStrider<LLVector4a> verticesp;
+ verticesp = v;
+
+ getGeometry(part, verticesp);
+
+ F32 a,b,t;
+ if (LLTriangleRayIntersect(v[0], v[1], v[2], start, dir, a,b,t) ||
+ LLTriangleRayIntersect(v[1], v[3], v[2], start, dir, a,b,t))
+ {
+ if (t >= 0.f &&
+ t <= 1.f &&
+ t < closest_t)
+ {
+ ret = TRUE;
+ closest_t = t;
+ if (face_hit)
+ {
+ *face_hit = idx;
+ }
+
+ if (intersection)
+ {
+ LLVector4a intersect = dir;
+ intersect.mul(closest_t);
+ intersection->setAdd(intersect, start);
+ }
+ }
+ }
}
- const LLViewerPart &part = *((LLViewerPart*) (mViewerPartGroupp->mParticles[idx]));
+ return ret;
+}
+void LLVOPartGroup::getGeometry(const LLViewerPart& part,
+ LLStrider<LLVector4a>& verticesp)
+{
LLVector4a part_pos_agent;
part_pos_agent.load3(part.mPosAgent.mV);
LLVector4a camera_agent;
@@ -452,8 +536,6 @@ void LLVOPartGroup::getGeometry(S32 idx,
up.mul(0.5f*part.mScale.mV[1]);
- LLVector3 normal = -LLViewerCamera::getInstance()->getXAxis();
-
//HACK -- the verticesp->mV[3] = 0.f here are to set the texture index to 0 (particles don't use texture batching, maybe they should)
// this works because there is actually a 4th float stored after the vertex position which is used as a texture index
// also, somebody please VECTORIZE THIS
@@ -472,6 +554,25 @@ void LLVOPartGroup::getGeometry(S32 idx,
(*verticesp++).getF32ptr()[3] = 0.f;
verticesp->setAdd(ppamu, right);
(*verticesp++).getF32ptr()[3] = 0.f;
+}
+
+
+
+void LLVOPartGroup::getGeometry(S32 idx,
+ LLStrider<LLVector4a>& verticesp,
+ LLStrider<LLVector3>& normalsp,
+ LLStrider<LLVector2>& texcoordsp,
+ LLStrider<LLColor4U>& colorsp,
+ LLStrider<U16>& indicesp)
+{
+ if (idx >= (S32) mViewerPartGroupp->mParticles.size())
+ {
+ return;
+ }
+
+ const LLViewerPart &part = *((LLViewerPart*) (mViewerPartGroupp->mParticles[idx]));
+
+ getGeometry(part, verticesp);
*colorsp++ = part.mColor;
*colorsp++ = part.mColor;
@@ -480,6 +581,7 @@ void LLVOPartGroup::getGeometry(S32 idx,
if (!(part.mFlags & LLPartData::LL_PART_EMISSIVE_MASK))
{ //not fullbright, needs normal
+ LLVector3 normal = -LLViewerCamera::getInstance()->getXAxis();
*normalsp++ = normal;
*normalsp++ = normal;
*normalsp++ = normal;
diff --git a/indra/newview/llvopartgroup.h b/indra/newview/llvopartgroup.h
index 42c1252d01..2befb01823 100755
--- a/indra/newview/llvopartgroup.h
+++ b/indra/newview/llvopartgroup.h
@@ -69,11 +69,23 @@ public:
virtual void updateSpatialExtents(LLVector4a& newMin, LLVector4a& newMax);
virtual U32 getPartitionType() const;
+ /*virtual*/ BOOL lineSegmentIntersect(const LLVector4a& start, const LLVector4a& end,
+ S32 face,
+ BOOL pick_transparent,
+ S32* face_hit,
+ LLVector4a* intersection,
+ LLVector2* tex_coord,
+ LLVector4a* normal,
+ LLVector4a* tangent);
+
/*virtual*/ void setPixelAreaAndAngle(LLAgent &agent);
/*virtual*/ void updateTextures();
/*virtual*/ LLDrawable* createDrawable(LLPipeline *pipeline);
/*virtual*/ BOOL updateGeometry(LLDrawable *drawable);
+ void getGeometry(const LLViewerPart& part,
+ LLStrider<LLVector4a>& verticesp);
+
void getGeometry(S32 idx,
LLStrider<LLVector4a>& verticesp,
LLStrider<LLVector3>& normalsp,
@@ -83,6 +95,9 @@ public:
void updateFaceSize(S32 idx) { }
F32 getPartSize(S32 idx);
+ LLUUID getPartOwner(S32 idx);
+ LLUUID getPartSource(S32 idx);
+
void setViewerPartGroup(LLViewerPartGroup *part_groupp) { mViewerPartGroupp = part_groupp; }
LLViewerPartGroup* getViewerPartGroup() { return mViewerPartGroupp; }
diff --git a/indra/newview/llvovolume.cpp b/indra/newview/llvovolume.cpp
index 3be1f52352..e6385dceea 100755
--- a/indra/newview/llvovolume.cpp
+++ b/indra/newview/llvovolume.cpp
@@ -1113,7 +1113,13 @@ void LLVOVolume::sculpt()
S32 max_discard = mSculptTexture->getMaxDiscardLevel();
if (discard_level > max_discard)
- discard_level = max_discard; // clamp to the best we can do
+ {
+ discard_level = max_discard; // clamp to the best we can do
+ }
+ if(discard_level > MAX_DISCARD_LEVEL)
+ {
+ return; //we think data is not ready yet.
+ }
S32 current_discard = getVolume()->getSculptLevel() ;
if(current_discard < -2)
@@ -1452,7 +1458,7 @@ BOOL LLVOVolume::genBBoxes(BOOL force_global)
continue;
}
res &= face->genVolumeBBoxes(*volume, i,
- mRelativeXform, mRelativeXformInvTrans,
+ mRelativeXform,
(mVolumeImpl && mVolumeImpl->isVolumeGlobal()) || force_global);
if (rebuild)
@@ -4833,7 +4839,14 @@ void LLVolumeGeometryManager::rebuildGeom(LLSpatialGroup* group)
if (is_rigged)
{
- drawablep->setState(LLDrawable::RIGGED);
+ if (!drawablep->isState(LLDrawable::RIGGED))
+ {
+ drawablep->setState(LLDrawable::RIGGED);
+
+ //first time this is drawable is being marked as rigged,
+ // do another LoD update to use avatar bounding box
+ vobj->updateLOD();
+ }
}
else
{
diff --git a/indra/newview/noise.h b/indra/newview/noise.h
index 0923bffcf2..b3efad73c5 100755
--- a/indra/newview/noise.h
+++ b/indra/newview/noise.h
@@ -310,6 +310,8 @@ static void normalize3(F32 v[3])
static void init(void)
{
+ // we want repeatable noise (e.g. for stable terrain texturing), so seed with known value
+ srand(42);
int i, j, k;
for (i = 0 ; i < B ; i++) {
@@ -340,6 +342,9 @@ static void init(void)
for (j = 0 ; j < 3 ; j++)
g3[B + i][j] = g3[i][j];
}
+
+ // reintroduce entropy
+ srand(time(NULL)); // Flawfinder: ignore
}
#undef B
diff --git a/indra/newview/pipeline.cpp b/indra/newview/pipeline.cpp
index c25d22bbdf..f49395da34 100755
--- a/indra/newview/pipeline.cpp
+++ b/indra/newview/pipeline.cpp
@@ -163,6 +163,7 @@ S32 LLPipeline::RenderGlowIterations;
F32 LLPipeline::RenderGlowWidth;
F32 LLPipeline::RenderGlowStrength;
BOOL LLPipeline::RenderDepthOfField;
+BOOL LLPipeline::RenderDepthOfFieldInEditMode;
F32 LLPipeline::CameraFocusTransitionTime;
F32 LLPipeline::CameraFNumber;
F32 LLPipeline::CameraFocalLength;
@@ -615,6 +616,7 @@ void LLPipeline::init()
connectRefreshCachedSettingsSafe("RenderGlowWidth");
connectRefreshCachedSettingsSafe("RenderGlowStrength");
connectRefreshCachedSettingsSafe("RenderDepthOfField");
+ connectRefreshCachedSettingsSafe("RenderDepthOfFieldInEditMode");
connectRefreshCachedSettingsSafe("CameraFocusTransitionTime");
connectRefreshCachedSettingsSafe("CameraFNumber");
connectRefreshCachedSettingsSafe("CameraFocalLength");
@@ -1125,6 +1127,7 @@ void LLPipeline::refreshCachedSettings()
RenderGlowWidth = gSavedSettings.getF32("RenderGlowWidth");
RenderGlowStrength = gSavedSettings.getF32("RenderGlowStrength");
RenderDepthOfField = gSavedSettings.getBOOL("RenderDepthOfField");
+ RenderDepthOfFieldInEditMode = gSavedSettings.getBOOL("RenderDepthOfFieldInEditMode");
CameraFocusTransitionTime = gSavedSettings.getF32("CameraFocusTransitionTime");
CameraFNumber = gSavedSettings.getF32("CameraFNumber");
CameraFocalLength = gSavedSettings.getF32("CameraFocalLength");
@@ -4864,18 +4867,6 @@ void LLPipeline::renderPhysicsDisplay()
}
}
- for (LLCullResult::bridge_iterator i = sCull->beginVisibleBridge(); i != sCull->endVisibleBridge(); ++i)
- {
- LLSpatialBridge* bridge = *i;
- if (!bridge->isDead() && hasRenderType(bridge->mDrawableType))
- {
- gGL.pushMatrix();
- gGL.multMatrix((F32*)bridge->mDrawable->getRenderMatrix().mMatrix);
- bridge->renderPhysicsShapes();
- gGL.popMatrix();
- }
- }
-
gGL.flush();
if (LLGLSLShader::sNoFixedFunction)
@@ -5323,6 +5314,42 @@ void LLPipeline::renderDebug()
gUIProgram.bind();
}
+ if (hasRenderDebugMask(LLPipeline::RENDER_DEBUG_RAYCAST) && !hud_only)
+ { //draw crosshairs on particle intersection
+ if (gDebugRaycastParticle)
+ {
+ if (LLGLSLShader::sNoFixedFunction)
+ { //this debug display requires shaders
+ gDebugProgram.bind();
+
+ gGL.getTexUnit(0)->unbind(LLTexUnit::TT_TEXTURE);
+
+ LLVector3 center(gDebugRaycastParticleIntersection.getF32ptr());
+ LLVector3 size(0.1f, 0.1f, 0.1f);
+
+ LLVector3 p[6];
+
+ p[0] = center + size.scaledVec(LLVector3(1,0,0));
+ p[1] = center + size.scaledVec(LLVector3(-1,0,0));
+ p[2] = center + size.scaledVec(LLVector3(0,1,0));
+ p[3] = center + size.scaledVec(LLVector3(0,-1,0));
+ p[4] = center + size.scaledVec(LLVector3(0,0,1));
+ p[5] = center + size.scaledVec(LLVector3(0,0,-1));
+
+ gGL.begin(LLRender::LINES);
+ gGL.diffuseColor3f(1.f, 1.f, 0.f);
+ for (U32 i = 0; i < 6; i++)
+ {
+ gGL.vertex3fv(p[i].mV);
+ }
+ gGL.end();
+ gGL.flush();
+
+ gDebugProgram.unbind();
+ }
+ }
+ }
+
if (hasRenderDebugMask(LLPipeline::RENDER_DEBUG_SHADOW_FRUSTA))
{
LLVertexBuffer::unbind();
@@ -5356,7 +5383,7 @@ void LLPipeline::renderDebug()
if (i > 3)
{ //render shadow frusta as volumes
if (mShadowFrustPoints[i-4].empty())
- {
+ {
continue;
}
@@ -7003,6 +7030,48 @@ void LLPipeline::setRenderHighlightTextureChannel(LLRender::eTexIndex channel)
sRenderHighlightTextureChannel = channel;
}
+LLVOPartGroup* LLPipeline::lineSegmentIntersectParticle(const LLVector4a& start, const LLVector4a& end, LLVector4a* intersection,
+ S32* face_hit)
+{
+ LLVector4a local_end = end;
+
+ LLVector4a position;
+
+ LLDrawable* drawable = NULL;
+
+ for (LLWorld::region_list_t::const_iterator iter = LLWorld::getInstance()->getRegionList().begin();
+ iter != LLWorld::getInstance()->getRegionList().end(); ++iter)
+ {
+ LLViewerRegion* region = *iter;
+
+ LLSpatialPartition* part = region->getSpatialPartition(LLViewerRegion::PARTITION_PARTICLE);
+ if (part && hasRenderType(part->mDrawableType))
+ {
+ LLDrawable* hit = part->lineSegmentIntersect(start, local_end, TRUE, face_hit, &position, NULL, NULL, NULL);
+ if (hit)
+ {
+ drawable = hit;
+ local_end = position;
+ }
+ }
+ }
+
+ LLVOPartGroup* ret = NULL;
+ if (drawable)
+ {
+ //make sure we're returning an LLVOPartGroup
+ llassert(drawable->getVObj()->getPCode() == LLViewerObject::LL_VO_PART_GROUP);
+ ret = (LLVOPartGroup*) drawable->getVObj().get();
+ }
+
+ if (intersection)
+ {
+ *intersection = position;
+ }
+
+ return ret;
+}
+
LLViewerObject* LLPipeline::lineSegmentIntersectInWorld(const LLVector4a& start, const LLVector4a& end,
BOOL pick_transparent,
S32* face_hit,
@@ -7562,7 +7631,7 @@ void LLPipeline::renderBloom(BOOL for_snapshot, F32 zoom_factor, int subfield)
{
bool dof_enabled = !LLViewerCamera::getInstance()->cameraUnderWater() &&
- !LLToolMgr::getInstance()->inBuildMode() &&
+ (RenderDepthOfFieldInEditMode || !LLToolMgr::getInstance()->inBuildMode()) &&
RenderDepthOfField;
@@ -9582,7 +9651,7 @@ BOOL LLPipeline::getVisiblePointCloud(LLCamera& camera, LLVector3& min, LLVector
pp.push_back(LLVector3(max.mV[0], max.mV[1], max.mV[2]));
//add corners of camera frustum
- for (U32 i = 0; i < 8; i++)
+ for (U32 i = 0; i < LLCamera::AGENT_FRUSTRUM_NUM; i++)
{
pp.push_back(camera.mAgentFrustum[i]);
}
@@ -9609,7 +9678,7 @@ BOOL LLPipeline::getVisiblePointCloud(LLCamera& camera, LLVector3& min, LLVector
for (U32 i = 0; i < 12; i++)
{ //for each line segment in bounding box
- for (U32 j = 0; j < 6; j++)
+ for (U32 j = 0; j < LLCamera::AGENT_PLANE_NO_USER_CLIP_NUM; j++)
{ //for each plane in camera frustum
const LLPlane& cp = camera.getAgentPlane(j);
const LLVector3& v1 = pp[bs[i*2+0]];
@@ -9695,19 +9764,19 @@ BOOL LLPipeline::getVisiblePointCloud(LLCamera& camera, LLVector3& min, LLVector
}
}
- for (U32 j = 0; j < 6; ++j)
+ for (U32 j = 0; j < LLCamera::AGENT_PLANE_NO_USER_CLIP_NUM; ++j)
{
const LLPlane& cp = camera.getAgentPlane(j);
F32 dist = cp.dist(pp[i]);
if (dist > 0.05f) //point is above some plane, not contained
- {
+ {
found = false;
break;
- }
- }
+ }
+ }
- if (found)
- {
+ if (found)
+ {
fp.push_back(pp[i]);
}
}
diff --git a/indra/newview/pipeline.h b/indra/newview/pipeline.h
index 70dcf80407..f0bebbe20d 100755
--- a/indra/newview/pipeline.h
+++ b/indra/newview/pipeline.h
@@ -58,6 +58,7 @@ class LLRenderFunc;
class LLCubeMap;
class LLCullResult;
class LLVOAvatar;
+class LLVOPartGroup;
class LLGLSLShader;
class LLCurlRequest;
class LLDrawPoolAlpha;
@@ -202,6 +203,12 @@ public:
LLVector4a* normal = NULL, // return the surface normal at the intersection point
LLVector4a* tangent = NULL // return the surface tangent at the intersection point
);
+
+ //get the closest particle to start between start and end, returns the LLVOPartGroup and particle index
+ LLVOPartGroup* lineSegmentIntersectParticle(const LLVector4a& start, const LLVector4a& end, LLVector4a* intersection,
+ S32* face_hit);
+
+
LLViewerObject* lineSegmentIntersectInHUD(const LLVector4a& start, const LLVector4a& end,
BOOL pick_transparent,
S32* face_hit, // return the face hit
@@ -910,6 +917,7 @@ public:
static F32 RenderGlowWidth;
static F32 RenderGlowStrength;
static BOOL RenderDepthOfField;
+ static BOOL RenderDepthOfFieldInEditMode;
static F32 CameraFocusTransitionTime;
static F32 CameraFNumber;
static F32 CameraFocalLength;
diff --git a/indra/newview/skins/default/colors.xml b/indra/newview/skins/default/colors.xml
index a9176595c7..f53995732f 100755
--- a/indra/newview/skins/default/colors.xml
+++ b/indra/newview/skins/default/colors.xml
@@ -884,4 +884,19 @@
<color
name="blue"
value="0 0 1 1"/>
+
+ <!--Resize bar colors -->
+
+ <color
+ name="ResizebarBorderLight"
+ value="0.231 0.231 0.231 1"/>
+
+ <color
+ name="ResizebarBorderDark"
+ value="0.133 0.133 0.133 1"/>
+
+ <color
+ name="ResizebarBody"
+ value="0.208 0.208 0.208 1"/>
+
</colors>
diff --git a/indra/newview/skins/default/textures/textures.xml b/indra/newview/skins/default/textures/textures.xml
index b0e4b71d21..54f60f4441 100755
--- a/indra/newview/skins/default/textures/textures.xml
+++ b/indra/newview/skins/default/textures/textures.xml
@@ -774,4 +774,7 @@ with the same filename but different name
<texture name="Popup_Caution" file_name="icons/pop_up_caution.png"/>
<texture name="Camera_Drag_Dot" file_name="world/CameraDragDot.png"/>
<texture name="NavBar Separator" file_name="navbar/separator.png"/>
+
+ <texture name="Horizontal Drag Handle" file_name="widgets/horizontal_drag_handle.png"/>
+ <texture name="Vertical Drag Handle" file_name="widgets/vertical_drag_handle.png"/>
</textures>
diff --git a/indra/newview/skins/default/textures/widgets/horizontal_drag_handle.png b/indra/newview/skins/default/textures/widgets/horizontal_drag_handle.png
new file mode 100644
index 0000000000..642eac4065
--- /dev/null
+++ b/indra/newview/skins/default/textures/widgets/horizontal_drag_handle.png
Binary files differ
diff --git a/indra/newview/skins/default/textures/widgets/vertical_drag_handle.png b/indra/newview/skins/default/textures/widgets/vertical_drag_handle.png
new file mode 100644
index 0000000000..b06b70cf36
--- /dev/null
+++ b/indra/newview/skins/default/textures/widgets/vertical_drag_handle.png
Binary files differ
diff --git a/indra/newview/skins/default/xui/en/floater_im_container.xml b/indra/newview/skins/default/xui/en/floater_im_container.xml
index 65f623a47e..1215efb7f9 100755
--- a/indra/newview/skins/default/xui/en/floater_im_container.xml
+++ b/indra/newview/skins/default/xui/en/floater_im_container.xml
@@ -4,6 +4,7 @@
can_minimize="true"
can_resize="true"
height="210"
+ min_height="210"
layout="topleft"
name="floater_im_box"
help_topic="floater_im_box"
@@ -24,24 +25,28 @@
value="Conv_toolbar_expand"/>
<layout_stack
animate="true"
- bottom="-1"
+ bottom="-5"
+ drag_handle_gap="6"
+ drag_handle_first_indent="27"
+ drag_handle_second_indent="10"
follows="all"
layout="topleft"
left="0"
name="conversations_stack"
orientation="horizontal"
right="-1"
+ show_drag_handle="true"
top="0">
<layout_panel
auto_resize="false"
user_resize="true"
name="conversations_layout_panel"
min_dim="38"
- expanded_min_dim="156">
+ expanded_min_dim="136">
<layout_stack
animate="false"
follows="left|top|right"
- height="35"
+ height="27"
layout="topleft"
left="0"
name="conversations_pane_buttons_stack"
@@ -50,7 +55,6 @@
top="0">
<layout_panel
auto_resize="true"
- height="35"
name="conversations_pane_buttons_expanded">
<menu_button
follows="top|left"
@@ -64,7 +68,7 @@
left="5"
name="sort_btn"
tool_tip="View/sort options"
- top="5"
+ top="1"
width="31" />
<button
follows="top|left"
@@ -74,7 +78,7 @@
image_selected="Toolbar_Middle_Selected"
image_unselected="Toolbar_Middle_Off"
layout="topleft"
- top="5"
+ top="1"
left_pad="2"
name="add_btn"
tool_tip="Start a new conversation"
@@ -87,7 +91,7 @@
image_selected="Toolbar_Middle_Selected"
image_unselected="Toolbar_Middle_Off"
layout="topleft"
- top="5"
+ top="1"
left_pad="2"
name="speak_btn"
tool_tip="Speak with people using your microphone"
@@ -95,9 +99,8 @@
</layout_panel>
<layout_panel
auto_resize="false"
- height="35"
name="conversations_pane_buttons_collapsed"
- width="41">
+ width="31">
<button
follows="right|top"
height="25"
@@ -106,8 +109,8 @@
image_selected="Toolbar_Middle_Selected"
image_unselected="Toolbar_Middle_Off"
layout="topleft"
- top="5"
- left="1"
+ top="1"
+ left="0"
name="expand_collapse_btn"
tool_tip="Collapse/Expand this list"
width="31" />
@@ -119,7 +122,7 @@
layout="topleft"
name="conversations_list_panel"
opaque="true"
- top="35"
+ top_pad="0"
left="5"
right="-1"/>
</layout_panel>
@@ -127,7 +130,7 @@
auto_resize="true"
user_resize="true"
name="messages_layout_panel"
- expanded_min_dim="222">
+ expanded_min_dim="212">
<panel_container
bottom="-1"
follows="all"
@@ -136,44 +139,44 @@
name="im_box_tab_container"
right="-1"
top="0">
- <panel
- bottom="-1"
- follows="all"
- layout="topleft"
- name="stub_panel"
- opaque="true"
- top_pad="0"
- left="0"
- right="-1">
- <button
- follows="right|top"
- height="25"
- image_hover_unselected="Toolbar_Middle_Over"
- image_overlay="Conv_toolbar_collapse"
- image_selected="Toolbar_Middle_Selected"
- image_unselected="Toolbar_Middle_Off"
+ <panel
+ bottom="-1"
+ follows="all"
layout="topleft"
- top="5"
- right="-10"
- name="stub_collapse_btn"
- tool_tip="Collapse this pane"
- width="31" />
- <text
- type="string"
- clip_partial="false"
- follows="left|top|right"
- layout="topleft"
- left="15"
- right="-15"
- name="stub_textbox"
- top="25"
- height="40"
- valign="center"
- parse_urls="true"
- wrap="true">
- This conversation is in a separate window. [secondlife:/// Bring it back.]
- </text>
- </panel>
+ name="stub_panel"
+ opaque="true"
+ top_pad="0"
+ left="0"
+ right="-1">
+ <button
+ follows="right|top"
+ height="25"
+ image_hover_unselected="Toolbar_Middle_Over"
+ image_overlay="Conv_toolbar_collapse"
+ image_selected="Toolbar_Middle_Selected"
+ image_unselected="Toolbar_Middle_Off"
+ layout="topleft"
+ top="1"
+ right="-10"
+ name="stub_collapse_btn"
+ tool_tip="Collapse this pane"
+ width="31" />
+ <text
+ type="string"
+ clip_partial="false"
+ follows="left|top|right"
+ layout="topleft"
+ left="15"
+ right="-15"
+ name="stub_textbox"
+ top="25"
+ height="40"
+ valign="center"
+ parse_urls="true"
+ wrap="true">
+ This conversation is in a separate window. [secondlife:/// Bring it back.]
+ </text>
+ </panel>
</panel_container>
</layout_panel>
</layout_stack>
diff --git a/indra/newview/skins/default/xui/en/floater_im_session.xml b/indra/newview/skins/default/xui/en/floater_im_session.xml
index 2152a9f6e9..43d0f2fb18 100755
--- a/indra/newview/skins/default/xui/en/floater_im_session.xml
+++ b/indra/newview/skins/default/xui/en/floater_im_session.xml
@@ -70,26 +70,23 @@
top="0"
left="0"
right="-1"
- bottom="-3">
+ bottom="-1">
<layout_stack
animate="false"
+ bottom="-1"
default_tab_group="2"
follows="all"
- right="-5"
- bottom="-1"
- top="0"
- left="5"
- border_size="0"
+ left="3"
layout="topleft"
- orientation="vertical"
name="main_stack"
- tab_group="1">
+ right="-3"
+ orientation="vertical"
+ tab_group="1"
+ top="0">
<layout_panel
auto_resize="false"
name="toolbar_panel"
- height="35"
- right="-1"
- left="1">
+ height="25">
<menu_button
menu_filename="menu_im_session_showmodes.xml"
follows="top|left"
@@ -102,7 +99,7 @@
left="5"
name="view_options_btn"
tool_tip="View/sort options"
- top="5"
+ top="1"
width="31" />
<menu_button
menu_filename="menu_im_conversation.xml"
@@ -113,7 +110,7 @@
image_selected="Toolbar_Middle_Selected"
image_unselected="Toolbar_Middle_Off"
layout="topleft"
- top="5"
+ top="1"
left_pad="2"
name="gear_btn"
visible="false"
@@ -128,7 +125,7 @@
image_selected="Toolbar_Middle_Selected"
image_unselected="Toolbar_Middle_Off"
layout="topleft"
- top="5"
+ top="1"
left_pad="2"
name="add_btn"
tool_tip="Add someone to this conversation"
@@ -141,23 +138,11 @@
image_selected="Toolbar_Middle_Selected"
image_unselected="Toolbar_Middle_Off"
layout="topleft"
- top="5"
+ top="1"
left_pad="2"
name="voice_call_btn"
tool_tip="Open voice connection"
- width="31"/>
- <output_monitor
- auto_update="true"
- follows="top|left"
- draw_border="false"
- height="16"
- layout="topleft"
- top="10"
- left_pad="10"
- mouse_opaque="true"
- name="speaking_indicator"
- visible="false"
- width="20" />
+ width="31"/>
<button
follows="right|top"
height="25"
@@ -166,8 +151,8 @@
image_selected="Toolbar_Middle_Selected"
image_unselected="Toolbar_Middle_Off"
layout="topleft"
- top="5"
- right="-67"
+ top="1"
+ right="-70"
name="close_btn"
tool_tip="End this conversation"
width="31" />
@@ -179,7 +164,7 @@
image_selected="Toolbar_Middle_Selected"
image_unselected="Toolbar_Middle_Off"
layout="topleft"
- top="5"
+ top="1"
left_pad="2"
name="expand_collapse_btn"
tool_tip="Collapse/Expand this pane"
@@ -194,18 +179,21 @@
layout="topleft"
left_pad="2"
name="tear_off_btn"
- top="5"
+ top="1"
width="31" />
</layout_panel>
<layout_panel
name="body_panel"
- top="1"
- bottom="-1">
+ height="235">
<layout_stack
default_tab_group="2"
+ drag_handle_gap="6"
+ drag_handle_first_indent="0"
+ drag_handle_second_indent="1"
follows="all"
orientation="horizontal"
name="im_panels"
+ show_drag_handle="true"
tab_group="1"
top="0"
right="-1"
@@ -217,14 +205,12 @@
min_dim="0"
width="150"
user_resize="true"
- auto_resize="false"
- bottom="-1" />
+ auto_resize="false" />
<layout_panel
default_tab_group="3"
tab_group="2"
name="right_part_holder"
- min_width="221"
- bottom="-1">
+ min_width="172">
<layout_stack
animate="true"
default_tab_group="2"
@@ -233,7 +219,7 @@
name="translate_and_chat_stack"
tab_group="1"
top="0"
- left="0"
+ left="1"
right="-1"
bottom="-1">
<layout_panel
@@ -259,7 +245,7 @@
parse_highlights="true"
parse_urls="true"
right="-1"
- left="5"
+ left="0"
top="0"
bottom="-1" />
</layout_panel>
@@ -268,10 +254,7 @@
</layout_stack>
</layout_panel>
<layout_panel
- top_delta="0"
- top="0"
- height="26"
- bottom="-1"
+ height="35"
auto_resize="false"
name="chat_layout_panel">
<layout_stack
@@ -281,15 +264,11 @@
orientation="horizontal"
name="input_panels"
top="0"
- bottom="-2"
+ bottom="-1"
left="0"
right="-1">
<layout_panel
- name="input_editor_layout_panel"
- auto_resize="true"
- user_resize="false"
- top="0"
- bottom="-1">
+ name="input_editor_layout_panel">
<chat_editor
layout="topleft"
expand_lines_count="5"
@@ -302,32 +281,27 @@
max_length="1023"
spellcheck="true"
tab_group="3"
- top="1"
- bottom="-2"
- left="4"
- right="-4"
+ bottom="-8"
+ left="5"
+ right="-5"
wrap="true" />
</layout_panel>
<layout_panel
auto_resize="false"
- user_resize="false"
name="input_button_layout_panel"
- width="30"
- top="0"
- bottom="-1">
+ width="32">
<button
- layout="topleft"
left="1"
- right="-1"
- top="1"
- height="22"
+ top="4"
+ height="25"
follows="left|right|top"
image_hover_unselected="Toolbar_Middle_Over"
image_overlay="Conv_expand_one_line"
image_selected="Toolbar_Middle_Selected"
image_unselected="Toolbar_Middle_Off"
name="minz_btn"
- tool_tip="Shows/hides message panel" />
+ tool_tip="Shows/hides message panel"
+ width="28" />
</layout_panel>
</layout_stack>
</layout_panel>
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 46ba4bd29d..0a8beec7de 100755
--- a/indra/newview/skins/default/xui/en/menu_attachment_other.xml
+++ b/indra/newview/skins/default/xui/en/menu_attachment_other.xml
@@ -112,4 +112,15 @@
<menu_item_call.on_enable
function="Object.EnableInspect" />
</menu_item_call>
+ <menu_item_separator
+ layout="topleft" />
+ <menu_item_call
+ enabled="false"
+ label="Block Particle Owner"
+ name="Mute Particle">
+ <menu_item_call.on_click
+ function="Particle.Mute" />
+ <menu_item_call.on_enable
+ function="EnableMuteParticle" />
+ </menu_item_call>
</context_menu>
diff --git a/indra/newview/skins/default/xui/en/menu_attachment_self.xml b/indra/newview/skins/default/xui/en/menu_attachment_self.xml
index 28e032ce5f..bcbc8d5b86 100755
--- a/indra/newview/skins/default/xui/en/menu_attachment_self.xml
+++ b/indra/newview/skins/default/xui/en/menu_attachment_self.xml
@@ -143,4 +143,15 @@ name="Edit Outfit">
<menu_item_call.on_enable
function="Attachment.EnableDrop" />
</menu_item_call>
+ <menu_item_separator
+ layout="topleft" />
+ <menu_item_call
+ enabled="false"
+ label="Block Particle Owner"
+ name="Mute Particle">
+ <menu_item_call.on_click
+ function="Particle.Mute" />
+ <menu_item_call.on_enable
+ function="EnableMuteParticle" />
+ </menu_item_call>
</context_menu>
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 e7c2b80da2..8be2683680 100755
--- a/indra/newview/skins/default/xui/en/menu_avatar_other.xml
+++ b/indra/newview/skins/default/xui/en/menu_avatar_other.xml
@@ -103,4 +103,15 @@
<menu_item_call.on_enable
function="EnablePayAvatar" />
</menu_item_call>
+ <menu_item_separator
+ layout="topleft" />
+ <menu_item_call
+ enabled="false"
+ label="Block Particle Owner"
+ name="Mute Particle">
+ <menu_item_call.on_click
+ function="Particle.Mute" />
+ <menu_item_call.on_enable
+ function="EnableMuteParticle" />
+ </menu_item_call>
</context_menu>
diff --git a/indra/newview/skins/default/xui/en/menu_avatar_self.xml b/indra/newview/skins/default/xui/en/menu_avatar_self.xml
index c1ff026a74..ca0c9bd5e4 100755
--- a/indra/newview/skins/default/xui/en/menu_avatar_self.xml
+++ b/indra/newview/skins/default/xui/en/menu_avatar_self.xml
@@ -269,4 +269,16 @@
<menu_item_call.on_visible
function="Advanced.EnableAppearanceToXML"/>
</menu_item_call>
+ <menu_item_separator
+ layout="topleft" />
+ <menu_item_call
+ enabled="false"
+ label="Block Particle Owner"
+ name="Mute Particle">
+ <menu_item_call.on_click
+ function="Particle.Mute" />
+
+ <menu_item_call.on_enable
+ function="EnableMuteParticle" />
+ </menu_item_call>
</context_menu>
diff --git a/indra/newview/skins/default/xui/en/menu_conversation.xml b/indra/newview/skins/default/xui/en/menu_conversation.xml
index 5a13ef0a59..b3d28788da 100755
--- a/indra/newview/skins/default/xui/en/menu_conversation.xml
+++ b/indra/newview/skins/default/xui/en/menu_conversation.xml
@@ -11,7 +11,7 @@
layout="topleft"
name="close_conversation">
<on_click function="Avatar.DoToSelected" parameter="close_conversation"/>
- </menu_item_call>
+ </menu_item_call>
<menu_item_call
label="Open voice conversation"
layout="topleft"
@@ -25,6 +25,12 @@
<on_click function="Avatar.DoToSelected" parameter="disconnect_from_voice"/>
</menu_item_call>
<menu_item_separator layout="topleft" name="separator_disconnect_from_voice"/>
+ <menu_item_call
+ label="Close Selected"
+ layout="topleft"
+ name="close_selected_conversations">
+ <on_click function="Avatar.DoToSelected" parameter="close_selected_conversations"/>
+ </menu_item_call>
<menu_item_call
label="View Profile"
layout="topleft"
diff --git a/indra/newview/skins/default/xui/en/menu_land.xml b/indra/newview/skins/default/xui/en/menu_land.xml
index cc6d8ad9c1..2ad5cbbe95 100755
--- a/indra/newview/skins/default/xui/en/menu_land.xml
+++ b/indra/newview/skins/default/xui/en/menu_land.xml
@@ -61,4 +61,15 @@
<menu_item_call.on_enable
function="EnableEdit" />
</menu_item_call>
+ <menu_item_separator
+ layout="topleft" />
+ <menu_item_call
+ enabled="false"
+ label="Block Particle Owner"
+ name="Mute Particle">
+ <menu_item_call.on_click
+ function="Particle.Mute" />
+ <menu_item_call.on_enable
+ function="EnableMuteParticle" />
+ </menu_item_call>
</context_menu>
diff --git a/indra/newview/skins/default/xui/en/menu_mute_particle.xml b/indra/newview/skins/default/xui/en/menu_mute_particle.xml
new file mode 100644
index 0000000000..a4261bf39e
--- /dev/null
+++ b/indra/newview/skins/default/xui/en/menu_mute_particle.xml
@@ -0,0 +1,15 @@
+<?xml version="1.0" encoding="utf-8" standalone="yes" ?>
+<!-- *NOTE: See also menu_attachment_other.xml -->
+<context_menu
+ layout="topleft"
+ name="Mute Particle Pie">
+ <menu_item_call
+ enabled="false"
+ label="Block Particle Owner"
+ name="Mute Particle">
+ <menu_item_call.on_click
+ function="Particle.Mute" />
+ <menu_item_call.on_enable
+ function="EnableMuteParticle" />
+ </menu_item_call>
+</context_menu>
diff --git a/indra/newview/skins/default/xui/en/menu_object.xml b/indra/newview/skins/default/xui/en/menu_object.xml
index f6004621a6..52ab7da515 100755
--- a/indra/newview/skins/default/xui/en/menu_object.xml
+++ b/indra/newview/skins/default/xui/en/menu_object.xml
@@ -196,4 +196,15 @@
<menu_item_call.on_enable
function="Object.EnableDelete" />
</menu_item_call>
+ <menu_item_separator
+ layout="topleft" />
+ <menu_item_call
+ enabled="false"
+ label="Block Particle Owner"
+ name="Mute Particle">
+ <menu_item_call.on_click
+ function="Particle.Mute" />
+ <menu_item_call.on_enable
+ function="EnableMuteParticle" />
+ </menu_item_call>
</context_menu>
diff --git a/indra/newview/skins/default/xui/en/menu_people_friends_view.xml b/indra/newview/skins/default/xui/en/menu_people_friends_view.xml
index dde9432867..8790fde7c5 100755
--- a/indra/newview/skins/default/xui/en/menu_people_friends_view.xml
+++ b/indra/newview/skins/default/xui/en/menu_people_friends_view.xml
@@ -44,6 +44,8 @@
<menu_item_check.on_check
function="Floater.Visible"
parameter="conversation" />
+ <menu_item_check.on_enable
+ function="Conversation.IsConversationLoggingAllowed" />
<menu_item_check.on_click
function="Floater.Toggle"
parameter="conversation" />
diff --git a/indra/newview/skins/default/xui/en/menu_url_agent.xml b/indra/newview/skins/default/xui/en/menu_url_agent.xml
index 7cd56f257a..e8b6116026 100755
--- a/indra/newview/skins/default/xui/en/menu_url_agent.xml
+++ b/indra/newview/skins/default/xui/en/menu_url_agent.xml
@@ -21,8 +21,15 @@
layout="topleft"
name="add_friend">
<menu_item_call.on_click
- function="Url.AddFriend" />
+ function="Url.AddFriend" />
</menu_item_call>
+ <menu_item_call
+ label="Remove Friend..."
+ layout="topleft"
+ name="remove_friend">
+ <menu_item_call.on_click
+ function="Url.RemoveFriend" />
+ </menu_item_call>
<menu_item_separator
layout="topleft" />
<menu_item_call
diff --git a/indra/newview/skins/default/xui/en/menu_url_objectim.xml b/indra/newview/skins/default/xui/en/menu_url_objectim.xml
index 87ab58e622..b9d003b841 100755
--- a/indra/newview/skins/default/xui/en/menu_url_objectim.xml
+++ b/indra/newview/skins/default/xui/en/menu_url_objectim.xml
@@ -9,6 +9,13 @@
<menu_item_call.on_click
function="Url.Execute" />
</menu_item_call>
+ <menu_item_call
+ label="Block..."
+ layout="topleft"
+ name="block_object">
+ <menu_item_call.on_click
+ function="Url.Block" />
+ </menu_item_call>
<menu_item_separator
layout="topleft" />
<menu_item_call
diff --git a/indra/newview/skins/default/xui/en/menu_viewer.xml b/indra/newview/skins/default/xui/en/menu_viewer.xml
index b01c3067ff..f253ed3e06 100755
--- a/indra/newview/skins/default/xui/en/menu_viewer.xml
+++ b/indra/newview/skins/default/xui/en/menu_viewer.xml
@@ -874,6 +874,15 @@
function="Tools.EnableSelectNextPart" />
</menu_item_call>
</menu>
+ <menu_item_call
+ label="Linksets..."
+ name="pathfinding_linkset_menu_item">
+ <menu_item_call.on_click
+ function="Floater.ToggleOrBringToFront"
+ parameter="pathfinding_linksets" />
+ <menu_item_call.on_enable
+ function="Tools.EnablePathfinding" />
+ </menu_item_call>
<menu_item_separator/>
<menu_item_call
@@ -896,7 +905,7 @@
<menu_item_call.on_enable
function="Tools.SomethingSelectedNoHUD" />
</menu_item_call>
-
+
<menu_item_separator/>
<menu
diff --git a/indra/newview/skins/default/xui/en/notifications.xml b/indra/newview/skins/default/xui/en/notifications.xml
index 50e6c16d0f..ebd2799ebf 100755
--- a/indra/newview/skins/default/xui/en/notifications.xml
+++ b/indra/newview/skins/default/xui/en/notifications.xml
@@ -3736,6 +3736,17 @@ Leave Group?
</notification>
<notification
+ icon="alertmodal.tga"
+ name="OwnerCannotLeaveGroup"
+ type="alertmodal">
+ Unable to leave group. You cannot leave the group because you are the last owner of the group. Please assign another member to the owner role first.
+ <tag>group</tag>
+ <usetemplate
+ name="okbutton"
+ yestext="OK"/>
+ </notification>
+
+ <notification
icon="alert.tga"
name="ConfirmKick"
type="alert">
@@ -5970,9 +5981,7 @@ Your calling card was declined.
icon="notifytip.tga"
name="TeleportToPerson"
type="notifytip">
- To contact Residents like &apos;[NAME]&apos;, click on the &quot;People&quot; button , select a Resident from the window that opens, then click &apos;IM&apos; at the
- bottom of the window.
- (You can also double-click on their name in the list, or right-click and choose &apos;IM&apos;).
+ To open a private conversation with someone, right-click on their avatar and choose &apos;IM&apos; from the menu.
</notification>
<notification
@@ -6600,7 +6609,7 @@ Your object named &lt;nolink&gt;[OBJECTFROMNAME]&lt;/nolink&gt; has given you th
icon="notify.tga"
name="JoinGroup"
persist="true"
- type="notify">
+ type="offer">
<tag>group</tag>
[MESSAGE]
<form name="form">
@@ -6831,7 +6840,6 @@ This will add a bookmark in your inventory so you can quickly IM this Resident.
name="RegionRestartMinutes"
priority="high"
sound="UISndAlert"
- persist="true"
type="notify">
This region will restart in [MINUTES] minutes.
If you stay in this region you will be logged out.
@@ -6842,7 +6850,6 @@ If you stay in this region you will be logged out.
name="RegionRestartSeconds"
priority="high"
sound="UISndAlert"
- persist="true"
type="notify">
This region will restart in [SECONDS] seconds.
If you stay in this region you will be logged out.
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 bd096ebb88..8e867259c5 100755
--- a/indra/newview/skins/default/xui/en/panel_preferences_chat.xml
+++ b/indra/newview/skins/default/xui/en/panel_preferences_chat.xml
@@ -14,6 +14,7 @@
border="false"
height="60"
layout="topleft"
+ name="general_chat_settings"
top="10"
left="13"
width="517">
@@ -97,20 +98,13 @@
border="false"
height="165"
layout="topleft"
+ name="im_notification_settings"
left="13"
width="517">
<text
layout="topleft"
height="12"
- name="notifications"
- left="0"
- width="120">
- Notifications
- </text>
- <text
- layout="topleft"
- height="12"
name="friend_ims"
width="145"
left="0"
@@ -138,17 +132,27 @@
name="FlashToolbarButton"
value="flash"/>
<item
- label="None"
- name="None"
- value="none"/>
+ label="No action"
+ name="NoAction"
+ value="noaction"/>
</combo_box>
+ <check_box
+ control_name="PlaySoundFriendIM"
+ height="23"
+ label="Play sound"
+ layout="topleft"
+ name="play_sound_friend_im"
+ left_pad="7"
+ top_delta="-3"
+ width="28">
+ </check_box>
<text
layout="topleft"
height="12"
name="non_friend_ims"
width="145"
left="0"
- top_pad="9">
+ top_pad="11">
Non-friend IMs:
</text>
<combo_box
@@ -172,17 +176,27 @@
name="FlashToolbarButton"
value="flash"/>
<item
- label="None"
- name="None"
- value="none"/>
+ label="No action"
+ name="NoAction"
+ value="noaction"/>
</combo_box>
+ <check_box
+ control_name="PlaySoundNonFriendIM"
+ height="23"
+ label="Play sound"
+ layout="topleft"
+ name="play_sound_non_friend_im"
+ left_pad="7"
+ top_delta="-3"
+ width="28">
+ </check_box>
<text
layout="topleft"
left="0"
height="13"
name="conference_ims"
width="145"
- top_pad="9">
+ top_pad="11">
Conference IMs:
</text>
<combo_box
@@ -206,17 +220,27 @@
name="FlashToolbarButton"
value="flash"/>
<item
- label="None"
- name="None"
- value="none"/>
+ label="No action"
+ name="NoAction"
+ value="noaction"/>
</combo_box>
+ <check_box
+ control_name="PlaySoundConferenceIM"
+ height="23"
+ label="Play sound"
+ layout="topleft"
+ name="play_sound_conference_im"
+ left_pad="7"
+ top_delta="-3"
+ width="28">
+ </check_box>
<text
layout="topleft"
left="0"
height="13"
name="group_chat"
width="145"
- top_pad="9">
+ top_pad="11">
Group chat:
</text>
<combo_box
@@ -240,17 +264,27 @@
name="FlashToolbarButton"
value="flash"/>
<item
- label="None"
- name="None"
- value="none"/>
+ label="No action"
+ name="NoAction"
+ value="noaction"/>
</combo_box>
+ <check_box
+ control_name="PlaySoundGroupChatIM"
+ height="23"
+ label="Play sound"
+ layout="topleft"
+ name="play_sound_group_chat_im"
+ left_pad="7"
+ top_delta="-3"
+ width="28">
+ </check_box>
<text
layout="topleft"
left="0"
height="12"
name="nearby_chat"
width="145"
- top_pad="9">
+ top_pad="11">
Nearby chat:
</text>
<combo_box
@@ -274,10 +308,64 @@
name="FlashToolBarButton"
value="flash"/>
<item
- label="None"
- name="None"
- value="none"/>
+ label="No action"
+ name="NoAction"
+ value="noaction"/>
</combo_box>
+ <check_box
+ control_name="PlaySoundNearbyChatIM"
+ height="23"
+ label="Play sound"
+ layout="topleft"
+ name="play_sound_nearby_chat_im"
+ left_pad="7"
+ top_delta="-3"
+ width="28">
+ </check_box>
+ <text
+ layout="topleft"
+ left="0"
+ height="12"
+ name="object_ims"
+ width="145"
+ top_pad="11">
+ Object IMs:
+ </text>
+ <combo_box
+ control_name="NotificationObjectIMOptions"
+ height="23"
+ layout="topleft"
+ left_pad="5"
+ top_delta="-6"
+ name="ObjectIMOptions"
+ width="223">
+ <item
+ label="Open Conversations window"
+ name="OpenConversationsWindow"
+ value="openconversations"/>
+ <item
+ label="Pop up the message"
+ name="PopUpMessage"
+ value="toast"/>
+ <item
+ label="Flash toolbar button"
+ name="FlashToolBarButton"
+ value="flash"/>
+ <item
+ label="No action"
+ name="NoAction"
+ value="noaction"/>
+ </combo_box>
+ <check_box
+ control_name="PlaySoundObjectIM"
+ height="23"
+ label="Play sound"
+ layout="topleft"
+ name="play_sound_object_im"
+ left_pad="7"
+ top_delta="-3"
+ width="28">
+ </check_box>
<text
layout="topleft"
left="0"
@@ -296,6 +384,7 @@
border="false"
height="50"
layout="topleft"
+ name="play_sound_settings"
left="13"
top_pad="10"
width="517">
@@ -358,6 +447,7 @@
<panel
height="50"
layout="topleft"
+ name="log_settings"
left="13"
top_pad="10"
width="505">
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 d7db7caf66..3c4d288037 100755
--- a/indra/newview/skins/default/xui/en/panel_preferences_graphics1.xml
+++ b/indra/newview/skins/default/xui/en/panel_preferences_graphics1.xml
@@ -47,7 +47,7 @@
Better
</text>
<icon
- color="0.12 0.12 0.12 1"
+ color="DkGray"
height="14"
image_name="Rounded_Square"
layout="topleft"
@@ -56,16 +56,15 @@
top_delta="-2"
width="2" />
<icon
- color="0.12 0.12 0.12 1"
+ color="DkGray"
height="14"
image_name="Rounded_Square"
layout="topleft"
left_pad="41"
- name="LowMidraphicsDivet"
- top_delta="-2"
+ name="LowMidGraphicsDivet"
width="2" />
<icon
- color="0.12 0.12 0.12 1"
+ color="DkGray"
height="14"
image_name="Rounded_Square"
layout="topleft"
@@ -74,7 +73,7 @@
top_delta="0"
width="2" />
<icon
- color="0.12 0.12 0.12 1"
+ color="DkGray"
height="14"
image_name="Rounded_Square"
layout="topleft"
@@ -83,7 +82,7 @@
top_delta="0"
width="2" />
<icon
- color="0.12 0.12 0.12 1"
+ color="DkGray"
height="14"
image_name="Rounded_Square"
layout="topleft"
@@ -92,7 +91,7 @@
top_delta="0"
width="2" />
<icon
- color="0.12 0.12 0.12 1"
+ color="DkGray"
height="14"
image_name="Rounded_Square"
layout="topleft"
@@ -101,7 +100,7 @@
top_delta="0"
width="2" />
<icon
- color="0.12 0.12 0.12 1"
+ color="DkGray"
height="14"
image_name="Rounded_Square"
layout="topleft"
diff --git a/indra/newview/skins/default/xui/en/role_actions.xml b/indra/newview/skins/default/xui/en/role_actions.xml
index 89aef57cca..0eeccbeac5 100755
--- a/indra/newview/skins/default/xui/en/role_actions.xml
+++ b/indra/newview/skins/default/xui/en/role_actions.xml
@@ -70,8 +70,8 @@
longdescription="Toggle &apos;Show Place in Search&apos; and setting a parcel&apos;s category in About Land &gt; Options tab."
name="land find places" value="17" />
<action
- description="Change parcel name, description, and &apos;Show Place in Search&apos; settings"
- longdescription="Change parcel name, description, and &apos;Show Place in Search&apos; settings. This is done in About Land &gt; Options tab."
+ description="Change parcel name, description, and &apos;Moderate Content&apos; settings"
+ longdescription="Change parcel name, description, and &apos;Moderate Content&apos; settings. This is done in About Land &gt; Options tab."
name="land change identity" value="18" />
<action description="Set landing point and set teleport routing"
longdescription="On a group-owned parcel, Members in a Role with this Ability can set a landing point to specify where incoming teleports arrive, and also set teleport routing for further control. This is done in About Land &gt; Options tab."
diff --git a/indra/newview/skins/default/xui/en/strings.xml b/indra/newview/skins/default/xui/en/strings.xml
index f7b33b0a4a..73601ecb9f 100755
--- a/indra/newview/skins/default/xui/en/strings.xml
+++ b/indra/newview/skins/default/xui/en/strings.xml
@@ -209,7 +209,8 @@ Please try logging in again in a minute.</string>
<string name="SLappAgentIM">IM</string>
<string name="SLappAgentPay">Pay</string>
<string name="SLappAgentOfferTeleport">Offer Teleport to </string>
- <string name="SLappAgentRequestFriend">Friend Request </string>
+ <string name="SLappAgentRequestFriend">Friend Request</string>
+ <string name="SLappAgentRemoveFriend">Friend Removal</string>
<!-- ButtonToolTips, llfloater.cpp -->
<string name="BUTTON_CLOSE_DARWIN">Close (&#8984;W)</string>
@@ -2515,6 +2516,8 @@ Drag folders to this area and click "Send to Marketplace" to list them for sale
<string name="ATTACH_HUD_BOTTOM_LEFT">HUD Bottom Left</string>
<string name="ATTACH_HUD_BOTTOM">HUD Bottom</string>
<string name="ATTACH_HUD_BOTTOM_RIGHT">HUD Bottom Right</string>
+ <string name="ATTACH_NECK">Neck</string>
+ <string name="ATTACH_AVATAR_CENTER">Avatar Center</string>
<!-- script editor -->
<string name="CursorPos">Line [LINE], Column [COLUMN]</string>
@@ -3927,5 +3930,8 @@ Try enclosing path to the editor with double quotes.
<string name="logging_calls_enabled_log_empty">
There are no logged conversations. After you contact someone, or someone contacts you, a log entry will be shown here.
</string>
+ <string name="loading_chat_logs">
+ Loading...
+ </string>
</strings>