From 661ea9dab39d54b5b83719306f2fbd29a24ce6be Mon Sep 17 00:00:00 2001 From: Julien Frantz Date: Mon, 14 Oct 2024 12:49:47 +0200 Subject: [PATCH] UsdPreviewSurface shading nodes with opacityThreshold are now VP2 rendered as opaque. As discussed in PR [#3952](https://github.com/Autodesk/maya-usd/pull/3952). --- .../usdPreviewSurface.cpp | 58 ++++++++++++------- 1 file changed, 36 insertions(+), 22 deletions(-) diff --git a/lib/usd/pxrUsdPreviewSurface/usdPreviewSurface.cpp b/lib/usd/pxrUsdPreviewSurface/usdPreviewSurface.cpp index 13ea1c4092..8d2114e860 100644 --- a/lib/usd/pxrUsdPreviewSurface/usdPreviewSurface.cpp +++ b/lib/usd/pxrUsdPreviewSurface/usdPreviewSurface.cpp @@ -393,6 +393,8 @@ MStatus PxrMayaUsdPreviewSurface::initialize() status = attributeAffects(opacityAttr, outTransparencyOnAttr); CHECK_MSTATUS_AND_RETURN_IT(status); + status = attributeAffects(opacityThresholdAttr, outTransparencyOnAttr); + CHECK_MSTATUS_AND_RETURN_IT(status); return status; } @@ -461,32 +463,44 @@ MStatus PxrMayaUsdPreviewSurface::compute(const MPlug& plug, MDataBlock& dataBlo // details. We don't use the user-visible "outTransparency" attribute for transparency test // because its value depends on upstream nodes and thus error-prone when the "opacity" plug // is connected to certain textures. In that case, we should enable transparency. - bool opacityConnected = false; - const MObject opacityAttr - = depNodeFn.attribute(PxrMayaUsdPreviewSurfaceTokens->OpacityAttrName.GetText()); - const MPlug opacityPlug(thisMObject(), opacityAttr); - if (opacityPlug.isConnected()) { - const MPlug sourcePlug = opacityPlug.source(&status); - CHECK_MSTATUS(status); - const MObject sourceNode = sourcePlug.node(&status); - CHECK_MSTATUS(status); - - // Anim curve output will be evaluated to determine if transparency should be enabled. - if (!sourceNode.hasFn(MFn::kAnimCurve)) { - opacityConnected = true; - } - } + MObject opacityThresholdAttr = depNodeFn.attribute( + PxrMayaUsdPreviewSurfaceTokens->OpacityThresholdAttrName.GetText()); + const MDataHandle opacityThresholdData + = dataBlock.inputValue(opacityThresholdAttr, &status); + CHECK_MSTATUS(status); float transparencyOn = false; - if (opacityConnected) { - transparencyOn = true; - } else { - const MDataHandle opacityData = dataBlock.inputValue(opacityAttr, &status); - CHECK_MSTATUS(status); - const float opacity = opacityData.asFloat(); - if (opacity < 1.0f - std::numeric_limits::epsilon()) { + + // For masked transparency, we want VP2 to treat the shader as opaque. + if (opacityThresholdData.asFloat() <= 0.0f) { + bool opacityConnected = false; + + const MObject opacityAttr + = depNodeFn.attribute(PxrMayaUsdPreviewSurfaceTokens->OpacityAttrName.GetText()); + const MPlug opacityPlug(thisMObject(), opacityAttr); + if (opacityPlug.isConnected()) { + const MPlug sourcePlug = opacityPlug.source(&status); + CHECK_MSTATUS(status); + const MObject sourceNode = sourcePlug.node(&status); + CHECK_MSTATUS(status); + + // Anim curve output will be evaluated to determine if transparency should be + // enabled. + if (!sourceNode.hasFn(MFn::kAnimCurve)) { + opacityConnected = true; + } + } + + if (opacityConnected) { transparencyOn = true; + } else { + const MDataHandle opacityData = dataBlock.inputValue(opacityAttr, &status); + CHECK_MSTATUS(status); + const float opacity = opacityData.asFloat(); + if (opacity < 1.0f - std::numeric_limits::epsilon()) { + transparencyOn = true; + } } }