diff options
author | Jacques Lucke <jacques@blender.org> | 2020-11-06 16:40:49 +0300 |
---|---|---|
committer | Jacques Lucke <jacques@blender.org> | 2020-11-06 16:40:54 +0300 |
commit | 7dd76329e11cd5dc13b5804670bee0efe4d51fa6 (patch) | |
tree | adbe6bf0b3b0297512edc6dd66075c5bf85835e4 /source/blender/blenkernel/intern/pointcache.c | |
parent | 6bca9d8c113e80aa9550229719b7c59c34e46bb5 (diff) |
Refactor: move PointCache .blend I/O to blenkernel
Ref T76372.
Diffstat (limited to 'source/blender/blenkernel/intern/pointcache.c')
-rw-r--r-- | source/blender/blenkernel/intern/pointcache.c | 124 |
1 files changed, 124 insertions, 0 deletions
diff --git a/source/blender/blenkernel/intern/pointcache.c b/source/blender/blenkernel/intern/pointcache.c index 6a93245d995..5c60b39e9c8 100644 --- a/source/blender/blenkernel/intern/pointcache.c +++ b/source/blender/blenkernel/intern/pointcache.c @@ -44,6 +44,7 @@ #include "DNA_simulation_types.h" #include "BLI_blenlib.h" +#include "BLI_endian_switch.h" #include "BLI_math.h" #include "BLI_string.h" #include "BLI_utildefines.h" @@ -67,6 +68,8 @@ #include "BKE_scene.h" #include "BKE_softbody.h" +#include "BLO_read_write.h" + #include "BIK_api.h" #ifdef WITH_BULLET @@ -3779,3 +3782,124 @@ void BKE_ptcache_invalidate(PointCache *cache) cache->last_exact = MIN2(cache->startframe, 0); } } + +static const char *ptcache_data_struct[] = { + "", // BPHYS_DATA_INDEX + "", // BPHYS_DATA_LOCATION + "", // BPHYS_DATA_VELOCITY + "", // BPHYS_DATA_ROTATION + "", // BPHYS_DATA_AVELOCITY / BPHYS_DATA_XCONST */ + "", // BPHYS_DATA_SIZE: + "", // BPHYS_DATA_TIMES: + "BoidData", // case BPHYS_DATA_BOIDS: +}; +static const char *ptcache_extra_struct[] = { + "", + "ParticleSpring", + "vec3f", +}; +void BKE_ptcache_blend_write(BlendWriter *writer, ListBase *ptcaches) +{ + LISTBASE_FOREACH (PointCache *, cache, ptcaches) { + BLO_write_struct(writer, PointCache, cache); + + if ((cache->flag & PTCACHE_DISK_CACHE) == 0) { + LISTBASE_FOREACH (PTCacheMem *, pm, &cache->mem_cache) { + BLO_write_struct(writer, PTCacheMem, pm); + + for (int i = 0; i < BPHYS_TOT_DATA; i++) { + if (pm->data[i] && pm->data_types & (1 << i)) { + if (ptcache_data_struct[i][0] == '\0') { + BLO_write_raw(writer, MEM_allocN_len(pm->data[i]), pm->data[i]); + } + else { + BLO_write_struct_array_by_name( + writer, ptcache_data_struct[i], pm->totpoint, pm->data[i]); + } + } + } + + LISTBASE_FOREACH (PTCacheExtra *, extra, &pm->extradata) { + if (ptcache_extra_struct[extra->type][0] == '\0') { + continue; + } + BLO_write_struct(writer, PTCacheExtra, extra); + BLO_write_struct_array_by_name( + writer, ptcache_extra_struct[extra->type], extra->totdata, extra->data); + } + } + } + } +} + +static void direct_link_pointcache_cb(BlendDataReader *reader, void *data) +{ + PTCacheMem *pm = data; + for (int i = 0; i < BPHYS_TOT_DATA; i++) { + BLO_read_data_address(reader, &pm->data[i]); + + /* the cache saves non-struct data without DNA */ + if (pm->data[i] && ptcache_data_struct[i][0] == '\0' && + BLO_read_requires_endian_switch(reader)) { + /* data_size returns bytes. */ + int tot = (BKE_ptcache_data_size(i) * pm->totpoint) / sizeof(int); + + int *poin = pm->data[i]; + + BLI_endian_switch_int32_array(poin, tot); + } + } + + BLO_read_list(reader, &pm->extradata); + + LISTBASE_FOREACH (PTCacheExtra *, extra, &pm->extradata) { + BLO_read_data_address(reader, &extra->data); + } +} + +static void direct_link_pointcache(BlendDataReader *reader, PointCache *cache) +{ + if ((cache->flag & PTCACHE_DISK_CACHE) == 0) { + BLO_read_list_cb(reader, &cache->mem_cache, direct_link_pointcache_cb); + } + else { + BLI_listbase_clear(&cache->mem_cache); + } + + cache->flag &= ~PTCACHE_SIMULATION_VALID; + cache->simframe = 0; + cache->edit = NULL; + cache->free_edit = NULL; + cache->cached_frames = NULL; + cache->cached_frames_len = 0; +} + +void BKE_ptcache_blend_read_data(BlendDataReader *reader, + ListBase *ptcaches, + PointCache **ocache, + int force_disk) +{ + if (ptcaches->first) { + BLO_read_list(reader, ptcaches); + LISTBASE_FOREACH (PointCache *, cache, ptcaches) { + direct_link_pointcache(reader, cache); + if (force_disk) { + cache->flag |= PTCACHE_DISK_CACHE; + cache->step = 1; + } + } + + BLO_read_data_address(reader, ocache); + } + else if (*ocache) { + /* old "single" caches need to be linked too */ + BLO_read_data_address(reader, ocache); + direct_link_pointcache(reader, *ocache); + if (force_disk) { + (*ocache)->flag |= PTCACHE_DISK_CACHE; + (*ocache)->step = 1; + } + + ptcaches->first = ptcaches->last = *ocache; + } +} |