From 5a39e173b06698fd9e07d524e7044a41e86bdfbb Mon Sep 17 00:00:00 2001 From: "Brad Payne (Vir Linden)" Date: Mon, 28 Jun 2010 17:26:19 -0400 Subject: EXT-8063 WIP - last-ditch filtering of item counts in updateAppearanceFromCOF --- indra/newview/llappearancemgr.cpp | 71 ++++++++++++++++++++++++++++++++++++--- 1 file changed, 67 insertions(+), 4 deletions(-) (limited to 'indra/newview/llappearancemgr.cpp') diff --git a/indra/newview/llappearancemgr.cpp b/indra/newview/llappearancemgr.cpp index ce022ac840..8a3b4cb028 100644 --- a/indra/newview/llappearancemgr.cpp +++ b/indra/newview/llappearancemgr.cpp @@ -1537,16 +1537,79 @@ bool sort_by_description(const LLInventoryItem* item1, const LLInventoryItem* it return item1->LLInventoryItem::getDescription() < item2->LLInventoryItem::getDescription(); } -void LLAppearanceMgr::updateAppearanceFromCOF() +void item_array_diff(LLInventoryModel::item_array_t& full_list, + LLInventoryModel::item_array_t& keep_list, + LLInventoryModel::item_array_t& kill_list) + { - //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(); + for (LLInventoryModel::item_array_t::iterator it = full_list.begin(); + it != full_list.end(); + ++it) + { + LLViewerInventoryItem *item = *it; + if (keep_list.find(item) < 0) // Why on earth does LLDynamicArray need to redefine find()? + { + kill_list.push_back(item); + } + } +} +void LLAppearanceMgr::enforceItemCountLimits() +{ + S32 purge_count = 0; + + LLInventoryModel::item_array_t body_items; + getDescendentsOfAssetType(getCOF(), body_items, LLAssetType::AT_BODYPART, false); + LLInventoryModel::item_array_t curr_body_items = body_items; + removeDuplicateItems(body_items); + filterWearableItems(body_items, 1); + LLInventoryModel::item_array_t kill_body_items; + item_array_diff(curr_body_items,body_items,kill_body_items); + for (LLInventoryModel::item_array_t::iterator it = kill_body_items.begin(); + it != kill_body_items.end(); + ++it) + { + LLViewerInventoryItem *item = *it; + llinfos << "purging dup body part " << item->getName() << llendl; + gInventory.purgeObject(item->getUUID()); + purge_count++; + } + + LLInventoryModel::item_array_t wear_items; + getDescendentsOfAssetType(getCOF(), wear_items, LLAssetType::AT_CLOTHING, false); + LLInventoryModel::item_array_t curr_wear_items = wear_items; + removeDuplicateItems(wear_items); + filterWearableItems(wear_items, LLAgentWearables::MAX_CLOTHING_PER_TYPE); + LLInventoryModel::item_array_t kill_wear_items; + item_array_diff(curr_wear_items,wear_items,kill_wear_items); + for (LLInventoryModel::item_array_t::iterator it = kill_wear_items.begin(); + it != kill_wear_items.end(); + ++it) + { + LLViewerInventoryItem *item = *it; + llinfos << "purging excess clothing item " << item->getName() << llendl; + gInventory.purgeObject(item->getUUID()); + purge_count++; + } + + if (purge_count>0) + { + gInventory.notifyObservers(); + } +} + +void LLAppearanceMgr::updateAppearanceFromCOF() +{ // update dirty flag to see if the state of the COF matches // the saved outfit stored as a folder link llinfos << "starting" << llendl; + //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(); + + enforceItemCountLimits(); + updateIsDirty(); dumpCat(getCOF(),"COF, start"); -- cgit v1.3 From b81adf898cbe770e1579da5b1618330aac27c671 Mon Sep 17 00:00:00 2001 From: "Brad Payne (Vir Linden)" Date: Tue, 29 Jun 2010 11:59:40 -0400 Subject: EXT-8063 FIX, EXT-7986 FIX - enforce wearable counts in updateApperanceFromCOF() if UI lets any improper state through --- indra/newview/llappearancemgr.cpp | 33 ++++++++++++++++++++++++++++++--- indra/newview/llappearancemgr.h | 1 + 2 files changed, 31 insertions(+), 3 deletions(-) (limited to 'indra/newview/llappearancemgr.cpp') diff --git a/indra/newview/llappearancemgr.cpp b/indra/newview/llappearancemgr.cpp index 8a3b4cb028..ddbec25c04 100644 --- a/indra/newview/llappearancemgr.cpp +++ b/indra/newview/llappearancemgr.cpp @@ -1598,18 +1598,44 @@ void LLAppearanceMgr::enforceItemCountLimits() } } +class BoolSetter +{ +public: + BoolSetter(bool& var): + mVar(var) + { + mVar = true; + } + ~BoolSetter() + { + mVar = false; + } +private: + bool& mVar; +}; + void LLAppearanceMgr::updateAppearanceFromCOF() { - // update dirty flag to see if the state of the COF matches - // the saved outfit stored as a folder link + if (mIsInUpdateAppearanceFromCOF) + { + llwarns << "Called updateAppearanceFromCOF inside updateAppearanceFromCOF, skipping" << llendl; + return; + } + + BoolSetter setIsInUpdateAppearanceFromCOF(mIsInUpdateAppearanceFromCOF); + llinfos << "starting" << llendl; //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(); + // Remove duplicate or excess wearables. Should normally be enforced at the UI level, but + // this should catch anything that gets through. enforceItemCountLimits(); + // update dirty flag to see if the state of the COF matches + // the saved outfit stored as a folder link updateIsDirty(); dumpCat(getCOF(),"COF, start"); @@ -2556,7 +2582,8 @@ void LLAppearanceMgr::dumpItemArray(const LLInventoryModel::item_array_t& items, LLAppearanceMgr::LLAppearanceMgr(): mAttachmentInvLinkEnabled(false), - mOutfitIsDirty(false) + mOutfitIsDirty(false), + mIsInUpdateAppearanceFromCOF(false) { LLOutfitObserver& outfit_observer = LLOutfitObserver::instance(); diff --git a/indra/newview/llappearancemgr.h b/indra/newview/llappearancemgr.h index 15383381f8..afd1bf3ade 100644 --- a/indra/newview/llappearancemgr.h +++ b/indra/newview/llappearancemgr.h @@ -204,6 +204,7 @@ private: std::set mRegisteredAttachments; bool mAttachmentInvLinkEnabled; bool mOutfitIsDirty; + bool mIsInUpdateAppearanceFromCOF; // to detect recursive calls. /** * Lock for blocking operations on outfit until server reply or timeout exceed -- cgit v1.3 From 1c05b8cc3269531f781f1e97260868509b757327 Mon Sep 17 00:00:00 2001 From: "Brad Payne (Vir Linden)" Date: Wed, 30 Jun 2010 11:42:16 -0400 Subject: Cleanup - moved small utility class --- indra/newview/llappearancemgr.cpp | 35 +++++++++++++++++++---------------- 1 file changed, 19 insertions(+), 16 deletions(-) (limited to 'indra/newview/llappearancemgr.cpp') diff --git a/indra/newview/llappearancemgr.cpp b/indra/newview/llappearancemgr.cpp index ddbec25c04..547dfd7006 100644 --- a/indra/newview/llappearancemgr.cpp +++ b/indra/newview/llappearancemgr.cpp @@ -55,6 +55,25 @@ #include "llviewerregion.h" #include "llwearablelist.h" +// RAII thingy to guarantee that a variable gets reset when the Setter +// goes out of scope. More general utility would be handy - TODO: +// check boost. +class BoolSetter +{ +public: + BoolSetter(bool& var): + mVar(var) + { + mVar = true; + } + ~BoolSetter() + { + mVar = false; + } +private: + bool& mVar; +}; + char ORDER_NUMBER_SEPARATOR('@'); class LLOutfitUnLockTimer: public LLEventTimer @@ -1598,22 +1617,6 @@ void LLAppearanceMgr::enforceItemCountLimits() } } -class BoolSetter -{ -public: - BoolSetter(bool& var): - mVar(var) - { - mVar = true; - } - ~BoolSetter() - { - mVar = false; - } -private: - bool& mVar; -}; - void LLAppearanceMgr::updateAppearanceFromCOF() { if (mIsInUpdateAppearanceFromCOF) -- cgit v1.3