#include <maya/MIOStream.h>
#include <math.h>
#include <maya/MSimple.h>
#include <maya/MGlobal.h>
#include <maya/MDagPath.h>
#include <maya/MSelectionList.h>
#include <maya/MObjectArray.h>
#include <maya/MFnWeightGeometryFilter.h>
#include <maya/MSyntax.h>
#include <maya/MArgDatabase.h>
#include <maya/MItGeometry.h>
#include <maya/MPoint.h>
#define kSineFlag                               "-s"
#define kSineFlagLong                           "-sine"
#define kSineDistanceFlag                       "-sd"
#define kSineDistanceFlagLong                   "-sineDistance"
#define kSineDistance2Flag                      "-sd2"
#define kSineDistance2FlagLong                  "-sineDistance2"
#define kDistanceSineDistanceFlag               "-dsd"
#define kDistanceSineDistanceFlagLong           "-distanceSineDistance"
#define kInverseDistanceSineDistanceFlag        "-ids"
#define kInverseDistanceSineDistanceFlagLong    "-inverseDistanceSineDistance"
#define kDistanceFlag                           "-d"
#define kDistanceFlagLong                       "-distance"
#define kDistance2Flag                          "-d2"
#define kDistance2FlagLong                      "-distance2"
#define kDistance3Flag                          "-d3"
#define kDistance3FlagLong                      "-distance3"
#define kDistance4Flag                          "-d4"
#define kDistance4FlagLong                      "-distance4"
#define kInverseDistanceFlag                    "-id"
#define kInverseDistanceFlagLong                "-inverseDistance"
#define kInverseDistance2Flag                   "-id2"
#define kInverseDistance2FlagLong               "-inverseDistance2"
#define kInverseDistance3Flag                   "-id3"
#define kInverseDistance3FlagLong               "-inverseDistance3"
#define kInverseDistance4Flag                   "-id4"
#define kInverseDistance4FlagLong               "-inverseDistance4"
class clusterWeightFunctionCmd : 
public MPxCommand 
{
public:
    clusterWeightFunctionCmd();
    virtual ~clusterWeightFunctionCmd();
    static void *creator();
    
    enum effectType {
        kSine,
        kSineDistance,
        kSineDistance2,
        kDistanceSineDistance,
        kInverseDistanceSineDistance,
        kDistance,
        kDistance2,
        kDistance3,
        kDistance4,
        kInverseDistance,
        kInverseDistance2,
        kInverseDistance3,
        kInverseDistance4
    };
private:
    effectType fEffectType;
};
clusterWeightFunctionCmd::clusterWeightFunctionCmd()
{
}
clusterWeightFunctionCmd::~clusterWeightFunctionCmd()
{
}
{
    
    
    
    status = parseArgs(argList);
        status = performWeighting(cluster, dagPath, component);
    return status;
}
void *clusterWeightFunctionCmd::creator()
{
    return new clusterWeightFunctionCmd;
}
MSyntax clusterWeightFunctionCmd::newSyntax()
 
