diff options
-rw-r--r-- | indra/newview/llappearancemgr.cpp | 31 | ||||
-rw-r--r-- | indra/newview/llappearancemgr.h | 7 | ||||
-rw-r--r-- | indra/newview/llpaneloutfitedit.cpp | 39 | ||||
-rw-r--r-- | indra/newview/llpaneloutfitedit.h | 4 | ||||
-rw-r--r-- | indra/newview/llpaneloutfitsinventory.cpp | 15 | ||||
-rw-r--r-- | indra/newview/llpaneloutfitsinventory.h | 2 | ||||
-rw-r--r-- | indra/newview/llsidepanelappearance.cpp | 34 | ||||
-rw-r--r-- | indra/newview/llsidepanelappearance.h | 6 | ||||
-rw-r--r-- | indra/newview/skins/default/xui/en/menu_save_outfit.xml | 22 | ||||
-rw-r--r-- | indra/newview/skins/default/xui/en/panel_outfit_edit.xml | 13 |
10 files changed, 162 insertions, 11 deletions
diff --git a/indra/newview/llappearancemgr.cpp b/indra/newview/llappearancemgr.cpp index e0f1d5348d..40c1f89f3f 100644 --- a/indra/newview/llappearancemgr.cpp +++ b/indra/newview/llappearancemgr.cpp @@ -593,6 +593,23 @@ bool LLAppearanceMgr::getBaseOutfitName(std::string& name) return false; } +const LLUUID LLAppearanceMgr::getBaseOutfitUUID() +{ + const LLViewerInventoryItem* outfit_link = getBaseOutfitLink(); + if (!outfit_link || !outfit_link->getIsLinkType()) return LLUUID::null; + + const LLViewerInventoryCategory* outfit_cat = outfit_link->getLinkedCategory(); + if (!outfit_cat) return LLUUID::null; + + if (outfit_cat->getPreferredType() != LLFolderType::FT_OUTFIT) + { + llwarns << "Expected outfit type:" << LLFolderType::FT_OUTFIT << " but got type:" << outfit_cat->getType() << " for folder name:" << outfit_cat->getName() << llendl; + return LLUUID::null; + } + + return outfit_cat->getUUID(); +} + // Update appearance from outfit folder. void LLAppearanceMgr::changeOutfit(bool proceed, const LLUUID& category, bool append) { @@ -1516,6 +1533,20 @@ void LLAppearanceMgr::onFirstFullyVisible() autopopulateOutfits(); } +bool LLAppearanceMgr::updateBaseOutfit() +{ + const LLUUID base_outfit_id = getBaseOutfitUUID(); + if (base_outfit_id.isNull()) return false; + + // in a Base Outfit we do not remove items, only links + purgeCategory(base_outfit_id, false); + + //COF contains only links so we copy to the Base Outfit only links + shallowCopyCategoryContents(getCOF(), base_outfit_id, NULL); + + return true; +} + //#define DUMP_CAT_VERBOSE void LLAppearanceMgr::dumpCat(const LLUUID& cat_id, const std::string& msg) diff --git a/indra/newview/llappearancemgr.h b/indra/newview/llappearancemgr.h index 423d9bde69..c7a8bc3720 100644 --- a/indra/newview/llappearancemgr.h +++ b/indra/newview/llappearancemgr.h @@ -75,6 +75,9 @@ public: const LLViewerInventoryItem *getBaseOutfitLink(); bool getBaseOutfitName(std::string &name); + // find the UUID of the currently worn outfit (Base Outfit) + const LLUUID getBaseOutfitUUID(); + // Update the displayed outfit name in UI. void updatePanelOutfitName(const std::string& name); @@ -123,6 +126,10 @@ public: // Create initial outfits from library. void autopopulateOutfits(); + // Overrides the base outfit with the content from COF + // @return false if there is no base outfit + bool updateBaseOutfit(); + protected: LLAppearanceMgr(); ~LLAppearanceMgr(); diff --git a/indra/newview/llpaneloutfitedit.cpp b/indra/newview/llpaneloutfitedit.cpp index b956004129..850a766ff4 100644 --- a/indra/newview/llpaneloutfitedit.cpp +++ b/indra/newview/llpaneloutfitedit.cpp @@ -45,6 +45,7 @@ #include "llfloaterreg.h" #include "llinventoryfunctions.h" #include "llinventorypanel.h" +#include "llviewermenu.h" #include "llviewerwindow.h" #include "llviewerinventory.h" #include "llbutton.h" @@ -54,12 +55,14 @@ #include "llinventorybridge.h" #include "llinventorymodel.h" #include "llinventorymodelbackgroundfetch.h" +#include "llpaneloutfitsinventory.h" #include "lluiconstants.h" #include "llscrolllistctrl.h" #include "lltextbox.h" #include "lluictrlfactory.h" #include "llsdutil.h" #include "llsidepanelappearance.h" +#include "lltoggleablemenu.h" #include "llwearablelist.h" static LLRegisterPanelClassWrapper<LLPanelOutfitEdit> t_outfit_edit("panel_outfit_edit"); @@ -228,6 +231,15 @@ BOOL LLPanelOutfitEdit::postBuild() childSetAction("remove_item_btn", boost::bind(&LLPanelOutfitEdit::onRemoveFromLookClicked, this), this); + childSetAction("save_btn", boost::bind(&LLPanelOutfitEdit::saveOutfit, this, false)); + childSetAction("save_as_btn", boost::bind(&LLPanelOutfitEdit::saveOutfit, this, true)); + childSetAction("save_flyout_btn", boost::bind(&LLPanelOutfitEdit::showSaveMenu, this)); + + LLUICtrl::CommitCallbackRegistry::ScopedRegistrar save_registar; + save_registar.add("Outfit.Save.Action", boost::bind(&LLPanelOutfitEdit::saveOutfit, this, false)); + save_registar.add("Outfit.SaveAsNew.Action", boost::bind(&LLPanelOutfitEdit::saveOutfit, this, true)); + mSaveMenu = LLUICtrlFactory::getInstance()->createFromFile<LLToggleableMenu>("menu_save_outfit.xml", gMenuHolder, LLViewerMenuHolderGL::child_registry_t::instance()); + return TRUE; } @@ -236,6 +248,31 @@ void LLPanelOutfitEdit::showAddWearablesPanel() childSetVisible("add_wearables_panel", childGetValue("add_btn")); } +void LLPanelOutfitEdit::saveOutfit(bool as_new) +{ + if (!as_new && LLAppearanceMgr::getInstance()->updateBaseOutfit())
+ {
+ // we don't need to ask for an outfit name, and updateBaseOutfit() successfully saved.
+ // If updateBaseOutfit fails, ask for an outfit name anyways
+ return;
+ }
+ + LLPanelOutfitsInventory* panel_outfits_inventory = LLPanelOutfitsInventory::findInstance(); + if (panel_outfits_inventory) + { + panel_outfits_inventory->onSave(); + } +} + +void LLPanelOutfitEdit::showSaveMenu() +{ + S32 x, y; + LLUI::getMousePositionLocal(this, &x, &y); + + mSaveMenu->updateParent(LLMenuGL::sMenuContainer); + LLMenuGL::showPopup(this, mSaveMenu, x, y); +} + void LLPanelOutfitEdit::onTypeFilterChanged(LLUICtrl* ctrl) { LLComboBox* type_filter = dynamic_cast<LLComboBox*>(ctrl); @@ -301,6 +338,8 @@ void LLPanelOutfitEdit::onSearchEdit(const std::string& string) void LLPanelOutfitEdit::onAddToLookClicked(void) { LLFolderViewItem* curr_item = mInventoryItemsPanel->getRootFolder()->getCurSelectedItem(); + if (!curr_item) return; + LLFolderViewEventListener* listenerp = curr_item->getListener(); link_inventory_item(gAgent.getID(), listenerp->getUUID(), mCurrentOutfitID, listenerp->getName(), LLAssetType::AT_LINK, LLPointer<LLInventoryCallback>(NULL)); diff --git a/indra/newview/llpaneloutfitedit.h b/indra/newview/llpaneloutfitedit.h index ba382d7320..d09795156e 100644 --- a/indra/newview/llpaneloutfitedit.h +++ b/indra/newview/llpaneloutfitedit.h @@ -52,6 +52,7 @@ class LLInventoryPanel; class LLSaveFolderState; class LLFolderViewItem; class LLScrollListCtrl; +class LLToggleableMenu; class LLLookFetchObserver; class LLFilterEditor; @@ -86,6 +87,8 @@ public: // only update the location if there is none already available. void showAddWearablesPanel(); + void saveOutfit(bool as_new = false); + void showSaveMenu(); void onTypeFilterChanged(LLUICtrl* ctrl); void onSearchEdit(const std::string& string); @@ -117,6 +120,7 @@ private: LLButton* mRemoveFromLookBtn; LLButton* mUpBtn; LLButton* mEditWearableBtn; + LLToggleableMenu* mSaveMenu; LLLookFetchObserver* mFetchLook; LLInventoryLookObserver* mLookObserver; diff --git a/indra/newview/llpaneloutfitsinventory.cpp b/indra/newview/llpaneloutfitsinventory.cpp index 7d8b1dea0e..b78268da7b 100644 --- a/indra/newview/llpaneloutfitsinventory.cpp +++ b/indra/newview/llpaneloutfitsinventory.cpp @@ -217,8 +217,13 @@ bool LLPanelOutfitsInventory::onSaveCommit(const LLSD& notification, const LLSD& if( !outfit_name.empty() ) { LLUUID outfit_folder = gAgentWearables.makeNewOutfitLinks(outfit_name); - LLSD key; - LLSideTray::getInstance()->showPanel("panel_outfits_inventory", key); + + LLSidepanelAppearance* panel_appearance = + dynamic_cast<LLSidepanelAppearance *>(LLSideTray::getInstance()->getPanel("sidepanel_appearance")); + if (panel_appearance) + { + panel_appearance->showOutfitsInventoryPanel(); + } if (mAppearanceTabs) { @@ -309,6 +314,12 @@ LLFolderView *LLPanelOutfitsInventory::getRootFolder() return mActivePanel->getRootFolder(); } +//static +LLPanelOutfitsInventory* LLPanelOutfitsInventory::findInstance() +{ + return dynamic_cast<LLPanelOutfitsInventory*>(LLSideTray::getInstance()->getPanel("panel_outfits_inventory")); +} + ////////////////////////////////////////////////////////////////////////////////// // List Commands // diff --git a/indra/newview/llpaneloutfitsinventory.h b/indra/newview/llpaneloutfitsinventory.h index 41afc2f372..5d0d27ee4f 100644 --- a/indra/newview/llpaneloutfitsinventory.h +++ b/indra/newview/llpaneloutfitsinventory.h @@ -73,6 +73,8 @@ public: LLFolderView* getRootFolder(); + static LLPanelOutfitsInventory* findInstance(); + protected: void updateVerbs(); bool getIsCorrectType(const LLFolderViewEventListener *listenerp) const; diff --git a/indra/newview/llsidepanelappearance.cpp b/indra/newview/llsidepanelappearance.cpp index d90f36fc89..7561388990 100644 --- a/indra/newview/llsidepanelappearance.cpp +++ b/indra/newview/llsidepanelappearance.cpp @@ -135,7 +135,7 @@ BOOL LLSidepanelAppearance::postBuild() LLButton* back_btn = mOutfitEdit->getChild<LLButton>("back_btn"); if (back_btn) { - back_btn->setClickedCallback(boost::bind(&LLSidepanelAppearance::onBackButtonClicked, this)); + back_btn->setClickedCallback(boost::bind(&LLSidepanelAppearance::showOutfitsInventoryPanel, this)); } } @@ -176,7 +176,7 @@ void LLSidepanelAppearance::onOpen(const LLSD& key) if(key.size() == 0) return; - + toggleOutfitEditPanel(TRUE); updateVerbs(); @@ -258,12 +258,6 @@ void LLSidepanelAppearance::onNewOutfitButtonClicked() } } - -void LLSidepanelAppearance::onBackButtonClicked() -{ - toggleOutfitEditPanel(FALSE); -} - void LLSidepanelAppearance::onEditWearBackClicked() { mEditWearable->saveChanges(); @@ -271,6 +265,30 @@ void LLSidepanelAppearance::onEditWearBackClicked() toggleOutfitEditPanel(TRUE); } +void LLSidepanelAppearance::showOutfitsInventoryPanel() +{ + mOutfitEdit->setVisible(FALSE); + + mPanelOutfitsInventory->setVisible(TRUE); + + mFilterEditor->setVisible(TRUE); + mEditBtn->setVisible(TRUE); + mNewOutfitBtn->setVisible(TRUE); + mCurrOutfitPanel->setVisible(TRUE); +} + +void LLSidepanelAppearance::showOutfitEditPanel() +{ + mOutfitEdit->setVisible(TRUE); + + mPanelOutfitsInventory->setVisible(FALSE); + + mFilterEditor->setVisible(FALSE); + mEditBtn->setVisible(FALSE); + mNewOutfitBtn->setVisible(FALSE); + mCurrOutfitPanel->setVisible(FALSE); +} + void LLSidepanelAppearance::toggleOutfitEditPanel(BOOL visible) { if (!mOutfitEdit) diff --git a/indra/newview/llsidepanelappearance.h b/indra/newview/llsidepanelappearance.h index 1d78e92a84..0a609797fb 100644 --- a/indra/newview/llsidepanelappearance.h +++ b/indra/newview/llsidepanelappearance.h @@ -63,14 +63,18 @@ public: void updateVerbs(); void onNewOutfitButtonClicked(); + void showOutfitsInventoryPanel(); + void showOutfitEditPanel(); + private: void onFilterEdit(const std::string& search_string); void onOpenOutfitButtonClicked(); void onEditAppearanceButtonClicked(); void onEditButtonClicked(); - void onBackButtonClicked(); void onEditWearBackClicked(); + + //@deprecated use showXXX() methods instead void toggleOutfitEditPanel(BOOL visible); void toggleWearableEditPanel(BOOL visible, LLWearable* wearable); diff --git a/indra/newview/skins/default/xui/en/menu_save_outfit.xml b/indra/newview/skins/default/xui/en/menu_save_outfit.xml new file mode 100644 index 0000000000..a8778df7f6 --- /dev/null +++ b/indra/newview/skins/default/xui/en/menu_save_outfit.xml @@ -0,0 +1,22 @@ +<?xml version="1.0" encoding="utf-8" standalone="yes" ?> +<toggleable_menu + height="201" + layout="topleft" + mouse_opaque="false" + name="save_outfit_menu" + width="120"> + <menu_item_call + name="save_outfit" + label="Save"> + <menu_item_call.on_click + function="Outfit.Save.Action" + userdata=""/> + </menu_item_call> + <menu_item_call + name="save_as_new_outfit" + label="Save As New"> + <menu_item_call.on_click + function="Outfit.SaveAsNew.Action" + userdata="" /> + </menu_item_call> +</toggleable_menu> 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 c1800384a3..3fa3d6d039 100644 --- a/indra/newview/skins/default/xui/en/panel_outfit_edit.xml +++ b/indra/newview/skins/default/xui/en/panel_outfit_edit.xml @@ -338,6 +338,19 @@ name="save_btn" width="145" /> <button + follows="bottom|right" + height="23" + name="save_flyout_btn" + label="" + left_pad="-20" + tab_stop="false" + image_selected="SegmentedBtn_Right_Selected_Press" + image_unselected="SegmentedBtn_Right_Off" + image_pressed="SegmentedBtn_Right_Press" + image_pressed_selected="SegmentedBtn_Right_Selected_Press" + image_overlay="Arrow_Small_Up" + width="20"/> + <button follows="bottom|left|right" height="23" left_pad="15" |