- Main Page
- Related Pages
- Modules
- Classes
- Examples

# spiralAnimCurveCmd.cpp

    //-
    // ==========================================================================
    // Copyright 1995,2006,2008 Autodesk, Inc. All rights reserved.
    //
    // Use of this software is subject to the terms of the Autodesk
    // license agreement provided at the time of installation or download,
    // or which otherwise accompanies this software in either electronic
    // or hard copy form.
    // ==========================================================================
    //+

    #include <math.h>
    #include <maya/MIOStream.h>

    #include <maya/MGlobal.h>
    #include <maya/MFnPlugin.h>
    #include <maya/MSelectionList.h>
    #include <maya/MItSelectionList.h>
    #include <maya/MPoint.h>
    #include <maya/MVector.h>
    #include <maya/MMatrix.h>
    #include <maya/MDagPath.h>
    #include <maya/MFnAnimCurve.h>
    #include <maya/MFnDagNode.h>
    #include <maya/MPxCommand.h>
    #include <maya/MString.h>

    // Constants //

    #define OUTWARD_VELOCITY 0.075
    #define RADIAL_VELOCITY  0.05
    #define NUM_FRAMES       120

    // Class Definition //

    class spiralAnimCurve : public MPxCommand {
    public:

                        spiralAnimCurve() {};
        virtual         ~spiralAnimCurve();

        virtual MStatus doIt( const MArgList& args );
        static void*    creator();
    };

    // Class Implementation //

    #define NUM_SPANS        30
    #define WIDTH            10.0
    #define VERTICAL_SCALING 4.0

    spiralAnimCurve::~spiralAnimCurve() {}

    void* spiralAnimCurve::creator()
    {
        return new spiralAnimCurve();
    }

    // Set keyframes to move selected object in a spiral
    MStatus spiralAnimCurve::doIt( const MArgList& )
    {
        // Get the Active Selection List
        //
        MStatus status;
        MSelectionList  sList;
        MGlobal::getActiveSelectionList( sList );

        // Create an iterator for the selection list
        //
        MItSelectionList iter( sList, MFn::kDagNode, &status );
        if ( MS::kSuccess != status ) {
            cerr << "Failure in plugin setup";
            return MS::kFailure;
        }

        MDagPath mObject;
        MObject mComponent;

        for ( ; !iter.isDone(); iter.next() ) {
            status = iter.getDagPath( mObject, mComponent );

            // Check if there was an error
            //
            if ( MS::kSuccess != status ) continue;

            // We don't handle components
            //
            if ( !mComponent.isNull() ) continue;

            // Create the function set
            //
            MFnDagNode fnSet( mObject, &status );

            if ( MS::kSuccess != status ) {
                cerr << "Failure to create function set\n";
                continue;
            }

            // Get the plug for the X-translation channel
            //
            MString attrName( "translateX" );
            const MObject attrX = fnSet.attribute( attrName, &status );
            if ( MS::kSuccess != status ) {
                cerr << "Failure to find attribute\n";
            }
            MFnAnimCurve acFnSetX;
            acFnSetX.create( mObject.transform(), attrX, NULL, &status );

            if ( MS::kSuccess != status ) {
                cerr << "Failure creating MFnAnimCurve function set (translateX)\n";
                continue;
            }

            // Repeat for Y-translation
            //
            attrName.set( "translateZ" );
            const MObject attrZ = fnSet.attribute( attrName, &status );
            if ( MS::kSuccess != status ) {
                cerr << "Failure to find attribute\n";
            }
            MFnAnimCurve acFnSetZ;
            acFnSetZ.create( mObject.transform(), attrZ, NULL, &status );

            if ( MS::kSuccess != status ) {
                cerr << "Failure creating MFnAnimCurve function set (translateZ)\n";
                continue;
            }

            // Build spiral animation
            //
            for( int i = 1; i <= NUM_FRAMES; i++ ) {
                // Build the keyframe at frame i
                //
                double x = sin( (double)i * RADIAL_VELOCITY ) *
                                ( (double)i * OUTWARD_VELOCITY );
                double z = cos( (double)i * RADIAL_VELOCITY ) *
                                ( (double)i * OUTWARD_VELOCITY );

                // cerr << "Setting keys - frame: " << i << "  x: " << x << "  z: " << z << endl;

                MTime tm( (double)i, MTime::kFilm );
                if ( ( MS::kSuccess != acFnSetX.addKeyframe( tm, x ) ) ||
                     ( MS::kSuccess != acFnSetZ.addKeyframe( tm, z ) ) ) {
                    cerr << "Error setting the keyframe\n";
                }
            }

        }

        return status;
    }

    // Register command with system //

    MStatus initializePlugin( MObject obj )
    {
        MStatus   status;
        MFnPlugin plugin( obj, PLUGIN_COMPANY, "3.0", "Any");

        status = plugin.registerCommand( "spiralAnimCurve",
                                         spiralAnimCurve::creator );
        if (!status) {
            status.perror("registerCommand");
            return status;
        }

        return status;
    }

    MStatus uninitializePlugin( MObject obj )
    {
        MStatus   status;
        MFnPlugin plugin( obj );

        status = plugin.deregisterCommand( "spiralAnimCurve" );
        if (!status) {
            status.perror("deregisterCommand");
            return status;
        }

        return status;
    }