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:
authorDaniel Dunbar <daniel@zuster.org>2005-08-15 14:30:53 +0400
committerDaniel Dunbar <daniel@zuster.org>2005-08-15 14:30:53 +0400
commit2abd79b491c024eee8ad460815486fc051aefbf4 (patch)
treeb9579c776265c21f3fd8486f9a830dc6a26cf82a /source/blender/blenkernel
parent91cd2d8138fee78dbc1ea4ef05ce7517cc4a5909 (diff)
- readded DL_VERTS type to store lattice deformed verts
- new feature, twiddled with lattice resizing to try to maintain existing vertex changes... much nicer than just resetting the lattice if you decide you need more detail in the lattice. - modifiers work with lattices now. yes, that does mean you can make a chain of lattices effecting each other 8 miles long. - some cleanup of softbody code, was rather splintered and call path was twisted and confusing. reworked main object step routine to do things in a more obvious and consistent manner and without duplicate code - added ob->softflag OB_SB_RESET instead of sbObjectReset call - modifier changes reset softbody now - moved curve_getVertexCos/curve_applyVertexCos into curve.c - update curve modifier eval to work with virtual modifiers - update modifier apply to work with curves/surfs - update make parent to also recalc object data NOTE: Although you can turn SB on for curve/font objects at the moment it doesn't really work because they call deform in multiple steps and this confuses SB. Not sure how to deal with atm.
Diffstat (limited to 'source/blender/blenkernel')
-rw-r--r--source/blender/blenkernel/BKE_curve.h3
-rw-r--r--source/blender/blenkernel/BKE_displist.h1
-rw-r--r--source/blender/blenkernel/BKE_lattice.h6
-rw-r--r--source/blender/blenkernel/BKE_softbody.h24
-rw-r--r--source/blender/blenkernel/intern/curve.c54
-rw-r--r--source/blender/blenkernel/intern/displist.c70
-rw-r--r--source/blender/blenkernel/intern/lattice.c281
-rw-r--r--source/blender/blenkernel/intern/modifier.c2
-rw-r--r--source/blender/blenkernel/intern/object.c3
-rw-r--r--source/blender/blenkernel/intern/softbody.c408
10 files changed, 396 insertions, 456 deletions
diff --git a/source/blender/blenkernel/BKE_curve.h b/source/blender/blenkernel/BKE_curve.h
index 4effdb6af8a..03a7cfe0096 100644
--- a/source/blender/blenkernel/BKE_curve.h
+++ b/source/blender/blenkernel/BKE_curve.h
@@ -86,5 +86,8 @@ void sethandlesNurb(short code);
void swapdata(void *adr1, void *adr2, int len);
void switchdirectionNurb( struct Nurb *nu);
+float (*curve_getVertexCos(struct Curve *cu, struct ListBase *lb, int *numVerts_r))[3];
+void curve_applyVertexCos(struct Curve *cu, struct ListBase *lb, float (*vertexCos)[3]);
+
#endif
diff --git a/source/blender/blenkernel/BKE_displist.h b/source/blender/blenkernel/BKE_displist.h
index 434f9fb1ef9..021b584036f 100644
--- a/source/blender/blenkernel/BKE_displist.h
+++ b/source/blender/blenkernel/BKE_displist.h
@@ -42,6 +42,7 @@
#define DL_INDEX3 4
#define DL_INDEX4 5
#define DL_VERTCOL 6
+#define DL_VERTS 7
/* dl->flag */
#define DL_CYCL_U 1
diff --git a/source/blender/blenkernel/BKE_lattice.h b/source/blender/blenkernel/BKE_lattice.h
index 48e8f9fb8b3..073810fd37b 100644
--- a/source/blender/blenkernel/BKE_lattice.h
+++ b/source/blender/blenkernel/BKE_lattice.h
@@ -41,7 +41,7 @@ struct BPoint;
extern struct Lattice *editLatt;
-void resizelattice(struct Lattice *lt);
+void resizelattice(struct Lattice *lt, int u, int v, int w, struct Object *ltOb);
struct Lattice *add_lattice(void);
struct Lattice *copy_lattice(struct Lattice *lt);
void free_lattice(struct Lattice *lt);
@@ -51,11 +51,13 @@ void init_latt_deform(struct Object *oblatt, struct Object *ob);
void calc_latt_deform(float *co);
void end_latt_deform(void);
int object_deform_mball(struct Object *ob);
-struct BPoint *latt_bp(struct Lattice *lt, int u, int v, int w);
void outside_lattice(struct Lattice *lt);
void curve_deform_verts(struct Object *cuOb, struct Object *target, float (*vertexCos)[3], int numVerts);
void lattice_deform_verts(struct Object *laOb, struct Object *target, float (*vertexCos)[3], int numVerts);
void armature_deform_verts(struct Object *armOb, struct Object *target, float (*vertexCos)[3], int numVerts);
+float (*lattice_getVertexCos(struct Object *ob, int *numVerts_r))[3];
+void lattice_applyVertexCos(struct Object *ob, float (*vertexCos)[3]);
+void lattice_calc_modifiers(struct Object *ob);
#endif
diff --git a/source/blender/blenkernel/BKE_softbody.h b/source/blender/blenkernel/BKE_softbody.h
index f47cb1b51e3..3ead7445c03 100644
--- a/source/blender/blenkernel/BKE_softbody.h
+++ b/source/blender/blenkernel/BKE_softbody.h
@@ -34,19 +34,6 @@
#ifndef BKE_SOFTBODY_H
#define BKE_SOFTBODY_H
-typedef struct BodyPoint {
- float origS[3], origE[3], origT[3], pos[3], vec[3], force[3];
- float weight, goal;
- float prevpos[3], prevvec[3], prevdx[3], prevdv[3]; /* used for Heun integration */
- int nofsprings; int *springs;
- float contactfrict;
-} BodyPoint;
-
-typedef struct BodySpring {
- int v1, v2;
- float len, strength;
-} BodySpring;
-
struct Object;
struct SoftBody;
@@ -56,16 +43,11 @@ extern struct SoftBody *sbNew(void);
/* frees internal data and softbody itself */
extern void sbFree(struct SoftBody *sb);
-/* go one step in simulation, copy result in vertexCos for meshes, or
- * directly for lattices.
- */
-extern void sbObjectStep(struct Object *ob, float framnr, float (*vertexCos)[3]);
+/* do one simul step, reading and writing vertex locs from given array */
+extern void sbObjectStep(struct Object *ob, float framnr, float (*vertexCos)[3], int numVerts);
/* makes totally fresh start situation, resets time */
-extern void sbObjectToSoftbody(struct Object *ob, float (*vertexCos)[3]);
-
-/* resets all motion and time */
-extern void sbObjectReset(struct Object *ob, float (*vertexCos)[3]);
+extern void sbObjectToSoftbody(struct Object *ob);
#endif
diff --git a/source/blender/blenkernel/intern/curve.c b/source/blender/blenkernel/intern/curve.c
index 150f5eddd41..b1f8fcca6bf 100644
--- a/source/blender/blenkernel/intern/curve.c
+++ b/source/blender/blenkernel/intern/curve.c
@@ -2411,3 +2411,57 @@ void switchdirectionNurb(Nurb *nu)
}
}
}
+
+
+float (*curve_getVertexCos(Curve *cu, ListBase *lb, int *numVerts_r))[3]
+{
+ int i, numVerts = *numVerts_r = count_curveverts(lb);
+ float *co, (*cos)[3] = MEM_mallocN(sizeof(*cos)*numVerts, "cu_vcos");
+ Nurb *nu;
+
+ co = cos[0];
+ for (nu=lb->first; nu; nu=nu->next) {
+ if ((nu->type & 7)==CU_BEZIER) {
+ BezTriple *bezt = nu->bezt;
+
+ for (i=0; i<nu->pntsu; i++,bezt++) {
+ VECCOPY(co, bezt->vec[0]); co+=3;
+ VECCOPY(co, bezt->vec[1]); co+=3;
+ VECCOPY(co, bezt->vec[2]); co+=3;
+ }
+ } else {
+ BPoint *bp = nu->bp;
+
+ for (i=0; i<nu->pntsu*nu->pntsv; i++,bp++) {
+ VECCOPY(co, bp->vec); co+=3;
+ }
+ }
+ }
+
+ return cos;
+}
+
+void curve_applyVertexCos(Curve *cu, ListBase *lb, float (*vertexCos)[3])
+{
+ float *co = vertexCos[0];
+ Nurb *nu;
+ int i;
+
+ for (nu=lb->first; nu; nu=nu->next) {
+ if ((nu->type & 7)==CU_BEZIER) {
+ BezTriple *bezt = nu->bezt;
+
+ for (i=0; i<nu->pntsu; i++,bezt++) {
+ VECCOPY(bezt->vec[0], co); co+=3;
+ VECCOPY(bezt->vec[1], co); co+=3;
+ VECCOPY(bezt->vec[2], co); co+=3;
+ }
+ } else {
+ BPoint *bp = nu->bp;
+
+ for (i=0; i<nu->pntsu*nu->pntsv; i++,bp++) {
+ VECCOPY(bp->vec, co); co+=3;
+ }
+ }
+ }
+}
diff --git a/source/blender/blenkernel/intern/displist.c b/source/blender/blenkernel/intern/displist.c
index e9c0a1ee252..4ee8fc2640f 100644
--- a/source/blender/blenkernel/intern/displist.c
+++ b/source/blender/blenkernel/intern/displist.c
@@ -1417,65 +1417,13 @@ void makeDispListMBall(Object *ob)
boundbox_displist(ob);
}
-float (*curve_getVertexCos(Curve *cu, ListBase *lb, int *numVerts_r))[3]
-{
- int i, numVerts = *numVerts_r = count_curveverts(lb);
- float *co, (*cos)[3] = MEM_mallocN(sizeof(*cos)*numVerts, "cu_vcos");
- Nurb *nu;
-
- co = cos[0];
- for (nu=lb->first; nu; nu=nu->next) {
- if ((nu->type & 7)==CU_BEZIER) {
- BezTriple *bezt = nu->bezt;
-
- for (i=0; i<nu->pntsu; i++,bezt++) {
- VECCOPY(co, bezt->vec[0]); co+=3;
- VECCOPY(co, bezt->vec[1]); co+=3;
- VECCOPY(co, bezt->vec[2]); co+=3;
- }
- } else {
- BPoint *bp = nu->bp;
-
- for (i=0; i<nu->pntsu*nu->pntsv; i++,bp++) {
- VECCOPY(co, bp->vec); co+=3;
- }
- }
- }
-
- return cos;
-}
-
-void curve_applyVertexCos(Curve *cu, ListBase *lb, float (*vertexCos)[3])
-{
- float *co = vertexCos[0];
- Nurb *nu;
- int i;
-
- for (nu=lb->first; nu; nu=nu->next) {
- if ((nu->type & 7)==CU_BEZIER) {
- BezTriple *bezt = nu->bezt;
-
- for (i=0; i<nu->pntsu; i++,bezt++) {
- VECCOPY(bezt->vec[0], co); co+=3;
- VECCOPY(bezt->vec[1], co); co+=3;
- VECCOPY(bezt->vec[2], co); co+=3;
- }
- } else {
- BPoint *bp = nu->bp;
-
- for (i=0; i<nu->pntsu*nu->pntsv; i++,bp++) {
- VECCOPY(bp->vec, co); co+=3;
- }
- }
- }
-}
-
static ModifierData *curve_get_tesselate_point(Object *ob, int forRender, int editmode)
{
- ModifierData *md, *preTesselatePoint;
+ ModifierData *md = modifiers_getVirtualModifierList(ob);
+ ModifierData *preTesselatePoint;
preTesselatePoint = NULL;
- for (md=ob->modifiers.first; md; md=md->next) {
+ for (; md; md=md->next) {
ModifierTypeInfo *mti = modifierType_getInfo(md->type);
if (!(md->mode&(1<<forRender))) continue;
@@ -1493,13 +1441,14 @@ static ModifierData *curve_get_tesselate_point(Object *ob, int forRender, int ed
void curve_calc_modifiers_pre(Object *ob, ListBase *nurb, int forRender, float (**originalVerts_r)[3], float (**deformedVerts_r)[3], int *numVerts_r)
{
int editmode = (!forRender && ob==G.obedit);
- ModifierData *md, *preTesselatePoint = curve_get_tesselate_point(ob, forRender, editmode);
+ ModifierData *md = modifiers_getVirtualModifierList(ob);
+ ModifierData *preTesselatePoint = curve_get_tesselate_point(ob, forRender, editmode);
int numVerts = 0;
float (*originalVerts)[3] = NULL;
float (*deformedVerts)[3] = NULL;
if (preTesselatePoint) {
- for (md=ob->modifiers.first; md; md=md->next) {
+ for (; md; md=md->next) {
ModifierTypeInfo *mti = modifierType_getInfo(md->type);
if (!(md->mode&(1<<forRender))) continue;
@@ -1516,8 +1465,6 @@ void curve_calc_modifiers_pre(Object *ob, ListBase *nurb, int forRender, float (
if (md==preTesselatePoint)
break;
}
- } else {
- md = ob->modifiers.first;
}
if (deformedVerts) {
@@ -1532,13 +1479,12 @@ void curve_calc_modifiers_pre(Object *ob, ListBase *nurb, int forRender, float (
void curve_calc_modifiers_post(Object *ob, ListBase *nurb, ListBase *dispbase, int forRender, float (*originalVerts)[3], float (*deformedVerts)[3])
{
int editmode = (!forRender && ob==G.obedit);
- ModifierData *md, *preTesselatePoint = curve_get_tesselate_point(ob, forRender, editmode);
+ ModifierData *md = modifiers_getVirtualModifierList(ob);
+ ModifierData *preTesselatePoint = curve_get_tesselate_point(ob, forRender, editmode);
DispList *dl;
if (preTesselatePoint) {
md = preTesselatePoint->next;
- } else {
- md = ob->modifiers.first;
}
for (; md; md=md->next) {
diff --git a/source/blender/blenkernel/intern/lattice.c b/source/blender/blenkernel/intern/lattice.c
index 8f463886b3f..df0f9e7d8f8 100644
--- a/source/blender/blenkernel/intern/lattice.c
+++ b/source/blender/blenkernel/intern/lattice.c
@@ -46,6 +46,7 @@
#include "DNA_armature_types.h"
#include "DNA_mesh_types.h"
#include "DNA_meshdata_types.h"
+#include "DNA_modifier_types.h"
#include "DNA_object_types.h"
#include "DNA_scene_types.h"
#include "DNA_lattice_types.h"
@@ -62,6 +63,7 @@
#include "BKE_lattice.h"
#include "BKE_library.h"
#include "BKE_main.h"
+#include "BKE_modifier.h"
#include "BKE_object.h"
#include "BKE_screen.h"
#include "BKE_utildefines.h"
@@ -74,45 +76,120 @@
#include "blendef.h"
-Lattice *editLatt=0, *deformLatt=0;
+Lattice *editLatt=0;
+static Lattice *deformLatt=0;
-float *latticedata=0, latmat[4][4];
+static float *latticedata=0, latmat[4][4];
-void resizelattice(Lattice *lt)
+void calc_lat_fudu(int flag, int res, float *fu, float *du)
+{
+ if(res==1) {
+ *fu= 0.0;
+ *du= 0.0;
+ }
+ else if(flag & LT_GRID) {
+ *fu= -0.5f*(res-1);
+ *du= 1.0f;
+ }
+ else {
+ *fu= -1.0f;
+ *du= 2.0f/(res-1);
+ }
+}
+
+void resizelattice(Lattice *lt, int uNew, int vNew, int wNew, Object *ltOb)
{
BPoint *bp;
- int u, v, w;
- float vec[3], fu, fv, fw, du=0.0, dv=0.0, dw=0.0;
+ int i, u, v, w;
+ float fu, fv, fw, uc, vc, wc, du=0.0, dv=0.0, dw=0.0;
+ float *co, (*vertexCos)[3] = NULL;
+
+ while(uNew*vNew*wNew > 32000) {
+ if( uNew>=vNew && uNew>=wNew) uNew--;
+ else if( vNew>=uNew && vNew>=wNew) vNew--;
+ else wNew--;
+ }
+
+ vertexCos = MEM_mallocN(sizeof(*vertexCos)*uNew*vNew*wNew, "tmp_vcos");
+
+ calc_lat_fudu(lt->flag, uNew, &fu, &du);
+ calc_lat_fudu(lt->flag, vNew, &fv, &dv);
+ calc_lat_fudu(lt->flag, wNew, &fw, &dw);
+
+ /* If old size is different then resolution changed in interface,
+ * try to do clever reinit of points. Pretty simply idea, we just
+ * deform new verts by old lattice, but scaling them to match old
+ * size first.
+ */
+ if (ltOb) {
+ if (uNew!=1 && lt->pntsu!=1) {
+ fu = lt->fu;
+ du = (lt->pntsu-1)*lt->du/(uNew-1);
+ }
+
+ if (vNew!=1 && lt->pntsv!=1) {
+ fv = lt->fv;
+ dv = (lt->pntsv-1)*lt->dv/(vNew-1);
+ }
+
+ if (wNew!=1 && lt->pntsw!=1) {
+ fw = lt->fw;
+ dw = (lt->pntsw-1)*lt->dw/(wNew-1);
+ }
+ }
+
+ co = vertexCos[0];
+ for(w=0,wc=fw; w<wNew; w++,wc+=dw) {
+ for(v=0,vc=fv; v<vNew; v++,vc+=dv) {
+ for(u=0,uc=fu; u<uNew; u++,co+=3,uc+=du) {
+ co[0] = uc;
+ co[1] = vc;
+ co[2] = wc;
+ }
+ }
+ }
+ if (ltOb) {
+ float mat[4][4];
+ int typeu = lt->typeu, typev = lt->typev, typew = lt->typew;
+
+ /* works best if we force to linear type (endpoints match) */
+ lt->typeu = lt->typev = lt->typew = KEY_LINEAR;
+
+ /* prevent using deformed locations */
+ freedisplist(&ltOb->disp);
+
+ Mat4CpyMat4(mat, ltOb->obmat);
+ Mat4One(ltOb->obmat);
+ lattice_deform_verts(ltOb, NULL, vertexCos, uNew*vNew*wNew);
+ Mat4CpyMat4(ltOb->obmat, mat);
+
+ lt->typeu = typeu;
+ lt->typev = typev;
+ lt->typew = typew;
+ }
+
+ lt->fu = fu;
+ lt->fv = fv;
+ lt->fw = fw;
+ lt->du = du;
+ lt->dv = dv;
+ lt->dw = dw;
+
+ lt->pntsu = uNew;
+ lt->pntsv = vNew;
+ lt->pntsw = wNew;
MEM_freeN(lt->def);
lt->def= MEM_callocN(lt->pntsu*lt->pntsv*lt->pntsw*sizeof(BPoint), "lattice bp");
bp= lt->def;
- while(lt->pntsu*lt->pntsv*lt->pntsw > 32000) {
- if( lt->pntsu>=lt->pntsv && lt->pntsu>=lt->pntsw) lt->pntsu--;
- else if( lt->pntsv>=lt->pntsu && lt->pntsv>=lt->pntsw) lt->pntsv--;
- else lt->pntsw--;
- }
-
- calc_lat_fudu(lt->flag, lt->pntsu, &fu, &du);
- calc_lat_fudu(lt->flag, lt->pntsv, &fv, &dv);
- calc_lat_fudu(lt->flag, lt->pntsw, &fw, &dw);
-
- vec[2]= fw;
- for(w=0; w<lt->pntsw; w++) {
- vec[1]= fv;
- for(v=0; v<lt->pntsv; v++) {
- vec[0]= fu;
- for(u=0; u<lt->pntsu; u++, bp++) {
- VECCOPY(bp->vec, vec);
- vec[0]+= du;
- }
- vec[1]+= dv;
- }
- vec[2]+= dw;
+ for (i=0; i<lt->pntsu*lt->pntsv*lt->pntsw; i++,bp++) {
+ VECCOPY(bp->vec, vertexCos[i]);
}
+
+ MEM_freeN(vertexCos);
}
Lattice *add_lattice()
@@ -121,15 +198,12 @@ Lattice *add_lattice()
lt= alloc_libblock(&G.main->latt, ID_LT, "Lattice");
- lt->pntsu=lt->pntsv=lt->pntsw= 2;
lt->flag= LT_GRID;
lt->typeu= lt->typev= lt->typew= KEY_BSPLINE;
- /* temporally */
- lt->def= MEM_callocN(sizeof(BPoint), "lattvert");
-
- resizelattice(lt); /* creates a uniform lattice */
+ lt->def= MEM_callocN(sizeof(BPoint), "lattvert"); /* temporary */
+ resizelattice(lt, 2, 2, 2, NULL); /* creates a uniform lattice */
return lt;
}
@@ -207,45 +281,20 @@ void make_local_lattice(Lattice *lt)
}
}
-
-
-void calc_lat_fudu(int flag, int res, float *fu, float *du)
-{
-
- if(res==1) {
- *fu= 0.0;
- *du= 0.0;
- }
- else if(flag & LT_GRID) {
- *fu= -0.5f*(res-1);
- *du= 1.0f;
- }
- else {
- *fu= -1.0f;
- *du= 2.0f/(res-1);
- }
-
-}
-
void init_latt_deform(Object *oblatt, Object *ob)
{
- /* we make an array with all differences */
- BPoint *bp;
+ /* we make an array with all differences */
+ Lattice *lt = deformLatt = (oblatt==G.obedit)?editLatt:oblatt->data;
+ BPoint *bp = lt->def;
+ DispList *dl = find_displist(&oblatt->disp, DL_VERTS);
+ float *co = dl?dl->verts:NULL;
float *fp, imat[4][4];
- float vec[3], fu, fv, fw, du=0.0, dv=0.0, dw=0.0;
+ float fu, fv, fw;
int u, v, w;
-
- if(oblatt==G.obedit) deformLatt= editLatt;
- else deformLatt= oblatt->data;
-
+
fp= latticedata= MEM_mallocN(sizeof(float)*3*deformLatt->pntsu*deformLatt->pntsv*deformLatt->pntsw, "latticedata");
- do_latt_key(oblatt->data);
- bp= deformLatt->def;
-
- //if(ob) where_is_object(ob); causes lag here, but why! (ton)
-
- /* for example with a particle system: ob==0 */
+ /* for example with a particle system: ob==0 */
if(ob==0) {
/* in deformspace, calc matrix */
Mat4Invert(latmat, oblatt->obmat);
@@ -261,35 +310,30 @@ void init_latt_deform(Object *oblatt, Object *ob)
/* back: put in deform array */
Mat4Invert(imat, latmat);
}
- calc_lat_fudu(deformLatt->flag, deformLatt->pntsu, &fu, &du);
- calc_lat_fudu(deformLatt->flag, deformLatt->pntsv, &fv, &dv);
- calc_lat_fudu(deformLatt->flag, deformLatt->pntsw, &fw, &dw);
-
- /* we keep calculating the u v w lattice coordinates, not enough reason to store that */
- vec[2]= fw;
- for(w=0; w<deformLatt->pntsw; w++) {
- vec[1]= fv;
- for(v=0; v<deformLatt->pntsv; v++) {
- vec[0]= fu;
- for(u=0; u<deformLatt->pntsu; u++, bp++) {
-
- VecSubf(fp, bp->vec, vec);
+ for(w=0,fw=lt->fw; w<lt->pntsw; w++,fw+=lt->dw) {
+ for(v=0,fv=lt->fv; v<lt->pntsv; v++, fv+=lt->dv) {
+ for(u=0,fu=lt->fu; u<lt->pntsu; u++, bp++, co+=3, fp+=3, fu+=lt->du) {
+ if (dl) {
+ fp[0] = co[0] - fu;
+ fp[1] = co[1] - fv;
+ fp[2] = co[2] - fw;
+ } else {
+ fp[0] = bp->vec[0] - fu;
+ fp[1] = bp->vec[1] - fv;
+ fp[2] = bp->vec[2] - fw;
+ }
+
Mat4Mul3Vecfl(imat, fp);
-
- vec[0]+= du;
- fp+= 3;
}
- vec[1]+= dv;
}
- vec[2]+= dw;
}
}
void calc_latt_deform(float *co)
{
Lattice *lt;
- float fu, du, u, v, w, tu[4], tv[4], tw[4];
+ float u, v, w, tu[4], tv[4], tw[4];
float *fpw, *fpv, *fpu, vec[3];
int ui, vi, wi, uu, vv, ww;
@@ -305,8 +349,7 @@ void calc_latt_deform(float *co)
/* u v w coords */
if(lt->pntsu>1) {
- calc_lat_fudu(lt->flag, lt->pntsu, &fu, &du);
- u= (vec[0]-fu)/du;
+ u= (vec[0]-lt->fu)/lt->du;
ui= (int)floor(u);
u -= ui;
set_four_ipo(u, tu, lt->typeu);
@@ -317,8 +360,7 @@ void calc_latt_deform(float *co)
}
if(lt->pntsv>1) {
- calc_lat_fudu(lt->flag, lt->pntsv, &fu, &du);
- v= (vec[1]-fu)/du;
+ v= (vec[1]-lt->fv)/lt->dv;
vi= (int)floor(v);
v -= vi;
set_four_ipo(v, tv, lt->typev);
@@ -329,8 +371,7 @@ void calc_latt_deform(float *co)
}
if(lt->pntsw>1) {
- calc_lat_fudu(lt->flag, lt->pntsw, &fu, &du);
- w= (vec[2]-fu)/du;
+ w= (vec[2]-lt->fw)/lt->dw;
wi= (int)floor(w);
w -= wi;
set_four_ipo(w, tw, lt->typew);
@@ -568,7 +609,7 @@ int object_deform_mball(Object *ob)
}
}
-BPoint *latt_bp(Lattice *lt, int u, int v, int w)
+static BPoint *latt_bp(Lattice *lt, int u, int v, int w)
{
return lt->def+ u + v*lt->pntsu + w*lt->pntsu*lt->pntsv;
}
@@ -633,3 +674,61 @@ void outside_lattice(Lattice *lt)
}
}
+
+float (*lattice_getVertexCos(struct Object *ob, int *numVerts_r))[3]
+{
+ Lattice *lt = (G.obedit==ob)?editLatt:ob->data;
+ int i, numVerts = *numVerts_r = lt->pntsu*lt->pntsv*lt->pntsw;
+ float (*vertexCos)[3] = MEM_mallocN(sizeof(*vertexCos)*numVerts,"lt_vcos");
+
+ for (i=0; i<numVerts; i++) {
+ VECCOPY(vertexCos[i], lt->def[i].vec);
+ }
+
+ return vertexCos;
+}
+
+void lattice_applyVertexCos(struct Object *ob, float (*vertexCos)[3])
+{
+ Lattice *lt = ob->data;
+ int i, numVerts = lt->pntsu*lt->pntsv*lt->pntsw;
+
+ for (i=0; i<numVerts; i++) {
+ VECCOPY(lt->def[i].vec, vertexCos[i]);
+ }
+}
+
+void lattice_calc_modifiers(Object *ob)
+{
+ float (*vertexCos)[3] = NULL;
+ ModifierData *md = modifiers_getVirtualModifierList(ob);
+ int numVerts, editmode = G.obedit==ob;
+
+ freedisplist(&ob->disp);
+
+ if (!editmode) {
+ do_latt_key(ob->data);
+ }
+
+ for (; md; md=md->next) {
+ ModifierTypeInfo *mti = modifierType_getInfo(md->type);
+
+ if (!(md->mode&(1<<0))) continue;
+ if (editmode && !(md->mode&eModifierMode_Editmode)) continue;
+ if (mti->isDisabled && mti->isDisabled(md)) continue;
+ if (mti->type!=eModifierTypeType_OnlyDeform) continue;
+
+ if (!vertexCos) vertexCos = lattice_getVertexCos(ob, &numVerts);
+ mti->deformVerts(md, ob, NULL, vertexCos, numVerts);
+ }
+
+ if (vertexCos) {
+ DispList *dl = MEM_callocN(sizeof(*dl), "lt_dl");
+ dl->type = DL_VERTS;
+ dl->parts = 1;
+ dl->nr = numVerts;
+ dl->verts = (float*) vertexCos;
+
+ BLI_addtail(&ob->disp, dl);
+ }
+}
diff --git a/source/blender/blenkernel/intern/modifier.c b/source/blender/blenkernel/intern/modifier.c
index 8c5354b47e8..55f62446bfd 100644
--- a/source/blender/blenkernel/intern/modifier.c
+++ b/source/blender/blenkernel/intern/modifier.c
@@ -1172,7 +1172,7 @@ static void softbodyModifier_deformVerts(ModifierData *md, Object *ob, void *der
{
SoftbodyModifierData *hmd = (SoftbodyModifierData*) md;
- sbObjectStep(ob, (float)G.scene->r.cfra, vertexCos);
+ sbObjectStep(ob, (float)G.scene->r.cfra, vertexCos, numVerts);
}
/***/
diff --git a/source/blender/blenkernel/intern/object.c b/source/blender/blenkernel/intern/object.c
index a43ae4e2978..68f75234c3d 100644
--- a/source/blender/blenkernel/intern/object.c
+++ b/source/blender/blenkernel/intern/object.c
@@ -1762,6 +1762,9 @@ void object_handle_update(Object *ob)
else if(ELEM3(ob->type, OB_CURVE, OB_SURF, OB_FONT)) {
makeDispListCurveTypes(ob, 0);
}
+ else if(ob->type==OB_LATTICE) {
+ lattice_calc_modifiers(ob);
+ }
else if(ob->type==OB_ARMATURE) {
/* this actually only happens for reading old files... */
if(ob->pose==NULL || (ob->pose->flag & POSE_RECALC))
diff --git a/source/blender/blenkernel/intern/softbody.c b/source/blender/blenkernel/intern/softbody.c
index 86ec2cc0705..7833f968c76 100644
--- a/source/blender/blenkernel/intern/softbody.c
+++ b/source/blender/blenkernel/intern/softbody.c
@@ -85,6 +85,21 @@ extern int get_defgroup_num (Object *ob, bDeformGroup *dg);
/* ********** soft body engine ******* */
+
+typedef struct BodyPoint {
+ float origS[3], origE[3], origT[3], pos[3], vec[3], force[3];
+ float weight, goal;
+ float prevpos[3], prevvec[3], prevdx[3], prevdv[3]; /* used for Heun integration */
+ int nofsprings; int *springs;
+ float contactfrict;
+} BodyPoint;
+
+typedef struct BodySpring {
+ int v1, v2;
+ float len, strength;
+} BodySpring;
+
+
#define SOFTGOALSNAP 0.999f
// if bp-> goal is above make it a *forced follow original* and skip all ODE stuff for this bp
// removes *unnecessary* stiffnes from ODE system
@@ -179,12 +194,10 @@ static void add_mesh_quad_diag_springs(Object *ob)
bs->v1= mface->v1;
bs->v2= mface->v3;
bs->strength= 1.0;
- bs->len= VecLenf( (bp+bs->v1)->origS, (bp+bs->v2)->origS);
bs++;
bs->v1= mface->v2;
bs->v2= mface->v4;
bs->strength= 1.0;
- bs->len= VecLenf( (bp+bs->v1)->origS, (bp+bs->v2)->origS);
bs++;
}
@@ -245,10 +258,10 @@ static void build_bps_springlist(Object *ob)
/* creates new softbody if didn't exist yet, makes new points and springs arrays */
-/* called in mesh_to_softbody */
static void renew_softbody(Object *ob, int totpoint, int totspring)
{
SoftBody *sb;
+ int i;
if(ob->soft==NULL) ob->soft= sbNew();
else free_softbody_intern(ob->soft);
@@ -261,6 +274,24 @@ static void renew_softbody(Object *ob, int totpoint, int totspring)
sb->bpoint= MEM_mallocN( totpoint*sizeof(BodyPoint), "bodypoint");
if(totspring)
sb->bspring= MEM_mallocN( totspring*sizeof(BodySpring), "bodyspring");
+
+ /* initialise BodyPoint array */
+ for (i=0; i<totpoint; i++) {
+ BodyPoint *bp = &sb->bpoint[i];
+
+ bp->weight= 1.0;
+ if(ob->softflag & OB_SB_GOAL) {
+ bp->goal= ob->soft->defgoal;
+ }
+ else {
+ bp->goal= 0.0f;
+ /* so this will definily be below SOFTGOALSNAP */
+ }
+
+ bp->nofsprings= 0;
+ bp->springs= NULL;
+ bp->contactfrict = 0.0f;
+ }
}
}
@@ -723,94 +754,9 @@ static void interpolate_exciter(Object *ob, int timescale, int time)
/* ************ convertors ********** */
/* for each object type we need;
- - xxxx_to_softbody(Object *ob) : a full (new) copy
- - xxxx_update_softbody(Object *ob) : update refreshes current positions
- - softbody_to_xxxx(Object *ob) : after simulation, copy vertex locations back
+ - xxxx_to_softbody(Object *ob) : a full (new) copy, creates SB geometry
*/
-/* helper call */
-static int object_has_edges(Object *ob)
-{
- if(ob->type==OB_MESH) {
- Mesh *me= ob->data;
- if(me->medge) return 1;
- }
- else if(ob->type==OB_LATTICE) {
- ;
- }
-
- return 0;
-}
-
-/* helper call */
-static void set_body_point(Object *ob, BodyPoint *bp, float *vec)
-{
- VECCOPY(bp->pos, vec);
- Mat4MulVecfl(ob->obmat, bp->pos); // yep, sofbody is global coords
- VECCOPY(bp->origS, bp->pos);
- VECCOPY(bp->origE, bp->pos);
- VECCOPY(bp->origT, bp->pos);
-
- bp->vec[0]= bp->vec[1]= bp->vec[2]= 0.0;
- bp->weight= 1.0;
- if(ob->softflag & OB_SB_GOAL) {
- bp->goal= ob->soft->defgoal;
- }
- else {
- bp->goal= 0.0f;
- /* so this will definily be below SOFTGOALSNAP */
- }
-
- bp->nofsprings= 0;
- bp->springs= NULL;
- bp->contactfrict = 0.0f;
-}
-
-
-/* copy original (new) situation in softbody, as result of matrices or deform */
-/* is assumed to enter function with ob->soft, but can be without points */
-static void mesh_update_softbody(Object *ob, float (*vertexCos)[3])
-{
- Mesh *me= ob->data;
- BodyPoint *bp;
- int a;
-
- /* possible after a file read... */
- if(ob->soft->bpoint==NULL) sbObjectToSoftbody(ob, NULL);
-
- if(me->totvert) {
- bp= ob->soft->bpoint;
- for(a=0; a<me->totvert; a++, bp++) {
- VECCOPY(bp->origS, bp->origE);
- if (vertexCos) {
- VECCOPY(bp->origE, vertexCos[a]);
- } else {
- VECCOPY(bp->origE, me->mvert[a].co);
- }
- Mat4MulVecfl(ob->obmat, bp->origE);
- VECCOPY(bp->origT, bp->origE);
- }
-
- if(ob->softflag & OB_SB_EDGES) {
-
- /* happens when in UI edges was set */
- if(ob->soft->bspring==NULL)
- if(object_has_edges(ob)) sbObjectToSoftbody(ob, NULL);
-
- /* hrms .. do springs alter their lenght ? (yes, mesh keys would (ton))
- if(medge) {
- bs= ob->soft->bspring;
- bp= ob->soft->bpoint;
- for(a=0; (a<me->totedge && a < ob->soft->totspring ); a++, medge++, bs++) {
- bs->len= VecLenf( (bp+bs->v1)->origE, (bp+bs->v2)->origE);
- }
- }
- */
- }
- }
-}
-
-
static void get_scalar_from_vertexgroup(Object *ob, int vertID, short groupindex, float *target)
/* result 0 on success, else indicates error number
-- kind of *inverse* result defintion,
@@ -837,7 +783,7 @@ static void get_scalar_from_vertexgroup(Object *ob, int vertID, short groupindex
}
/* makes totally fresh start situation */
-static void mesh_to_softbody(Object *ob, float (*vertexCos)[3])
+static void mesh_to_softbody(Object *ob)
{
SoftBody *sb;
Mesh *me= ob->data;
@@ -859,12 +805,6 @@ static void mesh_to_softbody(Object *ob, float (*vertexCos)[3])
goalfac= ABS(sb->maxgoal - sb->mingoal);
for(a=0; a<me->totvert; a++, bp++) {
- if (vertexCos) {
- set_body_point(ob, bp, vertexCos[a]);
- } else {
- set_body_point(ob, bp, me->mvert[a].co);
- }
-
/* get scalar values needed *per vertex* from vertex group functions,
so we can *paint* them nicly ..
they are normalized [0.0..1.0] so may be we need amplitude for scale
@@ -891,12 +831,10 @@ static void mesh_to_softbody(Object *ob, float (*vertexCos)[3])
if (ob->softflag & OB_SB_EDGES) {
if(medge) {
bs= sb->bspring;
- bp= sb->bpoint;
for(a=me->totedge; a>0; a--, medge++, bs++) {
bs->v1= medge->v1;
bs->v2= medge->v2;
bs->strength= 1.0;
- bs->len= VecLenf( (bp+bs->v1)->origS, (bp+bs->v2)->origS);
}
@@ -911,19 +849,6 @@ static void mesh_to_softbody(Object *ob, float (*vertexCos)[3])
}
-/* copies current sofbody position in mesh, so do this within modifier stacks! */
-static void softbody_to_mesh(Object *ob, float (*vertexCos)[3])
-{
- Mesh *me= ob->data;
- BodyPoint *bp= ob->soft->bpoint;
- int a;
-
- for(a=me->totvert; a>0; a--, bp++, vertexCos++) {
- VECCOPY(vertexCos[0], bp->pos);
- Mat4MulVecfl(ob->imat, vertexCos[0]); // softbody is in global coords
- }
-}
-
static void makelatticesprings(Lattice *lt, BodySpring *bs, int dostiff)
{
@@ -1021,23 +946,17 @@ static void makelatticesprings(Lattice *lt, BodySpring *bs, int dostiff)
/* makes totally fresh start situation */
static void lattice_to_softbody(Object *ob)
{
- SoftBody *sb;
- BodySpring *bs;
Lattice *lt= ob->data;
- BodyPoint *bop;
- BPoint *bp;
- int a, totvert, totspring = 0;
+ int totvert, totspring = 0;
totvert= lt->pntsu*lt->pntsv*lt->pntsw;
if (ob->softflag & OB_SB_EDGES){
-
totspring = ((lt->pntsu -1) * lt->pntsv
+ (lt->pntsv -1) * lt->pntsu) * lt->pntsw
+lt->pntsu*lt->pntsv*(lt->pntsw -1);
if (ob->softflag & OB_SB_QUADS){
- totspring += 4*(lt->pntsu -1) * (lt->pntsv -1) * (lt->pntsw-1);
-
+ totspring += 4*(lt->pntsu -1) * (lt->pntsv -1) * (lt->pntsw-1);
}
}
@@ -1045,110 +964,31 @@ static void lattice_to_softbody(Object *ob)
/* renew ends with ob->soft with points and edges, also checks & makes ob->soft */
renew_softbody(ob, totvert, totspring);
- /* we always make body points */
- sb= ob->soft;
-
- for(a= totvert, bp= lt->def, bop= sb->bpoint; a>0; a--, bp++, bop++) {
- set_body_point(ob, bop, bp->vec);
- }
-
/* create some helper edges to enable SB lattice to be usefull at all */
if (ob->softflag & OB_SB_EDGES){
- bs = sb->bspring;
- makelatticesprings(lt,bs,ob->softflag & OB_SB_QUADS);
+ makelatticesprings(lt,ob->soft->bspring,ob->softflag & OB_SB_QUADS);
build_bps_springlist(ob); /* link bps to springs */
-
- /* recalculate lenght since BPoint and Bodypoint obviously can differ */
- bs= ob->soft->bspring;
- bop= ob->soft->bpoint;
- for(a=0; a < totspring ; a++, bs++) {
- bs->len= VecLenf( (bop+bs->v1)->origE, (bop+bs->v2)->origE);
- }
-
- }
-
-}
-
-/* copies current sofbody position */
-static void softbody_to_lattice(Object *ob)
-{
- SoftBody *sb;
- Lattice *lt= ob->data;
- BodyPoint *bop;
- BPoint *bp;
- int a, totvert;
-
- totvert= lt->pntsu*lt->pntsv*lt->pntsw;
- sb= ob->soft;
-
- for(a= totvert, bp= lt->def, bop= sb->bpoint; a>0; a--, bp++, bop++) {
- VECCOPY(bp->vec, bop->pos);
- Mat4MulVecfl(ob->imat, bp->vec); // softbody is in global coords
}
}
-/* copy original (new) situation in softbody, as result of matrices or deform */
-/* is assumed to enter function with ob->soft, but can be without points */
-static void lattice_update_softbody(Object *ob)
-{
- Lattice *lt= ob->data;
- BodyPoint *bop;
- BPoint *bp;
- int a, totvert;
-
- totvert= lt->pntsu*lt->pntsv*lt->pntsw;
-
- /* possible after a file read... */
- if(ob->soft->bpoint==NULL) sbObjectToSoftbody(ob, NULL);
-
- for(a= totvert, bp= lt->def, bop= ob->soft->bpoint; a>0; a--, bp++, bop++) {
- VECCOPY(bop->origS, bop->origE);
- VECCOPY(bop->origE, bp->vec);
- Mat4MulVecfl(ob->obmat, bop->origE);
- VECCOPY(bop->origT, bop->origE);
- }
-}
-
/* copies softbody result back in object */
-/* only used in sbObjectStep() */
-static void softbody_to_object(Object *ob, float (*vertexCos)[3])
+static void softbody_to_object(Object *ob, float (*vertexCos)[3], int numVerts)
{
-
- if(ob->soft==NULL) return;
-
+ BodyPoint *bp= ob->soft->bpoint;
+ int a;
+
/* inverse matrix is not uptodate... */
Mat4Invert(ob->imat, ob->obmat);
- switch(ob->type) {
- case OB_MESH:
- softbody_to_mesh(ob, vertexCos);
- break;
- case OB_LATTICE:
- softbody_to_lattice(ob);
- break;
- }
-}
-
-/* copy original (new) situation in softbody, as result of matrices or deform */
-/* used in sbObjectStep() and sbObjectReset() */
-/* assumes to have ob->soft, but can be entered without points */
-static void object_update_softbody(Object *ob, float (*vertexCos)[3])
-{
-
- switch(ob->type) {
- case OB_MESH:
- mesh_update_softbody(ob, vertexCos);
- break;
- case OB_LATTICE:
- lattice_update_softbody(ob);
- break;
+ for(a=0; a<numVerts; a++, bp++) {
+ VECCOPY(vertexCos[a], bp->pos);
+ Mat4MulVecfl(ob->imat, vertexCos[a]); // softbody is in global coords
}
-
}
/* return 1 if succesfully baked and applied step */
-static int softbody_baked_step(Object *ob, float framenr, float (*vertexCos)[3])
+static int softbody_baked_step(Object *ob, float framenr, float (*vertexCos)[3], int numVerts)
{
SoftBody *sb= ob->soft;
SBVertex *key0, *key1, *key2, *key3;
@@ -1200,7 +1040,7 @@ static int softbody_baked_step(Object *ob, float framenr, float (*vertexCos)[3])
bp->pos[2]= data[0]*key0->vec[2] + data[1]*key1->vec[2] + data[2]*key2->vec[2] + data[3]*key3->vec[2];
}
- softbody_to_object(ob, vertexCos);
+ softbody_to_object(ob, vertexCos, numVerts);
return 1;
}
@@ -1293,79 +1133,68 @@ void sbFree(SoftBody *sb)
/* makes totally fresh start situation */
-void sbObjectToSoftbody(Object *ob, float (*vertexCos)[3])
+void sbObjectToSoftbody(Object *ob)
{
+ ob->softflag |= OB_SB_REDO;
+}
+static void convert_object_to_sb(Object *ob, int numVerts)
+{
switch(ob->type) {
case OB_MESH:
- mesh_to_softbody(ob, vertexCos);
+ mesh_to_softbody(ob);
break;
case OB_LATTICE:
lattice_to_softbody(ob);
break;
+ default:
+ renew_softbody(ob, numVerts, 0);
+ break;
}
- if(ob->soft) ob->soft->ctime= bsystem_time(ob, NULL, (float)G.scene->r.cfra, 0.0);
ob->softflag &= ~OB_SB_REDO;
+
+ /* still need to update to correct vertex locations, happens on next step */
+ ob->softflag |= OB_SB_RESET;
}
-/* reset all motion */
-void sbObjectReset(Object *ob, float (*vertexCos)[3])
+static int object_has_edges(Object *ob)
{
- SoftBody *sb= ob->soft;
- BodyPoint *bp;
- int a;
-
- if(sb==NULL) return;
- if(sb->keys && sb->totkey) return; // only as cpu time saver
-
- sb->ctime= bsystem_time(ob, NULL, (float)G.scene->r.cfra, 0.0);
-
- object_update_softbody(ob, vertexCos);
-
- for(a=sb->totpoint, bp= sb->bpoint; a>0; a--, bp++) {
- // origS is previous timestep
- VECCOPY(bp->origS, bp->origE);
- VECCOPY(bp->pos, bp->origE);
- VECCOPY(bp->origT, bp->origE);
- bp->vec[0]= bp->vec[1]= bp->vec[2]= 0.0f;
-
- // no idea about the Heun stuff! (ton)
- VECCOPY(bp->prevpos, bp->pos);
- VECCOPY(bp->prevvec, bp->vec);
- VECCOPY(bp->prevdx, bp->vec);
- VECCOPY(bp->prevdv, bp->vec);
+ if(ob->type==OB_MESH) {
+ Mesh *me= ob->data;
+ return (me->medge && me->totedge);
+ }
+ else if(ob->type==OB_LATTICE) {
+ return 1;
+ }
+ else {
+ return 0;
}
}
-
/* simulates one step. framenr is in frames */
-/* copies result back to object, displist */
-void sbObjectStep(Object *ob, float framenr, float (*vertexCos)[3])
+void sbObjectStep(Object *ob, float framenr, float (*vertexCos)[3], int numVerts)
{
SoftBody *sb;
Base *base;
+ BodyPoint *bp;
float dtime;
- int timescale,t;
+ int a,timescale,t;
float ctime, forcetime;
float err;
-
- /* this variable is set while transform(). with lattices also having a softbody,
- it calls lattice_modifier() all the time... has no displist yet. Is temporal
- hack which should be resolved with proper depgraph usage + storage of deformed
- vertices in lattice (ton) */
- if(G.moving) return;
/* baking works with global time */
if(!(ob->softflag & OB_SB_BAKEDO) )
- if(softbody_baked_step(ob, framenr, vertexCos) ) return;
-
- /* remake softbody if: */
- if( (ob->softflag & OB_SB_REDO) || // signal after weightpainting
- (ob->soft==NULL) || // just to be nice we allow full init
- (ob->soft->bpoint==NULL) ) // after reading new file, or acceptable as signal to refresh
- sbObjectToSoftbody(ob, vertexCos);
+ if(softbody_baked_step(ob, framenr, vertexCos, numVerts) ) return;
+ /* remake softbody if: */
+ if( (ob->softflag & OB_SB_REDO) || // signal after weightpainting
+ (ob->soft==NULL) || // just to be nice we allow full init
+ (ob->soft->bpoint==NULL) || // after reading new file, or acceptable as signal to refresh
+ (numVerts!=ob->soft->totpoint) || // should never happen, just to be safe
+ ((ob->softflag & OB_SB_EDGES) && !ob->soft->bspring && object_has_edges(ob))) // happens when in UI edges was set
+ convert_object_to_sb(ob, numVerts);
+
sb= ob->soft;
/* still no points? go away */
@@ -1377,23 +1206,53 @@ void sbObjectStep(Object *ob, float framenr, float (*vertexCos)[3])
}
/* checking time: */
+
ctime= bsystem_time(ob, NULL, framenr, 0.0);
- dtime= ctime - sb->ctime;
- // bail out for negative or for large steps
- if(dtime<0.0 || dtime >= 9.9*G.scene->r.framelen) { // G.scene->r.framelen corrects for frame-mapping, so this is actually 10 frames for UI
- sbObjectReset(ob, vertexCos);
- return;
+
+ if (ob->softflag&OB_SB_RESET) {
+ dtime = 0.0;
+ } else {
+ dtime= ctime - sb->ctime;
}
-
+
/* the simulator */
-
- if(dtime > 0.0) { // note: what does this mean now? (ton)
- //answer (BM) :
- //dtime is still in [frames]
- //we made sure dtime is >= 0.0
- //but still need to handle dtime == 0.0 -> just return sb as is, just to be nice
- object_update_softbody(ob, vertexCos);
-
+
+ /* update the vertex locations */
+ if (dtime!=0.0) {
+ for(a=0,bp=sb->bpoint; a<numVerts; a++, bp++) {
+ VECCOPY(bp->origS, bp->origE);
+ VECCOPY(bp->origE, vertexCos[a]);
+ Mat4MulVecfl(ob->obmat, bp->origE);
+ VECCOPY(bp->origT, bp->origE);
+ }
+ }
+
+ // G.scene->r.framelen corrects for frame-mapping, so this is actually 10 frames for UI
+ if((ob->softflag&OB_SB_RESET) || dtime<0.0 || dtime>=9.9*G.scene->r.framelen) {
+ for(a=0,bp=sb->bpoint; a<numVerts; a++, bp++) {
+ VECCOPY(bp->pos, vertexCos[a]);
+ Mat4MulVecfl(ob->obmat, bp->pos); // yep, sofbody is global coords
+ VECCOPY(bp->origS, bp->pos);
+ VECCOPY(bp->origE, bp->pos);
+ VECCOPY(bp->origT, bp->pos);
+ bp->vec[0]= bp->vec[1]= bp->vec[2]= 0.0f;
+
+ // no idea about the Heun stuff! (ton)
+ VECCOPY(bp->prevpos, bp->pos);
+ VECCOPY(bp->prevvec, bp->vec);
+ VECCOPY(bp->prevdx, bp->vec);
+ VECCOPY(bp->prevdv, bp->vec);
+ }
+
+ for(a=0; a<sb->totspring; a++) {
+ BodySpring *bs = &sb->bspring[a];
+
+ bs->len= VecLenf(sb->bpoint[bs->v1].origS, sb->bpoint[bs->v2].origS);
+ }
+
+ ob->softflag &= ~OB_SB_RESET;
+ }
+ else if(dtime>0.0) {
if (TRUE) { // RSOL1 always true now (ton)
/* special case of 2nd order Runge-Kutta type AKA Heun */
float timedone =0.0; // how far did we get without violating error condition
@@ -1486,20 +1345,11 @@ void sbObjectStep(Object *ob, float framenr, float (*vertexCos)[3])
}
}
}
-
- /* and apply to vertices */
- softbody_to_object(ob, vertexCos);
-
- sb->ctime= ctime;
- } // if(ABS(dtime) > 0.0)
- else {
- // rule : you have asked for the current state of the softobject
- // since dtime= ctime - ob->soft->ctime== 0.0;
- // and we were not notifified about any other time changes
- // so here it is !
- softbody_to_object(ob, vertexCos);
}
+ softbody_to_object(ob, vertexCos, numVerts);
+ sb->ctime= ctime;
+
/* reset deflector cache */
for(base= G.scene->base.first; base; base= base->next) {
if(base->object->sumohandle) {