SOLVED Mograph Effector List

Hello

I'm working on a plugin that has an In/Exclude List for a user to feed in Effectors in a similar way to Mograph objects, my plugin is meant to act as a pseudo Mograph object. I've been able to mimic almost all of the same kind of functionality that Cinema offers with its Mograph objects.

The only functionality that I'm missing is when a Mograph object is selected and then an Effector is added into the scene, the Effector will be linked to the Mograph object's effector list.

Here is my code for creating my In/Exclude.


Bool EffectorClass::GetDDescription(GeListNode *node, Description *description, DESCFLAGS_DESC &flags)
{
	BaseContainer *datainstance;
	const DescID *singleid;   

	if (!description->LoadDescription(node->GetType()))
	{
	}

	datainstance = ((BaseList2D*)node)->GetDataInstance(); 
	if (!datainstance)
		return FALSE;
	singleid = description->GetSingleDescID();
	DescID cid;


	DescID DescMainTabGroup = DescLevel(10001, DTYPE_GROUP, 0);
	if (!singleid || DescMainTabGroup.IsPartOf(*singleid, NULL))
	{
		BaseContainer bc;
		bc = GetCustomDataTypeDefault(DTYPE_GROUP);
		bc.SetString(DESC_NAME, "Effector Control"_s);

		bc.SetInt32(DESC_COLUMNS, 1);
		bc.SetInt32(DESC_DEFAULT, 1);
		bc.SetBool(DESC_SCALEH, TRUE);

		if (!description->SetParameter(DescMainTabGroup, bc, DescLevel(ID_RKTMESHSPLINE)))
			return TRUE;
	}
	cid = DescLevel(10002, CUSTOMDATATYPE_INEXCLUDE_LIST, 0);
	if (!singleid || cid.IsPartOf(*singleid, NULL))
	{
		BaseContainer bc;
		bc = GetCustomDataTypeDefault(CUSTOMGUI_INEXCLUDE_LIST);

		bc.SetString(DESC_NAME, "Effectors"_s);
		BaseContainer acceptedObjects;
		acceptedObjects.InsData(Obaseeffector, String());
		acceptedObjects.InsData(Oweighteffector, String());
		acceptedObjects.InsData(1001381, String());


		bc.SetInt32(IN_EXCLUDE_FLAG_INIT_STATE, 3);
		bc.SetInt32(IN_EXCLUDE_FLAG_NUM_FLAGS, 2);
		bc.SetInt32(IN_EXCLUDE_FLAG_IMAGE_01_ON, 300000131);
		bc.SetInt32(IN_EXCLUDE_FLAG_IMAGE_01_OFF, 300000130);

		bc.SetContainer(DESC_ACCEPT, acceptedObjects);
		bc.SetBool(IN_EXCLUDE_FLAG_SEND_SELCHANGE_MSG, true);

		bc.SetInt32(IN_EXCLUDE_FLAG_BIG_MODE_SIZE, 150);
		if (!description->SetParameter(cid, bc, DescMainTabGroup))
			return TRUE;
	}




	flags |= DESCFLAGS_DESC::LOADED | DESCFLAGS_DESC::RECURSIONLOCK;

	return SUPER::GetDDescription(node, description, flags);
}

I've tried looking through the sdk and forum posts for anything in reference to this functionality and couldn't find anything.

Is there a particular flag that is needed to mimic the Mograph in this way or is the only way to do this with a Scene Hook?

Any help would be greatly appreciated.

John Terenece

hi,

the effector checks the selected object id and add itself to the mograph object in the in/exclude list (that have a pre defined ID)

The only way to reproduce that is to create a sceneHook and check for the message MSG_DOCUMENTINFO and MSG_DOCUMENTINFO_TYPE_OBJECT_INSERT. You can retrieve the selected object there and if the selected objects are the type of your generator.
Once you cast the data (of the message function) to DocumentInfoData you can retrieve the BaseList2D that have been added to the scene. (check if they are of type Obaseeffector)

Something like this in the message function of your scenehook.

	case MSG_DOCUMENTINFO:
		{
			DocumentInfoData* const msg = static_cast<DocumentInfoData*>(data);
			if (msg == nullptr)
				return false;
			// switch message sub-type
			if (msg->type == MSG_DOCUMENTINFO_TYPE_OBJECT_INSERT)
			{

				BaseDocument* doc = node->GetDocument();
				if (MAXON_UNLIKELY(doc == nullptr))
					return false;


				AutoAlloc<AtomArray>arr;
				if (!arr)
					return false;

				doc->GetActiveObjects(*arr, GETACTIVEOBJECTFLAGS::NONE);
				if (!arr->GetCount())
					return true;		// No objects to add

				for (Int32 i = arr->GetCount() - 1; i >= 0; --i)
				{
					BaseObject* obj = (BaseObject*)arr->GetIndex(i);
					if (obj->GetType() == 600000095)
					{
						ApplicationOutput("@", obj->GetName());
						BaseContainer* bc = obj->GetDataInstance();
						InExcludeData* inex = (InExcludeData*)bc->GetCustomDataType(1001, CUSTOMDATATYPE_INEXCLUDE_LIST);
						if (!inex)
							return false;
						if (!inex->InsertObject(msg->bl, true))
							return false;
					}
					
					
					/*
					
					*/
				}

Cheers,
Manuel

Thanks for the response.

I figured it would need to be the SceneHook but always best to double check.

John Terenece