Connect Manipulators to the Show Manipulator Tool
The Show Manipulator Tool uses manipulators to modify plug values or provide access to the construction history of a node. If you select several objects while in the Show Manipulator Tool, the corresponding manipulator is displayed for each of the objects selected.
The object that the manipulator is attached to does not have to be a DAG node. Some manipulators such as the Revolve manipulator are attached to a dependency node upstream of the final shape. For example, for a sphere called nurbsSphereShape1, the revolve manipulator must be attached to the makeNurbsSphere1 node which is upstream relative to nurbsSphereShape1.
Other manipulators, such as the camera manipulator and the light manipulator can be attached to either the transform or the shape of the light or camera.
The Show Manipulator Tool is explained in detail in the Basics guide.
Writing a Manipulator to Work with the Show Manipulator Tool
The first step when creating a manipulator that works with the Show Manipulator Tool for a node is to pick a name for the manipulator that corresponds to the node type name. To determine the name of the manipulator, take the name of the node and append Manip to the end of the node name. For example, the Show Manip for footPrintLocator is footPrintLocatorManip.
plugin.registerNode("footPrintLocator", // name of node
footPrintLocator::id,
&footPrintLocator::creator,
&footPrintLocator::initialize,
MPxNode::kLocatorNode);
plugin.registerNode("footPrintLocatorManip", // name of manip
footPrintLocatorManip::id,
&footPrintLocatorManip::creator,
&footPrintLocatorManip::initialize,
MPxNode::kManipContainer);
The second step is to have the initialize method of the node call MPxManipContainer::addToManipConnectTable()
. For example, in the footPrintLocator::initialize()
method:
MStatus footPrintLocator::initialize()
{
...
MPxManipContainer::addToManipConnectTable(id);
...
}
Where id is defined and declared as:
class footPrintLocator : public MPxLocatorNode
{
...
public:
static MTypeId id;
};
MTypeId footPrintLocator::id(0x81101);
Adding the Manipulator to a Context
An alternative to invoking a manipulator by the Show Manipulator Tool is to invoke the manipulator from a user-defined context.
The MPxSelectionContext
class has two methods to support the management of manipulators: addManipulator()
and deleteManipulator()
.
In addition to using these two methods, MPxSelectionContext::toolOnSetup
and MPxContext::toolOffCleanup
must be overridden so that toolOnSetup
adds a callback for manipulators, and toolOffCleanup
removes the callback when the active list is modified.
The callback can be an updateManipulators()
function which actually adds and deletes the manipulators.
For example:
MCallbackId id1;
void moveContext::toolOnSetup(MEvent &)
{
...
id1 = ModelMessage::addCallback(
MModelMessage::kActiveListModified,
updateManipulators, this, &status);
....
}
void moveContext::toolOffCleanup()
{
...
status = MModelMessage::removeCallback(id1);
...
}
void updateManipulators(void * data)
{
...
moveContext * ctxPtr = (moveContext *) data;
ctxPtr->deleteManipulators();
...
// for each object selected
MString manipName("moveManip");
MObject manipObject;
ctxPtr->moveM = (moveManip *)
moveManip::newManipulator(manipName,
manipObject);
...
ctxPtr->addManipulator(manipObject);
...
ctxPtr->moveM->connectToDependNode(dependNode);
...
}
Example Manipulators
Following are the manipulator examples that are available in the (devkit\plug-ins) folder of the Developer Kit installation:
moveManip
The moveManip.cpp plug-in shows how to create a manipulator from a context. The user-defined manipulator in moveToolManip.cpp is called moveManip and consists of two base manipulators: a FreePointTriadManip and a DistanceManip.
footPrintManip
This plug-in example demonstrates how to use the Show Manipulator Tool with a user-defined node and a user-defined manipulator. The user-defined manipulator consists of a DistanceManip.
customAttrManip
This plug-in demonstrates how to create user-defined manipulators on custom attributes of nodes within a user-defined context. This custom manipulator is composed of three DistanceManips.
moveManip
This plug-in shows how to create a manipulator from a context. The user-defined manipulator in moveToolManip.cpp is called moveManip and consists of two base manipulators: a FreePointTriadManip and a DistanceManip.
footPrintManip
This plug-in demonstrates how to use the Show Manipulator Tool with a user-defined node and a user-defined manipulator. The user-defined manipulator consists of a DistanceManip. It also demonstrates how to write plugToManip conversion callback functions so that DistanceManip is always following the location of the foot.
rotateManip
This plug-in demonstrates the different modes of the rotate base manipulator. The user-defined manipulator in rotateManip.cpp consists of a rotate base manipulator and a state base manipulator. The state manipulator is used to control the mode of the rotate manipulator: object mode, world space mode, gimbal mode, and object mode with snapping.
componentScaleManip
This plug-in demonstrates how to use the scale base manipulator and also demonstrates a method for manipulating components. The plug-in componentScaleManip.cpp consists of a scale base manipulator. The manipulator works by attaching manipToPlug conversion callbacks for every selected vertex. The conversion function computes the new vertex positions using stored initial vertex positions and the scale manipValue.
surfaceBumpManip
This plug-in demonstrates how the pointOnSurface base manipulator can be used to modify vertices close to the param manipValue. The plug-in uses a manipToPlug conversion function as a callback to update vertex positions on the NURBS surface.
undo
.swissArmyManip
This plug-in demonstrates a user-defined manipulator that is comprised of a variety of base manipulators such as, CircleSweepManip, DirectionManip, DiscManip, DistanceManip, FreePointTriadManip, StateManip, ToggleManip, RotateManip, and ScaleManip.
lineManip
This example demonstrates how to use the MPxManipulatorNode
class along with a command to create a user defined manipulator. The manipulator created is a simple line which is an OpenGL pickable component. As you move the pickable component, the scale attribute of the selected transforms are modified. The line's movements are restricted in a plane. A corresponding command is used to create and delete the manipulator node and to support undo
, redo
, and others.
squareScaleManip
This example demonstrates how to use the MPxManipulatorNode
class along with a command to create a user-defined manipulator. The manipulator is a simple square with four sides as OpenGL pickable components. As you move the pickable component, the scale attribute of the selected transforms are modified. A corresponding command is used to create and delete the manipulator node and to support undo
, redo
, and others.