diff options
Diffstat (limited to 'source/blender/editors')
-rw-r--r-- | source/blender/editors/include/ED_object.h | 17 | ||||
-rw-r--r-- | source/blender/editors/include/UI_interface.h | 2 | ||||
-rw-r--r-- | source/blender/editors/interface/interface_templates.c | 366 | ||||
-rw-r--r-- | source/blender/editors/object/object_intern.h | 1 | ||||
-rw-r--r-- | source/blender/editors/object/object_modifier.c | 108 | ||||
-rw-r--r-- | source/blender/editors/object/object_ops.c | 1 | ||||
-rw-r--r-- | source/blender/editors/space_buttons/space_buttons.c | 12 |
7 files changed, 157 insertions, 350 deletions
diff --git a/source/blender/editors/include/ED_object.h b/source/blender/editors/include/ED_object.h index e027efce1d3..cd25ee54392 100644 --- a/source/blender/editors/include/ED_object.h +++ b/source/blender/editors/include/ED_object.h @@ -370,12 +370,17 @@ bool ED_object_modifier_remove(struct ReportList *reports, struct Object *ob, struct ModifierData *md); void ED_object_modifier_clear(struct Main *bmain, struct Object *ob); -int ED_object_modifier_move_down(struct ReportList *reports, - struct Object *ob, - struct ModifierData *md); -int ED_object_modifier_move_up(struct ReportList *reports, - struct Object *ob, - struct ModifierData *md); +bool ED_object_modifier_move_down(struct ReportList *reports, + struct Object *ob, + struct ModifierData *md); +bool ED_object_modifier_move_up(struct ReportList *reports, + struct Object *ob, + struct ModifierData *md); +bool ED_object_modifier_move_to_index(struct ReportList *reports, + struct Object *ob, + struct ModifierData *md, + const int index); + int ED_object_modifier_convert(struct ReportList *reports, struct Main *bmain, struct Depsgraph *depsgraph, diff --git a/source/blender/editors/include/UI_interface.h b/source/blender/editors/include/UI_interface.h index 01bc59f71e7..11dbb105072 100644 --- a/source/blender/editors/include/UI_interface.h +++ b/source/blender/editors/include/UI_interface.h @@ -2002,7 +2002,7 @@ void uiTemplatePathBuilder(uiLayout *layout, const char *propname, struct PointerRNA *root_ptr, const char *text); -uiLayout *uiTemplateModifier(uiLayout *layout, struct bContext *C, struct PointerRNA *ptr); +void uiTemplateModifiers(uiLayout *layout, struct bContext *C); uiLayout *uiTemplateGpencilModifier(uiLayout *layout, struct bContext *C, struct PointerRNA *ptr); void uiTemplateGpencilColorPreview(uiLayout *layout, struct bContext *C, diff --git a/source/blender/editors/interface/interface_templates.c b/source/blender/editors/interface/interface_templates.c index 6001e1ea1b5..1d55e2b3e4b 100644 --- a/source/blender/editors/interface/interface_templates.c +++ b/source/blender/editors/interface/interface_templates.c @@ -1816,360 +1816,50 @@ void uiTemplatePathBuilder(uiLayout *layout, /** \} */ /* -------------------------------------------------------------------- */ -/** \name Modifier Template +/** \name Modifiers Template + * + * Template for building the panel layout for the active object's modifiers. * \{ */ -#define ERROR_LIBDATA_MESSAGE TIP_("Can't edit external library data") - -static void modifiers_convertToReal(bContext *C, void *ob_v, void *md_v) +static void modifier_panel_id(void *md_link, char *r_name) { - Object *ob = ob_v; - ModifierData *md = md_v; - ModifierData *nmd = BKE_modifier_new(md->type); - - BKE_modifier_copydata(md, nmd); - nmd->mode &= ~eModifierMode_Virtual; - - BLI_addhead(&ob->modifiers, nmd); - - BKE_modifier_unique_name(&ob->modifiers, nmd); - - ob->partype = PAROBJECT; - - WM_event_add_notifier(C, NC_OBJECT | ND_MODIFIER, ob); - DEG_id_tag_update(&ob->id, ID_RECALC_GEOMETRY); - - ED_undo_push(C, "Modifier convert to real"); + ModifierData *md = (ModifierData *)md_link; + BKE_modifier_type_panel_id(md->type, r_name); } -static bool modifier_can_delete(ModifierData *md) +void uiTemplateModifiers(uiLayout *UNUSED(layout), bContext *C) { - /* fluid particle modifier can't be deleted here */ - if (md->type == eModifierType_ParticleSystem) { - short particle_type = ((ParticleSystemModifierData *)md)->psys->part->type; - if (ELEM(particle_type, - PART_FLUID, - PART_FLUID_FLIP, - PART_FLUID_FOAM, - PART_FLUID_SPRAY, - PART_FLUID_BUBBLE, - PART_FLUID_TRACER, - PART_FLUID_SPRAYFOAM, - PART_FLUID_SPRAYBUBBLE, - PART_FLUID_FOAMBUBBLE, - PART_FLUID_SPRAYFOAMBUBBLE)) { - return false; - } - } - return true; -} + ScrArea *sa = CTX_wm_area(C); + ARegion *region = CTX_wm_region(C); -/* Check whether Modifier is a simulation or not, - * this is used for switching to the physics/particles context tab */ -static int modifier_is_simulation(ModifierData *md) -{ - /* Physic Tab */ - if (ELEM(md->type, - eModifierType_Cloth, - eModifierType_Collision, - eModifierType_Fluidsim, - eModifierType_Fluid, - eModifierType_Softbody, - eModifierType_Surface, - eModifierType_DynamicPaint)) { - return 1; - } - /* Particle Tab */ - else if (md->type == eModifierType_ParticleSystem) { - return 2; - } - else { - return 0; - } -} - -static uiLayout *draw_modifier(uiLayout *layout, - Scene *scene, - Object *ob, - ModifierData *md, - int index, - int cageIndex, - int lastCageIndex) -{ - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - PointerRNA ptr; - uiBut *but; - uiBlock *block; - uiLayout *box, *column, *row, *sub; - uiLayout *result = NULL; - int isVirtual = (md->mode & eModifierMode_Virtual); - char str[128]; - - /* create RNA pointer */ - RNA_pointer_create(&ob->id, &RNA_Modifier, md, &ptr); - - column = uiLayoutColumn(layout, true); - uiLayoutSetContextPointer(column, "modifier", &ptr); - - /* rounded header ------------------------------------------------------------------- */ - box = uiLayoutBox(column); - - if (isVirtual) { - row = uiLayoutRow(box, false); - uiLayoutSetAlignment(row, UI_LAYOUT_ALIGN_EXPAND); - block = uiLayoutGetBlock(row); - /* VIRTUAL MODIFIER */ - /* XXX this is not used now, since these cannot be accessed via RNA */ - BLI_snprintf(str, sizeof(str), IFACE_("%s parent deform"), md->name); - uiDefBut(block, - UI_BTYPE_LABEL, - 0, - str, - 0, - 0, - 185, - UI_UNIT_Y, - NULL, - 0.0, - 0.0, - 0.0, - 0.0, - TIP_("Modifier name")); - - but = uiDefBut(block, - UI_BTYPE_BUT, - 0, - IFACE_("Make Real"), - 0, - 0, - 80, - 16, - NULL, - 0.0, - 0.0, - 0.0, - 0.0, - TIP_("Convert virtual modifier to a real modifier")); - UI_but_func_set(but, modifiers_convertToReal, ob, md); + Object *ob; + SpaceProperties *sbuts = CTX_wm_space_properties(C); + if (sbuts != NULL && (sbuts->pinid != NULL) && GS(sbuts->pinid->name) == ID_OB) { + ob = (Object *)sbuts->pinid; } else { - /* REAL MODIFIER */ - row = uiLayoutRow(box, false); - block = uiLayoutGetBlock(row); - - UI_block_emboss_set(block, UI_EMBOSS_NONE); - /* Open/Close ................................. */ - uiItemR(row, &ptr, "show_expanded", 0, "", ICON_NONE); - - /* modifier-type icon */ - uiItemL(row, "", RNA_struct_ui_icon(ptr.type)); - UI_block_emboss_set(block, UI_EMBOSS); - - /* modifier name */ - if (mti->isDisabled && mti->isDisabled(scene, md, 0)) { - uiLayoutSetRedAlert(row, true); - } - uiItemR(row, &ptr, "name", 0, "", ICON_NONE); - uiLayoutSetRedAlert(row, false); - - /* mode enabling buttons */ - UI_block_align_begin(block); - /* Collision and Surface are always enabled, hide buttons! */ - if (((md->type != eModifierType_Collision) || !(ob->pd && ob->pd->deflect)) && - (md->type != eModifierType_Surface)) { - uiItemR(row, &ptr, "show_render", 0, "", ICON_NONE); - uiItemR(row, &ptr, "show_viewport", 0, "", ICON_NONE); - - if (mti->flags & eModifierTypeFlag_SupportsEditmode) { - sub = uiLayoutRow(row, true); - if (!(md->mode & eModifierMode_Realtime)) { - uiLayoutSetActive(sub, false); - } - uiItemR(sub, &ptr, "show_in_editmode", 0, "", ICON_NONE); - } - } - - if (ob->type == OB_MESH) { - if (BKE_modifier_supports_cage(scene, md) && (index <= lastCageIndex)) { - sub = uiLayoutRow(row, true); - if (index < cageIndex || !BKE_modifier_couldbe_cage(scene, md)) { - uiLayoutSetActive(sub, false); - } - uiItemR(sub, &ptr, "show_on_cage", 0, "", ICON_NONE); - } - } /* tessellation point for curve-typed objects */ - else if (ELEM(ob->type, OB_CURVE, OB_SURF, OB_FONT)) { - /* some modifiers could work with pre-tessellated curves only */ - if (ELEM(md->type, eModifierType_Hook, eModifierType_Softbody, eModifierType_MeshDeform)) { - /* add disabled pre-tessellated button, so users could have - * message for this modifiers */ - but = uiDefIconButBitI(block, - UI_BTYPE_TOGGLE, - eModifierMode_ApplyOnSpline, - 0, - ICON_SURFACE_DATA, - 0, - 0, - UI_UNIT_X - 2, - UI_UNIT_Y, - &md->mode, - 0.0, - 0.0, - 0.0, - 0.0, - TIP_("This modifier can only be applied on splines' points")); - UI_but_flag_enable(but, UI_BUT_DISABLED); - } - else if (mti->type != eModifierTypeType_Constructive) { - /* constructive modifiers tessellates curve before applying */ - uiItemR(row, &ptr, "use_apply_on_spline", 0, "", ICON_NONE); - } - } - - UI_block_align_end(block); - - /* Up/Down + Delete ........................... */ - UI_block_align_begin(block); - uiItemO(row, "", ICON_TRIA_UP, "OBJECT_OT_modifier_move_up"); - uiItemO(row, "", ICON_TRIA_DOWN, "OBJECT_OT_modifier_move_down"); - UI_block_align_end(block); - - UI_block_emboss_set(block, UI_EMBOSS_NONE); - /* When Modifier is a simulation, - * show button to switch to context rather than the delete button. */ - if (modifier_can_delete(md) && !modifier_is_simulation(md)) { - uiItemO(row, "", ICON_X, "OBJECT_OT_modifier_remove"); - } - else if (modifier_is_simulation(md) == 1) { - uiItemStringO( - row, "", ICON_PROPERTIES, "WM_OT_properties_context_change", "context", "PHYSICS"); - } - else if (modifier_is_simulation(md) == 2) { - uiItemStringO( - row, "", ICON_PROPERTIES, "WM_OT_properties_context_change", "context", "PARTICLES"); - } - UI_block_emboss_set(block, UI_EMBOSS); + ob = CTX_data_active_object(C); } + ListBase *modifiers = &ob->modifiers; - /* modifier settings (under the header) --------------------------------------------------- */ - if (!isVirtual && (md->mode & eModifierMode_Expanded)) { - /* apply/convert/copy */ - box = uiLayoutBox(column); - row = uiLayoutRow(box, false); + bool panels_match = UI_panel_list_matches_data(region, modifiers, modifier_panel_id); - if (!ELEM(md->type, eModifierType_Collision, eModifierType_Surface)) { - /* only here obdata, the rest of modifiers is ob level */ - UI_block_lock_set(block, BKE_object_obdata_is_libdata(ob), ERROR_LIBDATA_MESSAGE); + if (!panels_match) { + UI_panels_free_instanced(C, region); + ModifierData *md = modifiers->first; + for (int i = 0; md; i++, md = md->next) { + const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); + if (mti->panelRegister) { + char panel_idname[MAX_NAME]; + modifier_panel_id(md, panel_idname); - if (md->type == eModifierType_ParticleSystem) { - ParticleSystem *psys = ((ParticleSystemModifierData *)md)->psys; - - if (!(ob->mode & OB_MODE_PARTICLE_EDIT)) { - if (ELEM(psys->part->ren_as, PART_DRAW_GR, PART_DRAW_OB)) { - uiItemO(row, - CTX_IFACE_(BLT_I18NCONTEXT_OPERATOR_DEFAULT, "Convert"), - ICON_NONE, - "OBJECT_OT_duplicates_make_real"); - } - else if (psys->part->ren_as == PART_DRAW_PATH) { - uiItemO(row, - CTX_IFACE_(BLT_I18NCONTEXT_OPERATOR_DEFAULT, "Convert"), - ICON_NONE, - "OBJECT_OT_modifier_convert"); - } + Panel *new_panel = UI_panel_add_instanced(sa, region, ®ion->panels, panel_idname, i); + if (new_panel != NULL) { + UI_panel_set_expand_from_list_data(C, new_panel); } } - else { - uiLayoutSetOperatorContext(row, WM_OP_INVOKE_DEFAULT); - uiItemEnumO(row, - "OBJECT_OT_modifier_apply", - CTX_IFACE_(BLT_I18NCONTEXT_OPERATOR_DEFAULT, "Apply"), - 0, - "apply_as", - MODIFIER_APPLY_DATA); - - if (BKE_modifier_is_same_topology(md) && !BKE_modifier_is_non_geometrical(md)) { - uiItemEnumO(row, - "OBJECT_OT_modifier_apply", - CTX_IFACE_(BLT_I18NCONTEXT_OPERATOR_DEFAULT, "Apply as Shape Key"), - 0, - "apply_as", - MODIFIER_APPLY_SHAPE); - } - } - - UI_block_lock_clear(block); - UI_block_lock_set(block, ob && ID_IS_LINKED(ob), ERROR_LIBDATA_MESSAGE); - - if (!ELEM(md->type, - eModifierType_Fluidsim, - eModifierType_Softbody, - eModifierType_ParticleSystem, - eModifierType_Cloth, - eModifierType_Fluid)) { - uiItemO(row, - CTX_IFACE_(BLT_I18NCONTEXT_OPERATOR_DEFAULT, "Copy"), - ICON_NONE, - "OBJECT_OT_modifier_copy"); - } } - - /* result is the layout block inside the box, - * that we return so that modifier settings can be drawn */ - result = uiLayoutColumn(box, false); - block = uiLayoutAbsoluteBlock(box); } - - /* error messages */ - if (md->error) { - box = uiLayoutBox(column); - row = uiLayoutRow(box, false); - uiItemL(row, md->error, ICON_ERROR); - } - - return result; -} - -uiLayout *uiTemplateModifier(uiLayout *layout, bContext *C, PointerRNA *ptr) -{ - Scene *scene = CTX_data_scene(C); - Object *ob; - ModifierData *md, *vmd; - VirtualModifierData virtualModifierData; - int i, lastCageIndex, cageIndex; - - /* verify we have valid data */ - if (!RNA_struct_is_a(ptr->type, &RNA_Modifier)) { - RNA_warning("Expected modifier on object"); - return NULL; - } - - ob = (Object *)ptr->owner_id; - md = ptr->data; - - if (!ob || !(GS(ob->id.name) == ID_OB)) { - RNA_warning("Expected modifier on object"); - return NULL; - } - - UI_block_lock_set(uiLayoutGetBlock(layout), (ob && ID_IS_LINKED(ob)), ERROR_LIBDATA_MESSAGE); - - /* find modifier and draw it */ - cageIndex = BKE_modifiers_get_cage_index(scene, ob, &lastCageIndex, 0); - - /* XXX virtual modifiers are not accessible for python */ - vmd = BKE_modifiers_get_virtual_modifierlist(ob, &virtualModifierData); - - for (i = 0; vmd; i++, vmd = vmd->next) { - if (md == vmd) { - return draw_modifier(layout, scene, ob, md, i, cageIndex, lastCageIndex); - } - else if (vmd->mode & eModifierMode_Virtual) { - i--; - } - } - - return NULL; } /** \} */ @@ -2178,6 +1868,8 @@ uiLayout *uiTemplateModifier(uiLayout *layout, bContext *C, PointerRNA *ptr) /** \name Grease Pencil Modifier Template * \{ */ +#define ERROR_LIBDATA_MESSAGE TIP_("Can't edit external library data") + static uiLayout *gpencil_draw_modifier(uiLayout *layout, Object *ob, GpencilModifierData *md) { const GpencilModifierTypeInfo *mti = BKE_gpencil_modifier_get_info(md->type); diff --git a/source/blender/editors/object/object_intern.h b/source/blender/editors/object/object_intern.h index d7a7b4ca110..c5a6e38fbcb 100644 --- a/source/blender/editors/object/object_intern.h +++ b/source/blender/editors/object/object_intern.h @@ -162,6 +162,7 @@ void OBJECT_OT_modifier_add(struct wmOperatorType *ot); void OBJECT_OT_modifier_remove(struct wmOperatorType *ot); void OBJECT_OT_modifier_move_up(struct wmOperatorType *ot); void OBJECT_OT_modifier_move_down(struct wmOperatorType *ot); +void OBJECT_OT_modifier_move_to_index(struct wmOperatorType *ot); void OBJECT_OT_modifier_apply(struct wmOperatorType *ot); void OBJECT_OT_modifier_convert(struct wmOperatorType *ot); void OBJECT_OT_modifier_copy(struct wmOperatorType *ot); diff --git a/source/blender/editors/object/object_modifier.c b/source/blender/editors/object/object_modifier.c index 9398a5f2ce7..0bd49f74db9 100644 --- a/source/blender/editors/object/object_modifier.c +++ b/source/blender/editors/object/object_modifier.c @@ -430,7 +430,7 @@ void ED_object_modifier_clear(Main *bmain, Object *ob) DEG_relations_tag_update(bmain); } -int ED_object_modifier_move_up(ReportList *reports, Object *ob, ModifierData *md) +bool ED_object_modifier_move_up(ReportList *reports, Object *ob, ModifierData *md) { if (md->prev) { const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); @@ -440,18 +440,22 @@ int ED_object_modifier_move_up(ReportList *reports, Object *ob, ModifierData *md if (nmti->flags & eModifierTypeFlag_RequiresOriginalData) { BKE_report(reports, RPT_WARNING, "Cannot move above a modifier requiring original data"); - return 0; + return false; } } BLI_remlink(&ob->modifiers, md); BLI_insertlinkbefore(&ob->modifiers, md->prev, md); } + else { + BKE_report(reports, RPT_WARNING, "Cannot move modifier beyond the start of the list"); + return false; + } - return 1; + return true; } -int ED_object_modifier_move_down(ReportList *reports, Object *ob, ModifierData *md) +bool ED_object_modifier_move_down(ReportList *reports, Object *ob, ModifierData *md) { if (md->next) { const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); @@ -461,15 +465,53 @@ int ED_object_modifier_move_down(ReportList *reports, Object *ob, ModifierData * if (nmti->type != eModifierTypeType_OnlyDeform) { BKE_report(reports, RPT_WARNING, "Cannot move beyond a non-deforming modifier"); - return 0; + return false; } } BLI_remlink(&ob->modifiers, md); BLI_insertlinkafter(&ob->modifiers, md->next, md); } + else { + BKE_report(reports, RPT_WARNING, "Cannot move modifier beyond the end of the list"); + return false; + } - return 1; + return true; +} + +bool ED_object_modifier_move_to_index(ReportList *reports, + Object *ob, + ModifierData *md, + const int index) +{ + BLI_assert(md != NULL); + BLI_assert(index >= 0); + if (index >= BLI_listbase_count(&ob->modifiers)) { + BKE_report(reports, RPT_WARNING, "Cannot move modifier beyond the end of the stack"); + return false; + } + + int md_index = BLI_findindex(&ob->modifiers, md); + BLI_assert(md_index != -1); + if (md_index < index) { + /* Move modifier down in list. */ + for (; md_index < index; md_index++) { + if (!ED_object_modifier_move_down(reports, ob, md)) { + break; + } + } + } + else { + /* Move modifier up in list. */ + for (; md_index > index; md_index--) { + if (!ED_object_modifier_move_up(reports, ob, md)) { + break; + } + } + } + + return true; } int ED_object_modifier_convert(ReportList *UNUSED(reports), @@ -1180,6 +1222,60 @@ void OBJECT_OT_modifier_move_down(wmOperatorType *ot) /** \} */ /* ------------------------------------------------------------------- */ +/** \name Move to Index Modifier Operator + * \{ */ + +static bool modifier_move_to_index_poll(bContext *C) +{ + return edit_modifier_poll(C); +} + +static int modifier_move_to_index_exec(bContext *C, wmOperator *op) +{ + Object *ob = ED_object_active_context(C); + ModifierData *md = edit_modifier_property_get(op, ob, 0); + int index = RNA_int_get(op->ptr, "index"); + + if (!ED_object_modifier_move_to_index(op->reports, ob, md, index)) { + return OPERATOR_CANCELLED; + } + + DEG_id_tag_update(&ob->id, ID_RECALC_GEOMETRY); + WM_event_add_notifier(C, NC_OBJECT | ND_MODIFIER, ob); + + return OPERATOR_FINISHED; +} + +static int modifier_move_to_index_invoke(bContext *C, wmOperator *op, const wmEvent *UNUSED(event)) +{ + if (edit_modifier_invoke_properties(C, op)) { + return modifier_move_to_index_exec(C, op); + } + else { + return OPERATOR_CANCELLED; + } +} + +void OBJECT_OT_modifier_move_to_index(wmOperatorType *ot) +{ + ot->name = "Move Active Modifier to Index"; + ot->description = "Move the active modifier to an index in the stack"; + ot->idname = "OBJECT_OT_modifier_move_to_index"; + + ot->invoke = modifier_move_to_index_invoke; + ot->exec = modifier_move_to_index_exec; + ot->poll = modifier_move_to_index_poll; + + /* flags */ + ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO | OPTYPE_INTERNAL; + edit_modifier_properties(ot); + RNA_def_int( + ot->srna, "index", 0, 0, INT_MAX, "Index", "The index to move the modifier to", 0, INT_MAX); +} + +/** \} */ + +/* ------------------------------------------------------------------- */ /** \name Apply Modifier Operator * \{ */ diff --git a/source/blender/editors/object/object_ops.c b/source/blender/editors/object/object_ops.c index 819b6c18a44..05f1ced8615 100644 --- a/source/blender/editors/object/object_ops.c +++ b/source/blender/editors/object/object_ops.c @@ -130,6 +130,7 @@ void ED_operatortypes_object(void) WM_operatortype_append(OBJECT_OT_modifier_remove); WM_operatortype_append(OBJECT_OT_modifier_move_up); WM_operatortype_append(OBJECT_OT_modifier_move_down); + WM_operatortype_append(OBJECT_OT_modifier_move_to_index); WM_operatortype_append(OBJECT_OT_modifier_apply); WM_operatortype_append(OBJECT_OT_modifier_convert); WM_operatortype_append(OBJECT_OT_modifier_copy); diff --git a/source/blender/editors/space_buttons/space_buttons.c b/source/blender/editors/space_buttons/space_buttons.c index c06c107d4a3..187334a5c34 100644 --- a/source/blender/editors/space_buttons/space_buttons.c +++ b/source/blender/editors/space_buttons/space_buttons.c @@ -30,8 +30,11 @@ #include "BLI_utildefines.h" #include "BKE_context.h" +#include "BKE_modifier.h" #include "BKE_screen.h" +#include "DNA_modifier_types.h" + #include "ED_screen.h" #include "ED_space_api.h" #include "ED_view3d.h" /* To draw toolbar UI. */ @@ -632,6 +635,15 @@ void ED_spacetype_buttons(void) #endif BLI_addhead(&st->regiontypes, art); + /* Register the panel types from modifiers. The actual panels are built per modifier rather than + * per modifier type. */ + for (ModifierType i = 0; i < NUM_MODIFIER_TYPES; i++) { + const ModifierTypeInfo *mti = BKE_modifier_get_info(i); + if (mti != NULL && mti->panelRegister != NULL) { + mti->panelRegister(art); + } + } + /* regions: header */ art = MEM_callocN(sizeof(ARegionType), "spacetype buttons region"); art->regionid = RGN_TYPE_HEADER; |