12 import maya.api.OpenMaya 
as om
 
   13 import maya.api.OpenMayaRender 
as omr
 
   25     The presence of this function tells Maya that the plugin produces, and 
   26     expects to be passed, objects created using the Maya Python API 2.0. 
   33 class depthShader(om.MPxNode):
 
   35     id = om.MTypeId( 0x81002 )
 
   53         nAttr = om.MFnNumericAttribute()
 
   57         depthShader.aColorNear = nAttr.createColor(
"color", 
"c")
 
   62         nAttr.default = (0.0, 1.0, 0.0)         
 
   65         depthShader.aColorFar = nAttr.createColor(
"colorFar", 
"cf")
 
   70         nAttr.default = (0.0, 0.0, 1.0)         
 
   72         depthShader.aNear = nAttr.create(
"near", 
"n", om.MFnNumericData.kFloat)
 
   78         nAttr.setSoftMax(1000.0)
 
   80         depthShader.aFar = nAttr.create(
"far", 
"f", om.MFnNumericData.kFloat)
 
   86         nAttr.setSoftMax(1000.0)
 
   89         depthShader.aPointCamera = nAttr.createPoint(
"pointCamera", 
"p")
 
   97         depthShader.aOutColor = nAttr.createColor(
"outColor", 
"oc")
 
   99         nAttr.storable = 
False 
  100         nAttr.readable = 
True 
  101         nAttr.writable = 
False 
  103         om.MPxNode.addAttribute(depthShader.aColorNear)
 
  104         om.MPxNode.addAttribute(depthShader.aColorFar)
 
  105         om.MPxNode.addAttribute(depthShader.aNear)
 
  106         om.MPxNode.addAttribute(depthShader.aFar)
 
  107         om.MPxNode.addAttribute(depthShader.aPointCamera)
 
  108         om.MPxNode.addAttribute(depthShader.aOutColor)
 
  110         om.MPxNode.attributeAffects(depthShader.aColorNear, depthShader.aOutColor)
 
  111         om.MPxNode.attributeAffects(depthShader.aColorFar, depthShader.aOutColor)
 
  112         om.MPxNode.attributeAffects(depthShader.aNear, depthShader.aOutColor)
 
  113         om.MPxNode.attributeAffects(depthShader.aFar, depthShader.aOutColor)
 
  114         om.MPxNode.attributeAffects(depthShader.aPointCamera, depthShader.aOutColor)
 
  117         om.MPxNode.__init__(self)
 
  119     def compute(self, plug, block):
 
  121         if (plug != depthShader.aOutColor) 
and (plug.parent() != depthShader.aOutColor):
 
  125         pCamera   = block.inputValue(depthShader.aPointCamera).asFloatVector()
 
  126         cNear     = block.inputValue(depthShader.aColorNear).asFloatVector()
 
  127         cFar      = block.inputValue(depthShader.aColorFar).asFloatVector()
 
  128         nearClip  = block.inputValue(depthShader.aNear).asFloat()
 
  129         farClip   = block.inputValue(depthShader.aFar).asFloat()
 
  133         dist = farClip - nearClip
 
  135             ratio = (farClip + pCamera.z) / dist
 
  136         resultColor = cNear * ratio + cFar*(1.0 - ratio)
 
  139         outColorHandle = block.outputValue( depthShader.aOutColor )
 
  140         outColorHandle.setMFloatVector( resultColor )
 
  141         outColorHandle.setClean()
 
  146     def postConstructor(self):
 
  152 class depthShaderOverride(omr.MPxSurfaceShadingNodeOverride):
 
  155         return depthShaderOverride(obj)
 
  157     def __init__(self, obj):
 
  158         omr.MPxSurfaceShadingNodeOverride.__init__(self, obj)
 
  161         fragmentMgr = omr.MRenderer.getFragmentManager()
 
  162         if fragmentMgr != 
