void UpdateGadgets(Bool relevants=false) { Int32 mode; Bool add_dynamics; GetBool(CHK_ADDDYNAMICS, add_dynamics); GetInt32(CMB_MODE, mode); BaseDocument* doc = GetActiveDocument(); BaseObject* op = doc ? doc->GetActiveObject() : nullptr; Enable(EDT_MAXCONN, mode != CMB_MODE_CHAIN); Enable(EDT_RADIUS, mode != CMB_MODE_CHAIN); Enable(CHK_CLOSED, mode == CMB_MODE_CHAIN); Enable(CHK_COMPOUND, add_dynamics); // Need at least two child objects on the active object. Bool execEnabled = op != nullptr && op->GetDown() != nullptr && op->GetDown()->GetNext() != nullptr; Enable(BTN_EXECUTE, execEnabled); if (relevants) { FreeChildren(CMB_TYPE); Int32 pluginid; GetInt32(CMB_FORCE, pluginid); do { BaseObject* op = BaseObject::Alloc(pluginid); if (!op) break; AutoFree<BaseObject> free(op); AutoAlloc<Description> desc; if (!op->GetDescription(desc, DESCFLAGS_DESC_0)) break; BaseContainer temp; AutoAlloc<AtomArray> arr; const BaseContainer* param = desc->GetParameter(FORCE_TYPE, temp, arr); if (!param) break; const BaseContainer* cycle = param->GetContainerInstance(DESC_CYCLE); if (!cycle) break; const BaseContainer* icons = param->GetContainerInstance(DESC_CYCLEICONS); Int32 i = 0; Int32 last_id = -1; while (true) { Int32 id = cycle->GetIndexId(i++); if (id == NOTOK) break; Int32 icon = icons ? icons->GetInt32(id) : -1; String name = cycle->GetString(id); if (name.Content()) { if (icon > 0) name += "&i" + String::IntToString(icon); if (last_id < 0) last_id = id; AddChild(CMB_TYPE, id, name); } } SetInt32(CMB_TYPE, last_id); } while (0); LayoutChanged(CMB_TYPE); } }
Bool ExecuteAutoConnect() { ConnectOptions options; Bool addDynamicsTag = false, inheritDynamicsTag = true; GetInt32(CMB_FORCE, options.forcePluginId); GetInt32(CMB_TYPE, options.forceType); GetInt32(CMB_MODE, options.connectMode); GetInt32(EDT_MAXCONN, options.maxConnections); GetFloat(EDT_RADIUS, options.radius); GetBool(CHK_CLOSED, options.closedChain); GetBool(CHK_ADDDYNAMICS, addDynamicsTag); GetBool(CHK_COMPOUND, inheritDynamicsTag); // Create an InExcludeData for the selection object. GeData ge_selection(CUSTOMGUI_INEXCLUDE_LIST, DEFAULTVALUE); auto selectionList = static_cast<InExcludeData*>( ge_selection.GetCustomDataType(CUSTOMGUI_INEXCLUDE_LIST)); if (!selectionList) return false; // Get the active document and object. BaseDocument* doc = GetActiveDocument(); if (!doc) return false; BaseObject* op = doc->GetActiveObject(); if (!op) return false; // Create the root object that will contain the connectors. AutoFree<BaseObject> root(BaseObject::Alloc(Onull)); if (!root) return false; // Function to create a dynamics tag. auto fAddDynamicsTag = [doc] (BaseObject* op, Int32 mode) { // Create a dynamics tag for the root object if it // does not already exist. BaseTag* dyn = op->GetTag(ID_RIGIDBODY); if (!dyn) { dyn = op->MakeTag(ID_RIGIDBODY); if (dyn) doc->AddUndo(UNDOTYPE_NEW, dyn); } // Update the parameters. if (dyn) { dyn->SetParameter(RIGID_BODY_HIERARCHY, mode, DESCFLAGS_SET_0); doc->AddUndo(UNDOTYPE_CHANGE_SMALL, dyn); } }; // This list will contain all objects that should be connected. // While collecting, create the dynamics tags. maxon::BaseArray<BaseObject*> objects; doc->StartUndo(); for (BaseObject* child=op->GetDown(); child; child=child->GetNext()) { objects.Append(child); if (addDynamicsTag && inheritDynamicsTag) fAddDynamicsTag(child, RIGID_BODY_HIERARCHY_COMPOUND); } if (addDynamicsTag && !inheritDynamicsTag) fAddDynamicsTag(op, RIGID_BODY_HIERARCHY_INHERIT); // If no objects where collected, quit already. if (objects.GetCount() <= 0) { doc->EndUndo(); doc->DoUndo(false); return true; } // Create the connection objects. ConnectObjects(op->GetName() + ": ", objects, options); // Fill the selection list and insert the objects. for (auto it=options.output.Begin(); it != options.output.End(); ++it) { (*it)->InsertUnderLast(root); doc->AddUndo(UNDOTYPE_NEW, *it); selectionList->InsertObject(*it, 0); } root->SetName(op->GetName() + ": " + root->GetName() + " (" + options.forceName + ")"); doc->InsertObject(root, nullptr, nullptr); doc->AddUndo(UNDOTYPE_NEW, root); // Create the selection object. if (selectionList->GetObjectCount() > 0) { BaseObject* selection = BaseObject::Alloc(Oselection); if (selection) { selection->SetParameter(SELECTIONOBJECT_LIST, ge_selection, DESCFLAGS_SET_0); selection->SetName(op->GetName() + ": " + options.forceName + " (" + selection->GetName() + ")"); doc->InsertObject(selection, nullptr, nullptr); doc->AddUndo(UNDOTYPE_NEW, selection); } ActiveObjectManager_SetMode(ACTIVEOBJECTMODE_OBJECT, false); doc->SetActiveObject(selection); } else doc->SetActiveObject(root); root.Release(); doc->EndUndo(); EventAdd(); return true; }