#ifdef WIN32
#pragma warning( disable : 4786 ) // Disable STL warnings.
#endif
#include <maya/MIOStream.h>
#include <math.h>
#include <maya/MString.h>
#include <maya/MPlug.h>
#include <maya/MDataBlock.h>
#include <maya/MDataHandle.h>
#include <maya/MFnNumericAttribute.h>
#include <maya/MFnTypedAttribute.h>
#include <maya/MFloatVector.h>
#include <maya/MStringArray.h>
#include <maya/MFnPlugin.h>
#include <maya/MPxHwShaderNode.h>
#include <maya/MRenderUtilities.h>
#include <maya/MStringArray.h>
#include <maya/MFnMesh.h>
#include <maya/MGlobal.h>
#include <maya/MFloatPoint.h>
#include <maya/MFloatPointArray.h>
#include <maya/MHardwareRenderer.h>
#include <maya/MGeometryData.h>
#include <maya/MDrawRegistry.h>
#include <maya/MPxShaderOverride.h>
#include <maya/MDrawContext.h>
#include <maya/MStateManager.h>
#include <maya/MGLdefinitions.h>
#include <maya/MGLFunctionTable.h>
#include <maya/MHWGeometryUtilities.h>
#include <maya/MHWShaderSwatchGenerator.h>
#include <maya/MGL.h>
{
glPushAttrib(GL_ALL_ATTRIB_BITS);
{
glDisable( GL_LIGHTING );
glColor3f( color.
r, color.
g, color.
b);
glBegin( GL_LINE_STRIP );
glVertex3f( min.
x, min.
y, min.
z );
glVertex3f( max.
x, min.
y, min.
z );
glVertex3f( max.
x, max.
y, min.
z );
glVertex3f( min.
x, max.
y, min.
z );
glVertex3f( min.
x, min.
y, min.
z );
glVertex3f( min.
x, min.
y, max.
z );
glVertex3f( min.
x, max.
y, max.
z );
glVertex3f( min.
x, max.
y, min.
z );
glVertex3f( max.
x, max.
y, min.
z );
glVertex3f( max.
x, max.
y, max.
z );
glVertex3f( max.
x, min.
y, max.
z );
glVertex3f( max.
x, min.
y, min.
z );
glVertex3f( max.
x, min.
y, max.
z );
glVertex3f( min.
x, min.
y, max.
z );
glVertex3f( min.
x, max.
y, max.
z );
glVertex3f( max.
x, max.
y, max.
z );
glEnd();
}
glPopAttrib();
}
static const MString sHWCPVShaderRegistrantId(
"HWCPVShaderRegistrantId");
{
public:
hwColorPerVertexShader();
~hwColorPerVertexShader() override;
int prim,
unsigned int writable,
int indexCount,
const unsigned int * indexArray,
int vertexCount,
const int * vertexIDs,
const float * vertexArray,
int normalCount,
const float ** normalArrays,
int colorCount,
const float ** colorArrays,
int texCoordCount,
const float ** texCoordArrays) override;
int prim,
unsigned int writable,
int indexCount,
const unsigned int * indexArray,
int vertexCount,
const int * vertexIDs,
const float * vertexArray,
int normalCount,
const float ** normalArrays,
int colorCount,
const float ** colorArrays,
int texCoordCount,
const float ** texCoordArrays) override;
unsigned int* pIndexing,
unsigned int numberOfData,
unsigned int indexCount );
unsigned int writable,
int indexCount,
const unsigned int * indexArray,
int vertexCount,
const float * vertexArray,
int colorCount,
const float ** colorArrays);
const MString& colorSetName()
const{
return mColorSetName;}
static void * creator();
bool wantDrawBoundingBox() const { return mDrawBoundingBox; }
private:
void getFloat(
MObject attr,
float & val)
const;
float3 mColorGain;
float3 mColorBias;
float mTranspGain;
float mTranspBias;
unsigned int mNormalsPerVertex;
unsigned int mColorsPerVertex;
float mTexRotateX;
float mTexRotateY;
float mTexRotateZ;
bool mDrawBoundingBox;
GLuint mSampleImageId;
bool mAttributesChanged;
};
MTypeId hwColorPerVertexShader::id( 0x00105450 );
MObject hwColorPerVertexShader::aColorGain;
MObject hwColorPerVertexShader::aTranspGain;
MObject hwColorPerVertexShader::aColorBias;
MObject hwColorPerVertexShader::aTranspBias;
MObject hwColorPerVertexShader::aNormalsPerVertex;
MObject hwColorPerVertexShader::aColorsPerVertex;
MObject hwColorPerVertexShader::aColorSetName;
MObject hwColorPerVertexShader::aTexRotateX;
MObject hwColorPerVertexShader::aTexRotateY;
MObject hwColorPerVertexShader::aTexRotateZ;
MObject hwColorPerVertexShader::aDrawBoundingBox;
void hwColorPerVertexShader::postConstructor( )
{
setMPSafe(false);
}
hwColorPerVertexShader::hwColorPerVertexShader()
{
mColorGain[0] = mColorGain[1] = mColorGain[2] = 1.0f;
mColorBias[0] = mColorBias[1] = mColorBias[2] = 0.0f;
mTranspGain = 1.0f;
mTranspBias = 0.0f;
mAttributesChanged = false;
mNormalsPerVertex = 0;
mColorsPerVertex = 0;
mSampleImage = 0;
mSampleImageId = 0;
mTexRotateX = 0.0f;
mTexRotateY = 0.0f;
mTexRotateZ = 0.0f;
mDrawBoundingBox = false;
}
hwColorPerVertexShader::~hwColorPerVertexShader()
{
if ( mSampleImageId > 0 )
glDeleteTextures(1, &mSampleImageId );
}
void * hwColorPerVertexShader::creator()
{
return new hwColorPerVertexShader();
}
bool
hwColorPerVertexShader::setInternalValue(
const MPlug& plug,
const MDataHandle& handle )
{
bool handledAttribute = false;
if (plug == aNormalsPerVertex)
{
handledAttribute = true;
mNormalsPerVertex = (
unsigned int) handle.
asInt();
}
else if (plug == aColorsPerVertex)
{
handledAttribute = true;
mColorsPerVertex = (
unsigned int) handle.
asInt();
}
else if (plug == aColorSetName)
{
handledAttribute = true;
}
else if (plug == aTexRotateX)
{
handledAttribute = true;
}
else if (plug == aTexRotateY)
{
handledAttribute = true;
}
else if (plug == aTexRotateZ)
{
handledAttribute = true;
}
else if (plug == aColorGain)
{
handledAttribute = true;
if (val[0] != mColorGain[0] ||
val[1] != mColorGain[1] ||
val[2] != mColorGain[2])
{
mColorGain[0] = val[0];
mColorGain[1] = val[1];
mColorGain[2] = val[2];
mAttributesChanged = true;
}
}
else if (plug == aColorBias)
{
handledAttribute = true;
if (val[0] != mColorBias[0] ||
val[1] != mColorBias[1] ||
val[2] != mColorBias[2])
{
mColorBias[0] = val[0];
mColorBias[1] = val[1];
mColorBias[2] = val[2];
mAttributesChanged = true;
}
}
else if (plug == aTranspGain)
{
handledAttribute = true;
if (val != mTranspGain)
{
mTranspGain = val;
mAttributesChanged = true;
}
}
else if (plug == aTranspBias)
{
handledAttribute = true;
if (val != mTranspBias)
{
mTranspBias = val;
mAttributesChanged = true;
}
}
else if( plug == aDrawBoundingBox )
{
handledAttribute = true;
if( val != mDrawBoundingBox )
{
mDrawBoundingBox = val;
mAttributesChanged = true;
}
}
return handledAttribute;
}
bool
hwColorPerVertexShader::getInternalValue(
const MPlug& plug,
MDataHandle& handle )
{
bool handledAttribute = false;
if (plug == aColorGain)
{
handledAttribute = true;
handle.
set( mColorGain[0], mColorGain[1], mColorGain[2] );
}
else if (plug == aColorBias)
{
handledAttribute = true;
handle.
set( mColorBias[0], mColorBias[1], mColorBias[2] );
}
else if (plug == aTranspGain)
{
handledAttribute = true;
handle.
set( mTranspGain );
}
else if (plug == aTranspBias)
{
handledAttribute = true;
handle.
set( mTranspBias );
}
else if (plug == aNormalsPerVertex)
{
handledAttribute = true;
handle.
set( (
int)mNormalsPerVertex );
}
else if (plug == aColorsPerVertex)
{
handledAttribute = true;
handle.
set( (
int)mColorsPerVertex );
}
else if (plug == aColorSetName)
{
handledAttribute = true;
handle.
set( mColorSetName );
}
else if (plug == aTexRotateX)
{
handledAttribute = true;
handle.
set( mTexRotateX );
}
else if (plug == aTexRotateY)
{
handledAttribute = true;
handle.
set( mTexRotateY );
}
else if (plug == aTexRotateZ)
{
handledAttribute = true;
handle.
set( mTexRotateZ );
}
else if( plug == aDrawBoundingBox )
{
handledAttribute = true;
handle.
set( mDrawBoundingBox );
}
return handledAttribute;
}
MStatus hwColorPerVertexShader::initialize()
{
aColorGain = nAttr.
createColor(
"colorGain",
"cg", &status);
aTranspGain = nAttr.
create(
"transparencyGain",
"tg",
aColorBias = nAttr.
createColor(
"colorBias",
"cb", &status);
aTranspBias = nAttr.
create(
"transparencyBias",
"tb",
aNormalsPerVertex = nAttr.
create(
"normalsPerVertex",
"nv",
aColorsPerVertex = nAttr.
create(
"colorsPerVertex",
"cv",
aColorSetName = tAttr.
create(
"colorSetName",
"cs",
aTexRotateX = nAttr.
create(
"texRotateX",
"tx",
aTexRotateY = nAttr.
create(
"texRotateY",
"ty",
aTexRotateZ = nAttr.
create(
"texRotateZ",
"tz",
aDrawBoundingBox = nAttr.
create(
"drawBoundingBox",
"dbb",
return MS::kSuccess;
}
{
return MS::kSuccess;
}
hwColorPerVertexShader::unbind(
const MDrawRequest& request,
{
return MS::kSuccess;
}
hwColorPerVertexShader::geometry(
const MDrawRequest& request,
int prim,
unsigned int writable,
int indexCount,
const unsigned int * indexArray,
int vertexCount,
const int * vertexIDs,
const float * vertexArray,
int normalCount,
const float ** normalArrays,
int colorCount,
const float ** colorArrays,
int texCoordCount,
const float ** texCoordArrays)
{
if( mDrawBoundingBox )
{
int i;
for( i = 0; i < vertexCount; i++ )
{
box.
expand(
MPoint(vertexArray[i*3], vertexArray[i*3+1], vertexArray[i*3+2]) );
}
MColor wireColor( 0.1f, 0.15f, 0.35f );
drawBoundingBox( box, wireColor );
}
if( colorCount > 0 && colorArrays[ colorCount - 1] != NULL )
{
glPushAttrib(GL_ALL_ATTRIB_BITS);
glPushClientAttrib(GL_CLIENT_VERTEX_ARRAY_BIT);
glDisable(GL_LIGHTING);
glEnableClientState(GL_COLOR_ARRAY);
glColorPointer( 4, GL_FLOAT, 0, &colorArrays[colorCount - 1][0]);
glEnableClientState(GL_VERTEX_ARRAY);
glVertexPointer ( 3, GL_FLOAT, 0, &vertexArray[0] );
glDrawElements ( prim, indexCount, GL_UNSIGNED_INT, indexArray );
glEnableClientState(GL_COLOR_ARRAY);
glPopClientAttrib();
glPopAttrib();
return MS::kSuccess;
}
if ((unsigned int)normalCount > mNormalsPerVertex) {
normalCount = mNormalsPerVertex;
return MS::kSuccess;
}
else if (normalCount > 0)
{
glPushAttrib(GL_ALL_ATTRIB_BITS);
glPushClientAttrib(GL_CLIENT_VERTEX_ARRAY_BIT);
glDisable(GL_LIGHTING);
if (normalCount > 1)
{
if (normalCount == 2)
{
#ifdef _TANGENT_DEBUG
const float *tangents = (const float *)&normalArrays[1][0];
for (unsigned int i=0; i< vertexCount; i++)
{
cout<<"tangent["<<i
<<"] = "<<tangnets[i*3]
<<","<<tangents[i*3+1]<<","<<tangents[i*3+2]<<endl;
}
#endif
glEnableClientState(GL_COLOR_ARRAY);
glColorPointer(3, GL_FLOAT, 0, &normalArrays[1][0]);
}
else
{
#ifdef _BINORMAL_DEBUG
const float *binormals = (const float *)&normalArrays[2][0];
for (unsigned int i=0; i< vertexCount; i++)
{
cout<<"binormals["<<i<<"] = "<<binormals[i*3]
<<","<<binormals[i*3+1]<<","<<binormals[i*3+2]<<endl;
}
#endif
glEnableClientState(GL_COLOR_ARRAY);
glColorPointer(3, GL_FLOAT, 0, &normalArrays[2][0]);
}
}
else if (normalCount)
{
glEnableClientState(GL_COLOR_ARRAY);
glColorPointer(3, GL_FLOAT, 0, &normalArrays[0][0]);
}
glEnableClientState(GL_VERTEX_ARRAY);
glVertexPointer ( 3, GL_FLOAT, 0, &vertexArray[0] );
glDrawElements ( prim, indexCount, GL_UNSIGNED_INT, indexArray );
glDisableClientState(GL_COLOR_ARRAY);
glPopClientAttrib();
glPopAttrib();
return MS::kSuccess;
}
else
{
return draw( prim, writable, indexCount, indexArray,
vertexCount, vertexArray, colorCount, colorArrays );
}
}
hwColorPerVertexShader::glBind(
const MDagPath& shapePath)
{
return MS::kSuccess;
}
hwColorPerVertexShader::glUnbind(
const MDagPath& shapePath)
{
return MS::kSuccess;
}
int prim,
unsigned int writable,
int indexCount,
const unsigned int * indexArray,
int vertexCount,
const int * vertexIDs,
const float * vertexArray,
int normalCount,
const float ** normalArrays,
int colorCount,
const float ** colorArrays,
int texCoordCount,
const float ** texCoordArrays)
{
#ifdef _TEST_FILE_PATH_DURING_DRAW_
{
}
#endif
if ((unsigned int)normalCount > mNormalsPerVertex)
normalCount = mNormalsPerVertex;
if (normalCount > 0)
{
glPushAttrib(GL_ALL_ATTRIB_BITS);
glPushClientAttrib(GL_CLIENT_VERTEX_ARRAY_BIT);
glDisable(GL_LIGHTING);
glDisable(GL_BLEND);
if (normalCount > 1)
{
if (normalCount == 2)
{
#ifdef _TANGENT_DEBUG
const float *tangents = (const float *)&normalArrays[1][0];
for (int i=0; i< vertexCount; i++)
{
cout<<"tangent["<<i<<"] = "<<tangents[i*3]
<<","<<tangents[i*3+1]<<","<<tangents[i*3+2]<<endl;
}
#endif
glEnableClientState(GL_COLOR_ARRAY);
glColorPointer(3, GL_FLOAT, 0, &normalArrays[1][0]);
}
else
{
#ifdef _BINORMAL_DEBUG
const float *binormals = (const float *)&normalArrays[2][0];
for (unsigned int i=0; i< vertexCount; i++)
{
cout<<"binormals["<<i<<"] = "<<binormals[i*3]
<<","<<binormals[i*3+1]<<","<<binormals[i*3+2]<<endl;
}
#endif
glEnableClientState(GL_COLOR_ARRAY);
glColorPointer(3, GL_FLOAT, 0, &normalArrays[2][0]);
}
}
else if (normalCount)
{
glEnableClientState(GL_COLOR_ARRAY);
glColorPointer(3, GL_FLOAT, 0, &normalArrays[0][0]);
}
glEnableClientState(GL_VERTEX_ARRAY);
glVertexPointer ( 3, GL_FLOAT, 0, &vertexArray[0] );
glDrawElements ( prim, indexCount, GL_UNSIGNED_INT, indexArray );
glDisableClientState(GL_COLOR_ARRAY);
glPopClientAttrib();
glPopAttrib();
return MS::kSuccess;
}
else
{
return draw( prim, writable, indexCount, indexArray,
vertexCount, vertexArray, colorCount, colorArrays );
}
}
MStatus hwColorPerVertexShader::renderSwatchImage(
MImage& outImage )
{
{
thisMObject(),
outImage,
}
if (pRenderer)
{
unsigned int* pIndexing = 0;
unsigned int numberOfData = 0;
unsigned int indexCount = 0;
if( !pGeomData )
{
}
unsigned int width, height;
unsigned int origWidth = width;
unsigned int origHeight = height;
if( status2 != MS::kSuccess )
{
}
glPushAttrib(GL_ALL_ATTRIB_BITS);
{
float light_pos[4];
glMatrixMode(GL_MODELVIEW);
glPushMatrix();
glLoadIdentity();
glLightfv(GL_LIGHT0, GL_POSITION, light_pos );
glPopMatrix();
float light_ambt[4] = {1.0f, 1.0f, 1.0f, 1.0};
float light_diff[4] = {1.0f, 1.0f, 1.0f, 1.0};
float light_spec[4] = {1.0f, 1.0f, 1.0f, 1.0};
glLightfv( GL_LIGHT0, GL_AMBIENT, light_ambt );
glLightfv( GL_LIGHT0, GL_DIFFUSE, light_diff );
glLightfv( GL_LIGHT0, GL_SPECULAR, light_spec );
glEnable( GL_LIGHTING );
glEnable( GL_LIGHT0 );
}
{
double l, r, b, t, n, f;
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
glOrtho( l, r, b, t, n, f );
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
}
drawTheSwatch( pGeomData, pIndexing, numberOfData, indexCount );
if (width != origWidth || height != origHeight)
{
}
else
{
}
glPopAttrib();
}
return status;
}
void
unsigned int* pIndexing,
unsigned int numberOfData,
unsigned int indexCount )
{
if( !pRenderer ) return;
{
float r, g, b, a;
glClearColor( r, g, b, a );
}
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glShadeModel(GL_SMOOTH);
glEnable(GL_DEPTH_TEST);
glDepthFunc(GL_LEQUAL);
glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST);
{
glEnable(GL_BLEND);
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
}
if (mSampleImageId == 0)
{
MStatus rstatus = mSampleImage->readFromFile(
"C:\\temp\\maya.gif");
{
unsigned int w, h;
mSampleImage->getSize( w, h );
if (w > 2 && h > 2 )
{
glGenTextures( 1, &mSampleImageId );
if (mSampleImageId > 0)
{
glEnable(GL_TEXTURE_2D);
glBindTexture ( GL_TEXTURE_2D, mSampleImageId );
glTexImage2D( GL_TEXTURE_2D, 0, GL_RGBA8, w, h, 0,
GL_RGBA, GL_UNSIGNED_BYTE, (GLvoid *) mSampleImage->pixels() );
}
}
}
if (mSampleImage)
{
delete mSampleImage;
}
}
bool drawBackGround = ( mTranspBias > 0.0f );
bool drawBackGroundTexture = (mSampleImageId != 0);
if (drawBackGround)
{
if (drawBackGroundTexture)
{
glMatrixMode(GL_TEXTURE);
glLoadIdentity();
glMatrixMode(GL_MODELVIEW);
glBindTexture(GL_TEXTURE_2D, mSampleImageId );
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glEnable(GL_TEXTURE_2D);
}
unsigned int numberOfRepeats = 8;
MColor quadColor( 0.5f, 0.5f, 0.5f, 1.0f );
drawBackGroundTexture, numberOfRepeats );
if (drawBackGroundTexture)
glDisable(GL_TEXTURE_2D);
glEnable(GL_LIGHTING);
}
{
float ambient[4] = { 0.1f, 0.1f, 0.1f, 1.0f };
float diffuse[4] = { 0.7f, 0.7f, 0.7f, 1.0f };
float specular[4] = { 0.5f, 0.5f, 0.5f, 1.0f };
float emission[4] = { 0.0f, 0.0f, 0.0f, 1.0f };
glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, ambient);
glMaterialfv(GL_FRONT_AND_BACK, GL_EMISSION, emission );
glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, specular );
glMaterialf(GL_FRONT_AND_BACK, GL_SHININESS, 20.0f);
float swatchColor[4];
float biasT = 1.0f - mTranspGain - mTranspBias;
swatchColor[0] = (diffuse[0] * mColorGain[0]) + mColorBias[0];
swatchColor[1] = (diffuse[1] * mColorGain[1]) + mColorBias[1];
swatchColor[2] = (diffuse[2] * mColorGain[2]) + mColorBias[2];
swatchColor[3] = (diffuse[3] * mTranspGain) + biasT;
glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, swatchColor );
glColorMaterial(GL_FRONT_AND_BACK, GL_DIFFUSE);
glEnable(GL_COLOR_MATERIAL);
glColor4fv( swatchColor );
}
if (pGeomData)
{
glPushClientAttrib ( GL_CLIENT_VERTEX_ARRAY_BIT );
if (mNormalsPerVertex >= 1)
{
glDisable(GL_LIGHTING);
float *normalData = (float *)( pGeomData[1].data() );
float * tangentData = (float *)( pGeomData[3].data() );
float * binormalData = (float *)( pGeomData[4].data() );
if (normalData && mNormalsPerVertex == 1)
{
glEnableClientState(GL_COLOR_ARRAY);
glColorPointer(3, GL_FLOAT, 0, normalData);
}
else if (tangentData && mNormalsPerVertex == 2)
{
glEnableClientState(GL_COLOR_ARRAY);
glColorPointer(3, GL_FLOAT, 0, tangentData);
}
else if (binormalData)
{
glEnableClientState(GL_COLOR_ARRAY);
glColorPointer(3, GL_FLOAT, 0, binormalData);
}
}
float *vertexData = (float *)( pGeomData[0].data() );
if (vertexData)
{
glEnableClientState( GL_VERTEX_ARRAY );
glVertexPointer ( 3, GL_FLOAT, 0, vertexData );
}
float *normalData = (float *)( pGeomData[1].data() );
if (normalData)
{
glEnableClientState( GL_NORMAL_ARRAY );
glNormalPointer ( GL_FLOAT, 0, normalData );
}
if (mSampleImageId > 0)
{
float *uvData = (float *) (pGeomData[2].data() );
if (uvData)
{
glBindTexture ( GL_TEXTURE_2D, mSampleImageId );
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glEnable(GL_TEXTURE_2D);
glEnableClientState( GL_TEXTURE_COORD_ARRAY );
glTexCoordPointer( 2, GL_FLOAT, 0, uvData );
glMatrixMode(GL_TEXTURE);
glLoadIdentity();
glScalef( 0.5f, 0.5f, 1 );
glRotatef( mTexRotateX, 1.0f, 0.0f, 0.0f);
glRotatef( mTexRotateY, 0.0, 1.0f, 0.0f);
glRotatef( mTexRotateZ, 0.0, 0.0f, 1.0f);
glMatrixMode(GL_MODELVIEW);
}
}
if (vertexData && normalData && pIndexing )
glDrawElements ( GL_TRIANGLES, indexCount, GL_UNSIGNED_INT, pIndexing );
glPopClientAttrib();
}
glDisable( GL_COLOR_MATERIAL );
glDisable( GL_LIGHTING );
}
MStatus hwColorPerVertexShader::draw(
int prim,
unsigned int writable,
int indexCount,
const unsigned int * indexArray,
int vertexCount,
const float * vertexArray,
int colorCount,
const float ** colorArrays)
{
mAttributesChanged = false;
if (!vertexCount ||
!((prim == GL_TRIANGLES) || (prim == GL_TRIANGLE_STRIP)))
{
return MS::kFailure;
}
glPushAttrib( GL_ENABLE_BIT | GL_COLOR_BUFFER_BIT );
glPushClientAttrib(GL_CLIENT_VERTEX_ARRAY_BIT);
glDisable(GL_LIGHTING);
glEnableClientState(GL_VERTEX_ARRAY);
glVertexPointer ( 3, GL_FLOAT, 0, &vertexArray[0] );
bool localCopyOfColors = false;
float * colors = NULL;
bool blendSet = false;
if( colorCount <= 1 )
{
glDisable(GL_BLEND);
if( colorCount > 0 && colorArrays[0] != NULL)
{
glEnableClientState(GL_COLOR_ARRAY);
glColorPointer(4, GL_FLOAT, 0, colorArrays[0]);
}
else
{
glColor4f(1.0, 0.5, 1.0, 1.0);
}
glDrawElements ( prim, indexCount, GL_UNSIGNED_INT, indexArray );
}
else
{
glEnable(GL_BLEND);
glBlendFunc(GL_ONE, GL_ONE);
glEnableClientState(GL_COLOR_ARRAY);
blendSet = true;
for (int i=0; i<colorCount; i++)
{
if (colorArrays[i] != NULL)
{
bool haveTransparency = false;
if (mColorGain[0] != 1.0f ||
mColorGain[1] != 1.0f ||
mColorGain[2] != 1.0f ||
mColorBias[0] != 0.0f ||
mColorBias[1] != 0.0f ||
mColorBias[2] != 0.0f ||
mTranspGain != 1.0f ||
mTranspBias != 0.0f)
{
float biasT = 1 - mTranspGain - mTranspBias;
if (!(writable & kWriteColorArrays))
{
unsigned int numFloats = 4 * vertexCount;
colors = new float[numFloats];
localCopyOfColors = true;
}
else
{
colors = (float *)colorArrays[i];
}
float *origColors = (float *)colorArrays[i];
float *colorPtr = colors;
for (int ii = vertexCount ; ii-- ; )
{
colorPtr[0] = (origColors[0] * mColorGain[0]) + mColorBias[0];
colorPtr[1] = (origColors[1] * mColorGain[1]) + mColorBias[1];
colorPtr[2] = (origColors[2] * mColorGain[2]) + mColorBias[2];
colorPtr[3] = (origColors[3] * mTranspGain) + biasT;
if (colorPtr[3] != 1.0f)
haveTransparency = true;
colorPtr += 4;
origColors += 4;
}
}
else
{
colors = (float *)colorArrays[i];
float *colorPtr = colors;
for (int ii = vertexCount ; ii-- ; )
{
if (colorPtr[3] != 1.0f )
{
haveTransparency = true;
break;
}
else
colorPtr += 4;
}
}
if (!blendSet)
{
if (haveTransparency)
{
glEnable(GL_BLEND);
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
}
}
else {
glDisable(GL_BLEND);
}
glEnableClientState(GL_COLOR_ARRAY);
glColorPointer(4, GL_FLOAT, 0, colors);
}
else {
glDisable(GL_BLEND);
glDisableClientState(GL_COLOR_ARRAY);
glColor4f(1.0, 1.0, 1.0, 1.0);
}
glDrawElements ( prim, indexCount, GL_UNSIGNED_INT, indexArray );
}
}
glDisable(GL_BLEND);
glPopClientAttrib();
glPopAttrib();
if (localCopyOfColors)
{
delete[] colors;
colors = NULL;
}
return MS::kSuccess;
}
int hwColorPerVertexShader::normalsPerVertex()
{
unsigned int numNormals = mNormalsPerVertex;
{
if (fnMesh.numUVSets() == 0)
{
MString dispWarn(
"Asking for more uvsets then available for shape: ");
dispWarn = dispWarn + pathName;
numNormals = (mNormalsPerVertex > 1 ? 1 : 0);
}
}
return numNormals;
}
int hwColorPerVertexShader::texCoordsPerVertex()
{
return 0;
}
int hwColorPerVertexShader::colorsPerVertex()
{
int returnVal = 0;
if (mNormalsPerVertex)
return 0;
else {
{
if (numColorSets < 2)
returnVal = numColorSets;
else
returnVal = 2;
}
}
return returnVal;
}
bool hwColorPerVertexShader::hasTransparency()
{
return true;
}
{
if ((plug != outColor) && (plug.
parent() != outColor))
return MS::kUnknownParameter;
outColor = color;
return MS::kSuccess;
}
{
public:
{
return new hwCPVShaderOverride(obj);
}
~hwCPVShaderOverride() override
{
fShaderNode = NULL;
}
{
{
fShaderNode = (hwColorPerVertexShader*)
}
reqName,
3));
if(fShaderNode)
{
reqName = fShaderNode->colorSetName();
}
reqName,
4));
return MString(
"Autodesk Maya hwColorPerVertexShader");
}
bool customDraw(
{
return true;
}
{
}
{
return true;
}
protected:
hwCPVShaderOverride(
const MObject& obj)
, fShaderNode(NULL)
{
}
hwColorPerVertexShader *fShaderNode;
};
bool hwCPVShaderOverride::draw(
{
glMatrixMode(GL_MODELVIEW);
glPushMatrix();
if (status)
{
glLoadMatrixd(transform.
matrix[0]);
}
glMatrixMode(GL_PROJECTION);
glPushMatrix();
if (status)
{
glLoadMatrixd(projection.
matrix[0]);
}
{
return false;
}
if(!fBlendState)
{
{
}
{
return false;
}
}
{
return false;
}
if( fShaderNode->wantDrawBoundingBox() )
{
int numRenderItems = renderItemList.
length();
for( int i = 0; i < numRenderItems; i++ )
{
if( !renderItem )
{
continue;
}
MColor wireColor( 0.1f, 0.15f, 0.35f );
drawBoundingBox( box, wireColor );
}
}
bool useCustomDraw = false;
if(useCustomDraw)
{
customDraw(context, renderItemList);
}
else
{
drawGeometry(context);
}
glPopMatrix();
glMatrixMode(GL_MODELVIEW);
glPopMatrix();
return true;
}
bool hwCPVShaderOverride::customDraw(
{
if ( 0 == gGLFT )
MGLenum currentError = 0;
glPushClientAttrib ( GL_CLIENT_ALL_ATTRIB_BITS );
{
int numRenderItems = renderItemList.
length();
for (int renderItemIdx=0; renderItemIdx<numRenderItems; renderItemIdx++)
{
if (!renderItem) continue;
if (!geometry) continue;
#define GLOBJECT_BUFFER_OFFSET(i) ((char *)NULL + (i)) // For GLObject offsets
bool boundData = true;
for (int i=0; i<bufferCount && boundData; i++)
{
if (!buffer)
{
boundData = false;
continue;
}
GLuint * dataBufferId = NULL;
if (!dataHandle)
{
boundData = false;
continue;
}
dataBufferId = (GLuint *)(dataHandle);
unsigned int fieldOffset = desc.
offset();
unsigned int fieldStride = desc.
stride();
if (*dataBufferId > 0)
{
gGLFT->
glBindBufferARB(MGL_ARRAY_BUFFER_ARB, *dataBufferId);
currentError = gGLFT->
glGetError();
if (currentError != MGL_NO_ERROR)
boundData = false;
}
else
boundData = false;
if (boundData)
{
{
glEnableClientState(GL_VERTEX_ARRAY);
glVertexPointer(3, GL_FLOAT, fieldStride*4, GLOBJECT_BUFFER_OFFSET(fieldOffset));
currentError = gGLFT->glGetError();
if (currentError != MGL_NO_ERROR)
boundData = false;
}
{
glEnableClientState(GL_COLOR_ARRAY);
glColorPointer(4, GL_FLOAT, fieldStride*4, GLOBJECT_BUFFER_OFFSET(fieldOffset));
currentError = gGLFT->glGetError();
if (currentError != MGL_NO_ERROR)
boundData = false;
}
}
}
{
unsigned int indexBufferCount = 0;
GLuint *indexBufferId = NULL;
if (indexHandle)
{
indexBufferId = (GLuint *)(indexHandle);
indexBufferCount = buffer->
size();
}
if (indexBufferId && (*indexBufferId > 0))
{
gGLFT->glBindBufferARB(MGL_ELEMENT_ARRAY_BUFFER_ARB, *indexBufferId);
currentError = gGLFT->glGetError();
if (currentError == MGL_NO_ERROR)
{
GLenum indexPrimTypeGL = GL_TRIANGLES;
switch (indexPrimType) {
indexPrimTypeGL = GL_POINTS; break;
indexPrimTypeGL = GL_LINES; break;
indexPrimTypeGL = GL_LINE_STRIP; break;
indexPrimTypeGL = GL_TRIANGLES; break;
indexPrimTypeGL = GL_TRIANGLE_STRIP; break;
default:
boundData = false;
break;
};
if (boundData)
{
GLenum indexType =
glDrawElements(indexPrimTypeGL, indexBufferCount, indexType, GLOBJECT_BUFFER_OFFSET(0));
}
}
}
}
}
}
glPopClientAttrib();
return true;
}
{
const MString UserClassify(
"shader/surface/utility/:drawdb/shader/surface/hwColorPerVertexShader:swatch/"+swatchName );
MFnPlugin plugin( obj, PLUGIN_COMPANY,
"4.5",
"Any");
status = plugin.registerNode("hwColorPerVertexShader",
hwColorPerVertexShader::id,
hwColorPerVertexShader::creator,
hwColorPerVertexShader::initialize,
"drawdb/shader/surface/hwColorPerVertexShader",
sHWCPVShaderRegistrantId,
hwCPVShaderOverride::Creator);
if (status != MS::kSuccess) return status;
return status;
}
{
status = plugin.deregisterNode( hwColorPerVertexShader::id );
"drawdb/shader/surface/hwColorPerVertexShader", sHWCPVShaderRegistrantId);
if (status != MS::kSuccess) return status;
return status;
}