summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--indra/integration_tests/llui_libtest/llwidgetreg.cpp2
-rw-r--r--indra/llcommon/llcommonutils.h5
-rw-r--r--indra/llui/CMakeLists.txt2
-rw-r--r--indra/llui/llloadingindicator.cpp133
-rw-r--r--indra/llui/llloadingindicator.h93
-rw-r--r--indra/llui/llui.cpp4
-rw-r--r--indra/llui/lluifwd.h1
-rw-r--r--indra/llwindow/llwindowwin32.cpp7
-rw-r--r--indra/newview/CMakeLists.txt2
-rw-r--r--indra/newview/llappearancemgr.cpp59
-rw-r--r--indra/newview/llavatarlist.cpp18
-rw-r--r--indra/newview/llcofwearables.cpp153
-rw-r--r--indra/newview/llcofwearables.h66
-rw-r--r--indra/newview/lloutfitslist.cpp51
-rw-r--r--indra/newview/lloutfitslist.h6
-rw-r--r--indra/newview/llpanelgrouplandmoney.cpp3
-rw-r--r--indra/newview/llpaneloutfitedit.cpp123
-rw-r--r--indra/newview/llpaneloutfitedit.h6
-rw-r--r--indra/newview/llviewerinventory.cpp2
-rw-r--r--indra/newview/llviewermessage.cpp1
-rw-r--r--indra/newview/skins/default/textures/icons/Progress_1.pngbin0 -> 470 bytes
-rw-r--r--indra/newview/skins/default/textures/icons/Progress_10.pngbin0 -> 461 bytes
-rw-r--r--indra/newview/skins/default/textures/icons/Progress_11.pngbin0 -> 475 bytes
-rw-r--r--indra/newview/skins/default/textures/icons/Progress_12.pngbin0 -> 455 bytes
-rw-r--r--indra/newview/skins/default/textures/icons/Progress_2.pngbin0 -> 453 bytes
-rw-r--r--indra/newview/skins/default/textures/icons/Progress_3.pngbin0 -> 454 bytes
-rw-r--r--indra/newview/skins/default/textures/icons/Progress_4.pngbin0 -> 454 bytes
-rw-r--r--indra/newview/skins/default/textures/icons/Progress_5.pngbin0 -> 468 bytes
-rw-r--r--indra/newview/skins/default/textures/icons/Progress_6.pngbin0 -> 462 bytes
-rw-r--r--indra/newview/skins/default/textures/icons/Progress_7.pngbin0 -> 469 bytes
-rw-r--r--indra/newview/skins/default/textures/icons/Progress_8.pngbin0 -> 454 bytes
-rw-r--r--indra/newview/skins/default/textures/icons/Progress_9.pngbin0 -> 469 bytes
-rw-r--r--indra/newview/skins/default/textures/textures.xml13
-rw-r--r--indra/newview/skins/default/xui/en/panel_cof_wearables.xml65
-rw-r--r--indra/newview/skins/default/xui/en/panel_group_land_money.xml4
-rw-r--r--indra/newview/skins/default/xui/en/panel_outfit_edit.xml29
-rw-r--r--indra/newview/skins/default/xui/en/widgets/loading_indicator.xml8
37 files changed, 672 insertions, 184 deletions
diff --git a/indra/integration_tests/llui_libtest/llwidgetreg.cpp b/indra/integration_tests/llui_libtest/llwidgetreg.cpp
index c6e2e79a09..57c39243fb 100644
--- a/indra/integration_tests/llui_libtest/llwidgetreg.cpp
+++ b/indra/integration_tests/llui_libtest/llwidgetreg.cpp
@@ -37,6 +37,7 @@
#include "llcombobox.h"
#include "llcontainerview.h"
#include "lliconctrl.h"
+#include "llloadingindicator.h"
#include "llmenubutton.h"
#include "llmenugl.h"
#include "llmultislider.h"
@@ -72,6 +73,7 @@ void LLWidgetReg::initClass(bool register_widgets)
LLDefaultChildRegistry::Register<LLFlyoutButton> flyout_button("flyout_button");
LLDefaultChildRegistry::Register<LLContainerView> container_view("container_view");
LLDefaultChildRegistry::Register<LLIconCtrl> icon("icon");
+ LLDefaultChildRegistry::Register<LLLoadingIndicator> loading_indicator("loading_indicator");
LLDefaultChildRegistry::Register<LLLineEditor> line_editor("line_editor");
LLDefaultChildRegistry::Register<LLMenuItemSeparatorGL> menu_item_separator("menu_item_separator");
LLDefaultChildRegistry::Register<LLMenuItemCallGL> menu_item_call_gl("menu_item_call");
diff --git a/indra/llcommon/llcommonutils.h b/indra/llcommon/llcommonutils.h
index f769ab87d3..ad0d884e37 100644
--- a/indra/llcommon/llcommonutils.h
+++ b/indra/llcommon/llcommonutils.h
@@ -38,6 +38,11 @@ namespace LLCommonUtils
* Computes difference between 'vnew' and 'vcur' vectors.
* Items present in 'vnew' and missing in 'vcur' are treated as added and are copied into 'vadded'
* Items missing in 'vnew' and present in 'vcur' are treated as removed and are copied into 'vremoved'
+ *
+ * @param vnew[in] - incoming IDs
+ * @param vcur[in] - current IDs
+ * @param vadded[out] - difference between incoming and current IDS - added IDs
+ * @param vremoved[out] - difference between incoming and current IDS - removed IDs
*/
LL_COMMON_API void computeDifference(
const uuid_vec_t& vnew,
diff --git a/indra/llui/CMakeLists.txt b/indra/llui/CMakeLists.txt
index 532b6b6524..3ecab90756 100644
--- a/indra/llui/CMakeLists.txt
+++ b/indra/llui/CMakeLists.txt
@@ -52,6 +52,7 @@ set(llui_SOURCE_FILES
llkeywords.cpp
lllayoutstack.cpp
lllineeditor.cpp
+ llloadingindicator.cpp
lllocalcliprect.cpp
llmenubutton.cpp
llmenugl.cpp
@@ -144,6 +145,7 @@ set(llui_HEADER_FILES
lllayoutstack.h
lllazyvalue.h
lllineeditor.h
+ llloadingindicator.h
lllocalcliprect.h
llmenubutton.h
llmenugl.h
diff --git a/indra/llui/llloadingindicator.cpp b/indra/llui/llloadingindicator.cpp
new file mode 100644
index 0000000000..f8b029e19c
--- /dev/null
+++ b/indra/llui/llloadingindicator.cpp
@@ -0,0 +1,133 @@
+/**
+ * @file llloadingindicator.cpp
+ * @brief Perpetual loading indicator
+ *
+ * $LicenseInfo:firstyear=2010&license=viewergpl$
+ *
+ * Copyright (c) 2010, Linden Research, Inc.
+ *
+ * Second Life Viewer Source Code
+ * The source code in this file ("Source Code") is provided by Linden Lab
+ * to you under the terms of the GNU General Public License, version 2.0
+ * ("GPL"), unless you have obtained a separate licensing agreement
+ * ("Other License"), formally executed by you and Linden Lab. Terms of
+ * the GPL can be found in doc/GPL-license.txt in this distribution, or
+ * online at http://secondlifegrid.net/programs/open_source/licensing/gplv2
+ *
+ * There are special exceptions to the terms and conditions of the GPL as
+ * it is applied to this Source Code. View the full text of the exception
+ * in the file doc/FLOSS-exception.txt in this software distribution, or
+ * online at
+ * http://secondlifegrid.net/programs/open_source/licensing/flossexception
+ *
+ * By copying, modifying or distributing this software, you acknowledge
+ * that you have read and understood your obligations described above,
+ * and agree to abide by those obligations.
+ *
+ * ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
+ * WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
+ * COMPLETENESS OR PERFORMANCE.
+ * $/LicenseInfo$
+ */
+
+#include "linden_common.h"
+
+#include "llloadingindicator.h"
+
+// Linden library includes
+#include "llsingleton.h"
+
+// Project includes
+#include "lluictrlfactory.h"
+#include "lluiimage.h"
+
+static LLDefaultChildRegistry::Register<LLLoadingIndicator> r("loading_indicator");
+
+///////////////////////////////////////////////////////////////////////////////
+// LLLoadingIndicator::Data class
+///////////////////////////////////////////////////////////////////////////////
+
+/**
+ * Pre-loaded images shared by all instances of the widget
+ */
+class LLLoadingIndicator::Data: public LLSingleton<LLLoadingIndicator::Data>
+{
+public:
+ /*virtual*/ void initSingleton(); // from LLSingleton
+
+ LLPointer<LLUIImage> getNextImage(S8& idx) const;
+ U8 getImagesCount() const { return NIMAGES; }
+private:
+
+ static const U8 NIMAGES = 12;
+ LLPointer<LLUIImage> mImages[NIMAGES];
+};
+
+// virtual
+// Called right after the instance gets constructed.
+void LLLoadingIndicator::Data::initSingleton()
+{
+ // Load images.
+ for (U8 i = 0; i < NIMAGES; ++i)
+ {
+ std::string img_name = llformat("Progress_%d", i+1);
+ mImages[i] = LLUI::getUIImage(img_name, 0);
+ llassert(mImages[i]);
+ }
+}
+
+LLPointer<LLUIImage> LLLoadingIndicator::Data::getNextImage(S8& idx) const
+{
+ // Calculate next index, performing array bounds checking.
+ idx = (idx >= NIMAGES || idx < 0) ? 0 : (idx + 1) % NIMAGES;
+ return mImages[idx];
+}
+
+///////////////////////////////////////////////////////////////////////////////
+// LLLoadingIndicator class
+///////////////////////////////////////////////////////////////////////////////
+
+LLLoadingIndicator::LLLoadingIndicator(const Params& p)
+: LLUICtrl(p)
+ , mRotationsPerSec(p.rotations_per_sec > 0 ? p.rotations_per_sec : 1.0f)
+ , mCurImageIdx(-1)
+{
+ // Select initial image.
+ mCurImagep = Data::instance().getNextImage(mCurImageIdx);
+
+ // Start timer for switching images.
+ start();
+}
+
+void LLLoadingIndicator::draw()
+{
+ // Time to switch to the next image?
+ if (mImageSwitchTimer.getStarted() && mImageSwitchTimer.hasExpired())
+ {
+ // Switch to the next image.
+ mCurImagep = Data::instance().getNextImage(mCurImageIdx);
+
+ // Restart timer.
+ start();
+ }
+
+ // Draw current image.
+ if( mCurImagep.notNull() )
+ {
+ mCurImagep->draw(getLocalRect(), LLColor4::white % getDrawContext().mAlpha);
+ }
+
+ LLUICtrl::draw();
+}
+
+void LLLoadingIndicator::stop()
+{
+ mImageSwitchTimer.stop();
+}
+
+void LLLoadingIndicator::start()
+{
+ mImageSwitchTimer.start();
+ F32 period = 1.0f / (Data::instance().getImagesCount() * mRotationsPerSec);
+ mImageSwitchTimer.setTimerExpirySec(period);
+}
diff --git a/indra/llui/llloadingindicator.h b/indra/llui/llloadingindicator.h
new file mode 100644
index 0000000000..32dd1fead8
--- /dev/null
+++ b/indra/llui/llloadingindicator.h
@@ -0,0 +1,93 @@
+/**
+ * @file llloadingindicator.h
+ * @brief Perpetual loading indicator
+ *
+ * $LicenseInfo:firstyear=2010&license=viewergpl$
+ *
+ * Copyright (c) 2010, Linden Research, Inc.
+ *
+ * Second Life Viewer Source Code
+ * The source code in this file ("Source Code") is provided by Linden Lab
+ * to you under the terms of the GNU General Public License, version 2.0
+ * ("GPL"), unless you have obtained a separate licensing agreement
+ * ("Other License"), formally executed by you and Linden Lab. Terms of
+ * the GPL can be found in doc/GPL-license.txt in this distribution, or
+ * online at http://secondlifegrid.net/programs/open_source/licensing/gplv2
+ *
+ * There are special exceptions to the terms and conditions of the GPL as
+ * it is applied to this Source Code. View the full text of the exception
+ * in the file doc/FLOSS-exception.txt in this software distribution, or
+ * online at
+ * http://secondlifegrid.net/programs/open_source/licensing/flossexception
+ *
+ * By copying, modifying or distributing this software, you acknowledge
+ * that you have read and understood your obligations described above,
+ * and agree to abide by those obligations.
+ *
+ * ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
+ * WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
+ * COMPLETENESS OR PERFORMANCE.
+ * $/LicenseInfo$
+ */
+
+#ifndef LL_LLLOADINGINDICATOR_H
+#define LL_LLLOADINGINDICATOR_H
+
+#include "lluictrl.h"
+
+///////////////////////////////////////////////////////////////////////////////
+// class LLLoadingIndicator
+///////////////////////////////////////////////////////////////////////////////
+
+/**
+ * Perpetual loading indicator (a la MacOSX or YouTube)
+ *
+ * Number of rotations per second can be overriden
+ * with the "roations_per_sec" parameter.
+ *
+ * Can start/stop spinning.
+ *
+ * @see start()
+ * @see stop()
+ */
+class LLLoadingIndicator
+: public LLUICtrl
+{
+ LOG_CLASS(LLLoadingIndicator);
+public:
+ struct Params : public LLInitParam::Block<Params, LLUICtrl::Params>
+ {
+ Optional<F32> rotations_per_sec;
+ Params()
+ : rotations_per_sec("rotations_per_sec", 1.0f)
+ {}
+ };
+
+ virtual ~LLLoadingIndicator() {}
+
+ // llview overrides
+ virtual void draw();
+
+ /**
+ * Stop spinning.
+ */
+ void stop();
+
+ /**
+ * Start spinning.
+ */
+ void start();
+
+private:
+ LLLoadingIndicator(const Params&);
+ friend class LLUICtrlFactory;
+
+ class Data;
+
+ F32 mRotationsPerSec;
+ S8 mCurImageIdx;
+ LLPointer<LLUIImage> mCurImagep;
+ LLFrameTimer mImageSwitchTimer;
+};
+
+#endif // LL_LLLOADINGINDICATOR_H
diff --git a/indra/llui/llui.cpp b/indra/llui/llui.cpp
index f9a4ed7285..bf12384a28 100644
--- a/indra/llui/llui.cpp
+++ b/indra/llui/llui.cpp
@@ -56,6 +56,7 @@
#include "llfloaterreg.h"
#include "llmenugl.h"
#include "llmenubutton.h"
+#include "llloadingindicator.h"
#include "llwindow.h"
// for registration
@@ -94,7 +95,10 @@ std::list<std::string> gUntranslated;
static LLDefaultChildRegistry::Register<LLFilterEditor> register_filter_editor("filter_editor");
static LLDefaultChildRegistry::Register<LLFlyoutButton> register_flyout_button("flyout_button");
static LLDefaultChildRegistry::Register<LLSearchEditor> register_search_editor("search_editor");
+
+// register other widgets which otherwise may not be linked in
static LLDefaultChildRegistry::Register<LLMenuButton> register_menu_button("menu_button");
+static LLDefaultChildRegistry::Register<LLLoadingIndicator> register_loading_indicator("loading_indicator");
//
diff --git a/indra/llui/lluifwd.h b/indra/llui/lluifwd.h
index f99bb39fdd..d6047b943c 100644
--- a/indra/llui/lluifwd.h
+++ b/indra/llui/lluifwd.h
@@ -39,6 +39,7 @@ class LLComboBox;
class LLDragHandle;
class LLFloater;
class LLIconCtrl;
+class LLLoadingIndicator;
class LLLineEditor;
class LLMenuGL;
class LLPanel;
diff --git a/indra/llwindow/llwindowwin32.cpp b/indra/llwindow/llwindowwin32.cpp
index e2da3d1ad8..a96ad7e796 100644
--- a/indra/llwindow/llwindowwin32.cpp
+++ b/indra/llwindow/llwindowwin32.cpp
@@ -2877,8 +2877,13 @@ void LLSplashScreenWin32::updateImpl(const std::string& mesg)
{
if (!mWindow) return;
+ int output_str_len = MultiByteToWideChar(CP_UTF8, 0, mesg.c_str(), mesg.length(), NULL, 0);
+ if( output_str_len>1024 )
+ return;
+
WCHAR w_mesg[1024];
- mbstowcs(w_mesg, mesg.c_str(), 1024);
+
+ MultiByteToWideChar (CP_UTF8, 0, mesg.c_str(), mesg.length(), w_mesg, output_str_len);
SendDlgItemMessage(mWindow,
666, // HACK: text id
diff --git a/indra/newview/CMakeLists.txt b/indra/newview/CMakeLists.txt
index 99ba356d9e..70fc692a89 100644
--- a/indra/newview/CMakeLists.txt
+++ b/indra/newview/CMakeLists.txt
@@ -104,6 +104,7 @@ set(viewer_SOURCE_FILES
llclassifiedinfo.cpp
llclassifiedstatsresponder.cpp
llcloud.cpp
+ llcofwearables.cpp
llcolorswatch.cpp
llcommanddispatcherlistener.cpp
llcommandhandler.cpp
@@ -614,6 +615,7 @@ set(viewer_HEADER_FILES
llclassifiedinfo.h
llclassifiedstatsresponder.h
llcloud.h
+ llcofwearables.h
llcolorswatch.h
llcommanddispatcherlistener.h
llcommandhandler.h
diff --git a/indra/newview/llappearancemgr.cpp b/indra/newview/llappearancemgr.cpp
index 6aefecc787..5586b3cd4d 100644
--- a/indra/newview/llappearancemgr.cpp
+++ b/indra/newview/llappearancemgr.cpp
@@ -1059,6 +1059,10 @@ bool sort_by_description(const LLInventoryItem* item1, const LLInventoryItem* it
void LLAppearanceMgr::updateAppearanceFromCOF()
{
+ //checking integrity of the COF in terms of ordering of wearables,
+ //checking and updating links' descriptions of wearables in the COF (before analyzed for "dirty" state)
+ updateClothingOrderingInfo();
+
// update dirty flag to see if the state of the COF matches
// the saved outfit stored as a folder link
llinfos << "starting" << llendl;
@@ -1067,8 +1071,6 @@ void LLAppearanceMgr::updateAppearanceFromCOF()
dumpCat(getCOF(),"COF, start");
- updateClothingOrderingInfo();
-
bool follow_folder_links = true;
LLUUID current_outfit_id = getCOF();
@@ -1523,6 +1525,17 @@ void LLAppearanceMgr::removeCOFItemLinks(const LLUUID& item_id, bool do_update)
}
}
+bool sort_by_linked_uuid(const LLViewerInventoryItem* item1, const LLViewerInventoryItem* item2)
+{
+ if (!item1 || !item2)
+ {
+ llwarning("item1, item2 cannot be null, something is very wrong", 0);
+ return true;
+ }
+
+ return item1->getLinkedUUID() < item2->getLinkedUUID();
+}
+
void LLAppearanceMgr::updateIsDirty()
{
LLUUID cof = getCOF();
@@ -1562,33 +1575,37 @@ void LLAppearanceMgr::updateIsDirty()
// Current outfit folder should have one more item than the outfit folder.
// this one item is the link back to the outfit folder itself.
mOutfitIsDirty = true;
+ return;
}
- else
- {
- typedef std::set<LLUUID> item_set_t;
- item_set_t cof_set;
- item_set_t outfit_set;
- // sort COF items by UUID
- for (S32 i = 0; i < cof_items.count(); ++i)
+ //getting rid of base outfit folder link to simplify comparison
+ for (LLInventoryModel::item_array_t::iterator it = cof_items.begin(); it != cof_items.end(); ++it)
+ {
+ if (*it == base_outfit_item)
{
- LLViewerInventoryItem *item = cof_items.get(i);
- // don't add the base outfit link to the list of objects we're comparing
- if(item != base_outfit_item)
- {
- cof_set.insert(item->getLinkedUUID());
- }
+ cof_items.erase(it);
+ break;
}
+ }
- // sort outfit folder by UUID
- for (S32 i = 0; i < outfit_items.count(); ++i)
+ //"dirty" - also means a difference in linked UUIDs and/or a difference in wearables order (links' descriptions)
+ std::sort(cof_items.begin(), cof_items.end(), sort_by_linked_uuid);
+ std::sort(outfit_items.begin(), outfit_items.end(), sort_by_linked_uuid);
+
+ for (U32 i = 0; i < cof_items.size(); ++i)
+ {
+ LLViewerInventoryItem *item1 = cof_items.get(i);
+ LLViewerInventoryItem *item2 = outfit_items.get(i);
+
+ if (item1->getLinkedUUID() != item2->getLinkedUUID() ||
+ item1->LLInventoryItem::getDescription() != item2->LLInventoryItem::getDescription())
{
- LLViewerInventoryItem *item = outfit_items.get(i);
- outfit_set.insert(item->getLinkedUUID());
+ mOutfitIsDirty = true;
+ return;
}
-
- mOutfitIsDirty = (outfit_set != cof_set);
}
+
+ mOutfitIsDirty = false;
}
}
diff --git a/indra/newview/llavatarlist.cpp b/indra/newview/llavatarlist.cpp
index e32daf55ca..dfb213716c 100644
--- a/indra/newview/llavatarlist.cpp
+++ b/indra/newview/llavatarlist.cpp
@@ -34,6 +34,7 @@
// common
#include "lltrans.h"
+#include "llcommonutils.h"
#include "llavatarlist.h"
#include "llagentdata.h" // for comparator
@@ -406,7 +407,6 @@ void LLAvatarList::computeDifference(
uuid_vec_t& vremoved)
{
uuid_vec_t vcur;
- uuid_vec_t vnew = vnew_unsorted;
// Convert LLSDs to LLUUIDs.
{
@@ -417,21 +417,7 @@ void LLAvatarList::computeDifference(
vcur.push_back(vcur_values[i].asUUID());
}
- std::sort(vcur.begin(), vcur.end());
- std::sort(vnew.begin(), vnew.end());
-
- uuid_vec_t::iterator it;
- size_t maxsize = llmax(vcur.size(), vnew.size());
- vadded.resize(maxsize);
- vremoved.resize(maxsize);
-
- // what to remove
- it = set_difference(vcur.begin(), vcur.end(), vnew.begin(), vnew.end(), vremoved.begin());
- vremoved.erase(it, vremoved.end());
-
- // what to add
- it = set_difference(vnew.begin(), vnew.end(), vcur.begin(), vcur.end(), vadded.begin());
- vadded.erase(it, vadded.end());
+ LLCommonUtils::computeDifference(vnew_unsorted, vcur, vadded, vremoved);
}
// Refresh shown time of our last interaction with all listed avatars.
diff --git a/indra/newview/llcofwearables.cpp b/indra/newview/llcofwearables.cpp
new file mode 100644
index 0000000000..f0442ee3f6
--- /dev/null
+++ b/indra/newview/llcofwearables.cpp
@@ -0,0 +1,153 @@
+/**
+ * @file llcofwearables.cpp
+ * @brief LLCOFWearables displayes wearables from the current outfit split into three lists (attachments, clothing and body parts)
+ *
+ * $LicenseInfo:firstyear=2010&license=viewergpl$
+ *
+ * Copyright (c) 2010, Linden Research, Inc.
+ *
+ * Second Life Viewer Source Code
+ * The source code in this file ("Source Code") is provided by Linden Lab
+ * to you under the terms of the GNU General Public License, version 2.0
+ * ("GPL"), unless you have obtained a separate licensing agreement
+ * ("Other License"), formally executed by you and Linden Lab. Terms of
+ * the GPL can be found in doc/GPL-license.txt in this distribution, or
+ * online at http://secondlifegrid.net/programs/open_source/licensing/gplv2
+ *
+ * There are special exceptions to the terms and conditions of the GPL as
+ * it is applied to this Source Code. View the full text of the exception
+ * in the file doc/FLOSS-exception.txt in this software distribution, or
+ * online at
+ * http://secondlifegrid.net/programs/open_source/licensing/flossexception
+ *
+ * By copying, modifying or distributing this software, you acknowledge
+ * that you have read and understood your obligations described above,
+ * and agree to abide by those obligations.
+ *
+ * ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
+ * WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
+ * COMPLETENESS OR PERFORMANCE.
+ * $/LicenseInfo$
+ */
+
+#include "llviewerprecompiledheaders.h"
+
+#include "llcofwearables.h"
+
+#include "llappearancemgr.h"
+#include "llinventory.h"
+#include "llinventoryitemslist.h"
+#include "llinventoryfunctions.h"
+
+static LLRegisterPanelClassWrapper<LLCOFWearables> t_cof_wearables("cof_wearables");
+
+const LLSD REARRANGE = LLSD().with("rearrange", LLSD());
+
+
+LLCOFWearables::LLCOFWearables() : LLPanel(),
+ mAttachments(NULL),
+ mClothing(NULL),
+ mBodyParts(NULL),
+ mLastSelectedList(NULL)
+{
+};
+
+
+// virtual
+BOOL LLCOFWearables::postBuild()
+{
+ mAttachments = getChild<LLFlatListView>("list_attachments");
+ mClothing = getChild<LLFlatListView>("list_clothing");
+ mBodyParts = getChild<LLFlatListView>("list_body_parts");
+
+
+ //selection across different list/tabs is not supported
+ mAttachments->setCommitCallback(boost::bind(&LLCOFWearables::onSelectionChange, this, mAttachments));
+ mClothing->setCommitCallback(boost::bind(&LLCOFWearables::onSelectionChange, this, mClothing));
+ mBodyParts->setCommitCallback(boost::bind(&LLCOFWearables::onSelectionChange, this, mBodyParts));
+
+ mAttachments->setCommitOnSelectionChange(true);
+ mClothing->setCommitOnSelectionChange(true);
+ mBodyParts->setCommitOnSelectionChange(true);
+
+ return LLPanel::postBuild();
+}
+
+void LLCOFWearables::onSelectionChange(LLFlatListView* selected_list)
+{
+ if (!selected_list) return;
+
+ if (selected_list != mLastSelectedList)
+ {
+ if (selected_list != mAttachments) mAttachments->resetSelection(true);
+ if (selected_list != mClothing) mClothing->resetSelection(true);
+ if (selected_list != mBodyParts) mBodyParts->resetSelection(true);
+
+ mLastSelectedList = selected_list;
+ }
+
+ onCommit();
+}
+
+void LLCOFWearables::refresh()
+{
+ clear();
+
+ LLInventoryModel::cat_array_t cats;
+ LLInventoryModel::item_array_t items;
+
+ gInventory.collectDescendents(LLAppearanceMgr::getInstance()->getCOF(), cats, items, LLInventoryModel::EXCLUDE_TRASH);
+ if (items.empty()) return;
+
+ for (U32 i = 0; i < items.size(); ++i)
+ {
+ LLViewerInventoryItem* item = items.get(i);
+ if (!item) continue;
+
+ LLPanelInventoryListItem* item_panel = LLPanelInventoryListItem::createItemPanel(item);
+ if (!item_panel) continue;
+
+ switch (item->getType())
+ {
+ case LLAssetType::AT_OBJECT:
+ mAttachments->addItem(item_panel, item->getUUID(), ADD_BOTTOM, false);
+ break;
+
+ case LLAssetType::AT_BODYPART:
+ mBodyParts->addItem(item_panel, item->getUUID(), ADD_BOTTOM, false);
+ break;
+
+ case LLAssetType::AT_CLOTHING:
+ mClothing->addItem(item_panel, item->getUUID(), ADD_BOTTOM, false);
+ break;
+
+ default: break;
+ }
+ }
+
+ mAttachments->sort(); //*TODO by Name
+ mAttachments->notify(REARRANGE); //notifying the parent about the list's size change (cause items were added with rearrange=false)
+
+ mClothing->sort(); //*TODO by actual inventory item description
+ mClothing->notify(REARRANGE);
+
+ mBodyParts->sort(); //*TODO by name
+ mBodyParts->notify(REARRANGE);
+}
+
+
+LLUUID LLCOFWearables::getSelectedUUID()
+{
+ if (!mLastSelectedList) return LLUUID::null;
+
+ return mLastSelectedList->getSelectedUUID();
+}
+
+void LLCOFWearables::clear()
+{
+ mAttachments->clear();
+ mClothing->clear();
+ mBodyParts->clear();
+}
+
+//EOF
diff --git a/indra/newview/llcofwearables.h b/indra/newview/llcofwearables.h
new file mode 100644
index 0000000000..58d67ed32f
--- /dev/null
+++ b/indra/newview/llcofwearables.h
@@ -0,0 +1,66 @@
+/**
+ * @file llcofwearables.h
+ * @brief LLCOFWearables displayes wearables from the current outfit split into three lists (attachments, clothing and body parts)
+ *
+ * $LicenseInfo:firstyear=2010&license=viewergpl$
+ *
+ * Copyright (c) 2010, Linden Research, Inc.
+ *
+ * Second Life Viewer Source Code
+ * The source code in this file ("Source Code") is provided by Linden Lab
+ * to you under the terms of the GNU General Public License, version 2.0
+ * ("GPL"), unless you have obtained a separate licensing agreement
+ * ("Other License"), formally executed by you and Linden Lab. Terms of
+ * the GPL can be found in doc/GPL-license.txt in this distribution, or
+ * online at http://secondlifegrid.net/programs/open_source/licensing/gplv2
+ *
+ * There are special exceptions to the terms and conditions of the GPL as
+ * it is applied to this Source Code. View the full text of the exception
+ * in the file doc/FLOSS-exception.txt in this software distribution, or
+ * online at
+ * http://secondlifegrid.net/programs/open_source/licensing/flossexception
+ *
+ * By copying, modifying or distributing this software, you acknowledge
+ * that you have read and understood your obligations described above,
+ * and agree to abide by those obligations.
+ *
+ * ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
+ * WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
+ * COMPLETENESS OR PERFORMANCE.
+ * $/LicenseInfo$
+ */
+
+#ifndef LL_LLCOFWEARABLES_H
+#define LL_LLCOFWEARABLES_H
+
+#include "llpanel.h"
+
+class LLFlatListView;
+
+class LLCOFWearables : public LLPanel
+{
+public:
+ LLCOFWearables();
+ virtual ~LLCOFWearables() {};
+
+ /*virtual*/ BOOL postBuild();
+
+ LLUUID getSelectedUUID();
+
+ void refresh();
+ void clear();
+
+protected:
+
+ void onSelectionChange(LLFlatListView* selected_list);
+
+ LLFlatListView* mAttachments;
+ LLFlatListView* mClothing;
+ LLFlatListView* mBodyParts;
+
+ LLFlatListView* mLastSelectedList;
+
+};
+
+
+#endif
diff --git a/indra/newview/lloutfitslist.cpp b/indra/newview/lloutfitslist.cpp
index 1c627d452f..1215272685 100644
--- a/indra/newview/lloutfitslist.cpp
+++ b/indra/newview/lloutfitslist.cpp
@@ -36,6 +36,9 @@
// llcommon
#include "llcommonutils.h"
+// llcommon
+#include "llcommonutils.h"
+
#include "llaccordionctrl.h"
#include "llaccordionctrltab.h"
#include "llinventoryfunctions.h"
@@ -119,31 +122,11 @@ void LLOutfitsList::refreshList(const LLUUID& category_id)
LLInventoryModel::EXCLUDE_TRASH,
is_category);
- uuid_vec_t vnew;
-
- // Creating a vector of newly collected sub-categories UUIDs.
- for (LLInventoryModel::cat_array_t::const_iterator iter = cat_array.begin();
- iter != cat_array.end();
- ++iter)
- {
- vnew.push_back((*iter)->getUUID());
- }
-
- uuid_vec_t vcur;
-
- // Creating a vector of currently displayed sub-categories UUIDs.
- for (outfits_map_t::const_iterator iter = mOutfitsMap.begin();
- iter != mOutfitsMap.end();
- ++iter)
- {
- vcur.push_back((*iter).first);
- }
-
uuid_vec_t vadded;
uuid_vec_t vremoved;
// Create added and removed items vectors.
- LLCommonUtils::computeDifference(vnew, vcur, vadded, vremoved);
+ computeDifference(cat_array, vadded, vremoved);
// Handle added tabs.
for (uuid_vec_t::const_iterator iter = vadded.begin();
@@ -274,4 +257,30 @@ LLXMLNodePtr LLOutfitsList::getAccordionTabXMLNode()
return xmlNode;
}
+void LLOutfitsList::computeDifference(
+ const LLInventoryModel::cat_array_t& vcats,
+ uuid_vec_t& vadded,
+ uuid_vec_t& vremoved)
+{
+ uuid_vec_t vnew;
+ // Creating a vector of newly collected sub-categories UUIDs.
+ for (LLInventoryModel::cat_array_t::const_iterator iter = vcats.begin();
+ iter != vcats.end();
+ iter++)
+ {
+ vnew.push_back((*iter)->getUUID());
+ }
+
+ uuid_vec_t vcur;
+ // Creating a vector of currently displayed sub-categories UUIDs.
+ for (outfits_map_t::const_iterator iter = mOutfitsMap.begin();
+ iter != mOutfitsMap.end();
+ iter++)
+ {
+ vcur.push_back((*iter).first);
+ }
+
+ LLCommonUtils::computeDifference(vnew, vcur, vadded, vremoved);
+}
+
// EOF
diff --git a/indra/newview/lloutfitslist.h b/indra/newview/lloutfitslist.h
index de14c15415..2d103ea356 100644
--- a/indra/newview/lloutfitslist.h
+++ b/indra/newview/lloutfitslist.h
@@ -35,6 +35,7 @@
#include "llpanel.h"
// newview
+#include "llinventorymodel.h"
#include "llinventoryobserver.h"
class LLAccordionCtrl;
@@ -79,6 +80,11 @@ private:
*/
LLXMLNodePtr getAccordionTabXMLNode();
+ /**
+ * Wrapper for LLCommonUtils::computeDifference. @see LLCommonUtils::computeDifference
+ */
+ void computeDifference(const LLInventoryModel::cat_array_t& vcats, uuid_vec_t& vadded, uuid_vec_t& vremoved);
+
LLInventoryCategoriesObserver* mCategoriesObserver;
diff --git a/indra/newview/llpanelgrouplandmoney.cpp b/indra/newview/llpanelgrouplandmoney.cpp
index 9ac3a07041..65fe7165c2 100644
--- a/indra/newview/llpanelgrouplandmoney.cpp
+++ b/indra/newview/llpanelgrouplandmoney.cpp
@@ -236,6 +236,7 @@ public:
std::string mCantViewParcelsText;
std::string mCantViewAccountsText;
+ std::string mEmptyParcelsText;
};
//*******************************************
@@ -452,6 +453,7 @@ void LLPanelGroupLandMoney::impl::processGroupLand(LLMessageSystem* msg)
// This power was removed to make group roles simpler
//if ( !gAgent.hasPowerInGroup(mGroupID, GP_LAND_VIEW_OWNED) ) return;
if (!gAgent.isInGroup(mPanel.mGroupID)) return;
+ mGroupParcelsp->setCommentText(mEmptyParcelsText);
std::string name;
std::string desc;
@@ -696,6 +698,7 @@ BOOL LLPanelGroupLandMoney::postBuild()
mImplementationp->mCantViewParcelsText = getString("cant_view_group_land_text");
mImplementationp->mCantViewAccountsText = getString("cant_view_group_accounting_text");
+ mImplementationp->mEmptyParcelsText = getString("epmty_view_group_land_text");
if ( mImplementationp->mMapButtonp )
{
diff --git a/indra/newview/llpaneloutfitedit.cpp b/indra/newview/llpaneloutfitedit.cpp
index ae181e2819..dbccd243da 100644
--- a/indra/newview/llpaneloutfitedit.cpp
+++ b/indra/newview/llpaneloutfitedit.cpp
@@ -38,6 +38,7 @@
#include "llagent.h"
#include "llagentwearables.h"
#include "llappearancemgr.h"
+#include "llcofwearables.h"
#include "llfilteredwearablelist.h"
#include "llinventory.h"
#include "llinventoryitemslist.h"
@@ -121,9 +122,15 @@ private:
LLPanelOutfitEdit::LLPanelOutfitEdit()
-: LLPanel(), mCurrentOutfitID(), mFetchLook(NULL), mSearchFilter(NULL),
-mLookContents(NULL), mInventoryItemsPanel(NULL), mAddToOutfitBtn(NULL),
-mRemoveFromOutfitBtn(NULL), mLookObserver(NULL)
+: LLPanel(),
+ mCurrentOutfitID(),
+ mFetchLook(NULL),
+ mSearchFilter(NULL),
+ mCOFWearables(NULL),
+ mInventoryItemsPanel(NULL),
+ mAddToOutfitBtn(NULL),
+ mRemoveFromOutfitBtn(NULL),
+ mLookObserver(NULL)
{
mSavedFolderState = new LLSaveFolderState();
mSavedFolderState->setApply(FALSE);
@@ -171,9 +178,8 @@ BOOL LLPanelOutfitEdit::postBuild()
childSetCommitCallback("filter_button", boost::bind(&LLPanelOutfitEdit::showWearablesFilter, this), NULL);
childSetCommitCallback("list_view_btn", boost::bind(&LLPanelOutfitEdit::showFilteredWearablesPanel, this), NULL);
- mLookContents = getChild<LLScrollListCtrl>("look_items_list");
- mLookContents->sortByColumn("look_item_sort", TRUE);
- mLookContents->setCommitCallback(boost::bind(&LLPanelOutfitEdit::onOutfitItemSelectionChange, this));
+ mCOFWearables = getChild<LLCOFWearables>("cof_wearables_list");
+ mCOFWearables->setCommitCallback(boost::bind(&LLPanelOutfitEdit::onOutfitItemSelectionChange, this));
mInventoryItemsPanel = getChild<LLInventoryPanel>("inventory_items");
mInventoryItemsPanel->setFilterTypes(ALL_ITEMS_MASK);
@@ -206,15 +212,6 @@ BOOL LLPanelOutfitEdit::postBuild()
childSetAction("add_to_outfit_btn", boost::bind(&LLPanelOutfitEdit::onAddToOutfitClicked, this));
childSetEnabled("add_to_outfit_btn", false);
- mUpBtn = getChild<LLButton>("up_btn");
- mUpBtn->setEnabled(TRUE);
- mUpBtn->setClickedCallback(boost::bind(&LLPanelOutfitEdit::onUpClicked, this));
-
- //*TODO rename mLookContents to mOutfitContents
- mLookContents = getChild<LLScrollListCtrl>("look_items_list");
- mLookContents->sortByColumn("look_item_sort", TRUE);
- mLookContents->setCommitCallback(boost::bind(&LLPanelOutfitEdit::onOutfitItemSelectionChange, this));
-
mRemoveFromOutfitBtn = getChild<LLButton>("remove_from_outfit_btn");
mRemoveFromOutfitBtn->setEnabled(FALSE);
mRemoveFromOutfitBtn->setCommitCallback(boost::bind(&LLPanelOutfitEdit::onRemoveFromOutfitClicked, this));
@@ -245,7 +242,10 @@ BOOL LLPanelOutfitEdit::postBuild()
void LLPanelOutfitEdit::moveWearable(bool closer_to_body)
{
- LLViewerInventoryItem* wearable_to_move = gInventory.getItem(mLookContents->getSelectionInterface()->getCurrentID());
+ LLUUID item_id = mCOFWearables->getSelectedUUID();
+ if (item_id.isNull()) return;
+
+ LLViewerInventoryItem* wearable_to_move = gInventory.getItem(item_id);
LLAppearanceMgr::getInstance()->moveWearable(wearable_to_move, closer_to_body);
//*TODO why not to listen to inventory?
@@ -374,7 +374,7 @@ void LLPanelOutfitEdit::onAddToOutfitClicked(void)
void LLPanelOutfitEdit::onRemoveFromOutfitClicked(void)
{
- LLUUID id_to_remove = mLookContents->getSelectionInterface()->getCurrentID();
+ LLUUID id_to_remove = mCOFWearables->getSelectedUUID();
LLAppearanceMgr::getInstance()->removeItemFromAvatar(id_to_remove);
@@ -384,41 +384,9 @@ void LLPanelOutfitEdit::onRemoveFromOutfitClicked(void)
}
-void LLPanelOutfitEdit::onUpClicked(void)
-{
- LLUUID inv_id = mLookContents->getSelectionInterface()->getCurrentID();
- if (inv_id.isNull())
- {
- //nothing selected, do nothing
- return;
- }
-
- LLViewerInventoryItem *link_item = gInventory.getItem(inv_id);
- if (!link_item)
- {
- llwarns << "could not find inventory item based on currently worn link." << llendl;
- return;
- }
-
-
- LLUUID asset_id = link_item->getAssetUUID();
- if (asset_id.isNull())
- {
- llwarns << "inventory link has null Asset ID. could not get object reference" << llendl;
- }
-
- static const std::string empty = "";
- LLWearableList::instance().getAsset(asset_id,
- empty, // don't care about wearable name
- link_item->getActualType(),
- LLSidepanelAppearance::editWearable,
- (void*)getParentUICtrl());
-}
-
-
void LLPanelOutfitEdit::onEditWearableClicked(void)
{
- LLUUID id_to_edit = mLookContents->getSelectionInterface()->getCurrentID();
+ LLUUID id_to_edit = mCOFWearables->getSelectedUUID();
LLViewerInventoryItem * item_to_edit = gInventory.getItem(id_to_edit);
if (item_to_edit)
@@ -491,29 +459,11 @@ void LLPanelOutfitEdit::onInventorySelectionChange(const std::deque<LLFolderView
void LLPanelOutfitEdit::onOutfitItemSelectionChange(void)
{
- LLScrollListItem* item = mLookContents->getLastSelectedItem();
- if (!item)
- return;
+ LLUUID item_id = mCOFWearables->getSelectedUUID();
- LLRect item_rect;
- mLookContents->localRectToOtherView(item->getRect(), &item_rect, this);
+ //*TODO show Edit Wearable Button
- // TODO button(and item list) should be removed (when new widget is ready)
- LLRect btn_rect = mEditWearableBtn->getRect();
- btn_rect.set(item_rect.mRight - btn_rect.getWidth(), item_rect.mTop, item_rect.mRight, item_rect.mBottom);
-
- mEditWearableBtn->setShape(btn_rect);
- sendChildToFront(mEditWearableBtn);
-
- mEditWearableBtn->setEnabled(TRUE);
- if (!mEditWearableBtn->getVisible())
- {
- mEditWearableBtn->setVisible(TRUE);
- }
-
-
- const LLUUID& id_item_to_remove = item->getUUID();
- LLViewerInventoryItem* item_to_remove = gInventory.getItem(id_item_to_remove);
+ LLViewerInventoryItem* item_to_remove = gInventory.getItem(item_id);
if (!item_to_remove) return;
switch (item_to_remove->getType())
@@ -534,34 +484,7 @@ void LLPanelOutfitEdit::changed(U32 mask)
void LLPanelOutfitEdit::lookFetched(void)
{
- LLInventoryModel::cat_array_t cat_array;
- LLInventoryModel::item_array_t item_array;
-
- // collectDescendentsIf takes non-const reference:
- LLFindCOFValidItems is_cof_valid;
- gInventory.collectDescendentsIf(mCurrentOutfitID,
- cat_array,
- item_array,
- LLInventoryModel::EXCLUDE_TRASH,
- is_cof_valid);
- for (LLInventoryModel::item_array_t::const_iterator iter = item_array.begin();
- iter != item_array.end();
- iter++)
- {
- const LLViewerInventoryItem *item = (*iter);
-
- LLSD row;
- row["id"] = item->getUUID();
- LLSD& columns = row["columns"];
- columns[0]["column"] = "look_item";
- columns[0]["type"] = "text";
- columns[0]["value"] = item->getName();
- columns[1]["column"] = "look_item_sort";
- columns[1]["type"] = "text"; // TODO: multi-wearable sort "type" should go here.
- columns[1]["value"] = item->LLInventoryItem::getDescription();
-
- mLookContents->addElement(row);
- }
+ mCOFWearables->refresh();
updateVerbs();
}
@@ -570,8 +493,6 @@ void LLPanelOutfitEdit::updateLookInfo()
{
if (getVisible())
{
- mLookContents->clearRows();
-
mFetchLook->setFetchID(mCurrentOutfitID);
mFetchLook->startFetch();
if (mFetchLook->isFinished())
diff --git a/indra/newview/llpaneloutfitedit.h b/indra/newview/llpaneloutfitedit.h
index b6f121d484..21fa849289 100644
--- a/indra/newview/llpaneloutfitedit.h
+++ b/indra/newview/llpaneloutfitedit.h
@@ -45,6 +45,7 @@
#include "llinventorymodel.h"
class LLButton;
+class LLCOFWearables;
class LLTextBox;
class LLInventoryCategory;
class LLInventoryLookObserver;
@@ -102,7 +103,6 @@ public:
void onOutfitItemSelectionChange(void);
void onRemoveFromOutfitClicked(void);
void onEditWearableClicked(void);
- void onUpClicked(void);
void displayCurrentOutfit();
@@ -118,14 +118,12 @@ private:
LLUUID mCurrentOutfitID;
LLTextBox* mCurrentOutfitName;
- LLScrollListCtrl* mLookContents;
LLInventoryPanel* mInventoryItemsPanel;
LLFilterEditor* mSearchFilter;
LLSaveFolderState* mSavedFolderState;
std::string mSearchString;
LLButton* mAddToOutfitBtn;
LLButton* mRemoveFromOutfitBtn;
- LLButton* mUpBtn;
LLButton* mEditWearableBtn;
LLToggleableMenu* mSaveMenu;
@@ -134,6 +132,8 @@ private:
LLLookFetchObserver* mFetchLook;
LLInventoryLookObserver* mLookObserver;
std::vector<LLLookItemType> mLookItemTypes;
+
+ LLCOFWearables* mCOFWearables;
};
#endif // LL_LLPANELOUTFITEDIT_H
diff --git a/indra/newview/llviewerinventory.cpp b/indra/newview/llviewerinventory.cpp
index a23e42ea9e..b39ee8b2e0 100644
--- a/indra/newview/llviewerinventory.cpp
+++ b/indra/newview/llviewerinventory.cpp
@@ -87,7 +87,7 @@ public:
mInventoryItemsDict["New Jacket"] = LLTrans::getString("New Jacket");
mInventoryItemsDict["New Gloves"] = LLTrans::getString("New Gloves");
mInventoryItemsDict["New Undershirt"] = LLTrans::getString("New Undershirt");
- mInventoryItemsDict["New Undershirt"] = LLTrans::getString("New Undershirt");
+ mInventoryItemsDict["New Underpants"] = LLTrans::getString("New Underpants");
mInventoryItemsDict["New Skirt"] = LLTrans::getString("New Skirt");
mInventoryItemsDict["New Alpha"] = LLTrans::getString("New Alpha");
mInventoryItemsDict["New Tattoo"] = LLTrans::getString("New Tattoo");
diff --git a/indra/newview/llviewermessage.cpp b/indra/newview/llviewermessage.cpp
index e12457550a..3d042a8d8c 100644
--- a/indra/newview/llviewermessage.cpp
+++ b/indra/newview/llviewermessage.cpp
@@ -1700,6 +1700,7 @@ void LLOfferInfo::initRespondFunctionMap()
if(mRespondFunctions.empty())
{
mRespondFunctions["ObjectGiveItem"] = boost::bind(&LLOfferInfo::inventory_task_offer_callback, this, _1, _2);
+ mRespondFunctions["ObjectGiveItemUnknownUser"] = boost::bind(&LLOfferInfo::inventory_task_offer_callback, this, _1, _2);
mRespondFunctions["UserGiveItem"] = boost::bind(&LLOfferInfo::inventory_offer_callback, this, _1, _2);
}
}
diff --git a/indra/newview/skins/default/textures/icons/Progress_1.png b/indra/newview/skins/default/textures/icons/Progress_1.png
new file mode 100644
index 0000000000..5d6efbfa2a
--- /dev/null
+++ b/indra/newview/skins/default/textures/icons/Progress_1.png
Binary files differ
diff --git a/indra/newview/skins/default/textures/icons/Progress_10.png b/indra/newview/skins/default/textures/icons/Progress_10.png
new file mode 100644
index 0000000000..28203324f1
--- /dev/null
+++ b/indra/newview/skins/default/textures/icons/Progress_10.png
Binary files differ
diff --git a/indra/newview/skins/default/textures/icons/Progress_11.png b/indra/newview/skins/default/textures/icons/Progress_11.png
new file mode 100644
index 0000000000..6b87be0c3f
--- /dev/null
+++ b/indra/newview/skins/default/textures/icons/Progress_11.png
Binary files differ
diff --git a/indra/newview/skins/default/textures/icons/Progress_12.png b/indra/newview/skins/default/textures/icons/Progress_12.png
new file mode 100644
index 0000000000..089d58b090
--- /dev/null
+++ b/indra/newview/skins/default/textures/icons/Progress_12.png
Binary files differ
diff --git a/indra/newview/skins/default/textures/icons/Progress_2.png b/indra/newview/skins/default/textures/icons/Progress_2.png
new file mode 100644
index 0000000000..94cb73b1f7
--- /dev/null
+++ b/indra/newview/skins/default/textures/icons/Progress_2.png
Binary files differ
diff --git a/indra/newview/skins/default/textures/icons/Progress_3.png b/indra/newview/skins/default/textures/icons/Progress_3.png
new file mode 100644
index 0000000000..a04a5b5263
--- /dev/null
+++ b/indra/newview/skins/default/textures/icons/Progress_3.png
Binary files differ
diff --git a/indra/newview/skins/default/textures/icons/Progress_4.png b/indra/newview/skins/default/textures/icons/Progress_4.png
new file mode 100644
index 0000000000..a467098d82
--- /dev/null
+++ b/indra/newview/skins/default/textures/icons/Progress_4.png
Binary files differ
diff --git a/indra/newview/skins/default/textures/icons/Progress_5.png b/indra/newview/skins/default/textures/icons/Progress_5.png
new file mode 100644
index 0000000000..ea64f1d907
--- /dev/null
+++ b/indra/newview/skins/default/textures/icons/Progress_5.png
Binary files differ
diff --git a/indra/newview/skins/default/textures/icons/Progress_6.png b/indra/newview/skins/default/textures/icons/Progress_6.png
new file mode 100644
index 0000000000..fe4447935f
--- /dev/null
+++ b/indra/newview/skins/default/textures/icons/Progress_6.png
Binary files differ
diff --git a/indra/newview/skins/default/textures/icons/Progress_7.png b/indra/newview/skins/default/textures/icons/Progress_7.png
new file mode 100644
index 0000000000..64fa294771
--- /dev/null
+++ b/indra/newview/skins/default/textures/icons/Progress_7.png
Binary files differ
diff --git a/indra/newview/skins/default/textures/icons/Progress_8.png b/indra/newview/skins/default/textures/icons/Progress_8.png
new file mode 100644
index 0000000000..a1c9a7f2eb
--- /dev/null
+++ b/indra/newview/skins/default/textures/icons/Progress_8.png
Binary files differ
diff --git a/indra/newview/skins/default/textures/icons/Progress_9.png b/indra/newview/skins/default/textures/icons/Progress_9.png
new file mode 100644
index 0000000000..f3e9723184
--- /dev/null
+++ b/indra/newview/skins/default/textures/icons/Progress_9.png
Binary files differ
diff --git a/indra/newview/skins/default/textures/textures.xml b/indra/newview/skins/default/textures/textures.xml
index 84a99ba92a..bbb82d86b1 100644
--- a/indra/newview/skins/default/textures/textures.xml
+++ b/indra/newview/skins/default/textures/textures.xml
@@ -580,4 +580,17 @@ with the same filename but different name
<texture name="default_profile_picture.j2c" />
<texture name="locked_image.j2c" />
+ <texture name="Progress_1" file_name="icons/Progress_1.png" preload="true" />
+ <texture name="Progress_2" file_name="icons/Progress_2.png" preload="true" />
+ <texture name="Progress_3" file_name="icons/Progress_3.png" preload="true" />
+ <texture name="Progress_4" file_name="icons/Progress_4.png" preload="true" />
+ <texture name="Progress_5" file_name="icons/Progress_5.png" preload="true" />
+ <texture name="Progress_6" file_name="icons/Progress_6.png" preload="true" />
+ <texture name="Progress_7" file_name="icons/Progress_7.png" preload="true" />
+ <texture name="Progress_8" file_name="icons/Progress_8.png" preload="true" />
+ <texture name="Progress_9" file_name="icons/Progress_9.png" preload="true" />
+ <texture name="Progress_10" file_name="icons/Progress_10.png" preload="true" />
+ <texture name="Progress_11" file_name="icons/Progress_11.png" preload="true" />
+ <texture name="Progress_12" file_name="icons/Progress_12.png" preload="true" />
+
</textures>
diff --git a/indra/newview/skins/default/xui/en/panel_cof_wearables.xml b/indra/newview/skins/default/xui/en/panel_cof_wearables.xml
new file mode 100644
index 0000000000..01c7ae61d2
--- /dev/null
+++ b/indra/newview/skins/default/xui/en/panel_cof_wearables.xml
@@ -0,0 +1,65 @@
+<?xml version="1.0" encoding="utf-8" standalone="yes" ?>
+<panel
+ background_visible="true"
+ bg_alpha_color="DkGray"
+ border="false"
+ bottom="0"
+ follows="all"
+ height="200"
+ left="0"
+ name="cof_wearables"
+ width="313">
+ <accordion
+ follows="all"
+ height="373"
+ layout="topleft"
+ left="3"
+ top="0"
+ name="cof_wearables_accordion"
+ background_visible="true"
+ bg_alpha_color="DkGray2"
+ width="307">
+ <accordion_tab
+ layout="topleft"
+ name="tab_attachments"
+ title="Attachments">
+ <flat_list_view
+ allow_select="true"
+ follows="all"
+ height="150"
+ layout="topleft"
+ left="0"
+ name="list_attachments"
+ top="0"
+ width="307" />
+ </accordion_tab>
+ <accordion_tab
+ layout="topleft"
+ name="tab_clothing"
+ title="Clothing">
+ <flat_list_view
+ allow_select="true"
+ follows="all"
+ height="150"
+ layout="topleft"
+ left="0"
+ name="list_clothing"
+ top="0"
+ width="307" />
+ </accordion_tab>
+ <accordion_tab
+ layout="topleft"
+ name="tab_body_parts"
+ title="Body Parts">
+ <flat_list_view
+ allow_select="true"
+ follows="all"
+ height="150"
+ layout="topleft"
+ left="0"
+ name="list_body_parts"
+ top="0"
+ width="307" />
+ </accordion_tab>
+ </accordion>
+</panel>
diff --git a/indra/newview/skins/default/xui/en/panel_group_land_money.xml b/indra/newview/skins/default/xui/en/panel_group_land_money.xml
index 9e99a8ceaf..76f7484c68 100644
--- a/indra/newview/skins/default/xui/en/panel_group_land_money.xml
+++ b/indra/newview/skins/default/xui/en/panel_group_land_money.xml
@@ -17,6 +17,10 @@
You don&apos;t have permission to view group owned land
</panel.string>
<panel.string
+ name="epmty_view_group_land_text">
+ No entries
+ </panel.string>
+ <panel.string
name="cant_view_group_accounting_text">
You don&apos;t have permission to view the group&apos;s accounting information.
</panel.string>
diff --git a/indra/newview/skins/default/xui/en/panel_outfit_edit.xml b/indra/newview/skins/default/xui/en/panel_outfit_edit.xml
index 314d2389ae..73181392c9 100644
--- a/indra/newview/skins/default/xui/en/panel_outfit_edit.xml
+++ b/indra/newview/skins/default/xui/en/panel_outfit_edit.xml
@@ -149,29 +149,18 @@
auto_resize="true"
user_resize="true">
- <scroll_list
- width="300"
- column_padding="0"
- draw_heading="false"
- draw_stripes="false"
+ <!-- List containing items from the COF and Base outfit -->
+ <panel
+ background_visible="false"
+ class="cof_wearables"
+ filename="panel_cof_wearables.xml"
follows="left|top|right|bottom"
+ height="193"
layout="topleft"
- name="look_items_list"
- search_column="1"
- sort_column="2"
left="0"
- height="193"
- top="0">
- <scroll_list.columns
- label="Look Item"
- name="look_item"
- width="285" />
- <scroll_list.columns
- label="Outfit Item Sort"
- width="0"
- sort_column="look_item_sort"
- name="look_item_sort" />
- </scroll_list>
+ name="cof_wearables_list"
+ top="0"
+ width="300" />
<panel
background_visible="true"
diff --git a/indra/newview/skins/default/xui/en/widgets/loading_indicator.xml b/indra/newview/skins/default/xui/en/widgets/loading_indicator.xml
new file mode 100644
index 0000000000..6040d24128
--- /dev/null
+++ b/indra/newview/skins/default/xui/en/widgets/loading_indicator.xml
@@ -0,0 +1,8 @@
+<?xml version="1.0" encoding="utf-8" standalone="yes" ?>
+<loading_indicator
+ follows="left|top"
+ mouse_opaque="false"
+ name="loading_indicator"
+ rotations_per_sec="1.0"
+ tab_stop="false"
+/>