summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorleslie@leslie-HPz600.lindenlab.com <leslie@leslie-HPz600.lindenlab.com>2011-08-26 16:33:47 -0700
committerleslie@leslie-HPz600.lindenlab.com <leslie@leslie-HPz600.lindenlab.com>2011-08-26 16:33:47 -0700
commitc2443b95d3cd9f0f26e5e8f5c2dbeb5f6c307447 (patch)
tree70ca348ba23a2a38f5e53b07f5135064c28dabad
parente11e794716368257792c3ccce60ba7709e0f29e0 (diff)
EXP-1126 FIX -- Cannot use arrow keys to scroll up and down in Inbox and Outbox
EXP-1003 FIX -- Renaming a folder in Received Items panel resets the New flag for that folder EXP-1001 FIX -- Newness is removed on next login if you log out or crash before opening inventory panel EXP-857 FIX -- Add context menu entries as alternate path to populate outbox EXP-858 FIX -- Outbox sync failure error handling EXP-1158 FIX -- Viewer crash when deleting items from Outbox when some folders are open * Made inbox, outbox and inventory panels all legit tab stops for keyboard focus * Added mouse over indication on inventory panel primarily for increased clarity on outbox error messages * Disabled "Rename" option on inbox items * Added context menu option to copy/move an item to the merchant outbox * Context menu option to copy/move to outbox is visible and/or enabled/disabled when appropriate * "LastInventoryInboxCollapse" no longer written out as a setting when the panel is not visible * Fixed up collapse time check to not try to parse empty string on first load (deminishes text spam in log greatly) * Disabled double-click as a way to equip items in the inbox or outbox * Viewer code no longer removes items from the outbox after sync. We rely on the sim to do this now. * Basic outbox sync error handling now displays error messages as tooltips along with badge over item in outbox * Moved some scroll container default values out of code and into xml
-rw-r--r--indra/llui/llscrollcontainer.cpp3
-rw-r--r--indra/newview/llfolderviewitem.cpp21
-rw-r--r--indra/newview/llfolderviewitem.h3
-rw-r--r--indra/newview/llinventorybridge.cpp144
-rw-r--r--indra/newview/llinventorybridge.h11
-rw-r--r--indra/newview/llpanelmarketplaceinbox.cpp2
-rw-r--r--indra/newview/llpanelmarketplaceinboxinventory.cpp37
-rw-r--r--indra/newview/llpanelmarketplaceinboxinventory.h14
-rw-r--r--indra/newview/llpanelmarketplaceoutbox.cpp46
-rw-r--r--indra/newview/llpanelmarketplaceoutboxinventory.cpp108
-rw-r--r--indra/newview/llpanelmarketplaceoutboxinventory.h25
-rw-r--r--indra/newview/llsidepanelinventory.cpp26
-rw-r--r--indra/newview/skins/default/colors.xml8
-rw-r--r--indra/newview/skins/default/xui/en/menu_inventory.xml21
-rw-r--r--indra/newview/skins/default/xui/en/strings.xml12
-rw-r--r--indra/newview/skins/default/xui/en/widgets/scroll_container.xml5
16 files changed, 426 insertions, 60 deletions
diff --git a/indra/llui/llscrollcontainer.cpp b/indra/llui/llscrollcontainer.cpp
index 380c477eb2..112622d3f7 100644
--- a/indra/llui/llscrollcontainer.cpp
+++ b/indra/llui/llscrollcontainer.cpp
@@ -75,9 +75,6 @@ LLScrollContainer::Params::Params()
max_auto_scroll_rate("max_auto_scroll_rate", 1000),
reserve_scroll_corner("reserve_scroll_corner", false)
{
- name = "scroll_container";
- mouse_opaque(true);
- tab_stop(false);
}
diff --git a/indra/newview/llfolderviewitem.cpp b/indra/newview/llfolderviewitem.cpp
index 2f07e084ab..72e2294196 100644
--- a/indra/newview/llfolderviewitem.cpp
+++ b/indra/newview/llfolderviewitem.cpp
@@ -132,7 +132,8 @@ LLFolderViewItem::LLFolderViewItem(const LLFolderViewItem::Params& p)
mIconOpen(p.icon_open),
mIconOverlay(p.icon_overlay),
mListener(p.listener),
- mShowLoadStatus(false)
+ mShowLoadStatus(false),
+ mIsMouseOverTitle(false)
{
}
@@ -724,6 +725,8 @@ BOOL LLFolderViewItem::handleMouseDown( S32 x, S32 y, MASK mask )
BOOL LLFolderViewItem::handleHover( S32 x, S32 y, MASK mask )
{
+ mIsMouseOverTitle = (y > (getRect().getHeight() - mItemHeight));
+
if( hasMouseCapture() && isMovable() )
{
S32 screen_x;
@@ -830,6 +833,11 @@ BOOL LLFolderViewItem::handleMouseUp( S32 x, S32 y, MASK mask )
return TRUE;
}
+void LLFolderViewItem::onMouseLeave(S32 x, S32 y, MASK mask)
+{
+ mIsMouseOverTitle = false;
+}
+
BOOL LLFolderViewItem::handleDragAndDrop(S32 x, S32 y, MASK mask, BOOL drop,
EDragAndDropType cargo_type,
void* cargo_data,
@@ -879,6 +887,7 @@ void LLFolderViewItem::draw()
static LLUIColor sLibraryColor = LLUIColorTable::instance().getColor("InventoryItemLibraryColor", DEFAULT_WHITE);
static LLUIColor sLinkColor = LLUIColorTable::instance().getColor("InventoryItemLinkColor", DEFAULT_WHITE);
static LLUIColor sSearchStatusColor = LLUIColorTable::instance().getColor("InventorySearchStatusColor", DEFAULT_WHITE);
+ static LLUIColor sMouseOverColor = LLUIColorTable::instance().getColor("InventoryMouseOverColor", DEFAULT_WHITE);
const Params& default_params = LLUICtrlFactory::getDefaultParams<LLFolderViewItem>();
const S32 TOP_PAD = default_params.item_top_pad;
@@ -960,6 +969,14 @@ void LLFolderViewItem::draw()
}
}
}
+ else if (mIsMouseOverTitle)
+ {
+ gl_rect_2d(FOCUS_LEFT,
+ focus_top,
+ getRect().getWidth() - 2,
+ focus_bottom,
+ sMouseOverColor, FALSE);
+ }
//--------------------------------------------------------------------------------//
// Draw DragNDrop highlight
@@ -2299,6 +2316,8 @@ BOOL LLFolderViewFolder::handleRightMouseDown( S32 x, S32 y, MASK mask )
BOOL LLFolderViewFolder::handleHover(S32 x, S32 y, MASK mask)
{
+ mIsMouseOverTitle = (y > (getRect().getHeight() - mItemHeight));
+
BOOL handled = LLView::handleHover(x, y, mask);
if (!handled)
diff --git a/indra/newview/llfolderviewitem.h b/indra/newview/llfolderviewitem.h
index dac0c3032c..ce936b4991 100644
--- a/indra/newview/llfolderviewitem.h
+++ b/indra/newview/llfolderviewitem.h
@@ -159,6 +159,7 @@ protected:
BOOL mIsLoading;
LLTimer mTimeSinceRequestStart;
bool mShowLoadStatus;
+ bool mIsMouseOverTitle;
// helper function to change the selection from the root.
void changeSelectionFromRoot(LLFolderViewItem* selection, BOOL selected);
@@ -328,6 +329,8 @@ public:
virtual BOOL handleMouseUp( S32 x, S32 y, MASK mask );
virtual BOOL handleDoubleClick( S32 x, S32 y, MASK mask );
+ virtual void onMouseLeave(S32 x, S32 y, MASK mask);
+
virtual LLView* findChildView(const std::string& name, BOOL recurse) const { return NULL; }
// virtual void handleDropped();
diff --git a/indra/newview/llinventorybridge.cpp b/indra/newview/llinventorybridge.cpp
index 0959a08359..f3429607e9 100644
--- a/indra/newview/llinventorybridge.cpp
+++ b/indra/newview/llinventorybridge.cpp
@@ -107,6 +107,23 @@ bool confirm_attachment_rez(const LLSD& notification, const LLSD& response);
void teleport_via_landmark(const LLUUID& asset_id);
static BOOL can_move_to_outfit(LLInventoryItem* inv_item, BOOL move_is_into_current_outfit);
+// Helper functions
+
+bool isAddAction(const std::string& action)
+{
+ return ("wear" == action || "attach" == action || "activate" == action);
+}
+
+bool isRemoveAction(const std::string& action)
+{
+ return ("take_off" == action || "detach" == action || "deactivate" == action);
+}
+
+bool isMarketplaceCopyAction(const std::string& action)
+{
+ return (("copy_to_outbox" == action) || ("move_to_outbox" == action));
+}
+
// +=================================================+
// | LLInvFVBridge |
// +=================================================+
@@ -538,10 +555,14 @@ void LLInvFVBridge::getClipboardEntries(bool show_asset_id,
{
items.push_back(std::string("Find Links"));
}
- items.push_back(std::string("Rename"));
- if (!isItemRenameable() || (flags & FIRST_SELECTED_ITEM) == 0)
+
+ if (!isInboxFolder())
{
- disabled_items.push_back(std::string("Rename"));
+ items.push_back(std::string("Rename"));
+ if (!isItemRenameable() || (flags & FIRST_SELECTED_ITEM) == 0)
+ {
+ disabled_items.push_back(std::string("Rename"));
+ }
}
if (show_asset_id)
@@ -569,6 +590,26 @@ void LLInvFVBridge::getClipboardEntries(bool show_asset_id,
{
disabled_items.push_back(std::string("Copy"));
}
+
+ if (canListOnMarketplace())
+ {
+ items.push_back(std::string("Marketplace Separator"));
+
+ bool copyable = true;
+ LLViewerInventoryItem* inv_item = gInventory.getItem(mUUID);
+ if (inv_item)
+ {
+ copyable = inv_item->getPermissions().allowCopyBy(gAgent.getID());
+ }
+
+ const std::string merchant_action = ((copyable == true) ? "Merchant Copy" : "Merchant Move");
+ items.push_back(merchant_action);
+
+ if (!canListOnMarketplaceNow())
+ {
+ disabled_items.push_back(merchant_action);
+ }
+ }
}
}
@@ -798,10 +839,9 @@ BOOL LLInvFVBridge::isInboxFolder() const
return gInventory.isObjectDescendentOf(mUUID, inbox_id);
}
-
BOOL LLInvFVBridge::isOutboxFolder() const
{
- const LLUUID outbox_id = gInventory.findCategoryUUIDForType(LLFolderType::FT_OUTBOX, false, false);
+ const LLUUID outbox_id = getOutboxFolder();
if (outbox_id.isNull())
{
@@ -811,6 +851,12 @@ BOOL LLInvFVBridge::isOutboxFolder() const
return gInventory.isObjectDescendentOf(mUUID, outbox_id);
}
+const LLUUID LLInvFVBridge::getOutboxFolder() const
+{
+ const LLUUID outbox_id = gInventory.findCategoryUUIDForType(LLFolderType::FT_OUTBOX, false, false);
+
+ return outbox_id;
+}
BOOL LLInvFVBridge::isItemPermissive() const
{
@@ -956,9 +1002,14 @@ LLInvFVBridge* LLInvFVBridge::createBridge(LLAssetType::EType asset_type,
new_listener = new LLMeshBridge(inventory, root, uuid);
break;
+ case LLAssetType::AT_IMAGE_TGA:
+ case LLAssetType::AT_IMAGE_JPEG:
+ //llwarns << LLAssetType::lookup(asset_type) << " asset type is unhandled for uuid " << uuid << llendl;
+ break;
+
default:
llinfos << "Unhandled asset type (llassetstorage.h): "
- << (S32)asset_type << llendl;
+ << (S32)asset_type << " (" << LLAssetType::lookup(asset_type) << ")" << llendl;
break;
}
@@ -1007,6 +1058,50 @@ BOOL LLInvFVBridge::canShare() const
return FALSE;
}
+BOOL LLInvFVBridge::canListOnMarketplace() const
+{
+ LLInventoryModel * model = getInventoryModel();
+ const LLViewerInventoryCategory * cat = model->getCategory(mUUID);
+ if (cat && LLFolderType::lookupIsProtectedType(cat->getPreferredType()))
+ {
+ return FALSE;
+ }
+
+ if (!isAgentInventory())
+ {
+ return FALSE;
+ }
+
+ if (getOutboxFolder().isNull())
+ {
+ return FALSE;
+ }
+
+ if (isInboxFolder() || isOutboxFolder())
+ {
+ return FALSE;
+ }
+
+ LLViewerInventoryItem * item = model->getItem(mUUID);
+ if (item && !item->getPermissions().allowOperationBy(PERM_TRANSFER, gAgent.getID()))
+ {
+ return FALSE;
+ }
+
+ return TRUE;
+}
+
+BOOL LLInvFVBridge::canListOnMarketplaceNow() const
+{
+ if (get_is_item_worn(mUUID))
+ {
+ return FALSE;
+ }
+
+ return TRUE;
+}
+
+
// +=================================================+
// | InventoryFVBridgeBuilder |
// +=================================================+
@@ -1104,6 +1199,16 @@ void LLItemBridge::performAction(LLInventoryModel* model, std::string action)
folder_view_itemp->getListener()->pasteLinkFromClipboard();
return;
}
+ else if (isMarketplaceCopyAction(action))
+ {
+ llinfos << "Copy item to marketplace action!" << llendl;
+
+ LLInventoryItem* itemp = model->getItem(mUUID);
+ if (!itemp) return;
+
+ const LLUUID outbox_id = getInventoryModel()->findCategoryUUIDForType(LLFolderType::FT_OUTBOX, false, false);
+ copy_item_to_outbox(itemp, outbox_id, LLUUID::null);
+ }
}
void LLItemBridge::selectItem()
@@ -1244,7 +1349,7 @@ std::string LLItemBridge::getLabelSuffix() const
{
// String table is loaded before login screen and inventory items are
// loaded after login, so LLTrans should be ready.
- static std::string NO_COPY =LLTrans::getString("no_copy");
+ static std::string NO_COPY = LLTrans::getString("no_copy");
static std::string NO_MOD = LLTrans::getString("no_modify");
static std::string NO_XFER = LLTrans::getString("no_transfer");
static std::string LINK = LLTrans::getString("link");
@@ -1312,6 +1417,11 @@ BOOL LLItemBridge::isItemRenameable() const
return FALSE;
}
+ if (isInboxFolder())
+ {
+ return FALSE;
+ }
+
return (item->getPermissions().allowModifyBy(gAgent.getID()));
}
return FALSE;
@@ -1475,16 +1585,6 @@ BOOL LLItemBridge::isItemPermissive() const
return FALSE;
}
-bool LLItemBridge::isAddAction(std::string action) const
-{
- return ("wear" == action || "attach" == action || "activate" == action);
-}
-
-bool LLItemBridge::isRemoveAction(std::string action) const
-{
- return ("take_off" == action || "detach" == action || "deactivate" == action);
-}
-
// +=================================================+
// | LLFolderBridge |
// +=================================================+
@@ -2324,6 +2424,16 @@ void LLFolderBridge::performAction(LLInventoryModel* model, std::string action)
removeSystemFolder();
}
#endif
+ else if (isMarketplaceCopyAction(action))
+ {
+ llinfos << "Copy folder to marketplace action!" << llendl;
+
+ LLInventoryCategory * cat = gInventory.getCategory(mUUID);
+ if (!cat) return;
+
+ const LLUUID outbox_id = getInventoryModel()->findCategoryUUIDForType(LLFolderType::FT_OUTBOX, false, false);
+ copy_folder_to_outbox(cat, outbox_id, cat->getUUID());
+ }
}
void LLFolderBridge::openItem()
diff --git a/indra/newview/llinventorybridge.h b/indra/newview/llinventorybridge.h
index 4a64df1371..2d625befb4 100644
--- a/indra/newview/llinventorybridge.h
+++ b/indra/newview/llinventorybridge.h
@@ -52,7 +52,7 @@ typedef std::vector<std::string> menuentry_vec_t;
//
// You'll want to call LLInvItemFVELister::createBridge() to actually create
// an instance of this class. This helps encapsulate the
-// funcationality a bit. (except for folders, you can create those
+// functionality a bit. (except for folders, you can create those
// manually...)
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
class LLInvFVBridge : public LLFolderViewEventListener
@@ -70,6 +70,8 @@ public:
virtual ~LLInvFVBridge() {}
BOOL canShare() const;
+ BOOL canListOnMarketplace() const;
+ BOOL canListOnMarketplaceNow() const;
//--------------------------------------------------------------------
// LLInvFVBridge functionality
@@ -141,7 +143,9 @@ protected:
BOOL isAgentInventory() const; // false if lost or in the inventory library
BOOL isCOFFolder() const; // true if COF or descendent of
BOOL isInboxFolder() const; // true if COF or descendent of marketplace inbox
- BOOL isOutboxFolder() const; // true if COF or descendent of marketplace inbox
+ BOOL isOutboxFolder() const; // true if COF or descendent of marketplace outbox
+ const LLUUID getOutboxFolder() const;
+
virtual BOOL isItemPermissive() const;
static void changeItemParent(LLInventoryModel* model,
LLViewerInventoryItem* item,
@@ -210,8 +214,7 @@ public:
/*virtual*/ void clearDisplayName() { mDisplayName.clear(); }
LLViewerInventoryItem* getItem() const;
- bool isAddAction(std::string action) const;
- bool isRemoveAction(std::string action) const;
+
protected:
BOOL confirmRemoveItem(const LLSD& notification, const LLSD& response);
virtual BOOL isItemPermissive() const;
diff --git a/indra/newview/llpanelmarketplaceinbox.cpp b/indra/newview/llpanelmarketplaceinbox.cpp
index 3fc10eb176..5a835eadf1 100644
--- a/indra/newview/llpanelmarketplaceinbox.cpp
+++ b/indra/newview/llpanelmarketplaceinbox.cpp
@@ -53,7 +53,7 @@ LLPanelMarketplaceInbox::LLPanelMarketplaceInbox(const Params& p)
LLPanelMarketplaceInbox::~LLPanelMarketplaceInbox()
{
- if (getChild<LLButton>("inbox_btn")->getToggleState())
+ if (getVisible() && getChild<LLButton>("inbox_btn")->getToggleState())
{
gSavedPerAccountSettings.setString("LastInventoryInboxCollapse", LLDate::now().asString());
}
diff --git a/indra/newview/llpanelmarketplaceinboxinventory.cpp b/indra/newview/llpanelmarketplaceinboxinventory.cpp
index de4e4414c4..e2f8af1280 100644
--- a/indra/newview/llpanelmarketplaceinboxinventory.cpp
+++ b/indra/newview/llpanelmarketplaceinboxinventory.cpp
@@ -133,6 +133,27 @@ LLFolderViewFolder * LLInboxInventoryPanel::createFolderViewFolder(LLInvFVBridge
return LLUICtrlFactory::create<LLInboxFolderViewFolder>(params);
}
+LLFolderViewItem * LLInboxInventoryPanel::createFolderViewItem(LLInvFVBridge * bridge)
+{
+ LLFolderViewItem::Params params;
+
+ params.name = bridge->getDisplayName();
+ params.icon = bridge->getIcon();
+ params.icon_open = bridge->getOpenIcon();
+
+ if (mShowItemLinkOverlays) // if false, then links show up just like normal items
+ {
+ params.icon_overlay = LLUI::getUIImage("Inv_Link");
+ }
+
+ params.creation_date = bridge->getCreationDate();
+ params.root = mFolderRoot;
+ params.listener = bridge;
+ params.rect = LLRect (0, 0, 0, 0);
+ params.tool_tip = params.name;
+
+ return LLUICtrlFactory::create<LLInboxFolderViewItem>(params);
+}
//
// LLInboxFolderViewFolder Implementation
@@ -182,8 +203,12 @@ void LLInboxFolderViewFolder::draw()
void LLInboxFolderViewFolder::updateFlag() const
{
- LLDate saved_freshness_date = LLDate(gSavedPerAccountSettings.getString("LastInventoryInboxCollapse"));
- mFresh = (mCreationDate > saved_freshness_date.secondsSinceEpoch());
+ const std::string& last_collapse = gSavedPerAccountSettings.getString("LastInventoryInboxCollapse");
+ if (!last_collapse.empty())
+ {
+ LLDate saved_freshness_date = LLDate(last_collapse);
+ mFresh = (mCreationDate > saved_freshness_date.secondsSinceEpoch());
+ }
}
void LLInboxFolderViewFolder::selectItem()
@@ -204,5 +229,13 @@ void LLInboxFolderViewFolder::setCreationDate(time_t creation_date_utc) const
updateFlag();
}
+//
+// LLInboxFolderViewItem Implementation
+//
+
+BOOL LLInboxFolderViewItem::handleDoubleClick(S32 x, S32 y, MASK mask)
+{
+ return TRUE;
+}
// eof
diff --git a/indra/newview/llpanelmarketplaceinboxinventory.h b/indra/newview/llpanelmarketplaceinboxinventory.h
index d2d42e11f4..6cb243dbd5 100644
--- a/indra/newview/llpanelmarketplaceinboxinventory.h
+++ b/indra/newview/llpanelmarketplaceinboxinventory.h
@@ -52,7 +52,8 @@ public:
void buildFolderView(const LLInventoryPanel::Params& params);
// virtual
- class LLFolderViewFolder* createFolderViewFolder(LLInvFVBridge * bridge);
+ LLFolderViewFolder * createFolderViewFolder(LLInvFVBridge * bridge);
+ LLFolderViewItem * createFolderViewItem(LLInvFVBridge * bridge);
};
@@ -89,4 +90,15 @@ protected:
};
+class LLInboxFolderViewItem : public LLFolderViewItem
+{
+public:
+ LLInboxFolderViewItem(const Params& p)
+ : LLFolderViewItem(p)
+ {
+ }
+
+ BOOL handleDoubleClick(S32 x, S32 y, MASK mask);
+};
+
#endif //LL_INBOXINVENTORYPANEL_H
diff --git a/indra/newview/llpanelmarketplaceoutbox.cpp b/indra/newview/llpanelmarketplaceoutbox.cpp
index 221420985a..839369bffe 100644
--- a/indra/newview/llpanelmarketplaceoutbox.cpp
+++ b/indra/newview/llpanelmarketplaceoutbox.cpp
@@ -27,6 +27,7 @@
#include "llviewerprecompiledheaders.h"
#include "llpanelmarketplaceoutbox.h"
+#include "llpanelmarketplaceoutboxinventory.h"
#include "llappviewer.h"
#include "llbutton.h"
@@ -36,6 +37,7 @@
#include "llloadingindicator.h"
#include "llnotificationsutil.h"
#include "llpanelmarketplaceinbox.h"
+#include "llsdutil.h"
#include "llsidepanelinventory.h"
#include "llsidetray.h"
#include "lltimer.h"
@@ -198,13 +200,6 @@ public:
{
// Complete success
llinfos << "success" << llendl;
- LLSD imported_list = content["imported"];
- LLSD::array_const_iterator it = imported_list.beginArray();
- for ( ; it != imported_list.endArray(); ++it)
- {
- LLUUID imported_folder = (*it).asUUID();
- remove_category(&gInventory, imported_folder);
- }
}
else
{
@@ -252,7 +247,9 @@ void LLPanelMarketplaceOutbox::onSyncComplete(bool goodStatus, const LLSD& conte
mSyncInProgress = false;
updateSyncButtonStatus();
- if (goodStatus)
+ const LLSD& errors_list = content["errors"];
+
+ if (goodStatus && (errors_list.size() == 0))
{
LLNotificationsUtil::add("OutboxUploadComplete", LLSD::emptyMap(), LLSD::emptyMap());
}
@@ -260,6 +257,39 @@ void LLPanelMarketplaceOutbox::onSyncComplete(bool goodStatus, const LLSD& conte
{
LLNotificationsUtil::add("OutboxUploadHadErrors", LLSD::emptyMap(), LLSD::emptyMap());
}
+
+ llinfos << "Marketplace upload llsd:" << llendl;
+ llinfos << ll_pretty_print_sd(content) << llendl;
+ llinfos << llendl;
+
+ const LLSD& imported_list = content["imported"];
+ LLSD::array_const_iterator it = imported_list.beginArray();
+ for ( ; it != imported_list.endArray(); ++it)
+ {
+ LLUUID imported_folder = (*it).asUUID();
+ llinfos << "Successfully uploaded folder " << imported_folder.asString() << " to marketplace." << llendl;
+ }
+
+ for (it = errors_list.beginArray(); it != errors_list.endArray(); ++it)
+ {
+ const LLSD& item_error_map = (*it);
+
+ LLUUID error_folder = item_error_map["folder_id"].asUUID();
+ const std::string& error_string = item_error_map["identifier"].asString();
+ LLUUID error_item = item_error_map["item_id"].asUUID();
+ const std::string& error_item_name = item_error_map["item_name"].asString();
+ const std::string& error_message = item_error_map["message"].asString();
+
+ llinfos << "Error item " << error_folder.asString() << ", " << error_string << ", "
+ << error_item.asString() << ", " << error_item_name << ", " << error_message << llendl;
+
+ LLFolderViewFolder * item_folder = mInventoryPanel->getRootFolder()->getFolderByID(error_folder);
+ LLOutboxFolderViewFolder * outbox_item_folder = dynamic_cast<LLOutboxFolderViewFolder *>(item_folder);
+
+ llassert(outbox_item_folder);
+
+ outbox_item_folder->setErrorString(error_string);
+ }
}
void LLPanelMarketplaceOutbox::updateSyncButtonStatus()
diff --git a/indra/newview/llpanelmarketplaceoutboxinventory.cpp b/indra/newview/llpanelmarketplaceoutboxinventory.cpp
index 638d3c5150..14b6ee9e0a 100644
--- a/indra/newview/llpanelmarketplaceoutboxinventory.cpp
+++ b/indra/newview/llpanelmarketplaceoutboxinventory.cpp
@@ -34,6 +34,7 @@
#include "llinventoryfunctions.h"
#include "llpanellandmarks.h"
#include "llplacesinventorybridge.h"
+#include "lltrans.h"
#include "llviewerfoldertype.h"
@@ -46,6 +47,50 @@ static LLDefaultChildRegistry::Register<LLOutboxFolderViewFolder> r2("outbox_fol
//
+// Marketplace errors
+//
+
+enum
+{
+ MKTERR_NONE = 0,
+
+ MKTERR_NOT_MERCHANT,
+ MKTERR_FOLDER_EMPTY,
+ MKTERR_UNASSOCIATED_PRODUCTS,
+ MKTERR_OBJECT_LIMIT,
+ MKTERR_FOLDER_DEPTH,
+ MKTERR_UNSELLABLE_ITEM,
+ MKTERR_INTERNAL_IMPORT,
+
+ MKTERR_COUNT
+};
+
+static const std::string MARKETPLACE_ERROR_STRINGS[MKTERR_COUNT] =
+{
+ "NO_ERROR",
+ "NOT_MERCHANT_ERROR",
+ "FOLDER_EMPTY_ERROR",
+ "UNASSOCIATED_PRODUCTS_ERROR",
+ "OBJECT_LIMIT_ERROR",
+ "FOLDER_DEPTH_ERROR",
+ "UNSELLABLE_ITEM_FOUND",
+ "INTERNAL_IMPORT_ERROR",
+};
+
+static const std::string MARKETPLACE_ERROR_NAMES[MKTERR_COUNT] =
+{
+ "Marketplace Error None",
+ "Marketplace Error Not Merchant",
+ "Marketplace Error Empty Folder",
+ "Marketplace Error Unassociated Products",
+ "Marketplace Error Object Limit",
+ "Marketplace Error Folder Depth",
+ "Marketplace Error Unsellable Item",
+ "Marketplace Error Internal Import",
+};
+
+
+//
// LLOutboxInventoryPanel Implementation
//
@@ -133,6 +178,27 @@ LLFolderViewFolder * LLOutboxInventoryPanel::createFolderViewFolder(LLInvFVBridg
return LLUICtrlFactory::create<LLOutboxFolderViewFolder>(params);
}
+LLFolderViewItem * LLOutboxInventoryPanel::createFolderViewItem(LLInvFVBridge * bridge)
+{
+ LLFolderViewItem::Params params;
+
+ params.name = bridge->getDisplayName();
+ params.icon = bridge->getIcon();
+ params.icon_open = bridge->getOpenIcon();
+
+ if (mShowItemLinkOverlays) // if false, then links show up just like normal items
+ {
+ params.icon_overlay = LLUI::getUIImage("Inv_Link");
+ }
+
+ params.creation_date = bridge->getCreationDate();
+ params.root = mFolderRoot;
+ params.listener = bridge;
+ params.rect = LLRect (0, 0, 0, 0);
+ params.tool_tip = params.name;
+
+ return LLUICtrlFactory::create<LLOutboxFolderViewItem>(params);
+}
//
// LLOutboxFolderViewFolder Implementation
@@ -141,7 +207,7 @@ LLFolderViewFolder * LLOutboxInventoryPanel::createFolderViewFolder(LLInvFVBridg
LLOutboxFolderViewFolder::LLOutboxFolderViewFolder(const Params& p)
: LLFolderViewFolder(p)
, LLBadgeOwner(getHandle())
- , mError(false)
+ , mError(0)
{
initBadgeParams(p.error_badge());
}
@@ -158,15 +224,53 @@ void LLOutboxFolderViewFolder::draw()
addBadgeToParentPanel();
}
- setBadgeVisibility(mError);
+ setBadgeVisibility(hasError());
LLFolderViewFolder::draw();
}
+void LLOutboxFolderViewFolder::setErrorString(const std::string& errorString)
+{
+ S32 error_code = MKTERR_NONE;
+
+ for (S32 i = 1; i < MKTERR_COUNT; ++i)
+ {
+ if (MARKETPLACE_ERROR_STRINGS[i] == errorString)
+ {
+ error_code = i;
+ break;
+ }
+ }
+
+ setError(error_code);
+}
+
+void LLOutboxFolderViewFolder::setError(S32 errorCode)
+{
+ mError = errorCode;
+
+ if (hasError())
+ {
+ setToolTip(LLTrans::getString(MARKETPLACE_ERROR_NAMES[mError]));
+ }
+ else
+ {
+ setToolTip(LLStringExplicit(""));
+ }
+}
+
void LLOutboxFolderViewFolder::setCreationDate(time_t creation_date_utc) const
{
mCreationDate = creation_date_utc;
}
+//
+// LLOutboxFolderViewItem Implementation
+//
+
+BOOL LLOutboxFolderViewItem::handleDoubleClick(S32 x, S32 y, MASK mask)
+{
+ return TRUE;
+}
// eof
diff --git a/indra/newview/llpanelmarketplaceoutboxinventory.h b/indra/newview/llpanelmarketplaceoutboxinventory.h
index ba68654ad7..ec55b7eb2e 100644
--- a/indra/newview/llpanelmarketplaceoutboxinventory.h
+++ b/indra/newview/llpanelmarketplaceoutboxinventory.h
@@ -48,7 +48,8 @@ public:
void buildFolderView(const LLInventoryPanel::Params& params);
// virtual
- class LLFolderViewFolder* createFolderViewFolder(LLInvFVBridge * bridge);
+ LLFolderViewFolder * createFolderViewFolder(LLInvFVBridge * bridge);
+ LLFolderViewItem * createFolderViewItem(LLInvFVBridge * bridge);
};
@@ -60,7 +61,7 @@ public:
Optional<LLBadge::Params> error_badge;
Params()
- : error_badge("error_badge")
+ : error_badge("error_badge")
{
}
};
@@ -69,13 +70,29 @@ public:
~LLOutboxFolderViewFolder();
void draw();
+
+ void setErrorString(const std::string& errorString);
+ void setError(S32 errorCode);
- bool hasError() const { return mError; }
+ bool hasError() const { return (mError != 0); }
protected:
void setCreationDate(time_t creation_date_utc) const;
- bool mError;
+ S32 mError;
+};
+
+
+class LLOutboxFolderViewItem : public LLFolderViewItem
+{
+public:
+ LLOutboxFolderViewItem(const Params& p)
+ : LLFolderViewItem(p)
+ {
+ }
+
+ // virtual
+ BOOL handleDoubleClick(S32 x, S32 y, MASK mask);
};
diff --git a/indra/newview/llsidepanelinventory.cpp b/indra/newview/llsidepanelinventory.cpp
index 5ae3a30fd5..9290b7ebef 100644
--- a/indra/newview/llsidepanelinventory.cpp
+++ b/indra/newview/llsidepanelinventory.cpp
@@ -520,14 +520,14 @@ bool LLSidepanelInventory::manageInboxOutboxPanels(LLButton * pressedButton, LLL
void LLSidepanelInventory::onToggleInboxBtn()
{
- LLButton* pressedButton = getChild<LLButton>(INBOX_BUTTON_NAME);
- LLLayoutPanel* pressedPanel = getChild<LLLayoutPanel>(INBOX_LAYOUT_PANEL_NAME);
- LLButton* otherButton = getChild<LLButton>(OUTBOX_BUTTON_NAME);
- LLLayoutPanel* otherPanel = getChild<LLLayoutPanel>(OUTBOX_LAYOUT_PANEL_NAME);
+ LLButton* inboxButton = getChild<LLButton>(INBOX_BUTTON_NAME);
+ LLLayoutPanel* inboxPanel = getChild<LLLayoutPanel>(INBOX_LAYOUT_PANEL_NAME);
+ LLButton* outboxButton = getChild<LLButton>(OUTBOX_BUTTON_NAME);
+ LLLayoutPanel* outboxPanel = getChild<LLLayoutPanel>(OUTBOX_LAYOUT_PANEL_NAME);
- bool inbox_expanded = manageInboxOutboxPanels(pressedButton, pressedPanel, otherButton, otherPanel);
+ bool inbox_expanded = manageInboxOutboxPanels(inboxButton, inboxPanel, outboxButton, outboxPanel);
- if (!inbox_expanded)
+ if (!inbox_expanded && inboxPanel->getVisible())
{
gSavedPerAccountSettings.setString("LastInventoryInboxCollapse", LLDate::now().asString());
}
@@ -535,15 +535,15 @@ void LLSidepanelInventory::onToggleInboxBtn()
void LLSidepanelInventory::onToggleOutboxBtn()
{
- LLButton* pressedButton = getChild<LLButton>(OUTBOX_BUTTON_NAME);
- LLLayoutPanel* pressedPanel = getChild<LLLayoutPanel>(OUTBOX_LAYOUT_PANEL_NAME);
- LLButton* otherButton = getChild<LLButton>(INBOX_BUTTON_NAME);
- LLLayoutPanel* otherPanel = getChild<LLLayoutPanel>(INBOX_LAYOUT_PANEL_NAME);
+ LLButton* inboxButton = getChild<LLButton>(INBOX_BUTTON_NAME);
+ LLLayoutPanel* inboxPanel = getChild<LLLayoutPanel>(INBOX_LAYOUT_PANEL_NAME);
+ LLButton* outboxButton = getChild<LLButton>(OUTBOX_BUTTON_NAME);
+ LLLayoutPanel* outboxPanel = getChild<LLLayoutPanel>(OUTBOX_LAYOUT_PANEL_NAME);
- bool inbox_was_expanded = otherButton->getToggleState();
- manageInboxOutboxPanels(pressedButton, pressedPanel, otherButton, otherPanel);
+ bool inbox_was_expanded = inboxButton->getToggleState();
+ manageInboxOutboxPanels(outboxButton, outboxPanel, inboxButton, inboxPanel);
- if (inbox_was_expanded)
+ if (inbox_was_expanded && inboxPanel->getVisible())
{
gSavedPerAccountSettings.setString("LastInventoryInboxCollapse", LLDate::now().asString());
}
diff --git a/indra/newview/skins/default/colors.xml b/indra/newview/skins/default/colors.xml
index 6144c761b7..d19e56e9a0 100644
--- a/indra/newview/skins/default/colors.xml
+++ b/indra/newview/skins/default/colors.xml
@@ -30,6 +30,9 @@
name="LtGray"
value="0.75 0.75 0.75 1" />
<color
+ name="LtGray_35"
+ value="0.75 0.75 0.75 0.35" />
+ <color
name="LtGray_50"
value="0.75 0.75 0.75 0.50" />
<color
@@ -427,11 +430,14 @@
name="InventoryItemLinkColor"
reference="LtGray_50" />
<color
+ name="InventoryMouseOverColor"
+ reference="LtGray_35" />
+ <color
name="InventorySearchStatusColor"
reference="EmphasisColor" />
<color
name="LabelDisabledColor"
- reference="White_25" />
+ reference="White_25" />
<color
name="LabelSelectedColor"
reference="White" />
diff --git a/indra/newview/skins/default/xui/en/menu_inventory.xml b/indra/newview/skins/default/xui/en/menu_inventory.xml
index e91f4458ae..fb85e5278a 100644
--- a/indra/newview/skins/default/xui/en/menu_inventory.xml
+++ b/indra/newview/skins/default/xui/en/menu_inventory.xml
@@ -674,7 +674,26 @@
function="Inventory.DoToSelected"
parameter="take_off" />
</menu_item_call>
- <menu_item_call
+ <menu_item_separator
+ layout="topleft"
+ name="Marketplace Separator" />
+ <menu_item_call
+ label="Copy to Merchant Outbox"
+ layout="topleft"
+ name="Merchant Copy">
+ <menu_item_call.on_click
+ function="Inventory.DoToSelected"
+ parameter="copy_to_outbox" />
+ </menu_item_call>
+ <menu_item_call
+ label="Move to Merchant Outbox"
+ layout="topleft"
+ name="Merchant Move">
+ <menu_item_call.on_click
+ function="Inventory.DoToSelected"
+ parameter="move_to_outbox" />
+ </menu_item_call>
+ <menu_item_call
label="--no options--"
layout="topleft"
name="--no options--" />
diff --git a/indra/newview/skins/default/xui/en/strings.xml b/indra/newview/skins/default/xui/en/strings.xml
index 5377b0ab05..1351ad6e52 100644
--- a/indra/newview/skins/default/xui/en/strings.xml
+++ b/indra/newview/skins/default/xui/en/strings.xml
@@ -2041,7 +2041,17 @@ Returns a string with the requested data about the region
<string name="InventoryOutboxNoItemsTitle">A new way to send items to the Marketplace</string>
<string name="InventoryOutboxNoItemsTooltip">Drag and drop items here to prepare them for sale on the Marketplace</string>
<string name="InventoryOutboxNoItems">Drag items or folders that you wish to sell into this area. A copy of the item will appear, leaving your inventory unchanged, unless you have dragged a no-copy item. When you are ready to send the items to the Marketplace, click the Upload button. Once your items have been moved to your Marketplace Inventory, they will disappear from this folder.</string>
- <!-- use value="" because they have preceding spaces -->
+
+ <string name="Marketplace Error None">No errors</string>
+ <string name="Marketplace Error Not Merchant">Error: Before sending items to the Marketplace you will need to set yourself up as a merchant (free of charge).</string>
+ <string name="Marketplace Error Empty Folder">Error: This folder has no contents.</string>
+ <string name="Marketplace Error Unassociated Products">Error: This item failed to upload because your merchant account has too many items unassociated with products. To fix this error, login to the marketplace website and reduce your unassociated item count.</string>
+ <string name="Marketplace Error Object Limit">Error: This item contains too many objects. Fix this error by placing objects together in boxes to reduce the total count to less than 200.</string>
+ <string name="Marketplace Error Folder Depth">Error: This item contains too many levels of nested folders. Reorganize it to a maximum of 3 levels of nested folders.</string>
+ <string name="Marketplace Error Unsellable Item">Error: This item can not be sold on the marketplace.</string>
+ <string name="Marketplace Error Internal Import">Error: There was a problem with this item. Try again later.</string>
+
+ <!-- use value="" because they have preceding spaces -->
<string name="no_transfer" value=" (no transfer)" />
<string name="no_modify" value=" (no modify)" />
<string name="no_copy" value=" (no copy)" />
diff --git a/indra/newview/skins/default/xui/en/widgets/scroll_container.xml b/indra/newview/skins/default/xui/en/widgets/scroll_container.xml
index 86356ff563..85fc64c8b4 100644
--- a/indra/newview/skins/default/xui/en/widgets/scroll_container.xml
+++ b/indra/newview/skins/default/xui/en/widgets/scroll_container.xml
@@ -2,4 +2,7 @@
<scroll_container color="black"
opaque="false"
min_auto_scroll_rate="120"
- max_auto_scroll_rate="500"/>
+ max_auto_scroll_rate="500"
+ tab_stop="false"
+ name="scroll_container"
+ mouse_opaque="true" />