Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'source/blender/blenkernel/intern')
-rw-r--r--source/blender/blenkernel/intern/DerivedMesh.c16
-rw-r--r--source/blender/blenkernel/intern/action.c29
-rw-r--r--source/blender/blenkernel/intern/cdderivedmesh.c4
-rw-r--r--source/blender/blenkernel/intern/depsgraph.c15
-rw-r--r--source/blender/blenkernel/intern/library.c79
-rw-r--r--source/blender/blenkernel/intern/multires.c14
-rw-r--r--source/blender/blenkernel/intern/node.c7
-rw-r--r--source/blender/blenkernel/intern/object.c9
-rw-r--r--source/blender/blenkernel/intern/particle_system.c4
-rw-r--r--source/blender/blenkernel/intern/rigidbody.c120
-rw-r--r--source/blender/blenkernel/intern/scene.c2
-rw-r--r--source/blender/blenkernel/intern/subsurf_ccg.c2
12 files changed, 186 insertions, 115 deletions
diff --git a/source/blender/blenkernel/intern/DerivedMesh.c b/source/blender/blenkernel/intern/DerivedMesh.c
index fa0f6e3af28..b48b7629d41 100644
--- a/source/blender/blenkernel/intern/DerivedMesh.c
+++ b/source/blender/blenkernel/intern/DerivedMesh.c
@@ -838,9 +838,9 @@ void DM_interp_poly_data(DerivedMesh *source, DerivedMesh *dest,
}
///
-DerivedMesh *mesh_create_derived(Mesh *me, Object *ob, float (*vertCos)[3])
+DerivedMesh *mesh_create_derived(Mesh *me, float (*vertCos)[3])
{
- DerivedMesh *dm = CDDM_from_mesh(me, ob);
+ DerivedMesh *dm = CDDM_from_mesh(me);
if (!dm)
return NULL;
@@ -874,7 +874,7 @@ DerivedMesh *mesh_create_derived_for_modifier(Scene *scene, Object *ob,
float (*deformedVerts)[3] = BKE_mesh_vertexCos_get(me, &numVerts);
modwrap_deformVerts(md, ob, NULL, deformedVerts, numVerts, 0);
- dm = mesh_create_derived(me, ob, deformedVerts);
+ dm = mesh_create_derived(me, deformedVerts);
if (build_shapekey_layers)
add_shapekey_layers(dm, me, ob);
@@ -882,7 +882,7 @@ DerivedMesh *mesh_create_derived_for_modifier(Scene *scene, Object *ob,
MEM_freeN(deformedVerts);
}
else {
- DerivedMesh *tdm = mesh_create_derived(me, ob, NULL);
+ DerivedMesh *tdm = mesh_create_derived(me, NULL);
if (build_shapekey_layers)
add_shapekey_layers(tdm, me, ob);
@@ -953,7 +953,7 @@ static DerivedMesh *create_orco_dm(Object *ob, Mesh *me, BMEditMesh *em, int lay
int free;
if (em) dm = CDDM_from_editbmesh(em, FALSE, FALSE);
- else dm = CDDM_from_mesh(me, ob);
+ else dm = CDDM_from_mesh(me);
orco = get_orco_coords_dm(ob, em, layer, &free);
@@ -1533,7 +1533,7 @@ static void mesh_calc_modifiers(Scene *scene, Object *ob, float (*inputVertexCos
* coordinates (vpaint, etc.)
*/
if (deform_r) {
- *deform_r = CDDM_from_mesh(me, ob);
+ *deform_r = CDDM_from_mesh(me);
if (build_shapekey_layers)
add_shapekey_layers(dm, me, ob);
@@ -1659,7 +1659,7 @@ static void mesh_calc_modifiers(Scene *scene, Object *ob, float (*inputVertexCos
}
}
else {
- dm = CDDM_from_mesh(me, ob);
+ dm = CDDM_from_mesh(me);
ASSERT_IS_VALID_DM(dm);
if (build_shapekey_layers)
@@ -1823,7 +1823,7 @@ static void mesh_calc_modifiers(Scene *scene, Object *ob, float (*inputVertexCos
#endif
}
else {
- finaldm = CDDM_from_mesh(me, ob);
+ finaldm = CDDM_from_mesh(me);
if (build_shapekey_layers) {
add_shapekey_layers(finaldm, me, ob);
diff --git a/source/blender/blenkernel/intern/action.c b/source/blender/blenkernel/intern/action.c
index c91fae2adbc..4991f1ce225 100644
--- a/source/blender/blenkernel/intern/action.c
+++ b/source/blender/blenkernel/intern/action.c
@@ -714,10 +714,12 @@ void BKE_pose_channels_hash_free(bPose *pose)
* Deallocates a pose channel.
* Does not free the pose channel itself.
*/
-void BKE_pose_channel_free(bPoseChannel *pchan)
+void BKE_pose_channel_free_ex(bPoseChannel *pchan, bool do_id_user)
{
if (pchan->custom) {
- id_us_min(&pchan->custom->id);
+ if (do_id_user) {
+ id_us_min(&pchan->custom->id);
+ }
pchan->custom = NULL;
}
@@ -734,17 +736,22 @@ void BKE_pose_channel_free(bPoseChannel *pchan)
}
}
+void BKE_pose_channel_free(bPoseChannel *pchan)
+{
+ BKE_pose_channel_free_ex(pchan, true);
+}
+
/**
* Removes and deallocates all channels from a pose.
* Does not free the pose itself.
*/
-void BKE_pose_channels_free(bPose *pose)
+void BKE_pose_channels_free_ex(bPose *pose, bool do_id_user)
{
bPoseChannel *pchan;
if (pose->chanbase.first) {
for (pchan = pose->chanbase.first; pchan; pchan = pchan->next)
- BKE_pose_channel_free(pchan);
+ BKE_pose_channel_free_ex(pchan, do_id_user);
BLI_freelistN(&pose->chanbase);
}
@@ -752,14 +759,19 @@ void BKE_pose_channels_free(bPose *pose)
BKE_pose_channels_hash_free(pose);
}
+void BKE_pose_channels_free(bPose *pose)
+{
+ BKE_pose_channels_free_ex(pose, true);
+}
+
/**
* Removes and deallocates all data from a pose, and also frees the pose.
*/
-void BKE_pose_free(bPose *pose)
+void BKE_pose_free_ex(bPose *pose, bool do_id_user)
{
if (pose) {
/* free pose-channels */
- BKE_pose_channels_free(pose);
+ BKE_pose_channels_free_ex(pose, do_id_user);
/* free pose-groups */
if (pose->agroups.first)
@@ -777,6 +789,11 @@ void BKE_pose_free(bPose *pose)
}
}
+void BKE_pose_free(bPose *pose)
+{
+ BKE_pose_free_ex(pose, true);
+}
+
static void copy_pose_channel_data(bPoseChannel *pchan, const bPoseChannel *chan)
{
bConstraint *pcon, *con;
diff --git a/source/blender/blenkernel/intern/cdderivedmesh.c b/source/blender/blenkernel/intern/cdderivedmesh.c
index d9447e51aa3..32914dedde1 100644
--- a/source/blender/blenkernel/intern/cdderivedmesh.c
+++ b/source/blender/blenkernel/intern/cdderivedmesh.c
@@ -1802,9 +1802,9 @@ DerivedMesh *CDDM_new(int numVerts, int numEdges, int numTessFaces, int numLoops
return dm;
}
-DerivedMesh *CDDM_from_mesh(Mesh *mesh, Object *UNUSED(ob))
+DerivedMesh *CDDM_from_mesh(Mesh *mesh)
{
- CDDerivedMesh *cddm = cdDM_create("CDDM_from_mesh dm");
+ CDDerivedMesh *cddm = cdDM_create(__func__);
DerivedMesh *dm = &cddm->dm;
CustomDataMask mask = CD_MASK_MESH & (~CD_MASK_MDISPS);
int alloctype;
diff --git a/source/blender/blenkernel/intern/depsgraph.c b/source/blender/blenkernel/intern/depsgraph.c
index 8074d6bceec..6376878c664 100644
--- a/source/blender/blenkernel/intern/depsgraph.c
+++ b/source/blender/blenkernel/intern/depsgraph.c
@@ -2735,7 +2735,7 @@ void DAG_threaded_update_begin(Scene *scene,
void (*func)(void *node, void *user_data),
void *user_data)
{
- DagNode *node, *root_node;
+ DagNode *node;
/* We reset num_pending_parents to zero first and tag node as not scheduled yet... */
for (node = scene->theDag->DagNode.first; node; node = node->next) {
@@ -2756,10 +2756,15 @@ void DAG_threaded_update_begin(Scene *scene,
}
}
- /* Add root node to the queue. */
- root_node = scene->theDag->DagNode.first;
- root_node->scheduled = true;
- func(root_node, user_data);
+ /* Add root nodes to the queue. */
+ BLI_spin_lock(&threaded_update_lock);
+ for (node = scene->theDag->DagNode.first; node; node = node->next) {
+ if (node->num_pending_parents == 0) {
+ node->scheduled = true;
+ func(node, user_data);
+ }
+ }
+ BLI_spin_unlock(&threaded_update_lock);
}
/* This function is called when handling node is done.
diff --git a/source/blender/blenkernel/intern/library.c b/source/blender/blenkernel/intern/library.c
index 00dee2611c1..43bd6a0b36c 100644
--- a/source/blender/blenkernel/intern/library.c
+++ b/source/blender/blenkernel/intern/library.c
@@ -868,7 +868,7 @@ void BKE_libblock_free_data(ID *id)
}
/* used in headerbuttons.c image.c mesh.c screen.c sound.c and library.c */
-void BKE_libblock_free(ListBase *lb, void *idv)
+void BKE_libblock_free_ex(ListBase *lb, void *idv, bool do_id_user)
{
Main *bmain = G.main; /* should eventually be an arg */
ID *id = idv;
@@ -885,7 +885,7 @@ void BKE_libblock_free(ListBase *lb, void *idv)
BKE_library_free((Library *)id);
break;
case ID_OB:
- BKE_object_free((Object *)id);
+ BKE_object_free_ex((Object *)id, do_id_user);
break;
case ID_ME:
BKE_mesh_free((Mesh *)id, 1);
@@ -951,7 +951,7 @@ void BKE_libblock_free(ListBase *lb, void *idv)
BKE_action_free((bAction *)id);
break;
case ID_NT:
- ntreeFreeTree((bNodeTree *)id);
+ ntreeFreeTree_ex((bNodeTree *)id, do_id_user);
break;
case ID_BR:
BKE_brush_free((Brush *)id);
@@ -988,6 +988,11 @@ void BKE_libblock_free(ListBase *lb, void *idv)
MEM_freeN(id);
}
+void BKE_libblock_free(ListBase *lb, void *idv)
+{
+ BKE_libblock_free_ex(lb, idv, true);
+}
+
void BKE_libblock_free_us(ListBase *lb, void *idv) /* test users */
{
ID *id = idv;
@@ -1025,44 +1030,44 @@ void free_main(Main *mainvar)
while ( (id = lb->first) ) {
#if 1
- BKE_libblock_free(lb, id);
+ BKE_libblock_free_ex(lb, id, false);
#else
/* errors freeing ID's can be hard to track down,
* enable this so valgrind will give the line number in its error log */
switch (a) {
- case 0: BKE_libblock_free(lb, id); break;
- case 1: BKE_libblock_free(lb, id); break;
- case 2: BKE_libblock_free(lb, id); break;
- case 3: BKE_libblock_free(lb, id); break;
- case 4: BKE_libblock_free(lb, id); break;
- case 5: BKE_libblock_free(lb, id); break;
- case 6: BKE_libblock_free(lb, id); break;
- case 7: BKE_libblock_free(lb, id); break;
- case 8: BKE_libblock_free(lb, id); break;
- case 9: BKE_libblock_free(lb, id); break;
- case 10: BKE_libblock_free(lb, id); break;
- case 11: BKE_libblock_free(lb, id); break;
- case 12: BKE_libblock_free(lb, id); break;
- case 13: BKE_libblock_free(lb, id); break;
- case 14: BKE_libblock_free(lb, id); break;
- case 15: BKE_libblock_free(lb, id); break;
- case 16: BKE_libblock_free(lb, id); break;
- case 17: BKE_libblock_free(lb, id); break;
- case 18: BKE_libblock_free(lb, id); break;
- case 19: BKE_libblock_free(lb, id); break;
- case 20: BKE_libblock_free(lb, id); break;
- case 21: BKE_libblock_free(lb, id); break;
- case 22: BKE_libblock_free(lb, id); break;
- case 23: BKE_libblock_free(lb, id); break;
- case 24: BKE_libblock_free(lb, id); break;
- case 25: BKE_libblock_free(lb, id); break;
- case 26: BKE_libblock_free(lb, id); break;
- case 27: BKE_libblock_free(lb, id); break;
- case 28: BKE_libblock_free(lb, id); break;
- case 29: BKE_libblock_free(lb, id); break;
- case 30: BKE_libblock_free(lb, id); break;
- case 31: BKE_libblock_free(lb, id); break;
- case 32: BKE_libblock_free(lb, id); break;
+ case 0: BKE_libblock_free_ex(lb, id, false); break;
+ case 1: BKE_libblock_free_ex(lb, id, false); break;
+ case 2: BKE_libblock_free_ex(lb, id, false); break;
+ case 3: BKE_libblock_free_ex(lb, id, false); break;
+ case 4: BKE_libblock_free_ex(lb, id, false); break;
+ case 5: BKE_libblock_free_ex(lb, id, false); break;
+ case 6: BKE_libblock_free_ex(lb, id, false); break;
+ case 7: BKE_libblock_free_ex(lb, id, false); break;
+ case 8: BKE_libblock_free_ex(lb, id, false); break;
+ case 9: BKE_libblock_free_ex(lb, id, false); break;
+ case 10: BKE_libblock_free_ex(lb, id, false); break;
+ case 11: BKE_libblock_free_ex(lb, id, false); break;
+ case 12: BKE_libblock_free_ex(lb, id, false); break;
+ case 13: BKE_libblock_free_ex(lb, id, false); break;
+ case 14: BKE_libblock_free_ex(lb, id, false); break;
+ case 15: BKE_libblock_free_ex(lb, id, false); break;
+ case 16: BKE_libblock_free_ex(lb, id, false); break;
+ case 17: BKE_libblock_free_ex(lb, id, false); break;
+ case 18: BKE_libblock_free_ex(lb, id, false); break;
+ case 19: BKE_libblock_free_ex(lb, id, false); break;
+ case 20: BKE_libblock_free_ex(lb, id, false); break;
+ case 21: BKE_libblock_free_ex(lb, id, false); break;
+ case 22: BKE_libblock_free_ex(lb, id, false); break;
+ case 23: BKE_libblock_free_ex(lb, id, false); break;
+ case 24: BKE_libblock_free_ex(lb, id, false); break;
+ case 25: BKE_libblock_free_ex(lb, id, false); break;
+ case 26: BKE_libblock_free_ex(lb, id, false); break;
+ case 27: BKE_libblock_free_ex(lb, id, false); break;
+ case 28: BKE_libblock_free_ex(lb, id, false); break;
+ case 29: BKE_libblock_free_ex(lb, id, false); break;
+ case 30: BKE_libblock_free_ex(lb, id, false); break;
+ case 31: BKE_libblock_free_ex(lb, id, false); break;
+ case 32: BKE_libblock_free_ex(lb, id, false); break;
default:
BLI_assert(0);
break;
diff --git a/source/blender/blenkernel/intern/multires.c b/source/blender/blenkernel/intern/multires.c
index 722ea536ed2..2189fbd2f55 100644
--- a/source/blender/blenkernel/intern/multires.c
+++ b/source/blender/blenkernel/intern/multires.c
@@ -769,7 +769,7 @@ void multiresModifier_base_apply(MultiresModifierData *mmd, Object *ob)
/* XXX - probably not necessary to regenerate the cddm so much? */
/* generate highest level with displacements */
- cddm = CDDM_from_mesh(me, NULL);
+ cddm = CDDM_from_mesh(me);
DM_set_only_copy(cddm, CD_MASK_BAREMESH);
dispdm = multires_dm_create_local(ob, cddm, totlvl, totlvl, 0, 0);
cddm->release(cddm);
@@ -782,7 +782,7 @@ void multiresModifier_base_apply(MultiresModifierData *mmd, Object *ob)
/* heuristic to produce a better-fitting base mesh */
- cddm = CDDM_from_mesh(me, NULL);
+ cddm = CDDM_from_mesh(me);
pmap = cddm->getPolyMap(ob, cddm);
origco = MEM_callocN(sizeof(float) * 3 * me->totvert, "multires apply base origco");
for (i = 0; i < me->totvert; ++i)
@@ -865,7 +865,7 @@ void multiresModifier_base_apply(MultiresModifierData *mmd, Object *ob)
BKE_mesh_calc_normals(me);
/* subdivide the mesh to highest level without displacements */
- cddm = CDDM_from_mesh(me, NULL);
+ cddm = CDDM_from_mesh(me);
DM_set_only_copy(cddm, CD_MASK_BAREMESH);
origdm = subsurf_dm_create_local(ob, cddm, totlvl, 0, 0, mmd->flags & eMultiresModifierFlag_PlainUv, 0);
cddm->release(cddm);
@@ -902,7 +902,7 @@ static void multires_subdivide(MultiresModifierData *mmd, Object *ob, int totlvl
int has_mask = CustomData_has_layer(&me->ldata, CD_GRID_PAINT_MASK);
/* create subsurf DM from original mesh at high level */
- cddm = CDDM_from_mesh(me, NULL);
+ cddm = CDDM_from_mesh(me);
DM_set_only_copy(cddm, CD_MASK_BAREMESH);
highdm = subsurf_dm_create_local(ob, cddm, totlvl, simple, 0, mmd->flags & eMultiresModifierFlag_PlainUv, has_mask);
ss = ((CCGDerivedMesh *)highdm)->ss;
@@ -1174,7 +1174,7 @@ void multires_modifier_update_mdisps(struct DerivedMesh *dm)
/* create subsurf DM from original mesh at high level */
if (ob->derivedDeform) cddm = CDDM_copy(ob->derivedDeform);
- else cddm = CDDM_from_mesh(me, NULL);
+ else cddm = CDDM_from_mesh(me);
DM_set_only_copy(cddm, CD_MASK_BAREMESH);
highdm = subsurf_dm_create_local(ob, cddm, totlvl, mmd->simple, 0, mmd->flags & eMultiresModifierFlag_PlainUv, has_mask);
@@ -1236,7 +1236,7 @@ void multires_modifier_update_mdisps(struct DerivedMesh *dm)
int has_mask = CustomData_has_layer(&me->ldata, CD_GRID_PAINT_MASK);
if (ob->derivedDeform) cddm = CDDM_copy(ob->derivedDeform);
- else cddm = CDDM_from_mesh(me, NULL);
+ else cddm = CDDM_from_mesh(me);
DM_set_only_copy(cddm, CD_MASK_BAREMESH);
subdm = subsurf_dm_create_local(ob, cddm, mmd->totlvl, mmd->simple, 0, mmd->flags & eMultiresModifierFlag_PlainUv, has_mask);
@@ -2114,7 +2114,7 @@ void multires_load_old(Object *ob, Mesh *me)
multiresModifier_subdivide(mmd, ob, 1, 0);
mmd->lvl = mmd->totlvl;
- orig = CDDM_from_mesh(me, NULL);
+ orig = CDDM_from_mesh(me);
/* XXX We *must* alloc paint mask here, else we have some kind of mismatch in
* multires_modifier_update_mdisps() (called by dm->release(dm)), which always creates the
* reference subsurfed dm with this option, before calling multiresModifier_disp_run(),
diff --git a/source/blender/blenkernel/intern/node.c b/source/blender/blenkernel/intern/node.c
index d0ce56332a7..977aa016d2e 100644
--- a/source/blender/blenkernel/intern/node.c
+++ b/source/blender/blenkernel/intern/node.c
@@ -1714,8 +1714,11 @@ void ntreeFreeTree_ex(bNodeTree *ntree, const short do_id_user)
}
}
- /* XXX not nice, but needed to free localized node groups properly */
- free_localized_node_groups(ntree);
+ /* when freeing main, this would check other ntree's which may have been freed, see [#37939] */
+ if (do_id_user) {
+ /* XXX not nice, but needed to free localized node groups properly */
+ free_localized_node_groups(ntree);
+ }
/* unregister associated RNA types */
ntreeInterfaceTypeFree(ntree);
diff --git a/source/blender/blenkernel/intern/object.c b/source/blender/blenkernel/intern/object.c
index 26684d19507..711065b0e8b 100644
--- a/source/blender/blenkernel/intern/object.c
+++ b/source/blender/blenkernel/intern/object.c
@@ -321,7 +321,7 @@ void BKE_object_free_derived_caches(Object *ob)
}
/* do not free object itself */
-void BKE_object_free(Object *ob)
+void BKE_object_free_ex(Object *ob, bool do_id_user)
{
int a;
@@ -364,7 +364,7 @@ void BKE_object_free(Object *ob)
if (ob->defbase.first)
BLI_freelistN(&ob->defbase);
if (ob->pose)
- BKE_pose_free(ob->pose);
+ BKE_pose_free_ex(ob->pose, do_id_user);
if (ob->mpath)
animviz_free_motionpath(ob->mpath);
BKE_bproperty_free_list(&ob->prop);
@@ -399,6 +399,11 @@ void BKE_object_free(Object *ob)
}
}
+void BKE_object_free(Object *ob)
+{
+ BKE_object_free_ex(ob, true);
+}
+
static void unlink_object__unlinkModifierLinks(void *userData, Object *ob, Object **obpoin)
{
Object *unlinkOb = userData;
diff --git a/source/blender/blenkernel/intern/particle_system.c b/source/blender/blenkernel/intern/particle_system.c
index 0f5707f9a60..37ca502970d 100644
--- a/source/blender/blenkernel/intern/particle_system.c
+++ b/source/blender/blenkernel/intern/particle_system.c
@@ -1106,7 +1106,7 @@ static int distribute_threads_init_data(ParticleThread *threads, Scene *scene, D
/* Grid distribution */
if (part->distr==PART_DISTR_GRID && from != PART_FROM_VERT) {
BLI_srandom(31415926 + psys->seed);
- dm= CDDM_from_mesh((Mesh*)ob->data, ob);
+ dm= CDDM_from_mesh((Mesh*)ob->data);
DM_ensure_tessface(dm);
distribute_grid(dm,psys);
dm->release(dm);
@@ -1145,7 +1145,7 @@ static int distribute_threads_init_data(ParticleThread *threads, Scene *scene, D
if (psys->part->use_modifier_stack)
dm = finaldm;
else
- dm= CDDM_from_mesh((Mesh*)ob->data, ob);
+ dm= CDDM_from_mesh((Mesh*)ob->data);
/* BMESH ONLY, for verts we don't care about tessfaces */
if (from != PART_FROM_VERT) {
diff --git a/source/blender/blenkernel/intern/rigidbody.c b/source/blender/blenkernel/intern/rigidbody.c
index 600805e71ce..271a9a91f95 100644
--- a/source/blender/blenkernel/intern/rigidbody.c
+++ b/source/blender/blenkernel/intern/rigidbody.c
@@ -225,26 +225,47 @@ void BKE_rigidbody_relink_constraint(RigidBodyCon *rbc)
/* ************************************** */
/* Setup Utilities - Validate Sim Instances */
+/* get the appropriate DerivedMesh based on rigid body mesh source */
+static DerivedMesh *rigidbody_get_mesh(Object *ob)
+{
+ if (ob->rigidbody_object->mesh_source == RBO_MESH_DEFORM) {
+ return ob->derivedDeform;
+ }
+ else if (ob->rigidbody_object->mesh_source == RBO_MESH_FINAL) {
+ return ob->derivedFinal;
+ }
+ else {
+ return CDDM_from_mesh(ob->data);
+ }
+}
+
/* create collision shape of mesh - convex hull */
static rbCollisionShape *rigidbody_get_shape_convexhull_from_mesh(Object *ob, float margin, bool *can_embed)
{
rbCollisionShape *shape = NULL;
- Mesh *me = NULL;
+ DerivedMesh *dm = NULL;
+ MVert *mvert = NULL;
+ int totvert = 0;
if (ob->type == OB_MESH && ob->data) {
- me = ob->data;
+ dm = rigidbody_get_mesh(ob);
+ mvert = (dm) ? dm->getVertArray(dm) : NULL;
+ totvert = (dm) ? dm->getNumVerts(dm) : 0;
}
else {
printf("ERROR: cannot make Convex Hull collision shape for non-Mesh object\n");
}
- if (me && me->totvert) {
- shape = RB_shape_new_convex_hull((float *)me->mvert, sizeof(MVert), me->totvert, margin, can_embed);
+ if (totvert) {
+ shape = RB_shape_new_convex_hull((float *)mvert, sizeof(MVert), totvert, margin, can_embed);
}
else {
printf("ERROR: no vertices to define Convex Hull collision shape with\n");
}
+ if (dm && ob->rigidbody_object->mesh_source == RBO_MESH_BASE)
+ dm->release(dm);
+
return shape;
}
@@ -256,14 +277,20 @@ static rbCollisionShape *rigidbody_get_shape_trimesh_from_mesh(Object *ob)
rbCollisionShape *shape = NULL;
if (ob->type == OB_MESH) {
- DerivedMesh *dm = CDDM_from_mesh(ob->data, ob);
-
+ DerivedMesh *dm = NULL;
MVert *mvert;
MFace *mface;
int totvert;
int totface;
+ int tottris = 0;
+ int triangle_index = 0;
+
+ dm = rigidbody_get_mesh(ob);
/* ensure mesh validity, then grab data */
+ if (dm == NULL)
+ return NULL;
+
DM_ensure_tessface(dm);
mvert = (dm) ? dm->getVertArray(dm) : NULL;
@@ -278,32 +305,32 @@ static rbCollisionShape *rigidbody_get_shape_trimesh_from_mesh(Object *ob)
else {
rbMeshData *mdata;
int i;
+
+ /* count triangles */
+ for (i = 0; i < totface; i++) {
+ (mface[i].v4) ? (tottris += 2) : (tottris += 1);
+ }
/* init mesh data for collision shape */
- mdata = RB_trimesh_data_new();
+ mdata = RB_trimesh_data_new(tottris, totvert);
+
+ RB_trimesh_add_vertices(mdata, (float*)mvert, totvert, sizeof(MVert));
/* loop over all faces, adding them as triangles to the collision shape
* (so for some faces, more than triangle will get added)
*/
for (i = 0; (i < totface) && (mface) && (mvert); i++, mface++) {
/* add first triangle - verts 1,2,3 */
- {
- MVert *va = (mface->v1 < totvert) ? (mvert + mface->v1) : (mvert);
- MVert *vb = (mface->v2 < totvert) ? (mvert + mface->v2) : (mvert);
- MVert *vc = (mface->v3 < totvert) ? (mvert + mface->v3) : (mvert);
-
- RB_trimesh_add_triangle(mdata, va->co, vb->co, vc->co);
- }
+ RB_trimesh_add_triangle_indices(mdata, triangle_index, mface->v1, mface->v2, mface->v3);
+ triangle_index++;
/* add second triangle if needed - verts 1,3,4 */
if (mface->v4) {
- MVert *va = (mface->v1 < totvert) ? (mvert + mface->v1) : (mvert);
- MVert *vb = (mface->v3 < totvert) ? (mvert + mface->v3) : (mvert);
- MVert *vc = (mface->v4 < totvert) ? (mvert + mface->v4) : (mvert);
-
- RB_trimesh_add_triangle(mdata, va->co, vb->co, vc->co);
+ RB_trimesh_add_triangle_indices(mdata, triangle_index, mface->v1, mface->v3, mface->v4);
+ triangle_index++;
}
}
+ RB_trimesh_finish(mdata);
/* construct collision shape
*
@@ -323,7 +350,7 @@ static rbCollisionShape *rigidbody_get_shape_trimesh_from_mesh(Object *ob)
}
/* cleanup temp data */
- if (dm) {
+ if (dm && ob->rigidbody_object->mesh_source == RBO_MESH_BASE) {
dm->release(dm);
}
}
@@ -337,7 +364,7 @@ static rbCollisionShape *rigidbody_get_shape_trimesh_from_mesh(Object *ob)
/* Create new physics sim collision shape for object and store it,
* or remove the existing one first and replace...
*/
-void BKE_rigidbody_validate_sim_shape(Object *ob, short rebuild)
+static void rigidbody_validate_sim_shape(Object *ob, bool rebuild)
{
RigidBodyOb *rbo = ob->rigidbody_object;
rbCollisionShape *new_shape = NULL;
@@ -425,9 +452,10 @@ void BKE_rigidbody_validate_sim_shape(Object *ob, short rebuild)
rbo->physics_shape = new_shape;
RB_shape_set_margin(rbo->physics_shape, RBO_GET_MARGIN(rbo));
}
- else { /* otherwise fall back to box shape */
+ /* use box shape if we can't fall back to old shape */
+ else if (rbo->physics_shape == NULL) {
rbo->shape = RB_SHAPE_BOX;
- BKE_rigidbody_validate_sim_shape(ob, true);
+ rigidbody_validate_sim_shape(ob, true);
}
}
@@ -436,7 +464,7 @@ void BKE_rigidbody_validate_sim_shape(Object *ob, short rebuild)
/* Create physics sim representation of object given RigidBody settings
* < rebuild: even if an instance already exists, replace it
*/
-void BKE_rigidbody_validate_sim_object(RigidBodyWorld *rbw, Object *ob, short rebuild)
+static void rigidbody_validate_sim_object(RigidBodyWorld *rbw, Object *ob, bool rebuild)
{
RigidBodyOb *rbo = (ob) ? ob->rigidbody_object : NULL;
float loc[3];
@@ -451,10 +479,9 @@ void BKE_rigidbody_validate_sim_object(RigidBodyWorld *rbw, Object *ob, short re
/* make sure collision shape exists */
/* FIXME we shouldn't always have to rebuild collision shapes when rebuilding objects, but it's needed for constraints to update correctly */
if (rbo->physics_shape == NULL || rebuild)
- BKE_rigidbody_validate_sim_shape(ob, true);
+ rigidbody_validate_sim_shape(ob, true);
- if (rbo->physics_object) {
- if (rebuild == false)
+ if (rbo->physics_object && rebuild == false) {
RB_dworld_remove_body(rbw->physics_world, rbo->physics_object);
}
if (!rbo->physics_object || rebuild) {
@@ -500,7 +527,7 @@ void BKE_rigidbody_validate_sim_object(RigidBodyWorld *rbw, Object *ob, short re
/* Create physics sim representation of constraint given rigid body constraint settings
* < rebuild: even if an instance already exists, replace it
*/
-void BKE_rigidbody_validate_sim_constraint(RigidBodyWorld *rbw, Object *ob, short rebuild)
+static void rigidbody_validate_sim_constraint(RigidBodyWorld *rbw, Object *ob, bool rebuild)
{
RigidBodyCon *rbc = (ob) ? ob->rigidbody_constraint : NULL;
float loc[3];
@@ -527,8 +554,7 @@ void BKE_rigidbody_validate_sim_constraint(RigidBodyWorld *rbw, Object *ob, shor
return;
}
- if (rbc->physics_constraint) {
- if (rebuild == false)
+ if (rbc->physics_constraint && rebuild == false) {
RB_dworld_remove_constraint(rbw->physics_world, rbc->physics_constraint);
}
if (rbc->physics_constraint == NULL || rebuild) {
@@ -672,7 +698,7 @@ void BKE_rigidbody_validate_sim_constraint(RigidBodyWorld *rbw, Object *ob, shor
/* Create physics sim world given RigidBody world settings */
// NOTE: this does NOT update object references that the scene uses, in case those aren't ready yet!
-void BKE_rigidbody_validate_sim_world(Scene *scene, RigidBodyWorld *rbw, short rebuild)
+void BKE_rigidbody_validate_sim_world(Scene *scene, RigidBodyWorld *rbw, bool rebuild)
{
/* sanity checks */
if (rbw == NULL)
@@ -798,6 +824,8 @@ RigidBodyOb *BKE_rigidbody_create_object(Scene *scene, Object *ob, short type)
else
rbo->shape = RB_SHAPE_TRIMESH;
+ rbo->mesh_source = RBO_MESH_DEFORM;
+
/* set initial transform */
mat4_to_loc_quat(rbo->pos, rbo->orn, ob->obmat);
@@ -1000,6 +1028,17 @@ static void rigidbody_update_sim_ob(Scene *scene, RigidBodyWorld *rbw, Object *o
if (rbo->physics_object == NULL)
return;
+ if (rbo->shape == RB_SHAPE_TRIMESH && rbo->flag & RBO_FLAG_USE_DEFORM) {
+ DerivedMesh *dm = ob->derivedDeform;
+ if (dm) {
+ MVert *mvert = dm->getVertArray(dm);
+ int totvert = dm->getNumVerts(dm);
+ BoundBox *bb = BKE_object_boundbox_get(ob);
+
+ RB_shape_trimesh_update(rbo->physics_shape, (float*)mvert, totvert, sizeof(MVert), bb->vec[0], bb->vec[6]);
+ }
+ }
+
mat4_decompose(loc, rot, scale, ob->obmat);
/* update scale for all objects */
@@ -1091,7 +1130,7 @@ static void rigidbody_update_simulation(Scene *scene, RigidBodyWorld *rbw, int r
* - assume object to be active? That is the default for newly added settings...
*/
ob->rigidbody_object = BKE_rigidbody_create_object(scene, ob, RBO_TYPE_ACTIVE);
- BKE_rigidbody_validate_sim_object(rbw, ob, true);
+ rigidbody_validate_sim_object(rbw, ob, true);
rbo = ob->rigidbody_object;
}
@@ -1100,15 +1139,15 @@ static void rigidbody_update_simulation(Scene *scene, RigidBodyWorld *rbw, int r
/* refresh object... */
if (rebuild) {
/* World has been rebuilt so rebuild object */
- BKE_rigidbody_validate_sim_object(rbw, ob, true);
+ rigidbody_validate_sim_object(rbw, ob, true);
}
else if (rbo->flag & RBO_FLAG_NEEDS_VALIDATE) {
- BKE_rigidbody_validate_sim_object(rbw, ob, false);
+ rigidbody_validate_sim_object(rbw, ob, false);
}
/* refresh shape... */
if (rbo->flag & RBO_FLAG_NEEDS_RESHAPE) {
/* mesh/shape data changed, so force shape refresh */
- BKE_rigidbody_validate_sim_shape(ob, true);
+ rigidbody_validate_sim_shape(ob, true);
/* now tell RB sim about it */
// XXX: we assume that this can only get applied for active/passive shapes that will be included as rigidbodies
RB_body_set_collision_shape(rbo->physics_object, rbo->physics_shape);
@@ -1137,7 +1176,7 @@ static void rigidbody_update_simulation(Scene *scene, RigidBodyWorld *rbw, int r
* constraint settings (perhaps it was added manually), add!
*/
ob->rigidbody_constraint = BKE_rigidbody_create_constraint(scene, ob, RBC_TYPE_FIXED);
- BKE_rigidbody_validate_sim_constraint(rbw, ob, true);
+ rigidbody_validate_sim_constraint(rbw, ob, true);
rbc = ob->rigidbody_constraint;
}
@@ -1145,10 +1184,10 @@ static void rigidbody_update_simulation(Scene *scene, RigidBodyWorld *rbw, int r
/* perform simulation data updates as tagged */
if (rebuild) {
/* World has been rebuilt so rebuild constraint */
- BKE_rigidbody_validate_sim_constraint(rbw, ob, true);
+ rigidbody_validate_sim_constraint(rbw, ob, true);
}
else if (rbc->flag & RBC_FLAG_NEEDS_VALIDATE) {
- BKE_rigidbody_validate_sim_constraint(rbw, ob, false);
+ rigidbody_validate_sim_constraint(rbw, ob, false);
}
rbc->flag &= ~RBC_FLAG_NEEDS_VALIDATE;
}
@@ -1355,10 +1394,7 @@ void BKE_rigidbody_free_constraint(Object *ob) {}
struct RigidBodyOb *BKE_rigidbody_copy_object(Object *ob) { return NULL; }
struct RigidBodyCon *BKE_rigidbody_copy_constraint(Object *ob) { return NULL; }
void BKE_rigidbody_relink_constraint(RigidBodyCon *rbc) {}
-void BKE_rigidbody_validate_sim_shape(Object *ob, short rebuild) {}
-void BKE_rigidbody_validate_sim_object(RigidBodyWorld *rbw, Object *ob, short rebuild) {}
-void BKE_rigidbody_validate_sim_constraint(RigidBodyWorld *rbw, Object *ob, short rebuild) {}
-void BKE_rigidbody_validate_sim_world(Scene *scene, RigidBodyWorld *rbw, short rebuild) {}
+void BKE_rigidbody_validate_sim_world(Scene *scene, RigidBodyWorld *rbw, bool rebuild) {}
struct RigidBodyWorld *BKE_rigidbody_create_world(Scene *scene) { return NULL; }
struct RigidBodyWorld *BKE_rigidbody_world_copy(RigidBodyWorld *rbw) { return NULL; }
void BKE_rigidbody_world_groups_relink(struct RigidBodyWorld *rbw) {}
diff --git a/source/blender/blenkernel/intern/scene.c b/source/blender/blenkernel/intern/scene.c
index 84b9b0aadf4..3ca702e0068 100644
--- a/source/blender/blenkernel/intern/scene.c
+++ b/source/blender/blenkernel/intern/scene.c
@@ -1293,7 +1293,7 @@ static void scene_update_object_func(TaskPool *pool, void *taskdata, int threadi
}
/* Update will decrease child's valency and schedule child with zero valency. */
- DAG_threaded_update_handle_node_updated(node,scene_update_object_add_task, pool);
+ DAG_threaded_update_handle_node_updated(node, scene_update_object_add_task, pool);
#undef PRINT
}
diff --git a/source/blender/blenkernel/intern/subsurf_ccg.c b/source/blender/blenkernel/intern/subsurf_ccg.c
index e94db6f637c..188c80e7cc8 100644
--- a/source/blender/blenkernel/intern/subsurf_ccg.c
+++ b/source/blender/blenkernel/intern/subsurf_ccg.c
@@ -3693,7 +3693,7 @@ void subsurf_calculate_limit_positions(Mesh *me, float (*positions_r)[3])
CCGSubSurf *ss = _getSubSurf(NULL, 1, 3, CCG_USE_ARENA);
float edge_sum[3], face_sum[3];
CCGVertIterator *vi;
- DerivedMesh *dm = CDDM_from_mesh(me, NULL);
+ DerivedMesh *dm = CDDM_from_mesh(me);
ss_sync_from_derivedmesh(ss, dm, NULL, 0);