From 488958250c1ef8e0e4f5300080ff7edf6776de82 Mon Sep 17 00:00:00 2001 From: Abdullah Al-Soussi Date: Tue, 2 Mar 2021 11:55:38 -0500 Subject: [PATCH 1/4] MAYA-110196 - Multiple ProxyShapes with Same Stage (InStageData) Bug MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit We can have a situation where we have multiple proxy shapes that point to the same exact stage, using the InStageData port. Unfortunately this causes an issue in the layer editor since the combo-box is keeping track of the stage only, so two entries with the same stage is ambiguous.  The fix was to move away from storing the Pixar Stage Reference as the data in the combo box and move to the StageEntry which encapsulates both stage and the proxy shape path. --- lib/usd/ui/layerEditor/layerTreeModel.cpp | 2 +- .../ui/layerEditor/mayaLayerEditorWindow.cpp | 11 ++- lib/usd/ui/layerEditor/mayaSessionState.cpp | 64 ++++++++--------- lib/usd/ui/layerEditor/mayaSessionState.h | 11 ++- lib/usd/ui/layerEditor/saveLayersDialog.cpp | 18 ++--- lib/usd/ui/layerEditor/sessionState.cpp | 11 +-- lib/usd/ui/layerEditor/sessionState.h | 70 ++++++++++++++++--- .../ui/layerEditor/stageSelectorWidget.cpp | 65 ++++++++++------- lib/usd/ui/layerEditor/stageSelectorWidget.h | 14 ++-- 9 files changed, 160 insertions(+), 106 deletions(-) diff --git a/lib/usd/ui/layerEditor/layerTreeModel.cpp b/lib/usd/ui/layerEditor/layerTreeModel.cpp index 38a10f1523..953255ff75 100644 --- a/lib/usd/ui/layerEditor/layerTreeModel.cpp +++ b/lib/usd/ui/layerEditor/layerTreeModel.cpp @@ -233,7 +233,7 @@ void LayerTreeModel::setSessionState(SessionState* in_sessionState) in_sessionState, &SessionState::autoHideSessionLayerSignal, this, - &LayerTreeModel::sessionStageChanged); + &LayerTreeModel::autoHideSessionLayerChanged); } void LayerTreeModel::rebuildModelOnIdle() diff --git a/lib/usd/ui/layerEditor/mayaLayerEditorWindow.cpp b/lib/usd/ui/layerEditor/mayaLayerEditorWindow.cpp index 938261c28c..4c3e621972 100644 --- a/lib/usd/ui/layerEditor/mayaLayerEditorWindow.cpp +++ b/lib/usd/ui/layerEditor/mayaLayerEditorWindow.cpp @@ -44,7 +44,7 @@ class LayerEditorWindowCreator : public AbstractLayerEditorCreator { public: LayerEditorWindowCreator() { ; }; - virtual ~LayerEditorWindowCreator() { } + virtual ~LayerEditorWindowCreator() {} AbstractLayerEditorWindow* createWindow(const char* panelName) override; AbstractLayerEditorWindow* getWindow(const char* panelName) const override; @@ -232,11 +232,10 @@ void MayaLayerEditorWindow::selectPrimsWithSpec() void MayaLayerEditorWindow::selectProxyShape(const char* shapePath) { - auto prim = UsdMayaQuery::GetPrim(shapePath); - if (prim) { - auto stage = prim.GetStage(); - if (stage != nullptr) { - _sessionState.setStage(stage); + SessionState::StageEntry entry; + if (_sessionState.getStageEntry(&entry, shapePath)) { + if (entry._stage != nullptr) { + _sessionState.setStageEntry(entry); } } } diff --git a/lib/usd/ui/layerEditor/mayaSessionState.cpp b/lib/usd/ui/layerEditor/mayaSessionState.cpp index c1392b1aa4..78db47da72 100644 --- a/lib/usd/ui/layerEditor/mayaSessionState.cpp +++ b/lib/usd/ui/layerEditor/mayaSessionState.cpp @@ -32,6 +32,7 @@ #include #include + #ifdef THIS #undef THIS #endif @@ -59,19 +60,11 @@ MayaSessionState::~MayaSessionState() // } -void MayaSessionState::setStage(PXR_NS::UsdStageRefPtr const& in_stage) +void MayaSessionState::setStageEntry(StageEntry const& inEntry) { - PARENT_CLASS::setStage(in_stage); - if (in_stage) { - auto stageList = allStages(); - for (auto const& entry : stageList) { - if (entry._stage == in_stage) { - _currentProxyShapePath = entry._proxyShapePath; - break; - } - } - } else { - _currentProxyShapePath.clear(); + PARENT_CLASS::setStageEntry(inEntry); + if (!inEntry._stage) { + _currentStageEntry.clear(); } } @@ -155,25 +148,23 @@ void MayaSessionState::unregisterNotifications() void MayaSessionState::mayaUsdStageReset(const MayaUsdProxyStageSetNotice& notice) { - auto shapePath = notice.GetShapePath(); - auto stage = notice.GetStage(); - if (shapePath == _currentProxyShapePath) { - QTimer::singleShot(0, this, [this, stage]() { setStage(stage); }); - } else { - auto shapePath = notice.GetShapePath(); - QTimer::singleShot( - 0, this, [this, shapePath, stage]() { mayaUsdStageResetCBOnIdle(shapePath, stage); }); + auto shapePath = notice.GetShapePath(); + StageEntry entry; + if (getStageEntry(&entry, shapePath.c_str())) { + if (entry._proxyShapePath == _currentStageEntry._proxyShapePath) { + QTimer::singleShot(0, this, [this, entry]() { + mayaUsdStageResetCBOnIdle(entry); + setStageEntry(entry); + }); + } else { + QTimer::singleShot(0, this, [this, entry]() { mayaUsdStageResetCBOnIdle(entry); }); + } } } -void MayaSessionState::mayaUsdStageResetCBOnIdle( - const std::string& shapePath, - PXR_NS::UsdStageRefPtr const& stage) +void MayaSessionState::mayaUsdStageResetCBOnIdle(StageEntry const& entry) { - StageEntry entry; - if (getStageEntry(&entry, shapePath.c_str())) { - Q_EMIT stageResetSignal(entry._proxyShapePath, stage); - } + Q_EMIT stageResetSignal(entry); } /* static */ @@ -195,7 +186,7 @@ void MayaSessionState::proxyShapeAddedCBOnIdle(const MObject& obj) auto shapePath = dagPath.fullPathName(); StageEntry entry; if (getStageEntry(&entry, shapePath)) { - Q_EMIT stageListChangedSignal(entry._stage); + Q_EMIT stageListChangedSignal(entry); } } @@ -213,11 +204,12 @@ void MayaSessionState::nodeRenamedCB(MObject& obj, const MString& oldName, void* auto THIS = static_cast(clientData); // doing it on idle give time to the Load Stage to set a file name - QTimer::singleShot(0, [THIS, obj]() { THIS->nodeRenamedCBOnIdle(obj); }); + QTimer::singleShot( + 0, [THIS, obj, oldName]() { THIS->nodeRenamedCBOnIdle(oldName.asChar(), obj); }); } } -void MayaSessionState::nodeRenamedCBOnIdle(const MObject& obj) +void MayaSessionState::nodeRenamedCBOnIdle(std::string const& oldName, const MObject& obj) { // this does not work: // if OpenMaya.MFnDependencyNode(obj).typeName == PROXY_NODE_TYPE @@ -228,7 +220,13 @@ void MayaSessionState::nodeRenamedCBOnIdle(const MObject& obj) StageEntry entry; if (getStageEntry(&entry, shapePath)) { - Q_EMIT stageRenamedSignal(entry._displayName, entry._stage); + // Need to update the current Entry also + if (_currentStageEntry._displayName == oldName + && _currentStageEntry._stage == entry._stage) { + _currentStageEntry = entry; + } + + Q_EMIT stageRenamedSignal(oldName, entry); } } } @@ -325,10 +323,10 @@ std::string MayaSessionState::defaultLoadPath() const // in this case, the stage needs to be re-created on the new file void MayaSessionState::rootLayerPathChanged(std::string const& in_path) { - if (!_currentProxyShapePath.empty()) { + if (!_currentStageEntry._proxyShapePath.empty()) { MString script; - MString proxyShape(_currentProxyShapePath.c_str()); + MString proxyShape(_currentStageEntry._proxyShapePath.c_str()); MString newValue(in_path.c_str()); script.format("setAttr -type \"string\" ^1s.filePath \"^2s\"", proxyShape, newValue); MGlobal::executeCommand( diff --git a/lib/usd/ui/layerEditor/mayaSessionState.h b/lib/usd/ui/layerEditor/mayaSessionState.h index 4b83f6659a..70be8b9fc6 100644 --- a/lib/usd/ui/layerEditor/mayaSessionState.h +++ b/lib/usd/ui/layerEditor/mayaSessionState.h @@ -50,7 +50,7 @@ class MayaSessionState ~MayaSessionState(); // API implementation - void setStage(PXR_NS::UsdStageRefPtr const& in_stage) override; + void setStageEntry(StageEntry const& in_entry) override; void setAutoHideSessionLayer(bool hide) override; AbstractCommandHook* commandHook() override; std::vector allStages() const override; @@ -69,7 +69,7 @@ class MayaSessionState // in this case, the stage needs to be re-created on the new file void rootLayerPathChanged(std::string const& in_path) override; - std::string proxyShapePath() { return _currentProxyShapePath; } + std::string proxyShapePath() { return _currentStageEntry._proxyShapePath; } Q_SIGNALS: void clearUIOnSceneResetSignal(); @@ -78,10 +78,10 @@ class MayaSessionState void registerNotifications(); void unregisterNotifications(); -protected: // get the stage and proxy name for a path static bool getStageEntry(StageEntry* out_stageEntry, const MString& shapePath); +protected: // maya callback handers static void proxyShapeAddedCB(MObject& node, void* clientData); static void proxyShapeRemovedCB(MObject& node, void* clientData); @@ -89,15 +89,14 @@ class MayaSessionState static void sceneClosingCB(void* clientData); void proxyShapeAddedCBOnIdle(const MObject& node); - void nodeRenamedCBOnIdle(const MObject& obj); + void nodeRenamedCBOnIdle(std::string const& oldName, const MObject& obj); // Notice listener method for proxy stage set void mayaUsdStageReset(const MayaUsdProxyStageSetNotice& notice); - void mayaUsdStageResetCBOnIdle(const std::string& shapePath, UsdStageRefPtr const& stage); + void mayaUsdStageResetCBOnIdle(StageEntry const& entry); std::vector _callbackIds; TfNotice::Key _stageResetNoticeKey; - std::string _currentProxyShapePath; MayaCommandHook _mayaCommandHook; }; diff --git a/lib/usd/ui/layerEditor/saveLayersDialog.cpp b/lib/usd/ui/layerEditor/saveLayersDialog.cpp index eaba1ce1a4..ca454d30f2 100644 --- a/lib/usd/ui/layerEditor/saveLayersDialog.cpp +++ b/lib/usd/ui/layerEditor/saveLayersDialog.cpp @@ -275,19 +275,11 @@ SaveLayersDialog::SaveLayersDialog(SessionState* in_sessionState, QWidget* in_pa MString msg; QString dialogTitle = StringResources::getAsQString(StringResources::kSaveStage); if (TF_VERIFY(nullptr != _sessionState)) { - auto stage = _sessionState->stage(); - - auto stageList = _sessionState->allStages(); - for (auto const& entry : stageList) { - if (entry._stage == stage) { - std::string stageName = entry._displayName; - msg.format( - StringResources::getAsMString(StringResources::kSaveName), stageName.c_str()); - dialogTitle = MQtUtil::toQString(msg); - getLayersToSave(stage, stageName); - break; - } - } + auto stageEntry = _sessionState->stageEntry(); + std::string stageName = stageEntry._displayName; + msg.format(StringResources::getAsMString(StringResources::kSaveName), stageName.c_str()); + dialogTitle = MQtUtil::toQString(msg); + getLayersToSave(stageEntry._stage, stageName); } setWindowTitle(dialogTitle); diff --git a/lib/usd/ui/layerEditor/sessionState.cpp b/lib/usd/ui/layerEditor/sessionState.cpp index 1b5d2710b0..31cdbdccd0 100644 --- a/lib/usd/ui/layerEditor/sessionState.cpp +++ b/lib/usd/ui/layerEditor/sessionState.cpp @@ -23,18 +23,19 @@ void SessionState::setAutoHideSessionLayer(bool hideIt) Q_EMIT autoHideSessionLayerSignal(_autoHideSessionLayer); } -void SessionState::setStage(PXR_NS::UsdStageRefPtr const& in_stage) +void SessionState::setStageEntry(StageEntry const& in_entry) { - if (in_stage != _stage) { - _stage = in_stage; + if (_currentStageEntry != in_entry) { + auto oldEntry = _currentStageEntry; + _currentStageEntry = in_entry; Q_EMIT currentStageChangedSignal(); } } PXR_NS::SdfLayerRefPtr SessionState::targetLayer() const { - if (_stage != nullptr) { - const auto& target = _stage->GetEditTarget(); + if (_currentStageEntry._stage != nullptr) { + const auto& target = _currentStageEntry._stage->GetEditTarget(); return target.GetLayer(); } else { return nullptr; diff --git a/lib/usd/ui/layerEditor/sessionState.h b/lib/usd/ui/layerEditor/sessionState.h index a52addd65d..e611289ede 100644 --- a/lib/usd/ui/layerEditor/sessionState.h +++ b/lib/usd/ui/layerEditor/sessionState.h @@ -41,21 +41,70 @@ class SessionState : public QObject { Q_OBJECT public: - virtual ~SessionState() { } + virtual ~SessionState() {} struct StageEntry { PXR_NS::UsdStageRefPtr _stage; std::string _displayName; std::string _proxyShapePath; + + StageEntry() + { + _stage = PXR_NS::UsdStageRefPtr(); + _displayName = ""; + _proxyShapePath = ""; + } + + StageEntry( + PXR_NS::UsdStageRefPtr const& stage, + std::string const& displayName, + std::string const& proxyShapePath) + { + _stage = stage; + _displayName = displayName; + _proxyShapePath = proxyShapePath; + } + + StageEntry(const StageEntry& entry) + { + _stage = entry._stage; + _displayName = entry._displayName; + _proxyShapePath = entry._proxyShapePath; + } + + bool operator==(const StageEntry& entry) const + { + return ( + _stage == entry._stage && _displayName == entry._displayName + && _proxyShapePath == entry._proxyShapePath); + } + + bool operator!=(const StageEntry& entry) const { return !(*this == entry); } + + StageEntry& operator=(const StageEntry& entry) + { + _stage = entry._stage; + _displayName = entry._displayName; + _proxyShapePath = entry._proxyShapePath; + return *this; + } + + void clear() + { + _stage = PXR_NS::UsdStageRefPtr(); + _displayName = ""; + _proxyShapePath = ""; + } }; // properties virtual bool autoHideSessionLayer() const { return _autoHideSessionLayer; } virtual void setAutoHideSessionLayer(bool hide); - PXR_NS::UsdStageRefPtr const& stage() const { return _stage; } + PXR_NS::UsdStageRefPtr const& stage() const { return _currentStageEntry._stage; } + StageEntry const& stageEntry() const { return _currentStageEntry; } PXR_NS::SdfLayerRefPtr targetLayer() const; - virtual void setStage(PXR_NS::UsdStageRefPtr const& in_stage); + virtual void setStageEntry(StageEntry const& in_entry); virtual AbstractCommandHook* commandHook() = 0; virtual std::vector allStages() const = 0; // path to default load layer dialogs to @@ -73,18 +122,21 @@ class SessionState : public QObject // in this case, the stage needs to be re-created on the new file virtual void rootLayerPathChanged(std::string const& in_path) = 0; - bool isValid() { return _stage && _stage->GetRootLayer(); } + bool isValid() + { + return _currentStageEntry._stage && _currentStageEntry._stage->GetRootLayer(); + } Q_SIGNALS: void currentStageChangedSignal(); - void stageListChangedSignal(PXR_NS::UsdStageRefPtr const& toSelect = PXR_NS::UsdStageRefPtr()); - void stageRenamedSignal(std::string const& name, PXR_NS::UsdStageRefPtr const& stage); + void stageListChangedSignal(StageEntry const& toSelect = StageEntry()); + void stageRenamedSignal(std::string const& oldName, StageEntry const& renamedEntry); void autoHideSessionLayerSignal(bool hideIt); - void stageResetSignal(const std::string& proxyPath, PXR_NS::UsdStageRefPtr const& stage); + void stageResetSignal(StageEntry const& entry); protected: - PXR_NS::UsdStageRefPtr _stage; - bool _autoHideSessionLayer = true; + StageEntry _currentStageEntry; + bool _autoHideSessionLayer = true; }; } // namespace UsdLayerEditor diff --git a/lib/usd/ui/layerEditor/stageSelectorWidget.cpp b/lib/usd/ui/layerEditor/stageSelectorWidget.cpp index e34ff7b3e5..a772557459 100644 --- a/lib/usd/ui/layerEditor/stageSelectorWidget.cpp +++ b/lib/usd/ui/layerEditor/stageSelectorWidget.cpp @@ -16,6 +16,7 @@ #include "stageSelectorWidget.h" #include "qtUtils.h" +#include "sessionState.h" #include "stringResources.h" #include @@ -25,7 +26,7 @@ #include #include -Q_DECLARE_METATYPE(PXR_NS::UsdStageRefPtr); +Q_DECLARE_METATYPE(UsdLayerEditor::SessionState::StageEntry); namespace UsdLayerEditor { @@ -71,31 +72,30 @@ void StageSelectorWidget::setSessionState(SessionState* in_sessionState) updateFromSessionState(); } -PXR_NS::UsdStageRefPtr StageSelectorWidget::selectedStage() +SessionState::StageEntry const StageSelectorWidget::selectedStage() { if (_dropDown->currentIndex() != -1) { auto const& data = _dropDown->currentData(); - return data.value(); + return data.value(); } - return PXR_NS::UsdStageRefPtr(); + return SessionState::StageEntry(); } // repopulates the combo based on the session stage list -void StageSelectorWidget::updateFromSessionState(PXR_NS::UsdStageRefPtr const& stageToSelect) +void StageSelectorWidget::updateFromSessionState(SessionState::StageEntry const& entryToSelect) { QSignalBlocker blocker(_dropDown); _dropDown->clear(); auto allStages = _sessionState->allStages(); - for (auto const& stage : allStages) { - _dropDown->addItem(QString(stage._displayName.c_str()), QVariant::fromValue(stage._stage)); + for (auto const& stageEntry : allStages) { + _dropDown->addItem( + QString(stageEntry._displayName.c_str()), QVariant::fromValue(stageEntry)); } - if (!stageToSelect) { - const auto& newStage = selectedStage(); - if (newStage != _sessionState->stage()) { - _sessionState->setStage(newStage); - } + if (!entryToSelect._stage) { + const auto& newEntry = selectedStage(); + _sessionState->setStageEntry(newEntry); } else { - _sessionState->setStage(stageToSelect); + _sessionState->setStageEntry(entryToSelect); } } @@ -103,7 +103,7 @@ void StageSelectorWidget::updateFromSessionState(PXR_NS::UsdStageRefPtr const& s void StageSelectorWidget::selectedIndexChanged(int index) { _internalChange = true; - _sessionState->setStage(selectedStage()); + _sessionState->setStageEntry(selectedStage()); _internalChange = false; } @@ -112,7 +112,14 @@ void StageSelectorWidget::selectedIndexChanged(int index) void StageSelectorWidget::sessionStageChanged() { if (!_internalChange) { - auto index = _dropDown->findData(QVariant::fromValue(_sessionState->stage())); + size_t index = -1; + for (size_t i = 0; i < _dropDown->count(); i++) { + auto const& data = _dropDown->itemData(i); + auto entry = data.value(); + if (entry == _sessionState->stageEntry()) { + index = i; + } + } if (index != -1) { QSignalBlocker blocker(_dropDown); _dropDown->setCurrentIndex(index); @@ -120,17 +127,25 @@ void StageSelectorWidget::sessionStageChanged() } } -void StageSelectorWidget::stageRenamed(std::string const& name, PXR_NS::UsdStageRefPtr const& stage) +void StageSelectorWidget::stageRenamed( + std::string const& oldName, + SessionState::StageEntry const& renamedEntry) { - auto index = _dropDown->findData(QVariant::fromValue(stage)); + size_t index = -1; + for (size_t i = 0; i < _dropDown->count(); i++) { + auto const& data = _dropDown->itemData(i); + auto entry = data.value(); + if (entry._displayName == oldName && entry._stage == renamedEntry._stage) { + index = i; + } + } if (index != -1) { - _dropDown->setItemText(index, name.c_str()); + _dropDown->setItemText(index, renamedEntry._displayName.c_str()); + _dropDown->setItemData(index, QVariant::fromValue(renamedEntry)); } } -void StageSelectorWidget::stageReset( - const std::string& proxyPath, - PXR_NS::UsdStageRefPtr const& stage) +void StageSelectorWidget::stageReset(SessionState::StageEntry const& entry) { // Individual combo box entries have a short display name and a reference to a stage, // which is not a unique combination. By construction the combo box indices do line @@ -144,15 +159,15 @@ void StageSelectorWidget::stageReset( std::vector allStages = _sessionState->allStages(); auto it = std::find_if( - allStages.begin(), allStages.end(), [proxyPath](SessionState::StageEntry entry) { - return (proxyPath == entry._proxyShapePath); + allStages.begin(), allStages.end(), [entry](SessionState::StageEntry stageEntry) { + return (entry._proxyShapePath == stageEntry._proxyShapePath); }); if (it != allStages.end()) { - auto index = (it - allStages.begin()); + auto index = std::distance(allStages.begin(), it); if (index < count) { if (_dropDown->itemText(index) == QString::fromStdString((*it)._displayName)) { - _dropDown->setItemData(index, QVariant::fromValue(stage)); + _dropDown->setItemData(index, QVariant::fromValue(entry)); } } } diff --git a/lib/usd/ui/layerEditor/stageSelectorWidget.h b/lib/usd/ui/layerEditor/stageSelectorWidget.h index c3ba22a56b..9b24a79d63 100644 --- a/lib/usd/ui/layerEditor/stageSelectorWidget.h +++ b/lib/usd/ui/layerEditor/stageSelectorWidget.h @@ -26,8 +26,6 @@ namespace UsdLayerEditor { -class SessionState; - /** * @brief Drop down list that allows selecting a stage. Owned by the LayerEditorWidget * @@ -39,14 +37,14 @@ class StageSelectorWidget : public QWidget StageSelectorWidget(SessionState* in_sessionState, QWidget* in_parent); protected: - void setSessionState(SessionState* in_sessionState); - PXR_NS::UsdStageRefPtr selectedStage(); + void setSessionState(SessionState* in_sessionState); + SessionState::StageEntry const selectedStage(); // slot: - void - updateFromSessionState(PXR_NS::UsdStageRefPtr const& stageToSelect = PXR_NS::UsdStageRefPtr()); - void stageRenamed(std::string const& name, PXR_NS::UsdStageRefPtr const& stage); - void stageReset(const std::string& proxyPath, PXR_NS::UsdStageRefPtr const& stage); + void updateFromSessionState( + SessionState::StageEntry const& entryToSelect = SessionState::StageEntry()); + void stageRenamed(std::string const& oldName, SessionState::StageEntry const& renamedEntry); + void stageReset(SessionState::StageEntry const& entry); void sessionStageChanged(); void selectedIndexChanged(int index); From c4f46c25d622b36cd37fa560b3b35de81daf4107 Mon Sep 17 00:00:00 2001 From: Abdullah Al-Soussi Date: Wed, 3 Mar 2021 07:16:18 -0500 Subject: [PATCH 2/4] MAYA-110196 - Multiple ProxyShapes with Same Stage (InStageData) Bug (PR comments fixes) --- lib/usd/ui/layerEditor/mayaSessionState.cpp | 3 +- lib/usd/ui/layerEditor/sessionState.h | 19 +------ .../ui/layerEditor/stageSelectorWidget.cpp | 57 ++++++++----------- lib/usd/ui/layerEditor/stageSelectorWidget.h | 2 +- 4 files changed, 28 insertions(+), 53 deletions(-) diff --git a/lib/usd/ui/layerEditor/mayaSessionState.cpp b/lib/usd/ui/layerEditor/mayaSessionState.cpp index 78db47da72..ed29595a67 100644 --- a/lib/usd/ui/layerEditor/mayaSessionState.cpp +++ b/lib/usd/ui/layerEditor/mayaSessionState.cpp @@ -32,7 +32,6 @@ #include #include - #ifdef THIS #undef THIS #endif @@ -226,7 +225,7 @@ void MayaSessionState::nodeRenamedCBOnIdle(std::string const& oldName, const MOb _currentStageEntry = entry; } - Q_EMIT stageRenamedSignal(oldName, entry); + Q_EMIT stageRenamedSignal(entry); } } } diff --git a/lib/usd/ui/layerEditor/sessionState.h b/lib/usd/ui/layerEditor/sessionState.h index e611289ede..bac9821cd3 100644 --- a/lib/usd/ui/layerEditor/sessionState.h +++ b/lib/usd/ui/layerEditor/sessionState.h @@ -56,23 +56,6 @@ class SessionState : public QObject _proxyShapePath = ""; } - StageEntry( - PXR_NS::UsdStageRefPtr const& stage, - std::string const& displayName, - std::string const& proxyShapePath) - { - _stage = stage; - _displayName = displayName; - _proxyShapePath = proxyShapePath; - } - - StageEntry(const StageEntry& entry) - { - _stage = entry._stage; - _displayName = entry._displayName; - _proxyShapePath = entry._proxyShapePath; - } - bool operator==(const StageEntry& entry) const { return ( @@ -130,7 +113,7 @@ class SessionState : public QObject Q_SIGNALS: void currentStageChangedSignal(); void stageListChangedSignal(StageEntry const& toSelect = StageEntry()); - void stageRenamedSignal(std::string const& oldName, StageEntry const& renamedEntry); + void stageRenamedSignal(StageEntry const& renamedEntry); void autoHideSessionLayerSignal(bool hideIt); void stageResetSignal(StageEntry const& entry); diff --git a/lib/usd/ui/layerEditor/stageSelectorWidget.cpp b/lib/usd/ui/layerEditor/stageSelectorWidget.cpp index a772557459..ded6b9307f 100644 --- a/lib/usd/ui/layerEditor/stageSelectorWidget.cpp +++ b/lib/usd/ui/layerEditor/stageSelectorWidget.cpp @@ -28,6 +28,24 @@ Q_DECLARE_METATYPE(UsdLayerEditor::SessionState::StageEntry); +namespace { +int getEntryIndexByProxyPath( + UsdLayerEditor::SessionState::StageEntry const& entry, + std::vector const& stages) +{ + auto it = std::find_if( + stages.begin(), stages.end(), [entry](UsdLayerEditor::SessionState::StageEntry stageEntry) { + return (entry._proxyShapePath == stageEntry._proxyShapePath); + }); + + if (it != stages.end()) { + return std::distance(stages.begin(), it); + } + + return -1; +} +} // namespace + namespace UsdLayerEditor { StageSelectorWidget::StageSelectorWidget(SessionState* in_sessionState, QWidget* in_parent) @@ -112,14 +130,8 @@ void StageSelectorWidget::selectedIndexChanged(int index) void StageSelectorWidget::sessionStageChanged() { if (!_internalChange) { - size_t index = -1; - for (size_t i = 0; i < _dropDown->count(); i++) { - auto const& data = _dropDown->itemData(i); - auto entry = data.value(); - if (entry == _sessionState->stageEntry()) { - index = i; - } - } + auto index + = getEntryIndexByProxyPath(_sessionState->stageEntry(), _sessionState->allStages()); if (index != -1) { QSignalBlocker blocker(_dropDown); _dropDown->setCurrentIndex(index); @@ -127,18 +139,9 @@ void StageSelectorWidget::sessionStageChanged() } } -void StageSelectorWidget::stageRenamed( - std::string const& oldName, - SessionState::StageEntry const& renamedEntry) +void StageSelectorWidget::stageRenamed(SessionState::StageEntry const& renamedEntry) { - size_t index = -1; - for (size_t i = 0; i < _dropDown->count(); i++) { - auto const& data = _dropDown->itemData(i); - auto entry = data.value(); - if (entry._displayName == oldName && entry._stage == renamedEntry._stage) { - index = i; - } - } + auto index = getEntryIndexByProxyPath(renamedEntry, _sessionState->allStages()); if (index != -1) { _dropDown->setItemText(index, renamedEntry._displayName.c_str()); _dropDown->setItemData(index, QVariant::fromValue(renamedEntry)); @@ -157,19 +160,9 @@ void StageSelectorWidget::stageReset(SessionState::StageEntry const& entry) return; } - std::vector allStages = _sessionState->allStages(); - auto it = std::find_if( - allStages.begin(), allStages.end(), [entry](SessionState::StageEntry stageEntry) { - return (entry._proxyShapePath == stageEntry._proxyShapePath); - }); - - if (it != allStages.end()) { - auto index = std::distance(allStages.begin(), it); - if (index < count) { - if (_dropDown->itemText(index) == QString::fromStdString((*it)._displayName)) { - _dropDown->setItemData(index, QVariant::fromValue(entry)); - } - } + auto index = getEntryIndexByProxyPath(entry, _sessionState->allStages()); + if (index >= 0 && index < count) { + _dropDown->setItemData(index, QVariant::fromValue(entry)); } } diff --git a/lib/usd/ui/layerEditor/stageSelectorWidget.h b/lib/usd/ui/layerEditor/stageSelectorWidget.h index 9b24a79d63..3b900055d3 100644 --- a/lib/usd/ui/layerEditor/stageSelectorWidget.h +++ b/lib/usd/ui/layerEditor/stageSelectorWidget.h @@ -43,7 +43,7 @@ class StageSelectorWidget : public QWidget // slot: void updateFromSessionState( SessionState::StageEntry const& entryToSelect = SessionState::StageEntry()); - void stageRenamed(std::string const& oldName, SessionState::StageEntry const& renamedEntry); + void stageRenamed(SessionState::StageEntry const& renamedEntry); void stageReset(SessionState::StageEntry const& entry); void sessionStageChanged(); void selectedIndexChanged(int index); From 5799b5029a067d20b6c2b82d8c3fccf85a074073 Mon Sep 17 00:00:00 2001 From: Abdullah Al-Soussi Date: Thu, 4 Mar 2021 07:12:08 -0500 Subject: [PATCH 3/4] MAYA-110196 - Multiple ProxyShapes with Same Stage (InStageData) - Moving to UUID --- lib/usd/ui/layerEditor/mayaSessionState.cpp | 22 +++++++++++++++---- lib/usd/ui/layerEditor/sessionState.h | 12 +++------- .../ui/layerEditor/stageSelectorWidget.cpp | 12 +++++----- 3 files changed, 27 insertions(+), 19 deletions(-) diff --git a/lib/usd/ui/layerEditor/mayaSessionState.cpp b/lib/usd/ui/layerEditor/mayaSessionState.cpp index ed29595a67..467b51c67a 100644 --- a/lib/usd/ui/layerEditor/mayaSessionState.cpp +++ b/lib/usd/ui/layerEditor/mayaSessionState.cpp @@ -19,7 +19,7 @@ #include "saveLayersDialog.h" #include "stringResources.h" -#include +#include #include #include @@ -27,7 +27,9 @@ #include #include #include +#include #include +#include #include #include @@ -69,7 +71,19 @@ void MayaSessionState::setStageEntry(StageEntry const& inEntry) bool MayaSessionState::getStageEntry(StageEntry* out_stageEntry, const MString& shapePath) { - auto prim = UsdMayaQuery::GetPrim(shapePath.asChar()); + pxr::UsdPrim prim; + + MObject shapeObj; + MStatus status = UsdMayaUtil::GetMObjectByName(shapePath.asChar(), shapeObj); + CHECK_MSTATUS_AND_RETURN(status, false); + MFnDagNode dagNode(shapeObj, &status); + CHECK_MSTATUS_AND_RETURN(status, false); + + if (const UsdMayaUsdPrimProvider* usdPrimProvider + = dynamic_cast(dagNode.userNode())) { + prim = usdPrimProvider->usdPrim(); + } + if (prim) { auto stage = prim.GetStage(); // debatable, but we remove the path|to|shape @@ -81,6 +95,7 @@ bool MayaSessionState::getStageEntry(StageEntry* out_stageEntry, const MString& } else { niceName = tokenList[0]; } + out_stageEntry->_id = dagNode.uuid().asString().asChar(); out_stageEntry->_stage = stage; out_stageEntry->_displayName = niceName.toStdString(); out_stageEntry->_proxyShapePath = shapePath.asChar(); @@ -220,8 +235,7 @@ void MayaSessionState::nodeRenamedCBOnIdle(std::string const& oldName, const MOb StageEntry entry; if (getStageEntry(&entry, shapePath)) { // Need to update the current Entry also - if (_currentStageEntry._displayName == oldName - && _currentStageEntry._stage == entry._stage) { + if (_currentStageEntry._id == entry._id) { _currentStageEntry = entry; } diff --git a/lib/usd/ui/layerEditor/sessionState.h b/lib/usd/ui/layerEditor/sessionState.h index bac9821cd3..745d1808bf 100644 --- a/lib/usd/ui/layerEditor/sessionState.h +++ b/lib/usd/ui/layerEditor/sessionState.h @@ -45,12 +45,14 @@ class SessionState : public QObject struct StageEntry { + std::string _id; PXR_NS::UsdStageRefPtr _stage; std::string _displayName; std::string _proxyShapePath; StageEntry() { + _id = ""; _stage = PXR_NS::UsdStageRefPtr(); _displayName = ""; _proxyShapePath = ""; @@ -59,20 +61,12 @@ class SessionState : public QObject bool operator==(const StageEntry& entry) const { return ( - _stage == entry._stage && _displayName == entry._displayName + _id == entry._id && _stage == entry._stage && _displayName == entry._displayName && _proxyShapePath == entry._proxyShapePath); } bool operator!=(const StageEntry& entry) const { return !(*this == entry); } - StageEntry& operator=(const StageEntry& entry) - { - _stage = entry._stage; - _displayName = entry._displayName; - _proxyShapePath = entry._proxyShapePath; - return *this; - } - void clear() { _stage = PXR_NS::UsdStageRefPtr(); diff --git a/lib/usd/ui/layerEditor/stageSelectorWidget.cpp b/lib/usd/ui/layerEditor/stageSelectorWidget.cpp index ded6b9307f..c0a5eaf983 100644 --- a/lib/usd/ui/layerEditor/stageSelectorWidget.cpp +++ b/lib/usd/ui/layerEditor/stageSelectorWidget.cpp @@ -26,16 +26,17 @@ #include #include + Q_DECLARE_METATYPE(UsdLayerEditor::SessionState::StageEntry); namespace { -int getEntryIndexByProxyPath( +int getEntryIndexById( UsdLayerEditor::SessionState::StageEntry const& entry, std::vector const& stages) { auto it = std::find_if( stages.begin(), stages.end(), [entry](UsdLayerEditor::SessionState::StageEntry stageEntry) { - return (entry._proxyShapePath == stageEntry._proxyShapePath); + return (entry._id == stageEntry._id); }); if (it != stages.end()) { @@ -130,8 +131,7 @@ void StageSelectorWidget::selectedIndexChanged(int index) void StageSelectorWidget::sessionStageChanged() { if (!_internalChange) { - auto index - = getEntryIndexByProxyPath(_sessionState->stageEntry(), _sessionState->allStages()); + auto index = getEntryIndexById(_sessionState->stageEntry(), _sessionState->allStages()); if (index != -1) { QSignalBlocker blocker(_dropDown); _dropDown->setCurrentIndex(index); @@ -141,7 +141,7 @@ void StageSelectorWidget::sessionStageChanged() void StageSelectorWidget::stageRenamed(SessionState::StageEntry const& renamedEntry) { - auto index = getEntryIndexByProxyPath(renamedEntry, _sessionState->allStages()); + auto index = getEntryIndexById(renamedEntry, _sessionState->allStages()); if (index != -1) { _dropDown->setItemText(index, renamedEntry._displayName.c_str()); _dropDown->setItemData(index, QVariant::fromValue(renamedEntry)); @@ -160,7 +160,7 @@ void StageSelectorWidget::stageReset(SessionState::StageEntry const& entry) return; } - auto index = getEntryIndexByProxyPath(entry, _sessionState->allStages()); + auto index = getEntryIndexById(entry, _sessionState->allStages()); if (index >= 0 && index < count) { _dropDown->setItemData(index, QVariant::fromValue(entry)); } From bb8e6b35f7bcfa65f0cdb838ba7c44745f69728c Mon Sep 17 00:00:00 2001 From: Abdullah Al-Soussi Date: Thu, 4 Mar 2021 11:40:28 -0500 Subject: [PATCH 4/4] MAYA-110196 - Multiple ProxyShapes with Same Stage (InStageData) - Formatting --- lib/usd/ui/layerEditor/mayaLayerEditorWindow.cpp | 2 +- lib/usd/ui/layerEditor/sessionState.h | 2 +- lib/usd/ui/layerEditor/stageSelectorWidget.cpp | 1 - 3 files changed, 2 insertions(+), 3 deletions(-) diff --git a/lib/usd/ui/layerEditor/mayaLayerEditorWindow.cpp b/lib/usd/ui/layerEditor/mayaLayerEditorWindow.cpp index 4c3e621972..8f599cafe6 100644 --- a/lib/usd/ui/layerEditor/mayaLayerEditorWindow.cpp +++ b/lib/usd/ui/layerEditor/mayaLayerEditorWindow.cpp @@ -44,7 +44,7 @@ class LayerEditorWindowCreator : public AbstractLayerEditorCreator { public: LayerEditorWindowCreator() { ; }; - virtual ~LayerEditorWindowCreator() {} + virtual ~LayerEditorWindowCreator() { } AbstractLayerEditorWindow* createWindow(const char* panelName) override; AbstractLayerEditorWindow* getWindow(const char* panelName) const override; diff --git a/lib/usd/ui/layerEditor/sessionState.h b/lib/usd/ui/layerEditor/sessionState.h index 745d1808bf..e6c46713e3 100644 --- a/lib/usd/ui/layerEditor/sessionState.h +++ b/lib/usd/ui/layerEditor/sessionState.h @@ -41,7 +41,7 @@ class SessionState : public QObject { Q_OBJECT public: - virtual ~SessionState() {} + virtual ~SessionState() { } struct StageEntry { diff --git a/lib/usd/ui/layerEditor/stageSelectorWidget.cpp b/lib/usd/ui/layerEditor/stageSelectorWidget.cpp index c0a5eaf983..e36f07fb7e 100644 --- a/lib/usd/ui/layerEditor/stageSelectorWidget.cpp +++ b/lib/usd/ui/layerEditor/stageSelectorWidget.cpp @@ -26,7 +26,6 @@ #include #include - Q_DECLARE_METATYPE(UsdLayerEditor::SessionState::StageEntry); namespace {