static int multires_external_pack_exec(bContext *C, wmOperator *UNUSED(op)) { Object *ob = ED_object_active_context(C); Mesh *me= ob->data; if(!CustomData_external_test(&me->fdata, CD_MDISPS)) return OPERATOR_CANCELLED; // XXX don't remove.. CustomData_external_remove(&me->fdata, &me->id, CD_MDISPS, me->totface); return OPERATOR_FINISHED; }
static int modifier_apply_obdata(ReportList *reports, Scene *scene, Object *ob, ModifierData *md) { ModifierTypeInfo *mti= modifierType_getInfo(md->type); md->scene= scene; if (mti->isDisabled && mti->isDisabled(md, 0)) { BKE_report(reports, RPT_ERROR, "Modifier is disabled, skipping apply"); return 0; } if (ob->type==OB_MESH) { DerivedMesh *dm; Mesh *me = ob->data; MultiresModifierData *mmd= find_multires_modifier_before(scene, md); if(me->key && mti->type != eModifierTypeType_NonGeometrical) { BKE_report(reports, RPT_ERROR, "Modifier cannot be applied to Mesh with Shape Keys"); return 0; } /* Multires: ensure that recent sculpting is applied */ if(md->type == eModifierType_Multires) multires_force_update(ob); if (mmd && mmd->totlvl && mti->type==eModifierTypeType_OnlyDeform) { if(!multiresModifier_reshapeFromDeformMod (scene, mmd, ob, md)) { BKE_report(reports, RPT_ERROR, "Multires modifier returned error, skipping apply"); return 0; } } else { dm = mesh_create_derived_for_modifier(scene, ob, md); if (!dm) { BKE_report(reports, RPT_ERROR, "Modifier returned error, skipping apply"); return 0; } DM_to_mesh(dm, me); dm->release(dm); if(md->type == eModifierType_Multires) { CustomData_external_remove(&me->fdata, &me->id, CD_MDISPS, me->totface); CustomData_free_layer_active(&me->fdata, CD_MDISPS, me->totface); } } } else if (ELEM(ob->type, OB_CURVE, OB_SURF)) { Curve *cu; int numVerts; float (*vertexCos)[3]; if (ELEM(mti->type, eModifierTypeType_Constructive, eModifierTypeType_Nonconstructive)) { BKE_report(reports, RPT_ERROR, "Cannot apply constructive modifiers on curve"); return 0; } cu = ob->data; BKE_report(reports, RPT_INFO, "Applied modifier only changed CV points, not tesselated/bevel vertices"); vertexCos = curve_getVertexCos(cu, &cu->nurb, &numVerts); mti->deformVerts(md, ob, NULL, vertexCos, numVerts, 0, 0); curve_applyVertexCos(cu, &cu->nurb, vertexCos); MEM_freeN(vertexCos); DAG_id_tag_update(&ob->id, OB_RECALC_DATA); } else { BKE_report(reports, RPT_ERROR, "Cannot apply modifier for this object type"); return 0; } /* lattice modifier can be applied to particle system too */ if(ob->particlesystem.first) { ParticleSystem *psys = ob->particlesystem.first; for(; psys; psys=psys->next) { if(psys->part->type != PART_HAIR) continue; psys_apply_hair_lattice(scene, ob, psys); } } return 1; }
static int object_modifier_remove(Object *ob, ModifierData *md, int *sort_depsgraph) { ModifierData *obmd; /* It seems on rapid delete it is possible to * get called twice on same modifier, so make * sure it is in list. */ for(obmd=ob->modifiers.first; obmd; obmd=obmd->next) if(obmd==md) break; if(!obmd) return 0; /* special cases */ if(md->type == eModifierType_ParticleSystem) { ParticleSystemModifierData *psmd=(ParticleSystemModifierData*)md; BLI_remlink(&ob->particlesystem, psmd->psys); psys_free(ob, psmd->psys); psmd->psys= NULL; } else if(md->type == eModifierType_Softbody) { if(ob->soft) { sbFree(ob->soft); ob->soft= NULL; ob->softflag= 0; } } else if(md->type == eModifierType_Collision) { if(ob->pd) ob->pd->deflect= 0; *sort_depsgraph = 1; } else if(md->type == eModifierType_Surface) { if(ob->pd && ob->pd->shape == PFIELD_SHAPE_SURFACE) ob->pd->shape = PFIELD_SHAPE_PLANE; *sort_depsgraph = 1; } else if(md->type == eModifierType_Smoke) { ob->dt = OB_TEXTURE; } else if(md->type == eModifierType_Multires) { int ok= 1; Mesh *me= ob->data; ModifierData *tmpmd; /* ensure MDISPS CustomData layer is't used by another multires modifiers */ for(tmpmd= ob->modifiers.first; tmpmd; tmpmd= tmpmd->next) if(tmpmd!=md && tmpmd->type == eModifierType_Multires) { ok= 0; break; } if(ok) { if(me->edit_mesh) { EditMesh *em= me->edit_mesh; /* CustomData_external_remove is used here only to mark layer as non-external for further free-ing, so zero element count looks safer than em->totface */ CustomData_external_remove(&em->fdata, &me->id, CD_MDISPS, 0); EM_free_data_layer(em, &em->fdata, CD_MDISPS); } else { CustomData_external_remove(&me->fdata, &me->id, CD_MDISPS, me->totface); CustomData_free_layer_active(&me->fdata, CD_MDISPS, me->totface); } } } if(ELEM(md->type, eModifierType_Softbody, eModifierType_Cloth) && ob->particlesystem.first == NULL) { ob->mode &= ~OB_MODE_PARTICLE_EDIT; } BLI_remlink(&ob->modifiers, md); modifier_free(md); return 1; }
int ED_object_modifier_remove(ReportList *reports, Main *bmain, Scene *scene, Object *ob, ModifierData *md) { ModifierData *obmd; int sort_depsgraph = 0; /* It seems on rapid delete it is possible to * get called twice on same modifier, so make * sure it is in list. */ for(obmd=ob->modifiers.first; obmd; obmd=obmd->next) if(obmd==md) break; if(!obmd) { BKE_reportf(reports, RPT_ERROR, "Modifier '%s' not in object '%s'", ob->id.name, md->name); return 0; } /* special cases */ if(md->type == eModifierType_ParticleSystem) { ParticleSystemModifierData *psmd=(ParticleSystemModifierData*)md; BLI_remlink(&ob->particlesystem, psmd->psys); psys_free(ob, psmd->psys); psmd->psys= NULL; } else if(md->type == eModifierType_Softbody) { if(ob->soft) { sbFree(ob->soft); ob->soft= NULL; ob->softflag= 0; } } else if(md->type == eModifierType_Collision) { if(ob->pd) ob->pd->deflect= 0; sort_depsgraph = 1; } else if(md->type == eModifierType_Surface) { if(ob->pd && ob->pd->shape == PFIELD_SHAPE_SURFACE) ob->pd->shape = PFIELD_SHAPE_PLANE; sort_depsgraph = 1; } else if(md->type == eModifierType_Smoke) { ob->dt = OB_TEXTURE; } else if(md->type == eModifierType_Multires) { int ok= 1; Mesh *me= ob->data; ModifierData *tmpmd; /* ensure MDISPS CustomData layer is't used by another multires modifiers */ for(tmpmd= ob->modifiers.first; tmpmd; tmpmd= tmpmd->next) if(tmpmd!=md && tmpmd->type == eModifierType_Multires) { ok= 0; break; } if(ok) { if(me->edit_mesh) { EditMesh *em= me->edit_mesh; /* CustomData_external_remove is used here only to mark layer as non-external for further free-ing, so zero element count looks safer than em->totface */ CustomData_external_remove(&em->fdata, &me->id, CD_MDISPS, 0); EM_free_data_layer(em, &em->fdata, CD_MDISPS); } else { CustomData_external_remove(&me->fdata, &me->id, CD_MDISPS, me->totface); CustomData_free_layer_active(&me->fdata, CD_MDISPS, me->totface); } } } if(ELEM(md->type, eModifierType_Softbody, eModifierType_Cloth) && ob->particlesystem.first == NULL) { ob->mode &= ~OB_MODE_PARTICLE_EDIT; } BLI_remlink(&ob->modifiers, md); modifier_free(md); DAG_id_tag_update(&ob->id, OB_RECALC_DATA); /* sorting has to be done after the update so that dynamic systems can react properly */ if(sort_depsgraph) DAG_scene_sort(bmain, scene); return 1; }