None:
 
  163             if not fragmentMgr.hasFragment(
"depthShaderPluginFragment"):
 
  164                 fragmentBody  = textwrap.dedent(
""" 
  165                     <fragment uiName=\"depthShaderPluginFragment\" name=\"depthShaderPluginFragment\" type=\"plumbing\" class=\"ShadeFragment\" version=\"1.0\"> 
  166                         <description><![CDATA[Depth shader fragment]]></description> 
  168                             <float name=\"depthValue\" /> 
  169                             <float3 name=\"color\" /> 
  170                             <float3 name=\"colorFar\" /> 
  171                             <float name=\"near\" /> 
  172                             <float name=\"far\" /> 
  175                             <float name=\"depthValue\" value=\"0.0\" /> 
  176                             <float3 name=\"color\" value=\"0.0,1.0,0.0\" /> 
  177                             <float3 name=\"colorFar\" value=\"0.0,0.0,1.0\" /> 
  178                             <float name=\"near\" value=\"0.0\" /> 
  179                             <float name=\"far\" value=\"2.0\" /> 
  182                             <float3 name=\"outColor\" /> 
  185                             <implementation render=\"OGSRenderer\" language=\"Cg\" lang_version=\"2.1\"> 
  186                                 <function_name val=\"depthShaderPluginFragment\" /> 
  188                                     float3 depthShaderPluginFragment(float depthValue, float3 cNear, float3 cFar, float nearClip, float farClip) \n 
  190                                         float ratio = (farClip + depthValue)/(farClip - nearClip); \n 
  191                                         return cNear*ratio + cFar*(1.0f - ratio); \n 
  195                             <implementation render=\"OGSRenderer\" language=\"HLSL\" lang_version=\"11.0\"> 
  196                                 <function_name val=\"depthShaderPluginFragment\" /> 
  198                                     float3 depthShaderPluginFragment(float depthValue, float3 cNear, float3 cFar, float nearClip, float farClip) \n 
  200                                         float ratio = (farClip + depthValue)/(farClip - nearClip); \n 
  201                                         return cNear*ratio + cFar*(1.0f - ratio); \n 
  205                             <implementation render=\"OGSRenderer\" language=\"GLSL\" lang_version=\"3.0\"> 
  206                                 <function_name val=\"depthShaderPluginFragment\" /> 
  208                                     vec3 depthShaderPluginFragment(float depthValue, vec3 cNear, vec3 cFar, float nearClip, float farClip) \n 
  210                                         float ratio = (farClip + depthValue)/(farClip - nearClip); \n 
  211                                         return cNear*ratio + cFar*(1.0f - ratio); \n 
  218                 fragmentMgr.addShadeFragmentFromBuffer(fragmentBody, 
False)
 
  220             if not fragmentMgr.hasFragment(
"depthShaderPluginInterpolantFragment"):
 
  221                 vertexFragmentBody  = textwrap.dedent(
""" 
  222                     <fragment uiName=\"depthShaderPluginInterpolantFragment\" name=\"depthShaderPluginInterpolantFragment\" type=\"interpolant\" class=\"ShadeFragment\" version=\"1.0\"> 
  223                         <description><![CDATA[Depth shader vertex fragment]]></description> 
  225                             <float3 name=\"Pm\" semantic=\"Pm\" flags=\"varyingInputParam\" /> 
  226                             <float4x4 name=\"worldViewProj\" semantic=\"worldviewprojection\" /> 
  231                             <float name=\"outDepthValue\" ^1s/> 
  234                             <implementation render=\"OGSRenderer\" language=\"Cg\" lang_version=\"2.1\"> 
  235                                 <function_name val=\"depthShaderPluginInterpolantFragment\" /> 
  237                                     float depthShaderPluginInterpolantFragment(float depthValue) \n 
  239                                         return depthValue; \n 
  242                                 <vertex_source><![CDATA[ 
  243                                     float idepthShaderPluginInterpolantFragment(float3 Pm, float4x4 worldViewProj) \n 
  245                                         float4 pCamera = mul(worldViewProj, float4(Pm, 1.0f)); \n 
  246                                         return (pCamera.z - pCamera.w*2.0f); \n 
  250                             <implementation render=\"OGSRenderer\" language=\"HLSL\" lang_version=\"11.0\"> 
  251                                 <function_name val=\"depthShaderPluginInterpolantFragment\" /> 
  253                                     float depthShaderPluginInterpolantFragment(float depthValue) \n 
  255                                         return depthValue; \n 
  258                                 <vertex_source><![CDATA[ 
  259                                     float idepthShaderPluginInterpolantFragment(float3 Pm, float4x4 worldViewProj) \n 
  261                                         float4 pCamera = mul(float4(Pm, 1.0f), worldViewProj); \n 
  262                                         return (pCamera.z - pCamera.w*2.0f); \n 
  266                             <implementation render=\"OGSRenderer\" language=\"GLSL\" lang_version=\"3.0\"> 
  267                                 <function_name val=\"depthShaderPluginInterpolantFragment\" /> 
  269                                     float depthShaderPluginInterpolantFragment(float depthValue) \n 
  271                                         return depthValue; \n 
  274                                 <vertex_source><![CDATA[ 
  275                                     float idepthShaderPluginInterpolantFragment(vec3 Pm, mat4 worldViewProj) \n 
  277                                         vec4 pCamera = worldViewProj * vec4(Pm, 1.0f); \n 
  278                                         return (pCamera.z - pCamera.w*2.0f); \n 
  286                 if omr.MRenderer.drawAPI() == omr.MRenderer.kDirectX11:
 
  287                     vertexFragmentBody = replace(vertexFragmentBody, 
"^1s", 
"semantic=\"extraDepth\" ")
 
  289                     vertexFragmentBody = replace(vertexFragmentBody, 
"^1s", 
" ")
 
  291                 fragmentMgr.addShadeFragmentFromBuffer(vertexFragmentBody, 
False)
 
  293             if not fragmentMgr.hasFragment(
"depthShaderPluginGraph"):
 
  294                 fragmentGraphBody  = textwrap.dedent(
""" 
  295                     <fragment_graph name=\"depthShaderPluginGraph\" ref=\"depthShaderPluginGraph\" class=\"FragmentGraph\" version=\"1.0\"> 
  297                                 <fragment_ref name=\"depthShaderPluginFragment\" ref=\"depthShaderPluginFragment\" /> 
  298                                 <fragment_ref name=\"depthShaderPluginInterpolantFragment\" ref=\"depthShaderPluginInterpolantFragment\" /> 
  301                             <connect from=\"depthShaderPluginInterpolantFragment.outDepthValue\" to=\"depthShaderPluginFragment.depthValue\" /> 
  304                             <float3 name=\"Pm\" ref=\"depthShaderPluginInterpolantFragment.Pm\" semantic=\"Pm\" flags=\"varyingInputParam\" /> 
  305                             <float4x4 name=\"worldViewProj\" ref=\"depthShaderPluginInterpolantFragment.worldViewProj\" semantic=\"worldviewprojection\" /> 
  306                             <float3 name=\"color\" ref=\"depthShaderPluginFragment.color\" /> 
  307                             <float3 name=\"colorFar\" ref=\"depthShaderPluginFragment.colorFar\" /> 
  308                             <float name=\"near\" ref=\"depthShaderPluginFragment.near\" /> 
  309                             <float name=\"far\" ref=\"depthShaderPluginFragment.far\" /> 
  312                             <float3 name=\"color\" value=\"0.0,1.0,0.0\" /> 
  313                             <float3 name=\"colorFar\" value=\"0.0,0.0,1.0\" /> 
  314                             <float name=\"near\" value=\"0.0\" /> 
  315                             <float name=\"far\" value=\"2.0\" /> 
  318                             <float3 name=\"outColor\" ref=\"depthShaderPluginFragment.outColor\" /> 
  320                     </fragment_graph>""")
 
  322                 fragmentMgr.addFragmentGraphFromBuffer(fragmentGraphBody)
 
  324     def supportedDrawAPIs(self):
 
  325         return omr.MRenderer.kOpenGL | omr.MRenderer.kOpenGLCoreProfile | omr.MRenderer.kDirectX11
 
  327     def fragmentName(self):
 
  328         return "depthShaderPluginGraph" 
  333 sRegistrantId = 
"depthShaderPlugin" 
  335 def initializePlugin(obj):
 
  336     plugin = om.MFnPlugin(obj, 
"Autodesk", 
"4.5", 
"Any")
 
  338         userClassify = 
"shader/surface:drawdb/shader/surface/depthShader" 
  339         plugin.registerNode(
"depthShader", depthShader.id, depthShader.creator, depthShader.initialize, om.MPxNode.kDependNode, userClassify)
 
  341         sys.stderr.write(
"Failed to register node\n")
 
  346         omr.MDrawRegistry.registerSurfaceShadingNodeOverrideCreator(
"drawdb/shader/surface/depthShader", sRegistrantId, depthShaderOverride.creator)
 
  348         sys.stderr.write(
"Failed to register override\n")
 
  351 def uninitializePlugin(obj):
 
  352     plugin = om.MFnPlugin(obj)
 
  354         plugin.deregisterNode(depthShader.id)
 
  356         sys.stderr.write(
"Failed to deregister node\n")
 
  361         omr.MDrawRegistry.deregisterSurfaceShadingNodeOverrideCreator(
"drawdb/shader/surface/depthShader", sRegistrantId)
 
  363         sys.stderr.write(
"Failed to deregister override\n")