#include <maya/MPxNode.h>
#include <maya/MFnPlugin.h>
#include <maya/MIOStream.h>
#include <maya/MDrawRegistry.h>
#include <maya/MFnNumericAttribute.h>
#include <maya/MFnLightDataAttribute.h>
#include <algorithm>
#include "onbShaderOverride.h"
{
public:
static void* creator();
static MString drawDbClassification;
OnbShader();
~OnbShader() override;
private:
static MObject aLightShadowFraction;
static MObject aPreShadowIntensity;
};
MString OnbShader::nodeName(
"onbShader");
MString OnbShader::drawDbClassification(
"drawdb/shader/surface/onbShader");
MString OnbShader::classification(
"shader/surface:" + drawDbClassification);
MObject OnbShader::aOutTransparency;
MObject OnbShader::aSpecularRollOff;
MObject OnbShader::aLightDirection;
MObject OnbShader::aLightIntensity;
MObject OnbShader::aLightShadowFraction;
MObject OnbShader::aPreShadowIntensity;
MObject OnbShader::aLightBlindData;
#define MAKE_INPUT(attr) \
CHECK_MSTATUS(attr.setKeyable(true)); \
CHECK_MSTATUS(attr.setStorable(true)); \
CHECK_MSTATUS(attr.setReadable(true)); \
CHECK_MSTATUS(attr.setWritable(true));
#define MAKE_OUTPUT(attr) \
CHECK_MSTATUS(attr.setKeyable(false)); \
CHECK_MSTATUS(attr.setStorable(false)); \
CHECK_MSTATUS(attr.setReadable(true)); \
CHECK_MSTATUS(attr.setWritable(false));
void OnbShader::postConstructor()
{
setMPSafe(true);
}
OnbShader::OnbShader()
{
}
OnbShader::~OnbShader()
{
}
void* OnbShader::creator()
{
return new OnbShader();
}
{
aOutColor = nAttr.
create(
"outColor",
"oc", outcR, outcG, outcB);
MAKE_OUTPUT(nAttr);
aOutTransparency = nAttr.
create(
"outTransparency",
"ot", outtR, outtG, outtB);
MAKE_OUTPUT(nAttr);
aColor = nAttr.
create(
"color",
"c", cR, cG, cB);
MAKE_INPUT(nAttr);
MAKE_INPUT(nAttr);
aTransparency = nAttr.
create(
"transparency",
"it", tR, tG, tB);
MAKE_INPUT(nAttr);
aAmbientColor = nAttr.
create(
"ambientColor",
"ambc", aR, aG, aB);
MAKE_INPUT(nAttr);
aIncandescence = nAttr.
create(
"incandescence",
"ic", iR, iG, iB);
MAKE_INPUT(nAttr);
aSpecularColor = nAttr.
create(
"specularColor",
"sc", sR, sG, sB);
MAKE_INPUT(nAttr);
MAKE_INPUT(nAttr);
MAKE_INPUT(nAttr);
aNormalCamera = nAttr.
createPoint(
"normalCamera",
"n");
MAKE_INPUT(nAttr);
aRayDirection = nAttr.
createPoint(
"rayDirection",
"rd");
MAKE_INPUT(nAttr);
aLightDirection = nAttr.
createPoint(
"lightDirection",
"ld");
aLightIntensity = nAttr.
createColor(
"lightIntensity",
"li");
aLightBlindData = nAttr.
createAddr(
"lightBlindData",
"lbld");
aLightData = lAttr.
create(
"lightDataArray",
"ltd",
aLightDirection,
aLightIntensity,
aLightAmbient,
aLightDiffuse,
aLightSpecular,
aLightShadowFraction,
aPreShadowIntensity,
aLightBlindData);
CHECK_MSTATUS(lAttr.
setDefault(0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f,
true,
true,
false, 0.0f, 1.0f, NULL));
CHECK_MSTATUS(attributeAffects(aTransparency, aOutTransparency));
CHECK_MSTATUS(attributeAffects(aAmbientColor, aOutTransparency));
CHECK_MSTATUS(attributeAffects(aIncandescence, aOutTransparency));
CHECK_MSTATUS(attributeAffects(aSpecularColor, aOutTransparency));
CHECK_MSTATUS(attributeAffects(aEccentricity, aOutTransparency));
CHECK_MSTATUS(attributeAffects(aNormalCamera, aOutTransparency));
CHECK_MSTATUS(attributeAffects(aRayDirection, aOutTransparency));
CHECK_MSTATUS(attributeAffects(aSpecularRollOff, aOutTransparency));
CHECK_MSTATUS(attributeAffects(aLightDirection, aOutTransparency));
CHECK_MSTATUS(attributeAffects(aLightIntensity, aOutTransparency));
CHECK_MSTATUS(attributeAffects(aLightAmbient, aOutTransparency));
CHECK_MSTATUS(attributeAffects(aLightDiffuse, aOutTransparency));
CHECK_MSTATUS(attributeAffects(aLightSpecular, aOutTransparency));
CHECK_MSTATUS(attributeAffects(aLightShadowFraction, aOutColor));
CHECK_MSTATUS(attributeAffects(aLightShadowFraction, aOutTransparency));
CHECK_MSTATUS(attributeAffects(aPreShadowIntensity, aOutTransparency));
CHECK_MSTATUS(attributeAffects(aLightBlindData, aOutTransparency));
return MS::kSuccess;
}
{
if (plug != aOutColor && plug.
parent() != aOutColor &&
plug != aOutTransparency && plug.
parent() != aOutTransparency)
{
return MS::kUnknownParameter;
}
const float NV = viewDirection*surfaceNormal;
const float acosNV = acosf(NV);
const float roughnessSq = roughness*roughness;
const float A = 1.0f - 0.5f*(roughnessSq/(roughnessSq + 0.57f));
const float B = 0.45f*(roughnessSq/(roughnessSq + 0.09f));
for (int count=1; count<=numLights; count++)
{
{
const float NL = lightDirection*surfaceNormal;
const float acosNL = acosf(NL);
const float alpha = std::max(acosNV, acosNL);
const float beta = std::min(acosNV, acosNL);
const float gamma =
(viewDirection - (surfaceNormal*NV)) *
(lightDirection - (surfaceNormal*NL));
const float C = sinf(alpha)*tanf(beta);
const float factor =
std::max(0.0f, NL)*(A + B*std::max(0.0f, gamma)*C);
resultColor += lightIntensity*factor;
}
if (count < numLights)
{
status = lightData.
next();
}
}
resultColor[0] = resultColor[0]*surfaceColor[0];
resultColor[1] = resultColor[1]*surfaceColor[1];
resultColor[2] = resultColor[2]*surfaceColor[2];
if (plug == aOutColor || plug.
parent() == aOutColor)
{
outColor = resultColor;
}
if (plug == aOutTransparency || plug.
parent() == aOutTransparency)
{
outTrans = transparency;
}
return MS::kSuccess;
}
static const MString sRegistrantId(
"onbShaderPlugin");
{
MFnPlugin plugin(obj, PLUGIN_COMPANY,
"1.0",
"Any");
OnbShader::nodeName,
OnbShader::id,
OnbShader::creator,
OnbShader::initialize,
&OnbShader::classification));
OnbShader::drawDbClassification,
sRegistrantId,
onbShaderOverride::creator));
return MS::kSuccess;
}
{
OnbShader::drawDbClassification,
sRegistrantId));
return MS::kSuccess;
}