SH-3606 WIP - replaced several LLInventoryCallback subclasses with boost::func equivalents

master
Brad Payne (Vir Linden) 2012-12-10 14:47:17 -05:00
parent 542a9e0a41
commit 0777f53e2f
12 changed files with 239 additions and 365 deletions

View File

@ -61,19 +61,16 @@ using namespace LLAvatarAppearanceDefines;
///////////////////////////////////////////////////////////////////////////////
// Callback to wear and start editing an item that has just been created.
class LLWearAndEditCallback : public LLInventoryCallback
void wear_and_edit_cb(const LLUUID& inv_item)
{
void fire(const LLUUID& inv_item)
{
if (inv_item.isNull()) return;
// Request editing the item after it gets worn.
gAgentWearables.requestEditingWearable(inv_item);
// Wear it.
LLAppearanceMgr::instance().wearItemOnAvatar(inv_item);
}
};
if (inv_item.isNull()) return;
// Request editing the item after it gets worn.
gAgentWearables.requestEditingWearable(inv_item);
// Wear it.
LLAppearanceMgr::instance().wearItemOnAvatar(inv_item);
}
///////////////////////////////////////////////////////////////////////////////
@ -965,8 +962,8 @@ public:
llinfos << "All items created" << llendl;
LLPointer<LLInventoryCallback> link_waiter = new LLUpdateAppearanceOnDestroy;
LLAppearanceMgr::instance().linkAll(LLAppearanceMgr::instance().getCOF(),
mItemsToLink,
link_waiter);
mItemsToLink,
link_waiter);
}
void addPendingWearable(LLViewerWearable *wearable)
{
@ -1789,7 +1786,7 @@ void LLAgentWearables::createWearable(LLWearableType::EType type, bool wear, con
LLViewerWearable* wearable = LLWearableList::instance().createNewWearable(type, gAgentAvatarp);
LLAssetType::EType asset_type = wearable->getAssetType();
LLInventoryType::EType inv_type = LLInventoryType::IT_WEARABLE;
LLPointer<LLInventoryCallback> cb = wear ? new LLWearAndEditCallback : NULL;
LLPointer<LLInventoryCallback> cb = wear ? new LLBoostFuncInventoryCallback(wear_and_edit_cb) : NULL;
LLUUID folder_id;
if (parent_id.notNull())

View File

@ -35,54 +35,45 @@
#include "llvoavatarself.h"
class LLOrderMyOutfitsOnDestroy: public LLInventoryCallback
void order_my_outfits_cb()
{
public:
LLOrderMyOutfitsOnDestroy() {};
virtual ~LLOrderMyOutfitsOnDestroy()
if (!LLApp::isRunning())
{
if (!LLApp::isRunning())
{
llwarns << "called during shutdown, skipping" << llendl;
return;
}
llwarns << "called during shutdown, skipping" << llendl;
return;
}
const LLUUID& my_outfits_id = gInventory.findCategoryUUIDForType(LLFolderType::FT_MY_OUTFITS);
if (my_outfits_id.isNull()) return;
const LLUUID& my_outfits_id = gInventory.findCategoryUUIDForType(LLFolderType::FT_MY_OUTFITS);
if (my_outfits_id.isNull()) return;
LLInventoryModel::cat_array_t* cats;
LLInventoryModel::item_array_t* items;
gInventory.getDirectDescendentsOf(my_outfits_id, cats, items);
if (!cats) return;
LLInventoryModel::cat_array_t* cats;
LLInventoryModel::item_array_t* items;
gInventory.getDirectDescendentsOf(my_outfits_id, cats, items);
if (!cats) return;
//My Outfits should at least contain saved initial outfit and one another outfit
if (cats->size() < 2)
{
llwarning("My Outfits category was not populated properly", 0);
return;
}
llinfos << "Starting updating My Outfits with wearables ordering information" << llendl;
for (LLInventoryModel::cat_array_t::iterator outfit_iter = cats->begin();
outfit_iter != cats->end(); ++outfit_iter)
{
const LLUUID& cat_id = (*outfit_iter)->getUUID();
if (cat_id.isNull()) continue;
// saved initial outfit already contains wearables ordering information
if (cat_id == LLAppearanceMgr::getInstance()->getBaseOutfitUUID()) continue;
LLAppearanceMgr::getInstance()->updateClothingOrderingInfo(cat_id);
}
llinfos << "Finished updating My Outfits with wearables ordering information" << llendl;
//My Outfits should at least contain saved initial outfit and one another outfit
if (cats->size() < 2)
{
llwarning("My Outfits category was not populated properly", 0);
return;
}
/* virtual */ void fire(const LLUUID& inv_item) {};
};
llinfos << "Starting updating My Outfits with wearables ordering information" << llendl;
for (LLInventoryModel::cat_array_t::iterator outfit_iter = cats->begin();
outfit_iter != cats->end(); ++outfit_iter)
{
const LLUUID& cat_id = (*outfit_iter)->getUUID();
if (cat_id.isNull()) continue;
// saved initial outfit already contains wearables ordering information
if (cat_id == LLAppearanceMgr::getInstance()->getBaseOutfitUUID()) continue;
LLAppearanceMgr::getInstance()->updateClothingOrderingInfo(cat_id);
}
llinfos << "Finished updating My Outfits with wearables ordering information" << llendl;
}
LLInitialWearablesFetch::LLInitialWearablesFetch(const LLUUID& cof_id) :
LLInventoryFetchDescendentsObserver(cof_id)
@ -563,7 +554,7 @@ void LLLibraryOutfitsFetch::contentsDone()
LLInventoryModel::cat_array_t cat_array;
LLInventoryModel::item_array_t wearable_array;
LLPointer<LLOrderMyOutfitsOnDestroy> order_myoutfits_on_destroy = new LLOrderMyOutfitsOnDestroy;
LLPointer<LLInventoryCallback> order_myoutfits_on_destroy = new LLBoostFuncInventoryCallback(no_op_inventory_func, order_my_outfits_cb);
for (uuid_vec_t::const_iterator folder_iter = mImportedClothingFolders.begin();
folder_iter != mImportedClothingFolders.end();

View File

@ -155,8 +155,6 @@ LLUUID findDescendentCategoryIDByName(const LLUUID& parent_id, const std::string
}
}
void no_op() {}
class LLCallAfterInventoryBatchMgr: public LLEventTimer
{
public:
@ -423,22 +421,6 @@ public:
}
};
//Inventory callback updating "dirty" state when destroyed
class LLUpdateDirtyState: public LLInventoryCallback
{
public:
LLUpdateDirtyState() {}
virtual ~LLUpdateDirtyState()
{
if (LLAppearanceMgr::instanceExists())
{
LLAppearanceMgr::getInstance()->updateIsDirty();
}
}
virtual void fire(const LLUUID&) {}
};
LLUpdateAppearanceOnDestroy::LLUpdateAppearanceOnDestroy(bool update_base_outfit_ordering):
mFireCount(0),
mUpdateBaseOrder(update_base_outfit_ordering)
@ -777,100 +759,72 @@ bool LLWearableHoldingPattern::pollFetchCompletion()
return done;
}
class RecoveredItemLinkCB: public LLInventoryCallback
void recovered_item_link_cb(const LLUUID& item_id, LLWearableType::EType type, LLViewerWearable *wearable, LLWearableHoldingPattern* holder)
{
public:
RecoveredItemLinkCB(LLWearableType::EType type, LLViewerWearable *wearable, LLWearableHoldingPattern* holder):
mHolder(holder),
mWearable(wearable),
mType(type)
if (!holder->isMostRecent())
{
llwarns << "skipping because LLWearableHolding pattern is invalid (superceded by later outfit request)" << llendl;
// runway skip here?
}
void fire(const LLUUID& item_id)
llinfos << "Recovered item link for type " << type << llendl;
holder->eraseTypeToLink(type);
// Add wearable to FoundData for actual wearing
LLViewerInventoryItem *item = gInventory.getItem(item_id);
LLViewerInventoryItem *linked_item = item ? item->getLinkedItem() : NULL;
if (linked_item)
{
if (!mHolder->isMostRecent())
{
llwarns << "skipping because LLWearableHolding pattern is invalid (superceded by later outfit request)" << llendl;
// runway skip here?
}
llinfos << "Recovered item link for type " << mType << llendl;
mHolder->eraseTypeToLink(mType);
// Add wearable to FoundData for actual wearing
LLViewerInventoryItem *item = gInventory.getItem(item_id);
LLViewerInventoryItem *linked_item = item ? item->getLinkedItem() : NULL;
if (linked_item)
{
gInventory.addChangedMask(LLInventoryObserver::LABEL, linked_item->getUUID());
gInventory.addChangedMask(LLInventoryObserver::LABEL, linked_item->getUUID());
if (item)
{
LLFoundData found(linked_item->getUUID(),
linked_item->getAssetUUID(),
linked_item->getName(),
linked_item->getType(),
linked_item->isWearableType() ? linked_item->getWearableType() : LLWearableType::WT_INVALID,
true // is replacement
);
found.mWearable = mWearable;
mHolder->getFoundList().push_front(found);
}
else
{
llwarns << self_av_string() << "inventory item not found for recovered wearable" << llendl;
}
if (item)
{
LLFoundData found(linked_item->getUUID(),
linked_item->getAssetUUID(),
linked_item->getName(),
linked_item->getType(),
linked_item->isWearableType() ? linked_item->getWearableType() : LLWearableType::WT_INVALID,
true // is replacement
);
found.mWearable = wearable;
holder->getFoundList().push_front(found);
}
else
{
llwarns << self_av_string() << "inventory link not found for recovered wearable" << llendl;
llwarns << self_av_string() << "inventory item not found for recovered wearable" << llendl;
}
}
private:
LLWearableHoldingPattern* mHolder;
LLViewerWearable *mWearable;
LLWearableType::EType mType;
};
else
{
llwarns << self_av_string() << "inventory link not found for recovered wearable" << llendl;
}
}
class RecoveredItemCB: public LLInventoryCallback
void recovered_item_cb(const LLUUID& item_id, LLWearableType::EType type, LLViewerWearable *wearable, LLWearableHoldingPattern* holder)
{
public:
RecoveredItemCB(LLWearableType::EType type, LLViewerWearable *wearable, LLWearableHoldingPattern* holder):
mHolder(holder),
mWearable(wearable),
mType(type)
if (!holder->isMostRecent())
{
// runway skip here?
llwarns << self_av_string() << "skipping because LLWearableHolding pattern is invalid (superceded by later outfit request)" << llendl;
}
void fire(const LLUUID& item_id)
{
if (!mHolder->isMostRecent())
{
// runway skip here?
llwarns << self_av_string() << "skipping because LLWearableHolding pattern is invalid (superceded by later outfit request)" << llendl;
}
LL_DEBUGS("Avatar") << self_av_string() << "Recovered item for type " << mType << LL_ENDL;
LLViewerInventoryItem *itemp = gInventory.getItem(item_id);
mWearable->setItemID(item_id);
LLPointer<LLInventoryCallback> cb = new RecoveredItemLinkCB(mType,mWearable,mHolder);
mHolder->eraseTypeToRecover(mType);
llassert(itemp);
if (itemp)
{
link_inventory_item( gAgent.getID(),
item_id,
LLAppearanceMgr::instance().getCOF(),
itemp->getName(),
itemp->getDescription(),
LLAssetType::AT_LINK,
cb);
}
LL_DEBUGS("Avatar") << self_av_string() << "Recovered item for type " << type << LL_ENDL;
LLViewerInventoryItem *itemp = gInventory.getItem(item_id);
wearable->setItemID(item_id);
LLPointer<LLInventoryCallback> cb = new LLBoostFuncInventoryCallback(boost::bind(recovered_item_link_cb,_1,type,wearable,holder));
holder->eraseTypeToRecover(type);
llassert(itemp);
if (itemp)
{
link_inventory_item( gAgent.getID(),
item_id,
LLAppearanceMgr::instance().getCOF(),
itemp->getName(),
itemp->getDescription(),
LLAssetType::AT_LINK,
cb);
}
private:
LLWearableHoldingPattern* mHolder;
LLViewerWearable *mWearable;
LLWearableType::EType mType;
};
}
void LLWearableHoldingPattern::recoverMissingWearable(LLWearableType::EType type)
{
@ -888,7 +842,7 @@ void LLWearableHoldingPattern::recoverMissingWearable(LLWearableType::EType type
// Add a new one in the lost and found folder.
const LLUUID lost_and_found_id = gInventory.findCategoryUUIDForType(LLFolderType::FT_LOST_AND_FOUND);
LLPointer<LLInventoryCallback> cb = new RecoveredItemCB(type,wearable,this);
LLPointer<LLInventoryCallback> cb = new LLBoostFuncInventoryCallback(boost::bind(recovered_item_cb,_1,type,wearable,this));
create_inventory_item(gAgent.getID(),
gAgent.getSessionID(),
@ -1225,6 +1179,18 @@ const LLUUID LLAppearanceMgr::getBaseOutfitUUID()
return outfit_cat->getUUID();
}
void wear_on_avatar_cb(const LLUUID& inv_item, bool do_replace = false)
{
if (inv_item.isNull())
return;
LLViewerInventoryItem *item = gInventory.getItem(inv_item);
if (item)
{
LLAppearanceMgr::instance().wearItemOnAvatar(inv_item, true, do_replace);
}
}
bool LLAppearanceMgr::wearItemOnAvatar(const LLUUID& item_id_to_wear, bool do_update, bool replace, LLPointer<LLInventoryCallback> cb)
{
if (item_id_to_wear.isNull()) return false;
@ -1244,8 +1210,8 @@ bool LLAppearanceMgr::wearItemOnAvatar(const LLUUID& item_id_to_wear, bool do_up
if (gInventory.isObjectDescendentOf(item_to_wear->getUUID(), gInventory.getLibraryRootFolderID()))
{
LLPointer<LLInventoryCallback> cb = new WearOnAvatarCallback(replace);
copy_inventory_item(gAgent.getID(), item_to_wear->getPermissions().getOwner(), item_to_wear->getUUID(), LLUUID::null, std::string(),cb);
LLPointer<LLInventoryCallback> cb = new LLBoostFuncInventoryCallback(boost::bind(wear_on_avatar_cb,_1,replace));
copy_inventory_item(gAgent.getID(), item_to_wear->getPermissions().getOwner(), item_to_wear->getUUID(), LLUUID::null, std::string(), cb);
return false;
}
else if (!gInventory.isObjectDescendentOf(item_to_wear->getUUID(), gInventory.getRootFolderID()))
@ -2348,6 +2314,25 @@ void LLAppearanceMgr::addCOFItemLink(const LLUUID &item_id, bool do_update, LLPo
}
}
void modified_cof_cb(const LLUUID& inv_item)
{
LLAppearanceMgr::instance().updateAppearanceFromCOF();
// Start editing the item if previously requested.
gAgentWearables.editWearableIfRequested(inv_item);
// TODO: camera mode may not be changed if a debug setting is tweaked
if( gAgentCamera.cameraCustomizeAvatar() )
{
// If we're in appearance editing mode, the current tab may need to be refreshed
LLSidepanelAppearance *panel = dynamic_cast<LLSidepanelAppearance*>(LLFloaterSidePanelContainer::getPanel("appearance"));
if (panel)
{
panel->showDefaultSubpart();
}
}
}
void LLAppearanceMgr::addCOFItemLink(const LLInventoryItem *item, bool do_update, LLPointer<LLInventoryCallback> cb)
{
const LLViewerInventoryItem *vitem = dynamic_cast<const LLViewerInventoryItem*>(item);
@ -2411,7 +2396,7 @@ void LLAppearanceMgr::addCOFItemLink(const LLInventoryItem *item, bool do_update
{
if(do_update && cb.isNull())
{
cb = new ModifiedCOFCallback;
cb = new LLBoostFuncInventoryCallback(modified_cof_cb);
}
const std::string description = vitem->getIsLinkType() ? vitem->getDescription() : "";
link_inventory_item( gAgent.getID(),
@ -2425,22 +2410,6 @@ void LLAppearanceMgr::addCOFItemLink(const LLInventoryItem *item, bool do_update
return;
}
// BAP remove ensemble code for 2.1?
void LLAppearanceMgr::addEnsembleLink( LLInventoryCategory* cat, bool do_update )
{
#if SUPPORT_ENSEMBLES
// BAP add check for already in COF.
LLPointer<LLInventoryCallback> cb = do_update ? new ModifiedCOFCallback : 0;
link_inventory_item( gAgent.getID(),
cat->getLinkedUUID(),
getCOF(),
cat->getName(),
cat->getDescription(),
LLAssetType::AT_LINK_FOLDER,
cb);
#endif
}
void LLAppearanceMgr::removeAllClothesFromAvatar()
{
// Fetch worn clothes (i.e. the ones in COF).
@ -2668,7 +2637,7 @@ void LLAppearanceMgr::copyLibraryGestures()
folder_name == COMMON_GESTURES_FOLDER ||
folder_name == OTHER_GESTURES_FOLDER)
{
cb = new ActivateGestureCallback;
cb = new LLBoostFuncInventoryCallback(activate_gesture_cb);
}
LLUUID cat_id = findDescendentCategoryIDByName(lib_gesture_cat_id,folder_name);
@ -2722,6 +2691,16 @@ void LLAppearanceMgr::onFirstFullyVisible()
}
}
// update "dirty" state - defined outside class to allow for calling
// after appearance mgr instance has been destroyed.
void appearance_mgr_update_dirty_state()
{
if (LLAppearanceMgr::instanceExists())
{
LLAppearanceMgr::getInstance()->updateIsDirty();
}
}
bool LLAppearanceMgr::updateBaseOutfit()
{
if (isOutfitLocked())
@ -2742,8 +2721,8 @@ bool LLAppearanceMgr::updateBaseOutfit()
// in a Base Outfit we do not remove items, only links
purgeCategory(base_outfit_id, false);
LLPointer<LLInventoryCallback> dirty_state_updater = new LLUpdateDirtyState();
LLPointer<LLInventoryCallback> dirty_state_updater =
new LLBoostFuncInventoryCallback(no_op_inventory_func, appearance_mgr_update_dirty_state);
//COF contains only links so we copy to the Base Outfit only links
shallowCopyCategoryContents(getCOF(), base_outfit_id, dirty_state_updater);
@ -2998,48 +2977,34 @@ void LLAppearanceMgr::requestServerAppearanceUpdate(LLCurl::ResponderPtr respond
mLastUpdateRequestCOFVersion = cof_version;
}
class LLShowCreatedOutfit: public LLInventoryCallback
void show_created_outfit(LLUUID& folder_id, bool show_panel = true)
{
public:
LLShowCreatedOutfit(LLUUID& folder_id, bool show_panel = true): mFolderID(folder_id), mShowPanel(show_panel)
{}
virtual ~LLShowCreatedOutfit()
if (!LLApp::isRunning())
{
if (!LLApp::isRunning())
{
llwarns << "called during shutdown, skipping" << llendl;
return;
}
LLSD key;
//EXT-7727. For new accounts LLShowCreatedOutfit is created during login process
// add may be processed after login process is finished
if (mShowPanel)
{
LLFloaterSidePanelContainer::showPanel("appearance", "panel_outfits_inventory", key);
}
LLOutfitsList *outfits_list =
dynamic_cast<LLOutfitsList*>(LLFloaterSidePanelContainer::getPanel("appearance", "outfitslist_tab"));
if (outfits_list)
{
outfits_list->setSelectedOutfitByUUID(mFolderID);
}
LLAppearanceMgr::getInstance()->updateIsDirty();
gAgentWearables.notifyLoadingFinished(); // New outfit is saved.
LLAppearanceMgr::getInstance()->updatePanelOutfitName("");
llwarns << "called during shutdown, skipping" << llendl;
return;
}
virtual void fire(const LLUUID&)
{}
private:
LLUUID mFolderID;
bool mShowPanel;
};
LLSD key;
//EXT-7727. For new accounts inventory callback is created during login process
// and may be processed after login process is finished
if (show_panel)
{
LLFloaterSidePanelContainer::showPanel("appearance", "panel_outfits_inventory", key);
}
LLOutfitsList *outfits_list =
dynamic_cast<LLOutfitsList*>(LLFloaterSidePanelContainer::getPanel("appearance", "outfitslist_tab"));
if (outfits_list)
{
outfits_list->setSelectedOutfitByUUID(folder_id);
}
LLAppearanceMgr::getInstance()->updateIsDirty();
gAgentWearables.notifyLoadingFinished(); // New outfit is saved.
LLAppearanceMgr::getInstance()->updatePanelOutfitName("");
}
LLUUID LLAppearanceMgr::makeNewOutfitLinks(const std::string& new_folder_name, bool show_panel)
{
@ -3056,7 +3021,8 @@ LLUUID LLAppearanceMgr::makeNewOutfitLinks(const std::string& new_folder_name, b
updateClothingOrderingInfo();
LLPointer<LLInventoryCallback> cb = new LLShowCreatedOutfit(folder_id,show_panel);
LLPointer<LLInventoryCallback> cb = new LLBoostFuncInventoryCallback(no_op_inventory_func,
boost::bind(show_created_outfit,folder_id,show_panel));
shallowCopyCategoryContents(getCOF(),folder_id, cb);
createBaseOutfitLink(folder_id, cb);

View File

@ -137,9 +137,6 @@ public:
void removeAllClothesFromAvatar();
void removeAllAttachmentsFromAvatar();
// Add COF link to ensemble folder.
void addEnsembleLink(LLInventoryCategory* item, bool do_update = true);
//has the current outfit changed since it was loaded?
bool isOutfitDirty() { return mOutfitIsDirty; }

View File

@ -302,35 +302,26 @@ protected:
};
/**
* This class is needed to update an item being copied to the favorites folder
* This callback is needed to update an item being copied to the favorites folder
* with a sort field value (required to save favorites bar's tabs order).
* See method handleNewFavoriteDragAndDrop for more details on how this class is used.
*/
class LLItemCopiedCallback : public LLInventoryCallback
void item_copied_cb(const LLUUID& inv_item, S32 sort_field)
{
public:
LLItemCopiedCallback(S32 sortField): mSortField(sortField) {}
virtual void fire(const LLUUID& inv_item)
LLViewerInventoryItem* item = gInventory.getItem(inv_item);
if (item)
{
LLViewerInventoryItem* item = gInventory.getItem(inv_item);
if (item)
{
item->setSortField(mSortField);
item->setComplete(TRUE);
item->updateServer(FALSE);
gInventory.updateItem(item);
gInventory.notifyObservers();
}
LLView::getWindow()->setCursor(UI_CURSOR_ARROW);
item->setSortField(sort_field);
item->setComplete(TRUE);
item->updateServer(FALSE);
gInventory.updateItem(item);
gInventory.notifyObservers();
}
private:
S32 mSortField;
};
LLView::getWindow()->setCursor(UI_CURSOR_ARROW);
}
// updateButtons's helper
struct LLFavoritesSort
@ -574,7 +565,7 @@ void LLFavoritesBarCtrl::handleNewFavoriteDragAndDrop(LLInventoryItem *item, con
}
int sortField = 0;
LLPointer<LLItemCopiedCallback> cb;
LLPointer<LLInventoryCallback> cb;
// current order is saved by setting incremental values (1, 2, 3, ...) for the sort field
for (LLInventoryModel::item_array_t::iterator i = mItems.begin(); i != mItems.end(); ++i)
@ -583,7 +574,7 @@ void LLFavoritesBarCtrl::handleNewFavoriteDragAndDrop(LLInventoryItem *item, con
if (currItem->getUUID() == item->getUUID())
{
cb = new LLItemCopiedCallback(++sortField);
cb = new LLBoostFuncInventoryCallback(boost::bind(item_copied_cb, _1, ++sortField));
}
else
{

View File

@ -65,40 +65,27 @@ private:
LLFloaterGesture* mFloater;
};
//-----------------------------
// GestureCallback
// gesture callback funcs
//-----------------------------
class GestureShowCallback : public LLInventoryCallback
void gesture_show_cb(const LLUUID &inv_item)
{
public:
void fire(const LLUUID &inv_item)
{
LLPreviewGesture::show(inv_item, LLUUID::null);
}
};
LLPreviewGesture::show(inv_item, LLUUID::null);
}
class GestureCopiedCallback : public LLInventoryCallback
void gesture_copied_cb(const LLUUID &inv_item, LLFloaterGesture* floater)
{
private:
LLFloaterGesture* mFloater;
public:
GestureCopiedCallback(LLFloaterGesture* floater): mFloater(floater)
{}
void fire(const LLUUID &inv_item)
if(floater)
{
if(mFloater)
{
mFloater->addGesture(inv_item,NULL,mFloater->getChild<LLScrollListCtrl>("gesture_list"));
// EXP-1909 (Pasted gesture displayed twice)
// The problem is that addGesture is called here for the second time for the same item (which is copied)
// First time addGesture is called from LLFloaterGestureObserver::changed(), which is a callback for inventory
// change. So we need to refresh the gesture list to avoid duplicates.
mFloater->refreshAll();
}
floater->addGesture(inv_item,NULL,floater->getChild<LLScrollListCtrl>("gesture_list"));
// EXP-1909 (Pasted gesture displayed twice)
// The problem is that addGesture is called here for the second time for the same item (which is copied)
// First time addGesture is called from LLFloaterGestureObserver::changed(), which is a callback for inventory
// change. So we need to refresh the gesture list to avoid duplicates.
floater->refreshAll();
}
};
}
//---------------------------------------------------------------------------
// LLFloaterGesture
@ -448,7 +435,7 @@ void LLFloaterGesture::onClickPlay()
void LLFloaterGesture::onClickNew()
{
LLPointer<LLInventoryCallback> cb = new GestureShowCallback();
LLPointer<LLInventoryCallback> cb = new LLBoostFuncInventoryCallback(gesture_show_cb);
create_inventory_item(gAgent.getID(), gAgent.getSessionID(),
LLUUID::null, LLTransactionID::tnull, "New Gesture", "", LLAssetType::AT_GESTURE,
LLInventoryType::IT_GESTURE, NOT_WEARABLE, PERM_MOVE | PERM_TRANSFER, cb);
@ -520,7 +507,7 @@ void LLFloaterGesture::onCopyPasteAction(const LLSD& command)
return;
LLInventoryCategory* gesture_dir = gInventory.getCategory(mGestureFolderID);
llassert(gesture_dir);
LLPointer<GestureCopiedCallback> cb = new GestureCopiedCallback(this);
LLPointer<LLInventoryCallback> cb = new LLBoostFuncInventoryCallback(boost::bind(gesture_copied_cb, _1, this));
for(LLDynamicArray<LLUUID>::iterator it = ids.begin(); it != ids.end(); it++)
{

View File

@ -521,7 +521,7 @@ public:
void fire(const LLUUID& inv_item_id)
{
LLViewerInventoryItem* item = gInventory.getItem(inv_item_id);
if (item)
LLFriendCardsManager::instance().extractAvatarID(item->getCreatorUUID());
}
@ -557,7 +557,7 @@ void LLFriendCardsManager::addFriendCardToInventory(const LLUUID& avatarID)
lldebugs << "Sent create_inventory_item for " << avatarID << ", " << name << llendl;
// TODO: mantipov: Is CreateFriendCardCallback really needed? Probably not
LLPointer<LLInventoryCallback> cb = new CreateFriendCardCallback();
LLPointer<LLInventoryCallback> cb = new CreateFriendCardCallback;
create_inventory_callingcard(avatarID, findFriendAllSubfolderUUIDImpl(), cb);
}

View File

@ -5091,7 +5091,7 @@ void LLObjectBridge::performAction(LLInventoryModel* model, std::string action)
else if(item && item->isFinished())
{
// must be in library. copy it to our inventory and put it on.
LLPointer<LLInventoryCallback> cb = new RezAttachmentCallback(0);
LLPointer<LLInventoryCallback> cb = new LLBoostFuncInventoryCallback(boost::bind(rez_attachment_cb, _1, (LLViewerJointAttachment*)0));
copy_inventory_item(
gAgent.getID(),
item->getPermissions().getOwner(),

View File

@ -1709,7 +1709,7 @@ EAcceptance LLToolDragAndDrop::dad3dRezAttachmentFromInv(
{
if(mSource == SOURCE_LIBRARY)
{
LLPointer<LLInventoryCallback> cb = new RezAttachmentCallback(0);
LLPointer<LLInventoryCallback> cb = new LLBoostFuncInventoryCallback(boost::bind(rez_attachment_cb, _1, (LLViewerJointAttachment*)0));
copy_inventory_item(
gAgent.getID(),
item->getPermissions().getOwner(),
@ -2062,7 +2062,7 @@ EAcceptance LLToolDragAndDrop::dad3dActivateGesture(
{
// create item based on that one, and put it on if that
// was a success.
LLPointer<LLInventoryCallback> cb = new ActivateGestureCallback();
LLPointer<LLInventoryCallback> cb = new LLBoostFuncInventoryCallback(activate_gesture_cb);
copy_inventory_item(
gAgent.getID(),
item->getPermissions().getOwner(),

View File

@ -121,7 +121,7 @@ void LLViewerAttachMenu::attachObjects(const uuid_vec_t& items, const std::strin
else if(item && item->isFinished())
{
// must be in library. copy it to our inventory and put it on.
LLPointer<LLInventoryCallback> cb = new RezAttachmentCallback(attachmentp);
LLPointer<LLInventoryCallback> cb = new LLBoostFuncInventoryCallback(boost::bind(rez_attachment_cb, _1, attachmentp));
copy_inventory_item(gAgent.getID(),
item->getPermissions().getOwner(),
item->getUUID(),

View File

@ -65,6 +65,10 @@
#include "llavataractions.h"
#include "lllogininstance.h"
// Two do-nothing ops for use in callbacks.
void no_op_inventory_func(const LLUUID&) {}
void no_op() {}
///----------------------------------------------------------------------------
/// Helper class to store special inventory item names and their localized values.
///----------------------------------------------------------------------------
@ -949,7 +953,7 @@ void LLInventoryCallbackManager::fire(U32 callback_id, const LLUUID& item_id)
}
}
void WearOnAvatarCallback::fire(const LLUUID& inv_item)
void rez_attachment_cb(const LLUUID& inv_item, LLViewerJointAttachment *attachmentp)
{
if (inv_item.isNull())
return;
@ -957,50 +961,11 @@ void WearOnAvatarCallback::fire(const LLUUID& inv_item)
LLViewerInventoryItem *item = gInventory.getItem(inv_item);
if (item)
{
LLAppearanceMgr::instance().wearItemOnAvatar(inv_item, true, mReplace);
rez_attachment(item, attachmentp);
}
}
void ModifiedCOFCallback::fire(const LLUUID& inv_item)
{
LLAppearanceMgr::instance().updateAppearanceFromCOF();
// Start editing the item if previously requested.
gAgentWearables.editWearableIfRequested(inv_item);
// TODO: camera mode may not be changed if a debug setting is tweaked
if( gAgentCamera.cameraCustomizeAvatar() )
{
// If we're in appearance editing mode, the current tab may need to be refreshed
LLSidepanelAppearance *panel = dynamic_cast<LLSidepanelAppearance*>(LLFloaterSidePanelContainer::getPanel("appearance"));
if (panel)
{
panel->showDefaultSubpart();
}
}
}
RezAttachmentCallback::RezAttachmentCallback(LLViewerJointAttachment *attachmentp)
{
mAttach = attachmentp;
}
RezAttachmentCallback::~RezAttachmentCallback()
{
}
void RezAttachmentCallback::fire(const LLUUID& inv_item)
{
if (inv_item.isNull())
return;
LLViewerInventoryItem *item = gInventory.getItem(inv_item);
if (item)
{
rez_attachment(item, mAttach);
}
}
void ActivateGestureCallback::fire(const LLUUID& inv_item)
void activate_gesture_cb(const LLUUID& inv_item)
{
if (inv_item.isNull())
return;
@ -1013,7 +978,7 @@ void ActivateGestureCallback::fire(const LLUUID& inv_item)
LLGestureMgr::instance().activateGesture(inv_item);
}
void CreateGestureCallback::fire(const LLUUID& inv_item)
void create_gesture_cb(const LLUUID& inv_item)
{
if (inv_item.isNull())
return;
@ -1288,7 +1253,7 @@ void create_new_item(const std::string& name,
if (inv_type == LLInventoryType::IT_GESTURE)
{
LLPointer<LLInventoryCallback> cb = new CreateGestureCallback();
LLPointer<LLInventoryCallback> cb = new LLBoostFuncInventoryCallback(create_gesture_cb);
create_inventory_item(gAgent.getID(), gAgent.getSessionID(),
parent_id, LLTransactionID::tnull, name, desc, asset_type, inv_type,
NOT_WEARABLE, next_owner_perm, cb);

View File

@ -242,48 +242,13 @@ public:
virtual void fire(const LLUUID& inv_item) = 0;
};
class WearOnAvatarCallback : public LLInventoryCallback
{
public:
WearOnAvatarCallback(bool do_replace = false) : mReplace(do_replace) {}
void fire(const LLUUID& inv_item);
protected:
bool mReplace;
};
class ModifiedCOFCallback : public LLInventoryCallback
{
void fire(const LLUUID& inv_item);
};
class LLViewerJointAttachment;
class RezAttachmentCallback : public LLInventoryCallback
{
public:
RezAttachmentCallback(LLViewerJointAttachment *attachmentp);
void fire(const LLUUID& inv_item);
void rez_attachment_cb(const LLUUID& inv_item, LLViewerJointAttachment *attachmentp);
protected:
~RezAttachmentCallback();
void activate_gesture_cb(const LLUUID& inv_item);
private:
LLViewerJointAttachment* mAttach;
};
class ActivateGestureCallback : public LLInventoryCallback
{
public:
void fire(const LLUUID& inv_item);
};
class CreateGestureCallback : public LLInventoryCallback
{
public:
void fire(const LLUUID& inv_item);
};
void create_gesture_cb(const LLUUID& inv_item);
class AddFavoriteLandmarkCallback : public LLInventoryCallback
{
@ -297,25 +262,40 @@ private:
LLUUID mTargetLandmarkId;
};
// Shim between inventory callback and boost function/callable
typedef boost::function<void(const LLUUID&)> inventory_func_type;
void no_op_inventory_func(const LLUUID&); // A do-nothing inventory_func
typedef boost::function<void()> nullary_func_type;
void no_op(); // A do-nothing nullary func.
// Shim between inventory callback and boost function/callable
class LLBoostFuncInventoryCallback: public LLInventoryCallback
{
public:
LLBoostFuncInventoryCallback(const inventory_func_type& func):
mFunc(func)
LLBoostFuncInventoryCallback(inventory_func_type fire_func,
nullary_func_type destroy_func = no_op):
mFireFunc(fire_func),
mDestroyFunc(destroy_func)
{
}
// virtual
void fire(const LLUUID& item_id)
{
mFunc(item_id);
mFireFunc(item_id);
}
// virtual
~LLBoostFuncInventoryCallback()
{
mDestroyFunc;
}
private:
inventory_func_type mFunc;
inventory_func_type mFireFunc;
nullary_func_type mDestroyFunc;
};
// misc functions