{
    syntax.
addFlag(kSineFlag, kSineFlagLong);
    syntax.
addFlag(kSineDistanceFlag, kSineDistanceFlagLong);
    syntax.
addFlag(kSineDistance2Flag, kSineDistance2FlagLong);
    syntax.
addFlag(kDistanceSineDistanceFlag, kDistanceSineDistanceFlagLong);
    syntax.
addFlag(kInverseDistanceSineDistanceFlag, 
                   kInverseDistanceSineDistanceFlagLong);
    syntax.
addFlag(kDistanceFlag, kDistanceFlagLong);
    syntax.
addFlag(kDistance2Flag, kDistance2FlagLong);
    syntax.
addFlag(kDistance3Flag, kDistance3FlagLong);
    syntax.
addFlag(kDistance4Flag, kDistance4FlagLong);
    syntax.
addFlag(kInverseDistanceFlag, kInverseDistanceFlagLong);
    syntax.
addFlag(kInverseDistance2Flag, kInverseDistance2FlagLong);
    syntax.
addFlag(kInverseDistance3Flag, kInverseDistance3FlagLong);
    syntax.
addFlag(kInverseDistance4Flag, kInverseDistance4FlagLong);
    return syntax;
}
{
    if (argData.isFlagSet(kSineFlag)) {
        fEffectType = kSine;
    }
    else if (argData.isFlagSet(kSineDistanceFlag)) {
        fEffectType = kSineDistance;
    }
    else if (argData.isFlagSet(kSineDistance2Flag)) {
        fEffectType = kSineDistance2;
    }
    else if (argData.isFlagSet(kDistanceSineDistanceFlag)) {
        fEffectType = kDistanceSineDistance;
    }
    else if (argData.isFlagSet(kInverseDistanceSineDistanceFlag)) {
        fEffectType = kInverseDistanceSineDistance;
    }
    else if (argData.isFlagSet(kDistanceFlag)) {
        fEffectType = kDistance;
    }
    else if (argData.isFlagSet(kDistance2Flag)) {
        fEffectType = kDistance2;
    }
    else if (argData.isFlagSet(kDistance3Flag)) {
        fEffectType = kDistance3;
    }
    else if (argData.isFlagSet(kDistance4Flag)) {
        fEffectType = kDistance4;
    }
    else if (argData.isFlagSet(kInverseDistanceFlag)) {
        fEffectType = kInverseDistance;
    }
    else if (argData.isFlagSet(kInverseDistance2Flag)) {
        fEffectType = kInverseDistance2;
    }
    else if (argData.isFlagSet(kInverseDistance3Flag)) {
        fEffectType = kInverseDistance3;
    }
    else if (argData.isFlagSet(kInverseDistance4Flag)) {
        fEffectType = kInverseDistance4;
    }
}
{
    double weight = 0.0;
        for (; !geomIter.isDone(); geomIter.next()) {
            comp = geomIter.component();
            }
            if (kSine == fEffectType) {
                weight = sin(pnt.
x)*sin(pnt.
z);
            }
            else if (kSineDistance == fEffectType) {
                weight = sin(distance);
            }
            else if (kSineDistance2 == fEffectType) {
                weight = sin(distance*distance);
            }
            else if (kDistanceSineDistance == fEffectType) {
                weight = distance*sin(distance);
            }
            else if (kInverseDistanceSineDistance == fEffectType) {
                weight = sin(distance)/(distance+1);
            }
            else if (kDistance == fEffectType) {
                weight = distance;
            }
            else if (kDistance2 == fEffectType) {
                weight = distance*distance;
            }
            else if (kDistance3 == fEffectType) {
                weight = distance*distance*distance;
            }
            else if (kDistance4 == fEffectType) {
                weight = distance*distance*distance*distance;
            }
            else if (kInverseDistance == fEffectType) {
                weight = 1/(dist);
            }
            else if (kInverseDistance2 == fEffectType) {
                weight = 1/(dist*dist);
            }
            else if (kInverseDistance3 == fEffectType) {
                weight = 1/(dist*dist*dist);
            }
            else if (kInverseDistance4 == fEffectType) {
                weight = 1/(dist*dist*dist*dist);
            }
        }
        unsigned length = compArray.
length();
 
        for (unsigned i = 0; i < length; i++) {
            cluster.
setWeight(dagPath, compArray[i], (
float) weightArray[i]);
        }
    } else
}
{
    MFnPlugin plugin(obj, PLUGIN_COMPANY, 
"3.0", 
"Any");
 
    
    status = plugin.registerCommand("clusterWeightFunction",
                                    clusterWeightFunctionCmd::creator,
                                    clusterWeightFunctionCmd::newSyntax);
    
    if (!status) {
        status.
perror(
"registerCommand");
    }
    return status;
}
{
    
    status = plugin.deregisterCommand("clusterWeightFunction");
    if (!status) {
        status.
perror(
"deregisterCommand");
    }   
    return status;
}