[Bf-blender-cvs] [1051f71] fracture_modifier: fix for material loading in FM external mode and generally decreased file loading times, especially noticeable with large FM objects, by using sorted fd->datamap in readfile.c (avoids linear search)
Martin Felke
noreply at git.blender.org
Tue Feb 9 17:45:51 CET 2016
Commit: 1051f712910feaad13ef22e03e444f319b5eba9c
Author: Martin Felke
Date: Tue Feb 9 17:45:34 2016 +0100
Branches: fracture_modifier
https://developer.blender.org/rB1051f712910feaad13ef22e03e444f319b5eba9c
fix for material loading in FM external mode and generally decreased file loading times, especially noticeable with large FM objects, by using sorted fd->datamap in readfile.c (avoids linear search)
===================================================================
M source/blender/blenkernel/intern/fracture.c
M source/blender/blenloader/intern/readfile.c
M source/blender/blenloader/intern/writefile.c
===================================================================
diff --git a/source/blender/blenkernel/intern/fracture.c b/source/blender/blenkernel/intern/fracture.c
index 0ed6af9..39bd38b 100644
--- a/source/blender/blenkernel/intern/fracture.c
+++ b/source/blender/blenkernel/intern/fracture.c
@@ -1821,6 +1821,7 @@ DerivedMesh *BKE_shard_create_dm(Shard *s, bool doCustomData)
memcpy(mloops, s->mloop, s->totloop * sizeof(MLoop));
memcpy(mpolys, s->mpoly, s->totpoly * sizeof(MPoly));
+ CustomData_free(&dm->edgeData, 0);
CDDM_calc_edges(dm);
dm->dirty |= DM_DIRTY_NORMALS;
@@ -2361,7 +2362,7 @@ int BKE_fracture_update_visual_mesh(FractureModifierData *fmd, Object *ob, bool
DerivedMesh *dm = fmd->visible_mesh_cached;
int vertstart = 0, totvert = 0, totpoly = 0, polystart = 0, matstart = 1, defstart = 0;
MVert *mv = NULL;
- MPoly *mp = NULL, *mpoly = NULL;
+ MPoly *mp = NULL, *mpoly = NULL, *ppoly = NULL, *pp = NULL;
int i = 0, j = 0;
MDeformVert *dvert = NULL;
@@ -2461,6 +2462,8 @@ int BKE_fracture_update_visual_mesh(FractureModifierData *fmd, Object *ob, bool
if (dw->def_nr == l)
dw->def_nr = index;
}
+
+ //XXX TODO store this on physics mesh too ? to be able to reload it from blend
}
}
}
@@ -2468,7 +2471,8 @@ int BKE_fracture_update_visual_mesh(FractureModifierData *fmd, Object *ob, bool
defstart += mi->totdef;
totpoly = mi->physics_mesh->getNumPolys(mi->physics_mesh);
- for (j = 0, mp = mpoly + polystart; j < totpoly; j++, mp++)
+ ppoly = s->mpoly;
+ for (j = 0, mp = mpoly + polystart, pp = ppoly; j < totpoly; j++, mp++, pp++)
{
/* material index lookup and correction, avoid having the same material in different slots */
int index = GET_INT_FROM_POINTER(BLI_ghash_lookup(fmd->material_index_map,
@@ -2478,6 +2482,9 @@ int BKE_fracture_update_visual_mesh(FractureModifierData *fmd, Object *ob, bool
index--;
mp->mat_nr = index;
+ //store this on physics mesh as well, so for being able to reload it from blend later (without
+ // having a materialmap then)
+ pp->mat_nr = index;
}
/* fortunately we know how many faces "belong" to this meshisland, too */
diff --git a/source/blender/blenloader/intern/readfile.c b/source/blender/blenloader/intern/readfile.c
index 9286abb..0f2eeb0 100644
--- a/source/blender/blenloader/intern/readfile.c
+++ b/source/blender/blenloader/intern/readfile.c
@@ -373,6 +373,22 @@ static void *oldnewmap_lookup_and_inc(OldNewMap *onm, void *addr, bool increase_
int i;
if (addr == NULL) return NULL;
+
+ /* try sorted approach here too, maybe it helps */
+ if (onm->sorted) {
+ OldNew entry_s, *entry = NULL;
+
+ entry_s.old = addr;
+
+ entry = bsearch(&entry_s, onm->entries, onm->nentries, sizeof(OldNew), verg_oldnewmap);
+ if (entry) {
+ if (increase_users)
+ entry->nr++;
+ return entry->newp;
+ }
+
+ return NULL;
+ }
if (onm->lasthit < onm->nentries-1) {
OldNew *entry = &onm->entries[++onm->lasthit];
@@ -1836,20 +1852,20 @@ static void *read_struct(FileData *fd, BHead *bh, const char *blockname)
typedef void (*link_list_cb)(FileData *fd, void *data);
-static void link_list_ex(FileData *fd, ListBase *lb, link_list_cb callback) /* only direct data */
+static void link_list_ex(FileData *fd, ListBase *lb, link_list_cb callback, bool increase_lasthit) /* only direct data */
{
Link *ln, *prev;
if (BLI_listbase_is_empty(lb)) return;
- lb->first = newdataadr(fd, lb->first);
+ lb->first = newdataadr_ex(fd, lb->first, increase_lasthit);
if (callback != NULL) {
callback(fd, lb->first);
}
ln = lb->first;
prev = NULL;
while (ln) {
- ln->next = newdataadr(fd, ln->next);
+ ln->next = newdataadr_ex(fd, ln->next, increase_lasthit);
if (ln->next != NULL && callback != NULL) {
callback(fd, ln->next);
}
@@ -1862,7 +1878,7 @@ static void link_list_ex(FileData *fd, ListBase *lb, link_list_cb callback) /*
static void link_list(FileData *fd, ListBase *lb) /* only direct data */
{
- link_list_ex(fd, lb, NULL);
+ link_list_ex(fd, lb, NULL, true);
}
static void link_glob_list(FileData *fd, ListBase *lb) /* for glob data */
@@ -3926,7 +3942,7 @@ static void direct_link_pointcache_cb(FileData *fd, void *data)
static void direct_link_pointcache(FileData *fd, PointCache *cache)
{
if ((cache->flag & PTCACHE_DISK_CACHE)==0) {
- link_list_ex(fd, &cache->mem_cache, direct_link_pointcache_cb);
+ link_list_ex(fd, &cache->mem_cache, direct_link_pointcache_cb, true);
}
else
BLI_listbase_clear(&cache->mem_cache);
@@ -5000,9 +5016,11 @@ static void read_meshIsland(FileData *fd, MeshIsland **address)
mi->vertices_cached = NULL;
mi->vertco = newdataadr(fd, mi->vertco);
mi->temp = newdataadr(fd, mi->temp);
+#if 0
read_shard(fd, &(mi->temp));
mi->physics_mesh = BKE_shard_create_dm(mi->temp, true);
BKE_shard_free(mi->temp, true);
+#endif
mi->temp = NULL;
mi->vertno = newdataadr(fd, mi->vertno);
@@ -5179,7 +5197,7 @@ static void load_fracture_modifier(FileData* fd, FractureModifierData *fmd, Obje
MeshIsland *mi;
MVert *mverts;
int vertstart = 0;
- Shard *s;
+ Shard *s, **shards = NULL;
int count = 0;
fm->last_shard_tree = NULL;
@@ -5188,17 +5206,28 @@ static void load_fracture_modifier(FileData* fd, FractureModifierData *fmd, Obje
if (fmd->fracture_mode == MOD_FRACTURE_PREFRACTURED ||
fmd->fracture_mode == MOD_FRACTURE_EXTERNAL)
{
+ /*create temp array for quicker lookups*/
+ int count = 0;
+ int i = 0;
+
link_list(fd, &fmd->frac_mesh->shard_map);
+ link_list(fd, &fmd->islandShards);
+ count = BLI_listbase_count(&fmd->frac_mesh->shard_map) + BLI_listbase_count(&fmd->islandShards);
+
+ shards = MEM_callocN(sizeof(Shard*) * count, "readfile shard_lookup_array");
for (s = fmd->frac_mesh->shard_map.first; s; s = s->next) {
read_shard(fd, &s);
+ shards[i] = s;
+ i++;
}
fmd->dm = NULL;
fmd->visible_mesh = NULL;
- link_list(fd, &fmd->islandShards);
for (s = fmd->islandShards.first; s; s = s->next) {
read_shard(fd, &s);
+ shards[i] = s;
+ i++;
}
link_list(fd, &fmd->meshIslands);
@@ -5232,9 +5261,17 @@ static void load_fracture_modifier(FileData* fd, FractureModifierData *fmd, Obje
/* re-init cached verts here... */
mverts = CDDM_get_verts(fmd->visible_mesh_cached);
+ i = 0;
for (mi = fmd->meshIslands.first; mi; mi = mi->next) {
- read_meshIsland(fd, &mi);
- vertstart += initialize_meshisland(fmd, &mi, mverts, vertstart, ob, -1, -1);
+ Shard *s = NULL;
+ s = shards[i];
+ if (s)
+ {
+ mi->physics_mesh = BKE_shard_create_dm(s, true);
+ read_meshIsland(fd, &mi);
+ vertstart += initialize_meshisland(fmd, &mi, mverts, vertstart, ob, -1, -1);
+ }
+ i++;
}
if (fmd->fracture_mode == MOD_FRACTURE_EXTERNAL)
@@ -5250,19 +5287,23 @@ static void load_fracture_modifier(FileData* fd, FractureModifierData *fmd, Obje
con->flag |= RBC_FLAG_NEEDS_VALIDATE;
}
}
+
+ MEM_freeN(shards);
}
else if (fmd->fracture_mode == MOD_FRACTURE_DYNAMIC && !fd->memfile)
{
ShardSequence *ssq = NULL;
MeshIslandSequence *msq = NULL;
- fmd->dm = NULL;
+ fmd->dm = NULL;
link_list(fd, &fmd->shard_sequence);
+
for (ssq = fmd->shard_sequence.first; ssq; ssq = ssq->next)
{
ssq->is_new = false;
ssq->frac_mesh = newdataadr(fd, ssq->frac_mesh);
link_list(fd, &ssq->frac_mesh->shard_map);
+
for (s = ssq->frac_mesh->shard_map.first; s; s = s->next) {
read_shard(fd, &s);
}
@@ -5289,6 +5330,7 @@ static void load_fracture_modifier(FileData* fd, FractureModifierData *fmd, Obje
link_list(fd, &msq->meshIslands);
for (mi = msq->meshIslands.first; mi; mi = mi->next) {
read_meshIsland(fd, &mi);
+ mi->physics_mesh = BKE_shard_create_dm(sh, true);
vertstart += initialize_meshisland(fmd, &mi, mverts, vertstart, ob, sh->parent_id, sh->shard_id);
sh = sh->next;
}
@@ -8267,6 +8309,9 @@ static BHead *read_data_into_oldnewmap(FileData *fd, BHead *bhead, const char *a
bhead = blo_nextbhead(fd, bhead);
}
+
+ qsort(fd->datamap->entries, fd->datamap->nentries, sizeof(OldNew), verg_oldnewmap);
+ fd->datamap->sorted = 1;
return bhead;
}
diff --git a/source/blender/blenloader/intern/writefile.c b/source/blender/blenloader/intern/writefile.c
index 5175b0d..8b2ed9f 100644
--- a/source/blender/blenloader/intern/writefile.c
+++ b/source/blender/blenloader/intern/writefile.c
@@ -1568,19 +1568,22 @@ static void write_shard(WriteData* wd, Shard* s)
static void write_meshIsland(WriteData* wd, MeshIsland* mi)
{
+#if 0
DerivedMesh *dm = mi->physics_mesh;
mi->temp = BKE_create_fracture_shard(dm->getVertArray(dm), dm->getPolyArray(dm), dm->getLoopArray(dm),
dm->getNumVerts(dm), dm->getNumPolys(dm), dm->getNumLoops(dm), true);
mi->temp = BKE_custom_data_to_shard(mi->temp, dm);
-
+#endif
writestruct(wd, DATA, "MeshIsland", 1, mi);
writedata(wd, DATA, sizeof(float) * 3 * mi->vertex_count, mi->vertco);
+#if 0
/* write derivedmesh as shard... */
mi->temp->next = NULL;
mi->temp->prev = NULL;
write_shard(wd, mi->temp);
BKE_shard_free(mi->temp, true);
mi->temp = NULL;
+#endif
writedata(wd, DATA, sizeof(short) * 3 * mi->vertex_count, mi->vertno);
More information about the Bf-blender-cvs
mailing list