diff options
author | Hans Goudey <h.goudey@me.com> | 2022-09-30 00:43:09 +0300 |
---|---|---|
committer | Hans Goudey <h.goudey@me.com> | 2022-09-30 00:43:09 +0300 |
commit | 0ff485b6bac274c26605da56995ad6a3a63dd8e5 (patch) | |
tree | 8c55fbc1e9ddbbc691c4e1930b7a5f6b81aa6c11 /source/blender/blenkernel/intern/modifier.c | |
parent | 3059c0998a3db3e123a6894f7862fce3084001cd (diff) |
Cleanup: Move modifier.c to C++
Diffstat (limited to 'source/blender/blenkernel/intern/modifier.c')
-rw-r--r-- | source/blender/blenkernel/intern/modifier.c | 1516 |
1 files changed, 0 insertions, 1516 deletions
diff --git a/source/blender/blenkernel/intern/modifier.c b/source/blender/blenkernel/intern/modifier.c deleted file mode 100644 index ba84b27bf31..00000000000 --- a/source/blender/blenkernel/intern/modifier.c +++ /dev/null @@ -1,1516 +0,0 @@ -/* SPDX-License-Identifier: GPL-2.0-or-later - * Copyright 2005 Blender Foundation. All rights reserved. */ - -/** \file - * \ingroup bke - * Modifier stack implementation. - * BKE_modifier.h contains the function prototypes for this file. - */ - -/* Allow using deprecated functionality for .blend file I/O. */ -#define DNA_DEPRECATED_ALLOW - -#include <float.h> -#include <math.h> -#include <stdarg.h> -#include <stddef.h> -#include <stdlib.h> -#include <string.h> - -#include "MEM_guardedalloc.h" - -#include "DNA_armature_types.h" -#include "DNA_cloth_types.h" -#include "DNA_dynamicpaint_types.h" -#include "DNA_fluid_types.h" -#include "DNA_gpencil_modifier_types.h" -#include "DNA_mesh_types.h" -#include "DNA_object_fluidsim_types.h" -#include "DNA_object_force_types.h" -#include "DNA_object_types.h" -#include "DNA_scene_types.h" -#include "DNA_screen_types.h" - -#include "BLI_linklist.h" -#include "BLI_listbase.h" -#include "BLI_path_util.h" -#include "BLI_session_uuid.h" -#include "BLI_string.h" -#include "BLI_string_utils.h" -#include "BLI_utildefines.h" - -#include "BLT_translation.h" - -#include "BKE_DerivedMesh.h" -#include "BKE_appdir.h" -#include "BKE_editmesh.h" -#include "BKE_editmesh_cache.h" -#include "BKE_effect.h" -#include "BKE_fluid.h" -#include "BKE_global.h" -#include "BKE_gpencil_modifier.h" -#include "BKE_idtype.h" -#include "BKE_key.h" -#include "BKE_lib_id.h" -#include "BKE_lib_query.h" -#include "BKE_mesh.h" -#include "BKE_mesh_wrapper.h" -#include "BKE_multires.h" -#include "BKE_object.h" -#include "BKE_pointcache.h" - -/* may move these, only for BKE_modifier_path_relbase */ -#include "BKE_main.h" -/* end */ - -#include "DEG_depsgraph.h" -#include "DEG_depsgraph_query.h" - -#include "MOD_modifiertypes.h" - -#include "BLO_read_write.h" - -#include "CLG_log.h" - -static CLG_LogRef LOG = {"bke.modifier"}; -static ModifierTypeInfo *modifier_types[NUM_MODIFIER_TYPES] = {NULL}; -static VirtualModifierData virtualModifierCommonData; - -void BKE_modifier_init(void) -{ - ModifierData *md; - - /* Initialize modifier types */ - modifier_type_init(modifier_types); /* MOD_utils.c */ - - /* Initialize global common storage used for virtual modifier list. */ - md = BKE_modifier_new(eModifierType_Armature); - virtualModifierCommonData.amd = *((ArmatureModifierData *)md); - BKE_modifier_free(md); - - md = BKE_modifier_new(eModifierType_Curve); - virtualModifierCommonData.cmd = *((CurveModifierData *)md); - BKE_modifier_free(md); - - md = BKE_modifier_new(eModifierType_Lattice); - virtualModifierCommonData.lmd = *((LatticeModifierData *)md); - BKE_modifier_free(md); - - md = BKE_modifier_new(eModifierType_ShapeKey); - virtualModifierCommonData.smd = *((ShapeKeyModifierData *)md); - BKE_modifier_free(md); - - virtualModifierCommonData.amd.modifier.mode |= eModifierMode_Virtual; - virtualModifierCommonData.cmd.modifier.mode |= eModifierMode_Virtual; - virtualModifierCommonData.lmd.modifier.mode |= eModifierMode_Virtual; - virtualModifierCommonData.smd.modifier.mode |= eModifierMode_Virtual; -} - -const ModifierTypeInfo *BKE_modifier_get_info(ModifierType type) -{ - /* type unsigned, no need to check < 0 */ - if (type < NUM_MODIFIER_TYPES && modifier_types[type] && modifier_types[type]->name[0] != '\0') { - return modifier_types[type]; - } - - return NULL; -} - -void BKE_modifier_type_panel_id(ModifierType type, char *r_idname) -{ - const ModifierTypeInfo *mti = BKE_modifier_get_info(type); - - strcpy(r_idname, MODIFIER_TYPE_PANEL_PREFIX); - strcat(r_idname, mti->name); -} - -void BKE_modifier_panel_expand(ModifierData *md) -{ - md->ui_expand_flag |= UI_PANEL_DATA_EXPAND_ROOT; -} - -/***/ - -static ModifierData *modifier_allocate_and_init(int type) -{ - const ModifierTypeInfo *mti = BKE_modifier_get_info(type); - ModifierData *md = MEM_callocN(mti->structSize, mti->structName); - - /* NOTE: this name must be made unique later. */ - BLI_strncpy(md->name, DATA_(mti->name), sizeof(md->name)); - - md->type = type; - md->mode = eModifierMode_Realtime | eModifierMode_Render; - md->flag = eModifierFlag_OverrideLibrary_Local; - /* Only open the main panel at the beginning, not the sub-panels. */ - md->ui_expand_flag = UI_PANEL_DATA_EXPAND_ROOT; - - if (mti->flags & eModifierTypeFlag_EnableInEditmode) { - md->mode |= eModifierMode_Editmode; - } - - if (mti->initData) { - mti->initData(md); - } - - return md; -} - -ModifierData *BKE_modifier_new(int type) -{ - ModifierData *md = modifier_allocate_and_init(type); - - BKE_modifier_session_uuid_generate(md); - - return md; -} - -static void modifier_free_data_id_us_cb(void *UNUSED(userData), - Object *UNUSED(ob), - ID **idpoin, - int cb_flag) -{ - ID *id = *idpoin; - if (id != NULL && (cb_flag & IDWALK_CB_USER) != 0) { - id_us_min(id); - } -} - -void BKE_modifier_free_ex(ModifierData *md, const int flag) -{ - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - - if ((flag & LIB_ID_CREATE_NO_USER_REFCOUNT) == 0) { - if (mti->foreachIDLink) { - mti->foreachIDLink(md, NULL, modifier_free_data_id_us_cb, NULL); - } - } - - if (mti->freeData) { - mti->freeData(md); - } - if (md->error) { - MEM_freeN(md->error); - } - - MEM_freeN(md); -} - -void BKE_modifier_free(ModifierData *md) -{ - BKE_modifier_free_ex(md, 0); -} - -void BKE_modifier_remove_from_list(Object *ob, ModifierData *md) -{ - BLI_assert(BLI_findindex(&ob->modifiers, md) != -1); - - if (md->flag & eModifierFlag_Active) { - /* Prefer the previous modifier but use the next if this modifier is the first in the list. */ - if (md->next != NULL) { - BKE_object_modifier_set_active(ob, md->next); - } - else if (md->prev != NULL) { - BKE_object_modifier_set_active(ob, md->prev); - } - } - - BLI_remlink(&ob->modifiers, md); -} - -void BKE_modifier_session_uuid_generate(ModifierData *md) -{ - md->session_uuid = BLI_session_uuid_generate(); -} - -bool BKE_modifier_unique_name(ListBase *modifiers, ModifierData *md) -{ - if (modifiers && md) { - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - - return BLI_uniquename( - modifiers, md, DATA_(mti->name), '.', offsetof(ModifierData, name), sizeof(md->name)); - } - return false; -} - -bool BKE_modifier_depends_ontime(Scene *scene, ModifierData *md) -{ - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - - return mti->dependsOnTime && mti->dependsOnTime(scene, md); -} - -bool BKE_modifier_supports_mapping(ModifierData *md) -{ - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - - return (mti->type == eModifierTypeType_OnlyDeform || - (mti->flags & eModifierTypeFlag_SupportsMapping)); -} - -bool BKE_modifier_is_preview(ModifierData *md) -{ - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - - /* Constructive modifiers are highly likely to also modify data like vgroups or vcol! */ - if (!((mti->flags & eModifierTypeFlag_UsesPreview) || - (mti->type == eModifierTypeType_Constructive))) { - return false; - } - - if (md->mode & eModifierMode_Realtime) { - return true; - } - - return false; -} - -ModifierData *BKE_modifiers_findby_type(const Object *ob, ModifierType type) -{ - LISTBASE_FOREACH (ModifierData *, md, &ob->modifiers) { - if (md->type == type) { - return md; - } - } - return NULL; -} - -ModifierData *BKE_modifiers_findby_name(const Object *ob, const char *name) -{ - return BLI_findstring(&(ob->modifiers), name, offsetof(ModifierData, name)); -} - -ModifierData *BKE_modifiers_findby_session_uuid(const Object *ob, const SessionUUID *session_uuid) -{ - LISTBASE_FOREACH (ModifierData *, md, &ob->modifiers) { - if (BLI_session_uuid_is_equal(&md->session_uuid, session_uuid)) { - return md; - } - } - return NULL; -} - -void BKE_modifiers_clear_errors(Object *ob) -{ - LISTBASE_FOREACH (ModifierData *, md, &ob->modifiers) { - if (md->error) { - MEM_freeN(md->error); - md->error = NULL; - } - } -} - -void BKE_modifiers_foreach_ID_link(Object *ob, IDWalkFunc walk, void *userData) -{ - LISTBASE_FOREACH (ModifierData *, md, &ob->modifiers) { - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - - if (mti->foreachIDLink) { - mti->foreachIDLink(md, ob, walk, userData); - } - } -} - -void BKE_modifiers_foreach_tex_link(Object *ob, TexWalkFunc walk, void *userData) -{ - LISTBASE_FOREACH (ModifierData *, md, &ob->modifiers) { - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - - if (mti->foreachTexLink) { - mti->foreachTexLink(md, ob, walk, userData); - } - } -} - -ModifierData *BKE_modifier_copy_ex(const ModifierData *md, int flag) -{ - ModifierData *md_dst = modifier_allocate_and_init(md->type); - - BLI_strncpy(md_dst->name, md->name, sizeof(md_dst->name)); - BKE_modifier_copydata_ex(md, md_dst, flag); - - return md_dst; -} - -void BKE_modifier_copydata_generic(const ModifierData *md_src, - ModifierData *md_dst, - const int UNUSED(flag)) -{ - const ModifierTypeInfo *mti = BKE_modifier_get_info(md_src->type); - - /* md_dst may have already be fully initialized with some extra allocated data, - * we need to free it now to avoid memleak. */ - if (mti->freeData) { - mti->freeData(md_dst); - } - - const size_t data_size = sizeof(ModifierData); - const char *md_src_data = ((const char *)md_src) + data_size; - char *md_dst_data = ((char *)md_dst) + data_size; - BLI_assert(data_size <= (size_t)mti->structSize); - memcpy(md_dst_data, md_src_data, (size_t)mti->structSize - data_size); - - /* Runtime fields are never to be preserved. */ - md_dst->runtime = NULL; -} - -static void modifier_copy_data_id_us_cb(void *UNUSED(userData), - Object *UNUSED(ob), - ID **idpoin, - int cb_flag) -{ - ID *id = *idpoin; - if (id != NULL && (cb_flag & IDWALK_CB_USER) != 0) { - id_us_plus(id); - } -} - -void BKE_modifier_copydata_ex(const ModifierData *md, ModifierData *target, const int flag) -{ - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - - target->mode = md->mode; - target->flag = md->flag; - target->ui_expand_flag = md->ui_expand_flag; - - if (mti->copyData) { - mti->copyData(md, target, flag); - } - - if ((flag & LIB_ID_CREATE_NO_USER_REFCOUNT) == 0) { - if (mti->foreachIDLink) { - mti->foreachIDLink(target, NULL, modifier_copy_data_id_us_cb, NULL); - } - } - - if (flag & LIB_ID_CREATE_NO_MAIN) { - /* Make sure UUID is the same between the source and the target. - * This is needed in the cases when UUID is to be preserved and when there is no copyData - * callback, or the copyData does not do full byte copy of the modifier data. */ - target->session_uuid = md->session_uuid; - } - else { - /* In the case copyData made full byte copy force UUID to be re-generated. */ - BKE_modifier_session_uuid_generate(target); - } -} - -void BKE_modifier_copydata(const ModifierData *md, ModifierData *target) -{ - BKE_modifier_copydata_ex(md, target, 0); -} - -bool BKE_modifier_supports_cage(struct Scene *scene, ModifierData *md) -{ - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - - return ((!mti->isDisabled || !mti->isDisabled(scene, md, 0)) && - (mti->flags & eModifierTypeFlag_SupportsEditmode) && BKE_modifier_supports_mapping(md)); -} - -bool BKE_modifier_couldbe_cage(struct Scene *scene, ModifierData *md) -{ - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - - return ((md->mode & eModifierMode_Realtime) && (md->mode & eModifierMode_Editmode) && - (!mti->isDisabled || !mti->isDisabled(scene, md, 0)) && - BKE_modifier_supports_mapping(md)); -} - -bool BKE_modifier_is_same_topology(ModifierData *md) -{ - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - return ELEM(mti->type, eModifierTypeType_OnlyDeform, eModifierTypeType_NonGeometrical); -} - -bool BKE_modifier_is_non_geometrical(ModifierData *md) -{ - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - return (mti->type == eModifierTypeType_NonGeometrical); -} - -void BKE_modifier_set_error(const Object *ob, ModifierData *md, const char *_format, ...) -{ - char buffer[512]; - va_list ap; - const char *format = TIP_(_format); - - va_start(ap, _format); - vsnprintf(buffer, sizeof(buffer), format, ap); - va_end(ap); - buffer[sizeof(buffer) - 1] = '\0'; - - if (md->error) { - MEM_freeN(md->error); - } - - md->error = BLI_strdup(buffer); - -#ifndef NDEBUG - if ((md->mode & eModifierMode_Virtual) == 0) { - /* Ensure correct object is passed in. */ - BLI_assert(BKE_modifier_get_original(ob, md) != NULL); - } -#endif - - CLOG_ERROR(&LOG, "Object: \"%s\", Modifier: \"%s\", %s", ob->id.name + 2, md->name, md->error); -} - -void BKE_modifier_set_warning(const struct Object *ob, - struct ModifierData *md, - const char *_format, - ...) -{ - char buffer[512]; - va_list ap; - const char *format = TIP_(_format); - - va_start(ap, _format); - vsnprintf(buffer, sizeof(buffer), format, ap); - va_end(ap); - buffer[sizeof(buffer) - 1] = '\0'; - - /* Store the warning in the same field as the error. - * It is not expected to have both error and warning and having a single place to store the - * message simplifies interface code. */ - - if (md->error) { - MEM_freeN(md->error); - } - - md->error = BLI_strdup(buffer); - -#ifndef NDEBUG - if ((md->mode & eModifierMode_Virtual) == 0) { - /* Ensure correct object is passed in. */ - BLI_assert(BKE_modifier_get_original(ob, md) != NULL); - } -#endif - - UNUSED_VARS_NDEBUG(ob); -} - -int BKE_modifiers_get_cage_index(const Scene *scene, - Object *ob, - int *r_lastPossibleCageIndex, - bool is_virtual) -{ - VirtualModifierData virtualModifierData; - ModifierData *md = (is_virtual) ? - BKE_modifiers_get_virtual_modifierlist(ob, &virtualModifierData) : - ob->modifiers.first; - - if (r_lastPossibleCageIndex) { - /* ensure the value is initialized */ - *r_lastPossibleCageIndex = -1; - } - - /* Find the last modifier acting on the cage. */ - int cageIndex = -1; - for (int i = 0; md; i++, md = md->next) { - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - bool supports_mapping; - - if (mti->isDisabled && mti->isDisabled(scene, md, 0)) { - continue; - } - if (!(mti->flags & eModifierTypeFlag_SupportsEditmode)) { - continue; - } - if (md->mode & eModifierMode_DisableTemporary) { - continue; - } - - supports_mapping = BKE_modifier_supports_mapping(md); - if (r_lastPossibleCageIndex && supports_mapping) { - *r_lastPossibleCageIndex = i; - } - - if (!(md->mode & eModifierMode_Realtime)) { - continue; - } - if (!(md->mode & eModifierMode_Editmode)) { - continue; - } - - if (!supports_mapping) { - break; - } - - if (md->mode & eModifierMode_OnCage) { - cageIndex = i; - } - } - - return cageIndex; -} - -bool BKE_modifiers_is_softbody_enabled(Object *ob) -{ - ModifierData *md = BKE_modifiers_findby_type(ob, eModifierType_Softbody); - - return (md && md->mode & (eModifierMode_Realtime | eModifierMode_Render)); -} - -bool BKE_modifiers_is_cloth_enabled(Object *ob) -{ - ModifierData *md = BKE_modifiers_findby_type(ob, eModifierType_Cloth); - - return (md && md->mode & (eModifierMode_Realtime | eModifierMode_Render)); -} - -bool BKE_modifiers_is_modifier_enabled(Object *ob, int modifierType) -{ - ModifierData *md = BKE_modifiers_findby_type(ob, modifierType); - - return (md && md->mode & (eModifierMode_Realtime | eModifierMode_Render)); -} - -bool BKE_modifiers_is_particle_enabled(Object *ob) -{ - ModifierData *md = BKE_modifiers_findby_type(ob, eModifierType_ParticleSystem); - - return (md && md->mode & (eModifierMode_Realtime | eModifierMode_Render)); -} - -bool BKE_modifier_is_enabled(const struct Scene *scene, ModifierData *md, int required_mode) -{ - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - - if ((md->mode & required_mode) != required_mode) { - return false; - } - if (scene != NULL && mti->isDisabled && - mti->isDisabled(scene, md, required_mode == eModifierMode_Render)) { - return false; - } - if (md->mode & eModifierMode_DisableTemporary) { - return false; - } - if ((required_mode & eModifierMode_Editmode) && - !(mti->flags & eModifierTypeFlag_SupportsEditmode)) { - return false; - } - - return true; -} - -bool BKE_modifier_is_nonlocal_in_liboverride(const Object *ob, const ModifierData *md) -{ - return (ID_IS_OVERRIDE_LIBRARY(ob) && - (md == NULL || (md->flag & eModifierFlag_OverrideLibrary_Local) == 0)); -} - -CDMaskLink *BKE_modifier_calc_data_masks(const struct Scene *scene, - ModifierData *md, - CustomData_MeshMasks *final_datamask, - int required_mode, - ModifierData *previewmd, - const CustomData_MeshMasks *previewmask) -{ - CDMaskLink *dataMasks = NULL; - CDMaskLink *curr, *prev; - bool have_deform_modifier = false; - - /* build a list of modifier data requirements in reverse order */ - for (; md; md = md->next) { - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - - curr = MEM_callocN(sizeof(CDMaskLink), "CDMaskLink"); - - if (BKE_modifier_is_enabled(scene, md, required_mode)) { - if (mti->type == eModifierTypeType_OnlyDeform) { - have_deform_modifier = true; - } - - if (mti->requiredDataMask) { - mti->requiredDataMask(md, &curr->mask); - } - - if (previewmd == md && previewmask != NULL) { - CustomData_MeshMasks_update(&curr->mask, previewmask); - } - } - - if (!have_deform_modifier) { - /* Don't create orco layer when there is no deformation, we fall - * back to regular vertex coordinates */ - curr->mask.vmask &= ~CD_MASK_ORCO; - } - - /* prepend new datamask */ - curr->next = dataMasks; - dataMasks = curr; - } - - if (!have_deform_modifier) { - final_datamask->vmask &= ~CD_MASK_ORCO; - } - - /* build the list of required data masks - each mask in the list must - * include all elements of the masks that follow it - * - * note the list is currently in reverse order, so "masks that follow it" - * actually means "masks that precede it" at the moment - */ - for (curr = dataMasks, prev = NULL; curr; prev = curr, curr = curr->next) { - if (prev) { - CustomData_MeshMasks_update(&curr->mask, &prev->mask); - } - else { - CustomData_MeshMasks_update(&curr->mask, final_datamask); - } - } - - /* reverse the list so it's in the correct order */ - BLI_linklist_reverse((LinkNode **)&dataMasks); - - return dataMasks; -} - -ModifierData *BKE_modifier_get_last_preview(const struct Scene *scene, - ModifierData *md, - int required_mode) -{ - ModifierData *tmp_md = NULL; - - if ((required_mode & ~eModifierMode_Editmode) != eModifierMode_Realtime) { - return tmp_md; - } - - /* Find the latest modifier in stack generating preview. */ - for (; md; md = md->next) { - if (BKE_modifier_is_enabled(scene, md, required_mode) && BKE_modifier_is_preview(md)) { - tmp_md = md; - } - } - return tmp_md; -} - -ModifierData *BKE_modifiers_get_virtual_modifierlist(const Object *ob, - VirtualModifierData *virtualModifierData) -{ - ModifierData *md = ob->modifiers.first; - - *virtualModifierData = virtualModifierCommonData; - - if (ob->parent) { - if (ob->parent->type == OB_ARMATURE && ob->partype == PARSKEL) { - virtualModifierData->amd.object = ob->parent; - virtualModifierData->amd.modifier.next = md; - virtualModifierData->amd.deformflag = ((bArmature *)(ob->parent->data))->deformflag; - md = &virtualModifierData->amd.modifier; - } - else if (ob->parent->type == OB_CURVES_LEGACY && ob->partype == PARSKEL) { - virtualModifierData->cmd.object = ob->parent; - virtualModifierData->cmd.defaxis = ob->trackflag + 1; - virtualModifierData->cmd.modifier.next = md; - md = &virtualModifierData->cmd.modifier; - } - else if (ob->parent->type == OB_LATTICE && ob->partype == PARSKEL) { - virtualModifierData->lmd.object = ob->parent; - virtualModifierData->lmd.modifier.next = md; - md = &virtualModifierData->lmd.modifier; - } - } - - /* shape key modifier, not yet for curves */ - if (ELEM(ob->type, OB_MESH, OB_LATTICE) && BKE_key_from_object((Object *)ob)) { - if (ob->type == OB_MESH && (ob->shapeflag & OB_SHAPE_EDIT_MODE)) { - virtualModifierData->smd.modifier.mode |= eModifierMode_Editmode | eModifierMode_OnCage; - } - else { - virtualModifierData->smd.modifier.mode &= ~eModifierMode_Editmode | eModifierMode_OnCage; - } - - virtualModifierData->smd.modifier.next = md; - md = &virtualModifierData->smd.modifier; - } - - return md; -} - -Object *BKE_modifiers_is_deformed_by_armature(Object *ob) -{ - if (ob->type == OB_GPENCIL) { - GpencilVirtualModifierData gpencilvirtualModifierData; - ArmatureGpencilModifierData *agmd = NULL; - GpencilModifierData *gmd = BKE_gpencil_modifiers_get_virtual_modifierlist( - ob, &gpencilvirtualModifierData); - - /* return the first selected armature, this lets us use multiple armatures */ - for (; gmd; gmd = gmd->next) { - if (gmd->type == eGpencilModifierType_Armature) { - agmd = (ArmatureGpencilModifierData *)gmd; - if (agmd->object && (agmd->object->base_flag & BASE_SELECTED)) { - return agmd->object; - } - } - } - /* If we're still here then return the last armature. */ - if (agmd) { - return agmd->object; - } - } - else { - VirtualModifierData virtualModifierData; - ArmatureModifierData *amd = NULL; - ModifierData *md = BKE_modifiers_get_virtual_modifierlist(ob, &virtualModifierData); - - /* return the first selected armature, this lets us use multiple armatures */ - for (; md; md = md->next) { - if (md->type == eModifierType_Armature) { - amd = (ArmatureModifierData *)md; - if (amd->object && (amd->object->base_flag & BASE_SELECTED)) { - return amd->object; - } - } - } - /* If we're still here then return the last armature. */ - if (amd) { - return amd->object; - } - } - - return NULL; -} - -Object *BKE_modifiers_is_deformed_by_meshdeform(Object *ob) -{ - VirtualModifierData virtualModifierData; - ModifierData *md = BKE_modifiers_get_virtual_modifierlist(ob, &virtualModifierData); - MeshDeformModifierData *mdmd = NULL; - - /* return the first selected armature, this lets us use multiple armatures */ - for (; md; md = md->next) { - if (md->type == eModifierType_MeshDeform) { - mdmd = (MeshDeformModifierData *)md; - if (mdmd->object && (mdmd->object->base_flag & BASE_SELECTED)) { - return mdmd->object; - } - } - } - - if (mdmd) { /* if we're still here then return the last armature */ - return mdmd->object; - } - - return NULL; -} - -Object *BKE_modifiers_is_deformed_by_lattice(Object *ob) -{ - VirtualModifierData virtualModifierData; - ModifierData *md = BKE_modifiers_get_virtual_modifierlist(ob, &virtualModifierData); - LatticeModifierData *lmd = NULL; - - /* return the first selected lattice, this lets us use multiple lattices */ - for (; md; md = md->next) { - if (md->type == eModifierType_Lattice) { - lmd = (LatticeModifierData *)md; - if (lmd->object && (lmd->object->base_flag & BASE_SELECTED)) { - return lmd->object; - } - } - } - - if (lmd) { /* if we're still here then return the last lattice */ - return lmd->object; - } - - return NULL; -} - -Object *BKE_modifiers_is_deformed_by_curve(Object *ob) -{ - VirtualModifierData virtualModifierData; - ModifierData *md = BKE_modifiers_get_virtual_modifierlist(ob, &virtualModifierData); - CurveModifierData *cmd = NULL; - - /* return the first selected curve, this lets us use multiple curves */ - for (; md; md = md->next) { - if (md->type == eModifierType_Curve) { - cmd = (CurveModifierData *)md; - if (cmd->object && (cmd->object->base_flag & BASE_SELECTED)) { - return cmd->object; - } - } - } - - if (cmd) { /* if we're still here then return the last curve */ - return cmd->object; - } - - return NULL; -} - -bool BKE_modifiers_uses_multires(Object *ob) -{ - VirtualModifierData virtualModifierData; - ModifierData *md = BKE_modifiers_get_virtual_modifierlist(ob, &virtualModifierData); - MultiresModifierData *mmd = NULL; - - for (; md; md = md->next) { - if (md->type == eModifierType_Multires) { - mmd = (MultiresModifierData *)md; - if (mmd->totlvl != 0) { - return true; - } - } - } - return false; -} - -bool BKE_modifiers_uses_armature(Object *ob, bArmature *arm) -{ - VirtualModifierData virtualModifierData; - ModifierData *md = BKE_modifiers_get_virtual_modifierlist(ob, &virtualModifierData); - - for (; md; md = md->next) { - if (md->type == eModifierType_Armature) { - ArmatureModifierData *amd = (ArmatureModifierData *)md; - if (amd->object && amd->object->data == arm) { - return true; - } - } - } - - return false; -} - -bool BKE_modifier_is_correctable_deformed(ModifierData *md) -{ - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - return mti->deformMatricesEM != NULL; -} - -bool BKE_modifiers_is_correctable_deformed(const struct Scene *scene, Object *ob) -{ - VirtualModifierData virtualModifierData; - ModifierData *md = BKE_modifiers_get_virtual_modifierlist(ob, &virtualModifierData); - int required_mode = eModifierMode_Realtime; - - if (ob->mode == OB_MODE_EDIT) { - required_mode |= eModifierMode_Editmode; - } - for (; md; md = md->next) { - if (!BKE_modifier_is_enabled(scene, md, required_mode)) { - /* pass */ - } - else if (BKE_modifier_is_correctable_deformed(md)) { - return true; - } - } - return false; -} - -void BKE_modifier_free_temporary_data(ModifierData *md) -{ - if (md->type == eModifierType_Armature) { - ArmatureModifierData *amd = (ArmatureModifierData *)md; - - MEM_SAFE_FREE(amd->vert_coords_prev); - } -} - -void BKE_modifiers_test_object(Object *ob) -{ - ModifierData *md; - - /* just multires checked for now, since only multires - * modifies mesh data */ - - if (ob->type != OB_MESH) { - return; - } - - for (md = ob->modifiers.first; md; md = md->next) { - if (md->type == eModifierType_Multires) { - MultiresModifierData *mmd = (MultiresModifierData *)md; - - multiresModifier_set_levels_from_disps(mmd, ob); - } - } -} - -const char *BKE_modifier_path_relbase(Main *bmain, Object *ob) -{ - /* - If the ID is from a library, return library path. - * - Else if the file has been saved return the blend file path. - * - Else if the file isn't saved and the ID isn't from a library, return the temp dir. - */ - if ((bmain->filepath[0] != '\0') || ID_IS_LINKED(ob)) { - return ID_BLEND_PATH(bmain, &ob->id); - } - - /* Last resort, better than using "" which resolves to the current working directory. */ - return BKE_tempdir_session(); -} - -const char *BKE_modifier_path_relbase_from_global(Object *ob) -{ - return BKE_modifier_path_relbase(G_MAIN, ob); -} - -void BKE_modifier_path_init(char *path, int path_maxlen, const char *name) -{ - const char *blendfile_path = BKE_main_blendfile_path_from_global(); - BLI_join_dirfile(path, path_maxlen, blendfile_path[0] ? "//" : BKE_tempdir_session(), name); -} - -/** - * Call when #ModifierTypeInfo.dependsOnNormals callback requests normals. - */ -static void modwrap_dependsOnNormals(Mesh *me) -{ - switch ((eMeshWrapperType)me->runtime.wrapper_type) { - case ME_WRAPPER_TYPE_BMESH: { - EditMeshData *edit_data = me->runtime.edit_data; - if (edit_data->vertexCos) { - /* Note that 'ensure' is acceptable here since these values aren't modified in-place. - * If that changes we'll need to recalculate. */ - BKE_editmesh_cache_ensure_vert_normals(me->edit_mesh, edit_data); - } - else { - BM_mesh_normals_update(me->edit_mesh->bm); - } - break; - } - case ME_WRAPPER_TYPE_SUBD: - /* Not an expected case. */ - break; - case ME_WRAPPER_TYPE_MDATA: - /* Normals are calculated lazily. */ - break; - } -} - -/* wrapper around ModifierTypeInfo.modifyMesh that ensures valid normals */ - -struct Mesh *BKE_modifier_modify_mesh(ModifierData *md, - const ModifierEvalContext *ctx, - struct Mesh *me) -{ - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - - if (me->runtime.wrapper_type == ME_WRAPPER_TYPE_BMESH) { - if ((mti->flags & eModifierTypeFlag_AcceptsBMesh) == 0) { - BKE_mesh_wrapper_ensure_mdata(me); - } - } - - if (mti->dependsOnNormals && mti->dependsOnNormals(md)) { - modwrap_dependsOnNormals(me); - } - return mti->modifyMesh(md, ctx, me); -} - -void BKE_modifier_deform_verts(ModifierData *md, - const ModifierEvalContext *ctx, - Mesh *me, - float (*vertexCos)[3], - int numVerts) -{ - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - if (me && mti->dependsOnNormals && mti->dependsOnNormals(md)) { - modwrap_dependsOnNormals(me); - } - mti->deformVerts(md, ctx, me, vertexCos, numVerts); -} - -void BKE_modifier_deform_vertsEM(ModifierData *md, - const ModifierEvalContext *ctx, - struct BMEditMesh *em, - Mesh *me, - float (*vertexCos)[3], - int numVerts) -{ - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - if (me && mti->dependsOnNormals && mti->dependsOnNormals(md)) { - modwrap_dependsOnNormals(me); - } - mti->deformVertsEM(md, ctx, em, me, vertexCos, numVerts); -} - -/* end modifier callback wrappers */ - -Mesh *BKE_modifier_get_evaluated_mesh_from_evaluated_object(Object *ob_eval) -{ - Mesh *me = NULL; - - if ((ob_eval->type == OB_MESH) && (ob_eval->mode & OB_MODE_EDIT)) { - /* In EditMode, evaluated mesh is stored in BMEditMesh, not the object... */ - BMEditMesh *em = BKE_editmesh_from_object(ob_eval); - /* 'em' might not exist yet in some cases, just after loading a .blend file, see T57878. */ - if (em != NULL) { - me = BKE_object_get_editmesh_eval_final(ob_eval); - } - } - if (me == NULL) { - me = BKE_object_get_evaluated_mesh(ob_eval); - } - - return me; -} - -ModifierData *BKE_modifier_get_original(const Object *object, ModifierData *md) -{ - const Object *object_orig = DEG_get_original_object((Object *)object); - return BKE_modifiers_findby_session_uuid(object_orig, &md->session_uuid); -} - -struct ModifierData *BKE_modifier_get_evaluated(Depsgraph *depsgraph, - Object *object, - ModifierData *md) -{ - Object *object_eval = DEG_get_evaluated_object(depsgraph, object); - if (object_eval == object) { - return md; - } - return BKE_modifiers_findby_session_uuid(object_eval, &md->session_uuid); -} - -void BKE_modifier_check_uuids_unique_and_report(const Object *object) -{ - struct GSet *used_uuids = BLI_gset_new( - BLI_session_uuid_ghash_hash, BLI_session_uuid_ghash_compare, "modifier used uuids"); - - LISTBASE_FOREACH (ModifierData *, md, &object->modifiers) { - const SessionUUID *session_uuid = &md->session_uuid; - if (!BLI_session_uuid_is_generated(session_uuid)) { - printf("Modifier %s -> %s does not have UUID generated.\n", object->id.name + 2, md->name); - continue; - } - - if (BLI_gset_lookup(used_uuids, session_uuid) != NULL) { - printf("Modifier %s -> %s has duplicate UUID generated.\n", object->id.name + 2, md->name); - continue; - } - - BLI_gset_insert(used_uuids, (void *)session_uuid); - } - - BLI_gset_free(used_uuids, NULL); -} - -void BKE_modifier_blend_write(BlendWriter *writer, const ID *id_owner, ListBase *modbase) -{ - if (modbase == NULL) { - return; - } - - LISTBASE_FOREACH (ModifierData *, md, modbase) { - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - if (mti == NULL) { - continue; - } - - /* If the blendWrite callback is defined, it should handle the whole writing process. */ - if (mti->blendWrite != NULL) { - mti->blendWrite(writer, id_owner, md); - continue; - } - - BLO_write_struct_by_name(writer, mti->structName, md); - - if (md->type == eModifierType_Cloth) { - ClothModifierData *clmd = (ClothModifierData *)md; - - BLO_write_struct(writer, ClothSimSettings, clmd->sim_parms); - BLO_write_struct(writer, ClothCollSettings, clmd->coll_parms); - BLO_write_struct(writer, EffectorWeights, clmd->sim_parms->effector_weights); - BKE_ptcache_blend_write(writer, &clmd->ptcaches); - } - else if (md->type == eModifierType_Fluid) { - FluidModifierData *fmd = (FluidModifierData *)md; - - if (fmd->type & MOD_FLUID_TYPE_DOMAIN) { - BLO_write_struct(writer, FluidDomainSettings, fmd->domain); - - if (fmd->domain) { - BKE_ptcache_blend_write(writer, &(fmd->domain->ptcaches[0])); - - /* create fake pointcache so that old blender versions can read it */ - fmd->domain->point_cache[1] = BKE_ptcache_add(&fmd->domain->ptcaches[1]); - fmd->domain->point_cache[1]->flag |= PTCACHE_DISK_CACHE | PTCACHE_FAKE_SMOKE; - fmd->domain->point_cache[1]->step = 1; - - BKE_ptcache_blend_write(writer, &(fmd->domain->ptcaches[1])); - - if (fmd->domain->coba) { - BLO_write_struct(writer, ColorBand, fmd->domain->coba); - } - - /* cleanup the fake pointcache */ - BKE_ptcache_free_list(&fmd->domain->ptcaches[1]); - fmd->domain->point_cache[1] = NULL; - - BLO_write_struct(writer, EffectorWeights, fmd->domain->effector_weights); - } - } - else if (fmd->type & MOD_FLUID_TYPE_FLOW) { - BLO_write_struct(writer, FluidFlowSettings, fmd->flow); - } - else if (fmd->type & MOD_FLUID_TYPE_EFFEC) { - BLO_write_struct(writer, FluidEffectorSettings, fmd->effector); - } - } - else if (md->type == eModifierType_Fluidsim) { - FluidsimModifierData *fluidmd = (FluidsimModifierData *)md; - - BLO_write_struct(writer, FluidsimSettings, fluidmd->fss); - } - else if (md->type == eModifierType_DynamicPaint) { - DynamicPaintModifierData *pmd = (DynamicPaintModifierData *)md; - - if (pmd->canvas) { - BLO_write_struct(writer, DynamicPaintCanvasSettings, pmd->canvas); - - /* write surfaces */ - LISTBASE_FOREACH (DynamicPaintSurface *, surface, &pmd->canvas->surfaces) { - BLO_write_struct(writer, DynamicPaintSurface, surface); - } - /* write caches and effector weights */ - LISTBASE_FOREACH (DynamicPaintSurface *, surface, &pmd->canvas->surfaces) { - BKE_ptcache_blend_write(writer, &(surface->ptcaches)); - - BLO_write_struct(writer, EffectorWeights, surface->effector_weights); - } - } - if (pmd->brush) { - BLO_write_struct(writer, DynamicPaintBrushSettings, pmd->brush); - BLO_write_struct(writer, ColorBand, pmd->brush->paint_ramp); - BLO_write_struct(writer, ColorBand, pmd->brush->vel_ramp); - } - } - else if (md->type == eModifierType_Collision) { - -#if 0 - CollisionModifierData *collmd = (CollisionModifierData *)md; - /* TODO: CollisionModifier should use pointcache - * + have proper reset events before enabling this. */ - writestruct(wd, DATA, MVert, collmd->numverts, collmd->x); - writestruct(wd, DATA, MVert, collmd->numverts, collmd->xnew); - writestruct(wd, DATA, MFace, collmd->numfaces, collmd->mfaces); -#endif - } - } -} - -/* TODO(sergey): Find a better place for this. - * - * Unfortunately, this can not be done as a regular do_versions() since the modifier type is - * set to NONE, so the do_versions code wouldn't know where the modifier came from. - * - * The best approach seems to have the functionality in versioning_280.c but still call the - * function from #BKE_modifier_blend_read_data(). - */ - -/* Domain, inflow, ... */ -static void modifier_ensure_type(FluidModifierData *fluid_modifier_data, int type) -{ - fluid_modifier_data->type = type; - BKE_fluid_modifier_free(fluid_modifier_data); - BKE_fluid_modifier_create_type_data(fluid_modifier_data); -} - -/** - * \note The old_modifier_data is NOT linked. - * This means that in order to access sub-data pointers #BLO_read_get_new_data_address is to be - * used. - */ -static ModifierData *modifier_replace_with_fluid(BlendDataReader *reader, - Object *object, - ListBase *modifiers, - ModifierData *old_modifier_data) -{ - ModifierData *new_modifier_data = BKE_modifier_new(eModifierType_Fluid); - FluidModifierData *fluid_modifier_data = (FluidModifierData *)new_modifier_data; - - if (old_modifier_data->type == eModifierType_Fluidsim) { - FluidsimModifierData *old_fluidsim_modifier_data = (FluidsimModifierData *)old_modifier_data; - FluidsimSettings *old_fluidsim_settings = BLO_read_get_new_data_address( - reader, old_fluidsim_modifier_data->fss); - switch (old_fluidsim_settings->type) { - case OB_FLUIDSIM_ENABLE: - modifier_ensure_type(fluid_modifier_data, 0); - break; - case OB_FLUIDSIM_DOMAIN: - modifier_ensure_type(fluid_modifier_data, MOD_FLUID_TYPE_DOMAIN); - BKE_fluid_domain_type_set(object, fluid_modifier_data->domain, FLUID_DOMAIN_TYPE_LIQUID); - break; - case OB_FLUIDSIM_FLUID: - modifier_ensure_type(fluid_modifier_data, MOD_FLUID_TYPE_FLOW); - BKE_fluid_flow_type_set(object, fluid_modifier_data->flow, FLUID_FLOW_TYPE_LIQUID); - /* No need to emit liquid far away from surface. */ - fluid_modifier_data->flow->surface_distance = 0.0f; - break; - case OB_FLUIDSIM_OBSTACLE: - modifier_ensure_type(fluid_modifier_data, MOD_FLUID_TYPE_EFFEC); - BKE_fluid_effector_type_set( - object, fluid_modifier_data->effector, FLUID_EFFECTOR_TYPE_COLLISION); - break; - case OB_FLUIDSIM_INFLOW: - modifier_ensure_type(fluid_modifier_data, MOD_FLUID_TYPE_FLOW); - BKE_fluid_flow_type_set(object, fluid_modifier_data->flow, FLUID_FLOW_TYPE_LIQUID); - BKE_fluid_flow_behavior_set(object, fluid_modifier_data->flow, FLUID_FLOW_BEHAVIOR_INFLOW); - /* No need to emit liquid far away from surface. */ - fluid_modifier_data->flow->surface_distance = 0.0f; - break; - case OB_FLUIDSIM_OUTFLOW: - modifier_ensure_type(fluid_modifier_data, MOD_FLUID_TYPE_FLOW); - BKE_fluid_flow_type_set(object, fluid_modifier_data->flow, FLUID_FLOW_TYPE_LIQUID); - BKE_fluid_flow_behavior_set( - object, fluid_modifier_data->flow, FLUID_FLOW_BEHAVIOR_OUTFLOW); - break; - case OB_FLUIDSIM_PARTICLE: - /* "Particle" type objects not being used by Mantaflow fluid simulations. - * Skip this object, secondary particles can only be enabled through the domain object. */ - break; - case OB_FLUIDSIM_CONTROL: - /* "Control" type objects not being used by Mantaflow fluid simulations. - * Use guiding type instead which is similar. */ - modifier_ensure_type(fluid_modifier_data, MOD_FLUID_TYPE_EFFEC); - BKE_fluid_effector_type_set( - object, fluid_modifier_data->effector, FLUID_EFFECTOR_TYPE_GUIDE); - break; - } - } - else if (old_modifier_data->type == eModifierType_Smoke) { - SmokeModifierData *old_smoke_modifier_data = (SmokeModifierData *)old_modifier_data; - modifier_ensure_type(fluid_modifier_data, old_smoke_modifier_data->type); - if (fluid_modifier_data->type == MOD_FLUID_TYPE_DOMAIN) { - BKE_fluid_domain_type_set(object, fluid_modifier_data->domain, FLUID_DOMAIN_TYPE_GAS); - } - else if (fluid_modifier_data->type == MOD_FLUID_TYPE_FLOW) { - BKE_fluid_flow_type_set(object, fluid_modifier_data->flow, FLUID_FLOW_TYPE_SMOKE); - } - else if (fluid_modifier_data->type == MOD_FLUID_TYPE_EFFEC) { - BKE_fluid_effector_type_set( - object, fluid_modifier_data->effector, FLUID_EFFECTOR_TYPE_COLLISION); - } - } - - /* Replace modifier data in the stack. */ - new_modifier_data->next = old_modifier_data->next; - new_modifier_data->prev = old_modifier_data->prev; - if (new_modifier_data->prev != NULL) { - new_modifier_data->prev->next = new_modifier_data; - } - if (new_modifier_data->next != NULL) { - new_modifier_data->next->prev = new_modifier_data; - } - if (modifiers->first == old_modifier_data) { - modifiers->first = new_modifier_data; - } - if (modifiers->last == old_modifier_data) { - modifiers->last = new_modifier_data; - } - - /* Free old modifier data. */ - MEM_freeN(old_modifier_data); - - return new_modifier_data; -} - -void BKE_modifier_blend_read_data(BlendDataReader *reader, ListBase *lb, Object *ob) -{ - BLO_read_list(reader, lb); - - LISTBASE_FOREACH (ModifierData *, md, lb) { - BKE_modifier_session_uuid_generate(md); - - md->error = NULL; - md->runtime = NULL; - - /* Modifier data has been allocated as a part of data migration process and - * no reading of nested fields from file is needed. */ - bool is_allocated = false; - - if (md->type == eModifierType_Fluidsim) { - BLO_reportf_wrap( - BLO_read_data_reports(reader), - RPT_WARNING, - TIP_("Possible data loss when saving this file! %s modifier is deprecated (Object: %s)"), - md->name, - ob->id.name + 2); - md = modifier_replace_with_fluid(reader, ob, lb, md); - is_allocated = true; - } - else if (md->type == eModifierType_Smoke) { - BLO_reportf_wrap( - BLO_read_data_reports(reader), - RPT_WARNING, - TIP_("Possible data loss when saving this file! %s modifier is deprecated (Object: %s)"), - md->name, - ob->id.name + 2); - md = modifier_replace_with_fluid(reader, ob, lb, md); - is_allocated = true; - } - - const ModifierTypeInfo *mti = BKE_modifier_get_info(md->type); - - /* if modifiers disappear, or for upward compatibility */ - if (mti == NULL) { - md->type = eModifierType_None; - } - - if (is_allocated) { - /* All the fields has been properly allocated. */ - } - else if (md->type == eModifierType_Cloth) { - ClothModifierData *clmd = (ClothModifierData *)md; - - clmd->clothObject = NULL; - clmd->hairdata = NULL; - - BLO_read_data_address(reader, &clmd->sim_parms); - BLO_read_data_address(reader, &clmd->coll_parms); - - BKE_ptcache_blend_read_data(reader, &clmd->ptcaches, &clmd->point_cache, 0); - - if (clmd->sim_parms) { - if (clmd->sim_parms->presets > 10) { - clmd->sim_parms->presets = 0; - } - - clmd->sim_parms->reset = 0; - - BLO_read_data_address(reader, &clmd->sim_parms->effector_weights); - - if (!clmd->sim_parms->effector_weights) { - clmd->sim_parms->effector_weights = BKE_effector_add_weights(NULL); - } - } - - clmd->solver_result = NULL; - } - else if (md->type == eModifierType_Fluid) { - - FluidModifierData *fmd = (FluidModifierData *)md; - - if (fmd->type == MOD_FLUID_TYPE_DOMAIN) { - fmd->flow = NULL; - fmd->effector = NULL; - BLO_read_data_address(reader, &fmd->domain); - fmd->domain->fmd = fmd; - - fmd->domain->fluid = NULL; - fmd->domain->fluid_mutex = BLI_rw_mutex_alloc(); - fmd->domain->tex_density = NULL; - fmd->domain->tex_color = NULL; - fmd->domain->tex_shadow = NULL; - fmd->domain->tex_flame = NULL; - fmd->domain->tex_flame_coba = NULL; - fmd->domain->tex_coba = NULL; - fmd->domain->tex_field = NULL; - fmd->domain->tex_velocity_x = NULL; - fmd->domain->tex_velocity_y = NULL; - fmd->domain->tex_velocity_z = NULL; - fmd->domain->tex_wt = NULL; - BLO_read_data_address(reader, &fmd->domain->coba); - - BLO_read_data_address(reader, &fmd->domain->effector_weights); - if (!fmd->domain->effector_weights) { - fmd->domain->effector_weights = BKE_effector_add_weights(NULL); - } - - BKE_ptcache_blend_read_data( - reader, &(fmd->domain->ptcaches[0]), &(fmd->domain->point_cache[0]), 1); - - /* Manta sim uses only one cache from now on, so store pointer convert */ - if (fmd->domain->ptcaches[1].first || fmd->domain->point_cache[1]) { - if (fmd->domain->point_cache[1]) { - PointCache *cache = BLO_read_get_new_data_address(reader, fmd->domain->point_cache[1]); - if (cache->flag & PTCACHE_FAKE_SMOKE) { - /* Manta-sim/smoke was already saved in "new format" and this cache is a fake one. */ - } - else { - printf( - "High resolution manta cache not available due to pointcache update. Please " - "reset the simulation.\n"); - } - BKE_ptcache_free(cache); - } - BLI_listbase_clear(&fmd->domain->ptcaches[1]); - fmd->domain->point_cache[1] = NULL; - } - } - else if (fmd->type == MOD_FLUID_TYPE_FLOW) { - fmd->domain = NULL; - fmd->effector = NULL; - BLO_read_data_address(reader, &fmd->flow); - fmd->flow->fmd = fmd; - fmd->flow->mesh = NULL; - fmd->flow->verts_old = NULL; - fmd->flow->numverts = 0; - BLO_read_data_address(reader, &fmd->flow->psys); - } - else if (fmd->type == MOD_FLUID_TYPE_EFFEC) { - fmd->flow = NULL; - fmd->domain = NULL; - BLO_read_data_address(reader, &fmd->effector); - if (fmd->effector) { - fmd->effector->fmd = fmd; - fmd->effector->verts_old = NULL; - fmd->effector->numverts = 0; - fmd->effector->mesh = NULL; - } - else { - fmd->type = 0; - fmd->flow = NULL; - fmd->domain = NULL; - fmd->effector = NULL; - } - } - } - else if (md->type == eModifierType_DynamicPaint) { - DynamicPaintModifierData *pmd = (DynamicPaintModifierData *)md; - - if (pmd->canvas) { - BLO_read_data_address(reader, &pmd->canvas); - pmd->canvas->pmd = pmd; - pmd->canvas->flags &= ~MOD_DPAINT_BAKING; /* just in case */ - - if (pmd->canvas->surfaces.first) { - BLO_read_list(reader, &pmd->canvas->surfaces); - - LISTBASE_FOREACH (DynamicPaintSurface *, surface, &pmd->canvas->surfaces) { - surface->canvas = pmd->canvas; - surface->data = NULL; - BKE_ptcache_blend_read_data(reader, &(surface->ptcaches), &(surface->pointcache), 1); - - BLO_read_data_address(reader, &surface->effector_weights); - if (surface->effector_weights == NULL) { - surface->effector_weights = BKE_effector_add_weights(NULL); - } - } - } - } - if (pmd->brush) { - BLO_read_data_address(reader, &pmd->brush); - pmd->brush->pmd = pmd; - BLO_read_data_address(reader, &pmd->brush->psys); - BLO_read_data_address(reader, &pmd->brush->paint_ramp); - BLO_read_data_address(reader, &pmd->brush->vel_ramp); - } - } - - if ((mti != NULL) && (mti->blendRead != NULL)) { - mti->blendRead(reader, md); - } - } -} - -void BKE_modifier_blend_read_lib(BlendLibReader *reader, Object *ob) -{ - BKE_modifiers_foreach_ID_link(ob, BKE_object_modifiers_lib_link_common, reader); - - /* If linking from a library, clear 'local' library override flag. */ - if (ID_IS_LINKED(ob)) { - LISTBASE_FOREACH (ModifierData *, mod, &ob->modifiers) { - mod->flag &= ~eModifierFlag_OverrideLibrary_Local; - } - } -} |