Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

When selection changes mark the prims which are added/removed from the list dirty. #1838

Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
37 changes: 11 additions & 26 deletions lib/mayaUsd/render/vp2RenderDelegate/basisCurves.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -540,13 +540,6 @@ void HdVP2BasisCurves::Sync(
HdDirtyBits* dirtyBits,
TfToken const& reprToken)
{
// We don't create a repr for the selection token because this token serves
// for selection state update only. Return early to reserve dirty bits so
// they can be used to sync regular reprs later.
if (reprToken == HdVP2ReprTokens->selection) {
return;
}

// We don't update the repr if it is hidden by the render tags (purpose)
// of the ProxyRenderDelegate. In additional, we need to hide any already
// existing render items because they should not be drawn.
Expand All @@ -572,6 +565,13 @@ void HdVP2BasisCurves::Sync(

const SdfPath& id = GetId();

// Update the selection status if it changed.
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This code was in initRepr, but it is not really any different from other code that has dirty flags so there is not a reason for it to be there.

if (*dirtyBits & DirtySelectionHighlight) {
_selectionStatus = drawScene.GetSelectionStatus(id);
} else {
TF_VERIFY(_selectionStatus == drawScene.GetSelectionStatus(id));
}

if (*dirtyBits & HdChangeTracker::DirtyMaterialId) {
const SdfPath materialId = delegate->GetMaterialId(id);

Expand Down Expand Up @@ -1525,11 +1525,6 @@ void HdVP2BasisCurves::_UpdateDrawItem(
*/
HdDirtyBits HdVP2BasisCurves::_PropagateDirtyBits(HdDirtyBits bits) const
{
// Visibility and selection result in highlight changes:
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

DirtySelection is gone, it was never really used properly. There is now only DirtySelectionHighlight and DirtySelectionMode.

if ((bits & HdChangeTracker::DirtyVisibility) && (bits & DirtySelection)) {
bits |= DirtySelectionHighlight;
}

if (bits & HdChangeTracker::AllDirty) {
// RPrim is dirty, propagate dirty bits to all draw items.
for (const std::pair<TfToken, HdReprSharedPtr>& pair : _reprs) {
Expand Down Expand Up @@ -1594,26 +1589,19 @@ void HdVP2BasisCurves::_InitRepr(TfToken const& reprToken, HdDirtyBits* dirtyBit
if (ARCH_UNLIKELY(!subSceneContainer))
return;

// Update selection state on demand or when it is a new Rprim. DirtySelection
// Update selection state on demand or when it is a new Rprim. DirtySelectionHighlight
// will be propagated to all draw items, to trigger sync for each repr.
if (reprToken == HdVP2ReprTokens->selection || _reprs.empty()) {
if (_reprs.empty()) {
const HdVP2SelectionStatus selectionStatus
= param->GetDrawScene().GetSelectionStatus(GetId());
if (_selectionStatus != selectionStatus) {
_selectionStatus = selectionStatus;
*dirtyBits |= DirtySelection;
*dirtyBits |= DirtySelectionHighlight;
} else if (_selectionStatus == kPartiallySelected) {
*dirtyBits |= DirtySelection;
*dirtyBits |= DirtySelectionHighlight;
}

// We don't create a repr for the selection token because it serves for
// selection state update only. Return from here.
if (reprToken == HdVP2ReprTokens->selection)
return;
}

// If the repr has any draw item with the DirtySelection bit, mark the
// DirtySelectionHighlight bit to invoke the synchronization call.
_ReprVector::iterator it
= std::find_if(_reprs.begin(), _reprs.end(), _ReprComparator(reprToken));
if (it != _reprs.end()) {
Expand All @@ -1633,9 +1621,6 @@ void HdVP2BasisCurves::_InitRepr(TfToken const& reprToken, HdDirtyBits* dirtyBit
// items to ensure proper Sync
drawItem->SetDirtyBits(HdChangeTracker::DirtyRepr);
}
if (drawItem->GetDirtyBits() & DirtySelection) {
*dirtyBits |= DirtySelectionHighlight;
}
}
}
return;
Expand Down
1 change: 0 additions & 1 deletion lib/mayaUsd/render/vp2RenderDelegate/basisCurves.h
Original file line number Diff line number Diff line change
Expand Up @@ -157,7 +157,6 @@ class HdVP2BasisCurves final : public HdBasisCurves

enum DirtyBits : HdDirtyBits
{
DirtySelection = MayaPrimCommon::DirtySelection,
DirtySelectionHighlight = MayaPrimCommon::DirtySelectionHighlight
};

Expand Down
3 changes: 1 addition & 2 deletions lib/mayaUsd/render/vp2RenderDelegate/mayaPrimCommon.h
Original file line number Diff line number Diff line change
Expand Up @@ -48,8 +48,7 @@ struct MayaPrimCommon
{
enum DirtyBits : HdDirtyBits
{
DirtySelection = HdChangeTracker::CustomBitsBegin,
DirtySelectionHighlight = (DirtySelection << 1),
DirtySelectionHighlight = HdChangeTracker::CustomBitsBegin,
DirtySelectionMode = (DirtySelectionHighlight << 1),
DirtyBitLast = DirtySelectionMode
};
Expand Down
111 changes: 68 additions & 43 deletions lib/mayaUsd/render/vp2RenderDelegate/mesh.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -465,6 +465,12 @@ void HdVP2Mesh::_PrepareSharedVertexBuffers(
const HdDirtyBits& rprimDirtyBits,
const TfToken& reprToken)
{
MProfilingScope profilingScope(
HdVP2RenderDelegate::sProfilerCategory,
MProfiler::kColorC_L2,
_rprimId.asChar(),
"HdVP2Mesh::_PrepareSharedVertexBuffers");

// Normals have two possible sources. They could be authored by the scene delegate,
// in which case we should find them in _primvarInfo, or they could be computed
// normals. Compute the normal buffer if necessary.
Expand Down Expand Up @@ -838,26 +844,22 @@ void HdVP2Mesh::Sync(
HdDirtyBits* dirtyBits,
const TfToken& reprToken)
{
// We don't create render items for the selection repr. The selection repr
// is used when the Sync call is made during a selection pass.
// When the selection mode changes, we DO want the chance to update our
// shaded render items (to support things like point snapping to similar instances), so make
// another call to Sync but with the smoothHull repr.
if (reprToken == HdVP2ReprTokens->selection) {
if (*dirtyBits & DirtySelectionMode) {
Sync(delegate, renderParam, dirtyBits, HdReprTokens->smoothHull);
}
return;
}
const SdfPath& id = GetId();
auto* const param = static_cast<HdVP2RenderParam*>(_delegate->GetRenderParam());
ProxyRenderDelegate& drawScene = param->GetDrawScene();
UsdImagingDelegate* usdImagingDelegate = drawScene.GetUsdImagingDelegate();

const SdfPath& id = GetId();
// Update the selection status if it changed.
if (*dirtyBits & DirtySelectionHighlight) {
_selectionStatus = drawScene.GetSelectionStatus(id);
} else {
TF_VERIFY(_selectionStatus == drawScene.GetSelectionStatus(id));
}

// We don't update the repr if it is hidden by the render tags (purpose)
// of the ProxyRenderDelegate. In additional, we need to hide any already
// existing render items because they should not be drawn.
auto* const param = static_cast<HdVP2RenderParam*>(_delegate->GetRenderParam());
ProxyRenderDelegate& drawScene = param->GetDrawScene();
HdRenderIndex& renderIndex = delegate->GetRenderIndex();
HdRenderIndex& renderIndex = delegate->GetRenderIndex();
if (!drawScene.DrawRenderTag(renderIndex.GetRenderTag(id))) {
_HideAllDrawItems(reprToken);
*dirtyBits &= ~(
Expand All @@ -884,8 +886,7 @@ void HdVP2Mesh::Sync(
for (const auto& geomSubset : _meshSharedData->_topology.GetGeomSubsets()) {
if (!geomSubset.materialId.IsEmpty()) {
const SdfPath materialId
= dynamic_cast<UsdImagingDelegate*>(delegate)->ConvertCachePathToIndexPath(
geomSubset.materialId);
= usdImagingDelegate->ConvertCachePathToIndexPath(geomSubset.materialId);
HdVP2Material* material = static_cast<HdVP2Material*>(
renderIndex.GetSprim(HdPrimTypeTokens->material, materialId));

Expand All @@ -896,15 +897,21 @@ void HdVP2Mesh::Sync(
}
#endif

_meshSharedData->_topology = GetMeshTopology(delegate);
{
MProfilingScope profilingScope(
HdVP2RenderDelegate::sProfilerCategory,
MProfiler::kColorC_L2,
_rprimId.asChar(),
"HdVP2Mesh::GetMeshTopology");
_meshSharedData->_topology = GetMeshTopology(delegate);
}

// subscribe to material updates from the new geom subset materials
#ifdef HDVP2_MATERIAL_CONSOLIDATION_UPDATE_WORKAROUND
for (const auto& geomSubset : _meshSharedData->_topology.GetGeomSubsets()) {
if (!geomSubset.materialId.IsEmpty()) {
const SdfPath materialId
= dynamic_cast<UsdImagingDelegate*>(delegate)->ConvertCachePathToIndexPath(
geomSubset.materialId);
= usdImagingDelegate->ConvertCachePathToIndexPath(geomSubset.materialId);
HdVP2Material* material = static_cast<HdVP2Material*>(
renderIndex.GetSprim(HdPrimTypeTokens->material, materialId));

Expand Down Expand Up @@ -988,8 +995,7 @@ void HdVP2Mesh::Sync(

for (const auto& geomSubset : _meshSharedData->_topology.GetGeomSubsets()) {
addRequiredPrimvars(
dynamic_cast<UsdImagingDelegate*>(delegate)->ConvertCachePathToIndexPath(
geomSubset.materialId));
usdImagingDelegate->ConvertCachePathToIndexPath(geomSubset.materialId));
}

// also, we always require points
Expand All @@ -1000,6 +1006,12 @@ void HdVP2Mesh::Sync(
}

if (HdChangeTracker::IsTopologyDirty(*dirtyBits, id)) {
MProfilingScope profilingScope(
HdVP2RenderDelegate::sProfilerCategory,
MProfiler::kColorC_L2,
_rprimId.asChar(),
"HdVP2Mesh Create Rendering Topology");

const HdMeshTopology& topology = _meshSharedData->_topology;
const VtIntArray& faceVertexIndices = topology.GetFaceVertexIndices();
const size_t numFaceVertexIndices = faceVertexIndices.size();
Expand Down Expand Up @@ -1208,11 +1220,6 @@ HdDirtyBits HdVP2Mesh::_PropagateDirtyBits(HdDirtyBits bits) const
bits |= HdChangeTracker::DirtyExtent;
}

// Visibility and selection result in highlight changes:
if ((bits & HdChangeTracker::DirtyVisibility) && (bits & DirtySelection)) {
bits |= DirtySelectionHighlight;
}

if (bits & HdChangeTracker::AllDirty) {
// RPrim is dirty, propagate dirty bits to all draw items.
for (const std::pair<TfToken, HdReprSharedPtr>& pair : _reprs) {
Expand Down Expand Up @@ -1281,26 +1288,19 @@ void HdVP2Mesh::_InitRepr(const TfToken& reprToken, HdDirtyBits* dirtyBits)
if (ARCH_UNLIKELY(!subSceneContainer))
return;

// Update selection state on demand or when it is a new Rprim. DirtySelection
// Update selection state when it is a new Rprim. DirtySelectionHighlight
// will be propagated to all draw items, to trigger sync for each repr.
if (reprToken == HdVP2ReprTokens->selection || _reprs.empty()) {
if (_reprs.empty()) {
const HdVP2SelectionStatus selectionStatus
= param->GetDrawScene().GetSelectionStatus(GetId());
if (_selectionStatus != selectionStatus) {
_selectionStatus = selectionStatus;
*dirtyBits |= DirtySelection;
*dirtyBits |= DirtySelectionHighlight;
} else if (_selectionStatus == kPartiallySelected) {
*dirtyBits |= DirtySelection;
*dirtyBits |= DirtySelectionHighlight;
}

// We don't create a repr for the selection token because it serves for
// selection state update only. Return from here.
if (reprToken == HdVP2ReprTokens->selection)
return;
}

// If the repr has any draw item with the DirtySelection bit, mark the
// DirtySelectionHighlight bit to invoke the synchronization call.
_ReprVector::const_iterator it
= std::find_if(_reprs.begin(), _reprs.end(), _ReprComparator(reprToken));
if (it != _reprs.end()) {
Expand All @@ -1321,9 +1321,6 @@ void HdVP2Mesh::_InitRepr(const TfToken& reprToken, HdDirtyBits* dirtyBits)
// items to ensure proper Sync
renderItemData.SetDirtyBits(HdChangeTracker::DirtyRepr);
}
if (renderItemData.GetDirtyBits() & DirtySelection) {
*dirtyBits |= DirtySelectionHighlight;
}
}
}
}
Expand Down Expand Up @@ -1606,6 +1603,12 @@ void HdVP2Mesh::_UpdateRepr(HdSceneDelegate* sceneDelegate, const TfToken& reprT
if (ARCH_UNLIKELY(!subSceneContainer))
return;

MProfilingScope profilingScope(
HdVP2RenderDelegate::sProfilerCategory,
MProfiler::kColorC_L2,
_rprimId.asChar(),
"HdVP2Mesh::_UpdateRepr");

_MeshReprConfig::DescArray reprDescs = _GetReprDesc(reprToken);

// For each relevant draw item, update dirty buffer sources.
Expand Down Expand Up @@ -1648,6 +1651,7 @@ void HdVP2Mesh::_UpdateDrawItem(

auto* const param = static_cast<HdVP2RenderParam*>(_delegate->GetRenderParam());
ProxyRenderDelegate& drawScene = param->GetDrawScene();
UsdImagingDelegate* usdImagingDelegate = drawScene.GetUsdImagingDelegate();

#ifdef MAYA_NEW_POINT_SNAPPING_SUPPORT
// We don't need to update the shaded selected instance item when the selection mode is not
Expand Down Expand Up @@ -1709,6 +1713,12 @@ void HdVP2Mesh::_UpdateDrawItem(
if (requiresIndexUpdate && (itemDirtyBits & HdChangeTracker::DirtyTopology)) {
const HdMeshTopology& topologyToUse = _meshSharedData->_renderingTopology;

MProfilingScope profilingScope(
HdVP2RenderDelegate::sProfilerCategory,
MProfiler::kColorC_L2,
_rprimId.asChar(),
"HdVP2Mesh prepare index buffer");

if (desc.geomStyle == HdMeshGeomStyleHull) {
// _trianglesFaceVertexIndices has the full triangulation calculated in
// _updateRepr. Find the triangles which represent faces in the matching
Expand Down Expand Up @@ -1795,8 +1805,7 @@ void HdVP2Mesh::_UpdateDrawItem(
SdfPath cachePathMaterialId = drawItemData._geomSubset.materialId;
// This is annoying! The saved materialId is a cache path, but to look up the
// material in the render index we need the index path.
materialId = dynamic_cast<UsdImagingDelegate*>(sceneDelegate)
->ConvertCachePathToIndexPath(cachePathMaterialId);
materialId = usdImagingDelegate->ConvertCachePathToIndexPath(cachePathMaterialId);
}
const HdVP2Material* material = static_cast<const HdVP2Material*>(
renderIndex.GetSprim(HdPrimTypeTokens->material, materialId));
Expand Down Expand Up @@ -1938,6 +1947,12 @@ void HdVP2Mesh::_UpdateDrawItem(
bool instancerWithNoInstances = false;
if (!GetInstancerId().IsEmpty()) {

MProfilingScope profilingScope(
HdVP2RenderDelegate::sProfilerCategory,
MProfiler::kColorC_L2,
_rprimId.asChar(),
"HdVP2Mesh Update instances");

// Retrieve instance transforms from the instancer.
HdInstancer* instancer = renderIndex.GetInstancer(GetInstancerId());
VtMatrix4dArray transforms
Expand Down Expand Up @@ -2092,6 +2107,10 @@ void HdVP2Mesh::_UpdateDrawItem(
}
}

TF_VERIFY(
stateToCommit._ufeIdentifiers.length()
== stateToCommit._instanceTransforms.length());

if (stateToCommit._instanceTransforms.length() == 0)
instancerWithNoInstances = true;
}
Expand Down Expand Up @@ -2512,6 +2531,12 @@ void HdVP2Mesh::_UpdatePrimvarSources(
HdDirtyBits dirtyBits,
const TfTokenVector& requiredPrimvars)
{
MProfilingScope profilingScope(
HdVP2RenderDelegate::sProfilerCategory,
MProfiler::kColorC_L2,
_rprimId.asChar(),
"HdVP2Mesh::_UpdatePrimvarSources");

const SdfPath& id = GetId();

auto updatePrimvarInfo
Expand Down
1 change: 0 additions & 1 deletion lib/mayaUsd/render/vp2RenderDelegate/mesh.h
Original file line number Diff line number Diff line change
Expand Up @@ -187,7 +187,6 @@ class HdVP2Mesh final : public HdMesh
DirtyFlatNormals = (DirtySmoothNormals << 1),
//! "Forward" the enumerated types here so we don't have to keep writing MayaPrimCommon in
//! the cpp file.
DirtySelection = MayaPrimCommon::DirtySelection,
DirtySelectionHighlight = MayaPrimCommon::DirtySelectionHighlight,
DirtySelectionMode = MayaPrimCommon::DirtySelectionMode
};
Expand Down
Loading