diff options
-rw-r--r-- | source/blender/blenkernel/BKE_customdata.h | 7 | ||||
-rw-r--r-- | source/blender/blenkernel/intern/DerivedMesh.c | 12 | ||||
-rw-r--r-- | source/blender/blenkernel/intern/cdderivedmesh.c | 36 | ||||
-rw-r--r-- | source/blender/blenkernel/intern/customdata.c | 93 | ||||
-rw-r--r-- | source/blender/blenlib/BLI_editVert.h | 6 | ||||
-rw-r--r-- | source/blender/include/BIF_editmesh.h | 10 | ||||
-rw-r--r-- | source/blender/include/editmesh.h | 2 | ||||
-rw-r--r-- | source/blender/src/buttons_editing.c | 14 | ||||
-rw-r--r-- | source/blender/src/drawview.c | 20 | ||||
-rw-r--r-- | source/blender/src/editdeform.c | 83 | ||||
-rw-r--r-- | source/blender/src/editmesh.c | 121 | ||||
-rw-r--r-- | source/blender/src/editmesh_add.c | 18 | ||||
-rw-r--r-- | source/blender/src/editmesh_lib.c | 224 | ||||
-rw-r--r-- | source/blender/src/editmesh_mods.c | 26 | ||||
-rw-r--r-- | source/blender/src/editmesh_tools.c | 180 | ||||
-rw-r--r-- | source/blender/src/editobject.c | 16 | ||||
-rw-r--r-- | source/blender/src/retopo.c | 2 | ||||
-rw-r--r-- | source/blender/src/verse_mesh.c | 6 |
18 files changed, 424 insertions, 452 deletions
diff --git a/source/blender/blenkernel/BKE_customdata.h b/source/blender/blenkernel/BKE_customdata.h index 9733c26ade2..b36ab67f5e1 100644 --- a/source/blender/blenkernel/BKE_customdata.h +++ b/source/blender/blenkernel/BKE_customdata.h @@ -72,12 +72,16 @@ void CustomData_free(struct CustomData *data); * (flag & LAYERFLAG_NOFREE) is true * grows the number of layers in data if data->maxLayers has been reached * returns 1 on success, 0 on failure + * + * in editmode, use EM_add_data_layer instead of this function */ int CustomData_add_layer(struct CustomData *data, int type, int flag, void *layer); /* frees the first data layer with the give type. * returns 1 on succes, 0 if no layer with the given type is found + * + * in editmode, use EM_free_data_layer instead of this function */ int CustomData_free_layer(struct CustomData *data, int type); @@ -98,7 +102,8 @@ int CustomData_has_layer(const struct CustomData *data, int type); int CustomData_copy_data(const struct CustomData *source, struct CustomData *dest, int source_index, int dest_index, int count); -int CustomData_em_copy_data(struct CustomData *data, void *src_block, +int CustomData_em_copy_data(const struct CustomData *source, + struct CustomData *dest, void *src_block, void **dest_block); /* frees data in a CustomData object diff --git a/source/blender/blenkernel/intern/DerivedMesh.c b/source/blender/blenkernel/intern/DerivedMesh.c index 04cb371226b..f1285032802 100644 --- a/source/blender/blenkernel/intern/DerivedMesh.c +++ b/source/blender/blenkernel/intern/DerivedMesh.c @@ -1459,7 +1459,6 @@ static DerivedMesh *getEditMeshDerivedMesh(EditMesh *em, Object *ob, float (*vertexCos)[3]) { EditMeshDerivedMesh *emdm = MEM_callocN(sizeof(*emdm), "emdm"); - Mesh *me = ob->data; DM_init(&emdm->dm, BLI_countlist(&em->verts), BLI_countlist(&em->edges), BLI_countlist(&em->faces)); @@ -1492,16 +1491,15 @@ static DerivedMesh *getEditMeshDerivedMesh(EditMesh *em, Object *ob, emdm->em = em; emdm->vertexCos = vertexCos; - if(me->dvert) { + if(CustomData_has_layer(&em->vdata, LAYERTYPE_MDEFORMVERT)) { EditVert *eve; int i; + DM_add_vert_layer(&emdm->dm, LAYERTYPE_MDEFORMVERT, 0, NULL); - for(eve = em->verts.first, i = 0; eve; eve = eve->next, ++i) { - if(eve->keyindex != -1) - DM_set_vert_data(&emdm->dm, i, LAYERTYPE_MDEFORMVERT, - &me->dvert[eve->keyindex]); - } + for(eve = em->verts.first, i = 0; eve; eve = eve->next, ++i) + DM_set_vert_data(&emdm->dm, i, LAYERTYPE_MDEFORMVERT, + CustomData_em_get(&em->vdata, eve->data, LAYERTYPE_MDEFORMVERT)); } if(vertexCos) { diff --git a/source/blender/blenkernel/intern/cdderivedmesh.c b/source/blender/blenkernel/intern/cdderivedmesh.c index 21ad73aa240..9dc89760195 100644 --- a/source/blender/blenkernel/intern/cdderivedmesh.c +++ b/source/blender/blenkernel/intern/cdderivedmesh.c @@ -747,24 +747,25 @@ DerivedMesh *CDDM_from_editmesh(EditMesh *em, Mesh *me) EditVert *eve; EditEdge *eed; EditFace *efa; - int i; MVert *mvert = CDDM_get_verts(dm); MEdge *medge = CDDM_get_edges(dm); MFace *mface = CDDM_get_faces(dm); + int i, hassticky = 0, hasdvert = 0, hastface = 0, hasmcol = 0; int *index; - TFace *tf; /* set eve->hash to vert index */ for(i = 0, eve = em->verts.first; eve; eve = eve->next, ++i) eve->hash = i; - if(me->msticky) - CustomData_add_layer(&dm->vertData, LAYERTYPE_MDEFORMVERT, 0, NULL); - if(me->dvert) - CustomData_add_layer(&dm->vertData, LAYERTYPE_MDEFORMVERT, 0, NULL); - - if(me->tface) - CustomData_add_layer(&dm->faceData, LAYERTYPE_TFACE, 0, NULL); + /* check for availability of layers */ + if(CustomData_has_layer(&em->vdata, LAYERTYPE_MSTICKY)) + hassticky= CustomData_add_layer(&dm->vertData, LAYERTYPE_MSTICKY, 0, NULL); + if(CustomData_has_layer(&em->vdata, LAYERTYPE_MDEFORMVERT)) + hasdvert= CustomData_add_layer(&dm->vertData, LAYERTYPE_MDEFORMVERT, 0, NULL); + if(CustomData_has_layer(&em->vdata, LAYERTYPE_TFACE)) + hastface= CustomData_add_layer(&dm->vertData, LAYERTYPE_TFACE, 0, NULL); + if(CustomData_has_layer(&em->vdata, LAYERTYPE_MCOL)) + hasmcol= CustomData_add_layer(&dm->vertData, LAYERTYPE_MCOL, 0, NULL); /* Need to be able to mark loose edges */ for(eed = em->edges.first; eed; eed = eed->next) { @@ -793,12 +794,12 @@ DerivedMesh *CDDM_from_editmesh(EditMesh *em, Mesh *me) *index = i; - if(me->msticky && eve->keyindex != -1) + if(hassticky) DM_set_vert_data(dm, i, LAYERTYPE_MSTICKY, - &me->msticky[eve->keyindex]); - if(me->dvert && eve->keyindex != -1) + CustomData_em_get(&em->vdata, eve->data, LAYERTYPE_MSTICKY)); + if(hasdvert) DM_set_vert_data(dm, i, LAYERTYPE_MDEFORMVERT, - &me->dvert[eve->keyindex]); + CustomData_em_get(&em->vdata, eve->data, LAYERTYPE_MDEFORMVERT)); } index = dm->getEdgeDataArray(dm, LAYERTYPE_ORIGINDEX); @@ -833,9 +834,12 @@ DerivedMesh *CDDM_from_editmesh(EditMesh *em, Mesh *me) *index = i; - tf = CustomData_em_get(&em->fdata, efa->data, LAYERTYPE_TFACE); - if(tf) - DM_set_face_data(dm, i, LAYERTYPE_TFACE, tf); + if(hastface) + DM_set_face_data(dm, i, LAYERTYPE_TFACE, + CustomData_em_get(&em->fdata, efa->data, LAYERTYPE_TFACE)); + if(hasmcol) + DM_set_face_data(dm, i, LAYERTYPE_MCOL, + CustomData_em_get(&em->fdata, efa->data, LAYERTYPE_MCOL)); } return dm; diff --git a/source/blender/blenkernel/intern/customdata.c b/source/blender/blenkernel/intern/customdata.c index 9173a9e0758..c626c79bdcc 100644 --- a/source/blender/blenkernel/intern/customdata.c +++ b/source/blender/blenkernel/intern/customdata.c @@ -161,12 +161,17 @@ static void layerInterp_mdeformvert(void **sources, float *weights, /* now we know how many unique deform weights there are, so realloc */ if(dvert->dw) MEM_freeN(dvert->dw); - dvert->dw = MEM_callocN(sizeof(*dvert->dw) * totweight, - "layerInterp_mdeformvert dvert->dw"); - dvert->totweight = totweight; - for(i = 0, node = dest_dw; node; node = node->next, ++i) - dvert->dw[i] = *((MDeformWeight *)node->link); + if(totweight) { + dvert->dw = MEM_callocN(sizeof(*dvert->dw) * totweight, + "layerInterp_mdeformvert dvert->dw"); + dvert->totweight = totweight; + + for(i = 0, node = dest_dw; node; node = node->next, ++i) + dvert->dw[i] = *((MDeformWeight *)node->link); + } + else + memset(dvert, 0, sizeof(*dvert)); BLI_linklist_free(dest_dw, linklist_free_simple); } @@ -694,12 +699,34 @@ void CustomData_set_num_elems(CustomData *data, int numElems) /* EditMesh functions */ +void CustomData_em_free_block(CustomData *data, void **block) +{ + const LayerTypeInfo *typeInfo; + int i; + + if(!*block) return; + + for(i = 0; i < data->numLayers; ++i) { + if(!(data->layers[i].flag & LAYERFLAG_NOFREE)) { + typeInfo = layerType_getInfo(data->layers[i].type); + + if(typeInfo->free) { + int offset = data->layers[i].offset; + typeInfo->free((char*)*block + offset, 1, typeInfo->size); + } + } + } + + MEM_freeN(*block); + *block = NULL; +} + static void CustomData_em_alloc_block(CustomData *data, void **block) { /* TODO: optimize free/alloc */ if (*block) - MEM_freeN(*block); + CustomData_em_free_block(data, block); if (data->totSize > 0) *block = MEM_callocN(data->totSize, "CustomData EM block"); @@ -707,34 +734,48 @@ static void CustomData_em_alloc_block(CustomData *data, void **block) *block = NULL; } -void CustomData_em_free_block(CustomData *data, void **block) -{ - if (*block) { - MEM_freeN(*block); - *block = NULL; - } -} - -int CustomData_em_copy_data(CustomData *data, void *src_block, void **dest_block) +int CustomData_em_copy_data(const CustomData *source, CustomData *dest, + void *src_block, void **dest_block) { const LayerTypeInfo *type_info; - int i; + int dest_i, src_i; if (!*dest_block) - CustomData_em_alloc_block(data, dest_block); + CustomData_em_alloc_block(dest, dest_block); /* copies a layer at a time */ - for(i = 0; i < data->numLayers; ++i) { - int offset = data->layers[i].offset; - char *src_data = (char*)src_block + offset; - char *dest_data = (char*)*dest_block + offset; + dest_i = 0; + for(src_i = 0; src_i < source->numLayers; ++src_i) { + if(source->layers[src_i].flag & LAYERFLAG_NOCOPY) continue; - type_info = layerType_getInfo(data->layers[i].type); + /* find the first dest layer with type >= the source type + * (this should work because layers are ordered by type) + */ + while(dest_i < dest->numLayers + && dest->layers[dest_i].type < source->layers[src_i].type) + ++dest_i; - if(type_info->copy) - type_info->copy(src_data, dest_data, 1, type_info->size); - else - memcpy(dest_data, src_data, type_info->size); + /* if there are no more dest layers, we're done */ + if(dest_i >= dest->numLayers) return 1; + + /* if we found a matching layer, copy the data */ + if(dest->layers[dest_i].type == source->layers[src_i].type) { + char *src_data = (char*)src_block + source->layers[src_i].offset; + char *dest_data = (char*)*dest_block + dest->layers[dest_i].offset; + + type_info = layerType_getInfo(source->layers[src_i].type); + + if(type_info->copy) + type_info->copy(src_data, dest_data, 1, type_info->size); + else + memcpy(dest_data, src_data, type_info->size); + + /* if there are multiple source & dest layers of the same type, + * we don't want to copy all source layers to the same dest, so + * increment dest_i + */ + ++dest_i; + } } return 1; diff --git a/source/blender/blenlib/BLI_editVert.h b/source/blender/blenlib/BLI_editVert.h index 25559043bc8..d39cd748fb1 100644 --- a/source/blender/blenlib/BLI_editVert.h +++ b/source/blender/blenlib/BLI_editVert.h @@ -68,13 +68,13 @@ typedef struct EditVert f1 and f2 can be used for temp data, clear them first*/ unsigned char f, h, f1, f2; short fast; /* only 0 or 1, for editmesh_fastmalloc, do not store temp data here! */ - short totweight; /* __NLA total number of vertex weights for this vertex */ int hash; - struct MDeformWeight *dw; /* __NLA a pointer to an array of defirm weights */ int keyindex; /* original index #, for restoring key information */ /*#ifdef WITH_VERSE*/ void *vvert; /*#endif*/ + + void *data; /* custom vertex data */ } EditVert; struct EditEdge; @@ -168,7 +168,7 @@ typedef struct EditMesh char retopo_mode; /* 0=OFF, 1=ON, 2=PAINT */ struct RetopoPaintData *retopo_paint_data; - CustomData fdata; + CustomData vdata, fdata; #ifdef WITH_VERSE void *vnode; diff --git a/source/blender/include/BIF_editmesh.h b/source/blender/include/BIF_editmesh.h index ef568b9d84f..d08c6a39d7d 100644 --- a/source/blender/include/BIF_editmesh.h +++ b/source/blender/include/BIF_editmesh.h @@ -43,6 +43,7 @@ struct Mesh; struct bDeformGroup; struct View3D; struct EditSelection; +struct CustomData; // edge and face flag both #define EM_FGON 2 @@ -104,10 +105,15 @@ extern int faceselectedAND(struct EditFace *efa, int flag); extern void recalc_editnormals(void); extern void flip_editnormals(void); +extern void EM_data_interp_from_verts(struct EditVert *v1, + struct EditVert *v2, struct EditVert *eve, float fac); extern struct EditFace *EM_face_from_faces(struct EditFace *efa1, struct EditFace *efa2, int i1, int i2, int i3, int i4); -extern void EM_interp_from_faces(struct EditFace *efa1, struct EditFace *efa2, - struct EditFace *efan, int i1, int i2, int i3, int i4); +extern void EM_data_interp_from_faces(struct EditFace *efa1, + struct EditFace *efa2, struct EditFace *efan, int i1, int i2, int i3, int i4); + +void EM_add_data_layer(struct CustomData *data, int type); +void EM_free_data_layer(struct CustomData *data, int type); /* ******************* editmesh_mods.c */ diff --git a/source/blender/include/editmesh.h b/source/blender/include/editmesh.h index fc498fd662f..2deab0a6f22 100644 --- a/source/blender/include/editmesh.h +++ b/source/blender/include/editmesh.h @@ -53,7 +53,7 @@ extern void free_facelist(ListBase *lb); extern void remedge(EditEdge *eed); -extern struct EditVert *addvertlist(float *vec); +extern struct EditVert *addvertlist(float *vec, struct EditVert *example); extern struct EditEdge *addedgelist(struct EditVert *v1, struct EditVert *v2, struct EditEdge *example); extern struct EditFace *addfacelist(struct EditVert *v1, struct EditVert *v2, struct EditVert *v3, struct EditVert *v4, struct EditFace *example, struct EditFace *exampleEdges); extern struct EditEdge *findedgelist(struct EditVert *v1, struct EditVert *v2); diff --git a/source/blender/src/buttons_editing.c b/source/blender/src/buttons_editing.c index 07c02e279d2..0d9a32d26bd 100644 --- a/source/blender/src/buttons_editing.c +++ b/source/blender/src/buttons_editing.c @@ -3532,9 +3532,14 @@ void do_meshbuts(unsigned short event) break; case B_MAKEVERTCOL: - make_vertexcol(); + if(G.obedit) + EM_add_data_layer(&G.editMesh->fdata, LAYERTYPE_MCOL); + else + make_vertexcol(); break; case B_DELVERTCOL: + if(G.obedit) + EM_free_data_layer(&G.editMesh->fdata, LAYERTYPE_MCOL); if(me->mcol) MEM_freeN(me->mcol); me->mcol= NULL; G.f &= ~G_VERTEXPAINT; @@ -3544,11 +3549,16 @@ void do_meshbuts(unsigned short event) break; case B_MAKE_TFACES: - make_tfaces(me); + if(G.obedit) + EM_add_data_layer(&G.editMesh->fdata, LAYERTYPE_TFACE); + else + make_tfaces(me); allqueue(REDRAWBUTSEDIT, 0); break; case B_DEL_TFACES: + if(G.obedit) + EM_free_data_layer(&G.editMesh->fdata, LAYERTYPE_TFACE); if(me->tface) MEM_freeN(me->tface); me->tface= 0; G.f &= ~G_FACESELECT; diff --git a/source/blender/src/drawview.c b/source/blender/src/drawview.c index 1c174e8a0a7..de334b1517f 100644 --- a/source/blender/src/drawview.c +++ b/source/blender/src/drawview.c @@ -81,6 +81,7 @@ #include "BKE_anim.h" #include "BKE_constraint.h" #include "BKE_curve.h" +#include "BKE_customdata.h" #include "BKE_displist.h" #include "BKE_depsgraph.h" #include "BKE_DerivedMesh.h" @@ -1536,6 +1537,7 @@ static void v3d_editvertex_buts(uiBlock *block, Object *ob, float lim) EditMesh *em = G.editMesh; EditVert *eve, *evedef=NULL; EditEdge *eed; + MDeformVert *dvert; float median[5]; int tot, totw, totweight, totedge; char defstr[320]; @@ -1562,28 +1564,30 @@ static void v3d_editvertex_buts(uiBlock *block, Object *ob, float lim) } eed= eed->next; } + /* check for defgroups */ - if(tot==1 && evedef->totweight) { + dvert= CustomData_em_get(&em->vdata, evedef->data, LAYERTYPE_MDEFORMVERT); + if(tot==1 && dvert->totweight) { bDeformGroup *dg; int i, max=1, init=1; char str[32]; - for (i=0; i<evedef->totweight; i++){ - dg = BLI_findlink (&ob->defbase, evedef->dw[i].def_nr); + for (i=0; i<dvert->totweight; i++){ + dg = BLI_findlink (&ob->defbase, dvert->dw[i].def_nr); if(dg) { - max+= sprintf(str, "%s %%x%d|", dg->name, evedef->dw[i].def_nr); + max+= sprintf(str, "%s %%x%d|", dg->name, dvert->dw[i].def_nr); if(max<320) strcat(defstr, str); } else printf("oh no!\n"); - if(curdef==evedef->dw[i].def_nr) { + if(curdef==dvert->dw[i].def_nr) { init= 0; - defweightp= &evedef->dw[i].weight; + defweightp= &dvert->dw[i].weight; } } if(init) { // needs new initialized - curdef= evedef->dw[0].def_nr; - defweightp= &evedef->dw[0].weight; + curdef= dvert->dw[0].def_nr; + defweightp= &dvert->dw[0].weight; } } } diff --git a/source/blender/src/editdeform.c b/source/blender/src/editdeform.c index 62128be9a73..cea223f98df 100644 --- a/source/blender/src/editdeform.c +++ b/source/blender/src/editdeform.c @@ -45,6 +45,7 @@ #include "BLI_blenlib.h" #include "BLI_editVert.h" +#include "BKE_customdata.h" #include "BKE_DerivedMesh.h" #include "BKE_depsgraph.h" #include "BKE_deform.h" @@ -70,6 +71,7 @@ void sel_verts_defgroup (int select) EditVert *eve; Object *ob; int i; + MDeformVert *dvert; ob= G.obedit; @@ -79,9 +81,11 @@ void sel_verts_defgroup (int select) switch (ob->type){ case OB_MESH: for (eve=G.editMesh->verts.first; eve; eve=eve->next){ - if (eve->totweight){ - for (i=0; i<eve->totweight; i++){ - if (eve->dw[i].def_nr == (ob->actdef-1)){ + dvert= CustomData_em_get(&G.editMesh->vdata, eve->data, LAYERTYPE_MDEFORMVERT); + + if (dvert && dvert->totweight){ + for (i=0; i<dvert->totweight; i++){ + if (dvert->dw[i].def_nr == (ob->actdef-1)){ if (select) eve->f |= SELECT; else eve->f &= ~SELECT; @@ -98,9 +102,10 @@ void sel_verts_defgroup (int select) case OB_LATTICE: if(editLatt->dvert) { BPoint *bp; - MDeformVert *dvert= editLatt->dvert; int a, tot; + dvert= editLatt->dvert; + tot= editLatt->pntsu*editLatt->pntsv*editLatt->pntsw; for(a=0, bp= editLatt->def; a<tot; a++, bp++, dvert++) { for (i=0; i<dvert->totweight; i++){ @@ -215,12 +220,15 @@ void del_defgroup (Object *ob) if(ob->type==OB_MESH) { EditMesh *em = G.editMesh; EditVert *eve; + MDeformVert *dvert; for (eve=em->verts.first; eve; eve=eve->next){ - for (i=0; i<eve->totweight; i++){ - if (eve->dw[i].def_nr > (ob->actdef-1)) - eve->dw[i].def_nr--; - } + dvert= CustomData_em_get(&G.editMesh->vdata, eve->data, LAYERTYPE_MDEFORMVERT); + + if (dvert) + for (i=0; i<dvert->totweight; i++) + if (dvert->dw[i].def_nr > (ob->actdef-1)) + dvert->dw[i].def_nr--; } } else { @@ -482,6 +490,7 @@ void assign_verts_defgroup (void) EditVert *eve; bDeformGroup *dg, *eg; MDeformWeight *newdw; + MDeformVert *dvert; int i, done; ob= G.obedit; @@ -497,35 +506,40 @@ void assign_verts_defgroup (void) switch (ob->type){ case OB_MESH: + if (!CustomData_has_layer(&G.editMesh->vdata, LAYERTYPE_MDEFORMVERT)) + EM_add_data_layer(&G.editMesh->vdata, LAYERTYPE_MDEFORMVERT); + /* Go through the list of editverts and assign them */ for (eve=G.editMesh->verts.first; eve; eve=eve->next){ - if (eve->f & 1){ + dvert= CustomData_em_get(&G.editMesh->vdata, eve->data, LAYERTYPE_MDEFORMVERT); + + if (dvert && (eve->f & 1)){ done=0; /* See if this vert already has a reference to this group */ /* If so: Change its weight */ done=0; - for (i=0; i<eve->totweight; i++){ - eg = BLI_findlink (&ob->defbase, eve->dw[i].def_nr); + for (i=0; i<dvert->totweight; i++){ + eg = BLI_findlink (&ob->defbase, dvert->dw[i].def_nr); /* Find the actual group */ if (eg==dg){ - eve->dw[i].weight=editbutvweight; + dvert->dw[i].weight=editbutvweight; done=1; break; } } /* If not: Add the group and set its weight */ if (!done){ - newdw = MEM_callocN (sizeof(MDeformWeight)*(eve->totweight+1), "deformWeight"); - if (eve->dw){ - memcpy (newdw, eve->dw, sizeof(MDeformWeight)*eve->totweight); - MEM_freeN (eve->dw); + newdw = MEM_callocN (sizeof(MDeformWeight)*(dvert->totweight+1), "deformWeight"); + if (dvert->dw){ + memcpy (newdw, dvert->dw, sizeof(MDeformWeight)*dvert->totweight); + MEM_freeN (dvert->dw); } - eve->dw=newdw; + dvert->dw=newdw; - eve->dw[eve->totweight].weight= editbutvweight; - eve->dw[eve->totweight].def_nr= ob->actdef-1; + dvert->dw[dvert->totweight].weight= editbutvweight; + dvert->dw[dvert->totweight].def_nr= ob->actdef-1; - eve->totweight++; + dvert->totweight++; } } @@ -585,6 +599,7 @@ void remove_verts_defgroup (int allverts) { Object *ob; EditVert *eve; + MDeformVert *dvert; MDeformWeight *newdw; bDeformGroup *dg, *eg; int i; @@ -603,25 +618,27 @@ void remove_verts_defgroup (int allverts) switch (ob->type){ case OB_MESH: for (eve=G.editMesh->verts.first; eve; eve=eve->next){ - if (eve->dw && ((eve->f & 1) || allverts)){ - for (i=0; i<eve->totweight; i++){ + dvert= CustomData_em_get(&G.editMesh->vdata, eve->data, LAYERTYPE_MDEFORMVERT); + + if (dvert && dvert->dw && ((eve->f & 1) || allverts)){ + for (i=0; i<dvert->totweight; i++){ /* Find group */ - eg = BLI_findlink (&ob->defbase, eve->dw[i].def_nr); + eg = BLI_findlink (&ob->defbase, dvert->dw[i].def_nr); if (eg == dg){ - eve->totweight--; - if (eve->totweight){ - newdw = MEM_mallocN (sizeof(MDeformWeight)*(eve->totweight), "deformWeight"); + dvert->totweight--; + if (dvert->totweight){ + newdw = MEM_mallocN (sizeof(MDeformWeight)*(dvert->totweight), "deformWeight"); - if (eve->dw){ - memcpy (newdw, eve->dw, sizeof(MDeformWeight)*i); - memcpy (newdw+i, eve->dw+i+1, sizeof(MDeformWeight)*(eve->totweight-i)); - MEM_freeN (eve->dw); + if (dvert->dw){ + memcpy (newdw, dvert->dw, sizeof(MDeformWeight)*i); + memcpy (newdw+i, dvert->dw+i+1, sizeof(MDeformWeight)*(dvert->totweight-i)); + MEM_freeN (dvert->dw); } - eve->dw=newdw; + dvert->dw=newdw; } else{ - MEM_freeN (eve->dw); - eve->dw=NULL; + MEM_freeN (dvert->dw); + dvert->dw=NULL; } } } diff --git a/source/blender/src/editmesh.c b/source/blender/src/editmesh.c index a891fe1adab..34fb0f1d17a 100644 --- a/source/blender/src/editmesh.c +++ b/source/blender/src/editmesh.c @@ -134,7 +134,7 @@ static void *(*callocvert)(size_t, size_t) = calloc; static void *(*callocedge)(size_t, size_t) = calloc; static void *(*callocface)(size_t, size_t) = calloc; -EditVert *addvertlist(float *vec) +EditVert *addvertlist(float *vec, EditVert *example) { EditMesh *em = G.editMesh; EditVert *eve; @@ -156,6 +156,11 @@ EditVert *addvertlist(float *vec) createVerseVert(eve); #endif + if(example) + CustomData_em_copy_data(&em->vdata, &em->vdata, example->data, &eve->data); + else + CustomData_em_set_default(&em->vdata, &eve->data); + return eve; } @@ -172,11 +177,10 @@ void free_editvert (EditVert *eve) } #endif - if(eve->dw) MEM_freeN(eve->dw); EM_remove_selection(eve, EDITVERT); - if(eve->fast==0){ + CustomData_em_free_block(&G.editMesh->vdata, &eve->data); + if(eve->fast==0) free(eve); - } } @@ -411,7 +415,7 @@ EditFace *addfacelist(EditVert *v1, EditVert *v2, EditVert *v3, EditVert *v4, Ed if(example) { efa->mat_nr= example->mat_nr; efa->flag= example->flag; - CustomData_em_copy_data(&em->fdata, example->data, &efa->data); + CustomData_em_copy_data(&em->fdata, &em->fdata, example->data, &efa->data); } else { if (G.obedit && G.obedit->actcol) @@ -554,6 +558,7 @@ void free_editMesh(EditMesh *em) if(em->faces.first) free_facelist(&em->faces); if(em->selected.first) BLI_freelistN(&(em->selected)); + CustomData_free(&em->vdata); CustomData_free(&em->fdata); if(em->derivedFinal) { @@ -784,7 +789,7 @@ void make_editMesh() EditFace *efa; EditEdge *eed; EditSelection *ese; - CustomData mfdata; + CustomData mvdata, mfdata; int tot, a, eekadoodle= 0; #ifdef WITH_VERSE @@ -817,11 +822,16 @@ void make_editMesh() } /* make editverts */ + CustomData_init(&mvdata, 0, me->totvert, SUB_ELEMS_VERT); + if(me->dvert) + CustomData_add_layer(&mvdata, LAYERTYPE_MDEFORMVERT, LAYERFLAG_NOFREE, me->dvert); + CustomData_from_template(&mvdata, &em->vdata, 0, 0); + mvert= me->mvert; evlist= (EditVert **)MEM_mallocN(tot*sizeof(void *),"evlist"); for(a=0; a<tot; a++, mvert++) { - eve= addvertlist(mvert->co); + eve= addvertlist(mvert->co, NULL); evlist[a]= eve; // face select sets selection in next loop @@ -839,16 +849,11 @@ void make_editMesh() */ eve->keyindex = a; - if (me->dvert){ - eve->totweight = me->dvert[a].totweight; - if (me->dvert[a].dw){ - eve->dw = MEM_callocN (sizeof(MDeformWeight) * me->dvert[a].totweight, "deformWeight"); - memcpy (eve->dw, me->dvert[a].dw, sizeof(MDeformWeight) * me->dvert[a].totweight); - } - } - + CustomData_to_em_block(&mvdata, &em->vdata, a, &eve->data); } + CustomData_free(&mvdata); + if(actkey && actkey->totelem!=me->totvert); else { MEdge *medge= me->medge; @@ -972,8 +977,7 @@ void load_editMesh(void) EditSelection *ese; float *fp, *newkey, *oldkey, nor[3]; int i, a, ototvert, totedge=0; - MDeformVert *dvert; - CustomData mfdata; + CustomData mvdata, mfdata; #ifdef WITH_VERSE if(em->vnode) { @@ -1010,13 +1014,19 @@ void load_editMesh(void) if(G.totface==0) mface= NULL; else mface= MEM_callocN(G.totface*sizeof(MFace), "loadeditMesh face"); - /* are we adding dverts? */ - if (G.totvert==0) dvert= NULL; - else if(G.obedit->defbase.first==NULL) dvert= NULL; - else dvert = MEM_callocN(G.totvert*sizeof(MDeformVert), "loadeditMesh3"); - - if (me->dvert) free_dverts(me->dvert, me->totvert); - me->dvert=dvert; + /* free vertex and face data */ + if (me->dvert) { + free_dverts(me->dvert, me->totvert); + me->dvert= NULL; + } + if(me->tface) { + MEM_freeN(me->tface); + me->tface = NULL; + } + if(me->mcol) { + MEM_freeN(me->mcol); + me->mcol = NULL; + } /* lets save the old verts just in case we are actually working on * a key ... we now do processing of the keys at the end */ @@ -1036,15 +1046,8 @@ void load_editMesh(void) me->mface= mface; me->totface= G.totface; - /* face data */ - if(me->tface) { - MEM_freeN(me->tface); - me->tface = NULL; - } - if(me->mcol) { - MEM_freeN(me->mcol); - me->mcol = NULL; - } + /* vertex and face data */ + CustomData_from_template(&em->vdata, &mvdata, LAYERFLAG_NOFREE, me->totvert); CustomData_from_template(&em->fdata, &mfdata, LAYERFLAG_NOFREE, me->totface); /* the vertices, use ->tmp.l as counter */ @@ -1060,16 +1063,9 @@ void load_editMesh(void) VecMulf(nor, 32767.0); VECCOPY(mvert->no, nor); - /* note: it used to remove me->dvert when it was not in use, cancelled that... annoying when you have a fresh vgroup */ - if (dvert){ - dvert->totweight=eve->totweight; - if (eve->dw){ - dvert->dw = MEM_callocN (sizeof(MDeformWeight)*eve->totweight, - "deformWeight"); - memcpy (dvert->dw, eve->dw, - sizeof(MDeformWeight)*eve->totweight); - } - } + /* note: it used to remove me->dvert when it was not in use, cancelled + that... annoying when you have a fresh vgroup */ + CustomData_from_em_block(&em->vdata, &mvdata, eve->data, a); eve->tmp.l = a++; /* counter */ @@ -1086,9 +1082,12 @@ void load_editMesh(void) #endif eve= eve->next; mvert++; - if(dvert) dvert++; } + /* from CustomData to dvert in Mesh */ + me->dvert = CustomData_get(&mvdata, 0, LAYERTYPE_MDEFORMVERT); + CustomData_free(&mvdata); + /* the edges */ a= 0; eed= em->edges.first; @@ -1180,14 +1179,14 @@ void load_editMesh(void) /* sync hide and select flags with faceselect mode */ if(G.f & G_FACESELECT) { - if(me->tface && (me->totface > 0)) { + if(CustomData_has_layer(&mfdata, LAYERTYPE_TFACE) && (me->totface > 0)) { efa= em->faces.first; - for(a=0, efa=em->faces.first; efa; a++, efa++) { + for(a=0, efa=em->faces.first; efa; a++, efa=efa->next) { tf = CustomData_get(&mfdata, a, LAYERTYPE_TFACE); if(efa->h) tf->flag |= TF_HIDE; else tf->flag &= ~TF_HIDE; - if(efa->f & SELECT) tf->flag |= TF_SELECT; + if(efa->f & SELECT) tf->flag |= TF_SELECT; else tf->flag &= ~TF_SELECT; } } @@ -1196,7 +1195,6 @@ void load_editMesh(void) /* from CustomData to tface and mcol in Mesh */ me->tface = CustomData_get(&mfdata, 0, LAYERTYPE_TFACE); me->mcol = CustomData_get(&mfdata, 0, LAYERTYPE_MCOL); - CustomData_free(&mfdata); /* patch hook indices */ @@ -1566,6 +1564,7 @@ void separate_mesh(void) emcopy.alledges= NULL; emcopy.allfaces= NULL; emcopy.derivedFinal= emcopy.derivedCage= NULL; + memset(&emcopy.vdata, 0, sizeof(emcopy.vdata)); memset(&emcopy.fdata, 0, sizeof(emcopy.fdata)); free_editMesh(&emcopy); @@ -1760,6 +1759,7 @@ void separate_mesh_loose(void) emcopy.alledges= NULL; emcopy.allfaces= NULL; emcopy.derivedFinal= emcopy.derivedCage= NULL; + memset(&emcopy.vdata, 0, sizeof(emcopy.vdata)); memset(&emcopy.fdata, 0, sizeof(emcopy.fdata)); free_editMesh(&emcopy); @@ -1801,8 +1801,6 @@ typedef struct EditVertC float no[3]; float co[3]; unsigned char f, h; - short totweight; - struct MDeformWeight *dw; int keyindex; } EditVertC; @@ -1835,7 +1833,7 @@ typedef struct UndoMesh { short selectmode; RetopoPaintData *retopo_paint_data; char retopo_mode; - CustomData fdata; + CustomData vdata, fdata; } UndoMesh; /* for callbacks */ @@ -1843,18 +1841,13 @@ typedef struct UndoMesh { static void free_undoMesh(void *umv) { UndoMesh *um= umv; - EditVertC *evec; - int a; - - for(a=0, evec= um->verts; a<um->totvert; a++, evec++) { - if(evec->dw) MEM_freeN(evec->dw); - } if(um->verts) MEM_freeN(um->verts); if(um->edges) MEM_freeN(um->edges); if(um->faces) MEM_freeN(um->faces); if(um->selected) MEM_freeN(um->selected); if(um->retopo_paint_data) retopo_free_paint_data(um->retopo_paint_data); + CustomData_free(&um->vdata); CustomData_free(&um->fdata); MEM_freeN(um); } @@ -1888,6 +1881,7 @@ static void *editMesh_to_undoMesh(void) if(um->totface) efac= um->faces= MEM_callocN(um->totface*sizeof(EditFaceC), "allfacesC"); if(um->totsel) esec= um->selected= MEM_callocN(um->totsel*sizeof(EditSelectionC), "allselections"); + if(um->totvert) CustomData_from_template(&em->vdata, &um->vdata, 0, um->totvert); if(um->totface) CustomData_from_template(&em->fdata, &um->fdata, 0, um->totface); /* now copy vertices */ @@ -1899,9 +1893,9 @@ static void *editMesh_to_undoMesh(void) evec->f= eve->f; evec->h= eve->h; evec->keyindex= eve->keyindex; - evec->totweight= eve->totweight; - evec->dw= MEM_dupallocN(eve->dw); eve->tmp.l = a; /*store index*/ + + CustomData_from_em_block(&em->vdata, &um->vdata, eve->data, a); } /* copy edges */ @@ -1988,17 +1982,20 @@ static void undoMesh_to_editMesh(void *umv) #endif /* now copy vertices */ + CustomData_free(&em->vdata); + CustomData_from_template(&um->vdata, &em->vdata, 0, 0); + if(um->totvert) evar= MEM_mallocN(um->totvert*sizeof(EditVert *), "vertex ar"); for(a=0, evec= um->verts; a<um->totvert; a++, evec++) { - eve= addvertlist(evec->co); + eve= addvertlist(evec->co, NULL); evar[a]= eve; VECCOPY(eve->no, evec->no); eve->f= evec->f; eve->h= evec->h; - eve->totweight= evec->totweight; eve->keyindex= evec->keyindex; - eve->dw= MEM_dupallocN(evec->dw); + + CustomData_to_em_block(&um->vdata, &em->vdata, a, &eve->data); } /* copy edges */ diff --git a/source/blender/src/editmesh_add.c b/source/blender/src/editmesh_add.c index 9347d7f4793..d1ea36520d8 100644 --- a/source/blender/src/editmesh_add.c +++ b/source/blender/src/editmesh_add.c @@ -228,7 +228,7 @@ void add_click_mesh(void) float mat[3][3],imat[3][3]; float *curs= give_cursor(); - eve= addvertlist(0); + eve= addvertlist(0, NULL); Mat3CpyMat4(mat, G.obedit->obmat); Mat3Inv(imat, mat); @@ -837,7 +837,7 @@ void make_prim(int type, float imat[3][3], short tot, short seg, vec[1]= cent[1]- dia; vec[2]= cent[2]; Mat3MulVecfl(imat,vec); - eve= addvertlist(vec); + eve= addvertlist(vec, NULL); eve->f= 1+2+4; if (a) { addedgelist(eve->prev, eve, NULL); @@ -869,7 +869,7 @@ void make_prim(int type, float imat[3][3], short tot, short seg, vec[0]= dia*sin(phi); vec[1]= 0.0; vec[2]= dia*cos(phi); - eve= addvertlist(vec); + eve= addvertlist(vec, NULL); eve->f= 1+2+4; if(a==0) v1= eve; else addedgelist(eve->prev, eve, NULL); @@ -916,7 +916,7 @@ void make_prim(int type, float imat[3][3], short tot, short seg, vec[0]= dia*icovert[a][0]; vec[1]= dia*icovert[a][1]; vec[2]= dia*icovert[a][2]; - eva[a]= addvertlist(vec); + eva[a]= addvertlist(vec, NULL); eva[a]->f= 1+2; } for(a=0;a<20;a++) { @@ -962,9 +962,9 @@ void make_prim(int type, float imat[3][3], short tot, short seg, for (i=0; i<monkeynv; i++) { float v[3]; v[0]= (monkeyv[i][0]+127)/128.0, v[1]= monkeyv[i][1]/128.0, v[2]= monkeyv[i][2]/128.0; - tv[i]= addvertlist(v); + tv[i]= addvertlist(v, NULL); tv[i]->f |= SELECT; - tv[monkeynv+i]= (fabs(v[0]= -v[0])<0.001)?tv[i]:addvertlist(v); + tv[monkeynv+i]= (fabs(v[0]= -v[0])<0.001)?tv[i]:addvertlist(v, NULL); tv[monkeynv+i]->f |= SELECT; } for (i=0; i<monkeynf; i++) { @@ -997,7 +997,7 @@ void make_prim(int type, float imat[3][3], short tot, short seg, vec[2]= cent[2]+d; Mat3MulVecfl(imat, vec); - eve= addvertlist(vec); + eve= addvertlist(vec, NULL); eve->f= SELECT; if(a==0) { if(b==0) v1= eve; @@ -1012,12 +1012,12 @@ void make_prim(int type, float imat[3][3], short tot, short seg, VECCOPY(vec,cent); vec[2]-= -d; Mat3MulVecfl(imat,vec); - vdown= addvertlist(vec); + vdown= addvertlist(vec, NULL); if(ext || type==7) { VECCOPY(vec,cent); vec[2]-= d; Mat3MulVecfl(imat,vec); - vtop= addvertlist(vec); + vtop= addvertlist(vec, NULL); } } else { vdown= v1; diff --git a/source/blender/src/editmesh_lib.c b/source/blender/src/editmesh_lib.c index ca03dcef555..d40ab35a4db 100644 --- a/source/blender/src/editmesh_lib.c +++ b/source/blender/src/editmesh_lib.c @@ -709,26 +709,44 @@ void EM_hide_reset(void) } -void EM_interp_from_faces(EditFace *efa1, EditFace *efa2, EditFace *efan, int i1, int i2, int i3, int i4) +void EM_data_interp_from_verts(EditVert *v1, EditVert *v2, EditVert *eve, float fac) +{ + EditMesh *em= G.editMesh; + void *src[2]; + float w[2]; + + if (v1->data && v2->data) { + src[0]= v1->data; + src[1]= v2->data; + w[0] = 1.0f-fac; + w[1] = fac; + + CustomData_em_interp(&em->vdata, src, w, NULL, 2, eve->data); + } +} + +void EM_data_interp_from_faces(EditFace *efa1, EditFace *efa2, EditFace *efan, int i1, int i2, int i3, int i4) { EditMesh *em= G.editMesh; float w[2][4][4]; void *src[2]; int count = (efa2)? 2: 1; - /* set weights for copying from corners directly to other corners */ - memset(w, 0, sizeof(w)); + if (efa1->data) { + /* set weights for copying from corners directly to other corners */ + memset(w, 0, sizeof(w)); - w[i1/4][0][i1%4]= 1.0f; - w[i2/4][1][i2%4]= 1.0f; - w[i3/4][2][i3%4]= 1.0f; - if (i4 != -1) - w[i4/4][3][i4%4]= 1.0f; + w[i1/4][0][i1%4]= 1.0f; + w[i2/4][1][i2%4]= 1.0f; + w[i3/4][2][i3%4]= 1.0f; + if (i4 != -1) + w[i4/4][3][i4%4]= 1.0f; - src[0]= efa1->data; - src[1]= (efa2)? efa2->data: NULL; + src[0]= efa1->data; + src[1]= (efa2)? efa2->data: NULL; - CustomData_em_interp(&em->fdata, src, NULL, (float*)w, count, efan->data); + CustomData_em_interp(&em->fdata, src, NULL, (float*)w, count, efan->data); + } } EditFace *EM_face_from_faces(EditFace *efa1, EditFace *efa2, int i1, int i2, int i3, int i4) @@ -742,12 +760,66 @@ EditFace *EM_face_from_faces(EditFace *efa1, EditFace *efa2, int i1, int i2, int efan= addfacelist(v[i1/4][i1%4], v[i2/4][i2%4], v[i3/4][i3%4], (i4 == -1)? 0: v[i4/4][i4%4], efa1, NULL); - if (efa1->data) - EM_interp_from_faces(efa1, efa2, efan, i1, i2, i3, i4); + EM_data_interp_from_faces(efa1, efa2, efan, i1, i2, i3, i4); return efan; } +static void update_data_blocks(CustomData *olddata, CustomData *data) +{ + EditMesh *em= G.editMesh; + EditFace *efa; + EditVert *eve; + void *block; + + if (data == &G.editMesh->vdata) { + for(eve= em->verts.first; eve; eve= eve->next) { + block = NULL; + CustomData_em_copy_data(olddata, data, eve->data, &block); + CustomData_em_free_block(olddata, &eve->data); + eve->data= block; + } + } + else if (data == &G.editMesh->fdata) { + for(efa= em->faces.first; efa; efa= efa->next) { + block = NULL; + CustomData_em_copy_data(olddata, data, efa->data, &block); + CustomData_em_free_block(olddata, &efa->data); + efa->data= block; + } + } +} + +void EM_add_data_layer(CustomData *data, int type) +{ + CustomData olddata; + + if (CustomData_has_layer(data, type)) + return; + + olddata= *data; + olddata.layers= MEM_dupallocN(olddata.layers); + CustomData_add_layer(data, type, 0, NULL); + + update_data_blocks(&olddata, data); + MEM_freeN(olddata.layers); +} + +void EM_free_data_layer(CustomData *data, int type) +{ + CustomData olddata; + + if (!CustomData_has_layer(data, type)) + return; + + olddata= *data; + olddata.layers= MEM_dupallocN(olddata.layers); + CustomData_free_layer(data, type); + + update_data_blocks(&olddata, data); + MEM_freeN(olddata.layers); +} + /* ******** EXTRUDE ********* */ static void add_normal_aligned(float *nor, float *add) @@ -843,34 +915,16 @@ short extrudeflag_face_indiv(short flag, float *nor) /* step 2: make new faces from faces */ for(efa= em->faces.last; efa; efa= efa->prev) { if(efa->f & SELECT) { - v1= addvertlist(efa->v1->co); - if(efa->v1->totweight){ - v1->dw = MEM_dupallocN(efa->v1->dw); - v1->totweight = efa->v1->totweight; - } - - v2= addvertlist(efa->v2->co); - if(efa->v2->totweight){ - v2->dw = MEM_dupallocN(efa->v2->dw); - v2->totweight = efa->v2->totweight; - } - - v3= addvertlist(efa->v3->co); - if(efa->v3->totweight){ - v3->dw = MEM_dupallocN(efa->v3->dw); - v3->totweight = efa->v3->totweight; - } + v1= addvertlist(efa->v1->co, efa->v1); + v2= addvertlist(efa->v2->co, efa->v2); + v3= addvertlist(efa->v3->co, efa->v3); v1->f1= v2->f1= v3->f1= 1; VECCOPY(v1->no, efa->n); VECCOPY(v2->no, efa->n); VECCOPY(v3->no, efa->n); if(efa->v4) { - v4= addvertlist(efa->v4->co); - if(efa->v4->totweight){ - v4->dw = MEM_dupallocN(efa->v4->dw); - v4->totweight = efa->v4->totweight; - } + v4= addvertlist(efa->v4->co, efa->v4); v4->f1= 1; VECCOPY(v4->no, efa->n); } @@ -942,20 +996,11 @@ short extrudeflag_edges_indiv(short flag, float *nor) /* make the faces */ for(eed= em->edges.first; eed; eed= eed->next) { if(eed->f & flag) { - if(eed->v1->tmp.v == NULL){ - eed->v1->tmp.v = addvertlist(eed->v1->co); - if(eed->v1->totweight){ - eed->v1->tmp.v->dw = MEM_dupallocN(eed->v1->dw); - eed->v1->tmp.v->totweight = eed->v1->totweight; - } - } - if(eed->v2->tmp.v == NULL){ - eed->v2->tmp.v = addvertlist(eed->v2->co); - if(eed->v2->totweight){ - eed->v2->tmp.v->dw = MEM_dupallocN(eed->v2->dw); - eed->v2->tmp.v->totweight = eed->v2->totweight; - } - } + if(eed->v1->tmp.v == NULL) + eed->v1->tmp.v = addvertlist(eed->v1->co, eed->v1); + if(eed->v2->tmp.v == NULL) + eed->v2->tmp.v = addvertlist(eed->v2->co, eed->v2); + if(eed->dir==1) addfacelist(eed->v1, eed->v2, eed->v2->tmp.v, eed->v1->tmp.v, @@ -999,11 +1044,7 @@ short extrudeflag_verts_indiv(short flag, float *nor) /* make the edges */ for(eve= em->verts.first; eve; eve= eve->next) { if(eve->f & flag) { - eve->tmp.v = addvertlist(eve->co); - if(eve->totweight){ - eve->tmp.v->dw = MEM_dupallocN(eve->dw); - eve->tmp.v->totweight = eve->totweight; - } + eve->tmp.v = addvertlist(eve->co, eve); addedgelist(eve, eve->tmp.v, NULL); } else eve->tmp.v = NULL; @@ -1136,20 +1177,11 @@ static short extrudeflag_edge(short flag, float *nor) for(eed= em->edges.last; eed; eed= eed->prev) { if(eed->f & SELECT) { if(eed->f2<2) { - if(eed->v1->tmp.v == NULL){ - eed->v1->tmp.v = addvertlist(eed->v1->co); - if(eed->v1->totweight){ - eed->v1->tmp.v->dw = MEM_dupallocN(eed->v1->dw); - eed->v1->tmp.v->totweight = eed->v1->totweight; - } - } - if(eed->v2->tmp.v == NULL){ - eed->v2->tmp.v = addvertlist(eed->v2->co); - if(eed->v2->totweight){ - eed->v2->tmp.v->dw = MEM_dupallocN(eed->v2->dw); - eed->v2->tmp.v->totweight = eed->v2->totweight; - } - } + if(eed->v1->tmp.v == NULL) + eed->v1->tmp.v = addvertlist(eed->v1->co, eed->v1); + if(eed->v2->tmp.v == NULL) + eed->v2->tmp.v = addvertlist(eed->v2->co, eed->v2); + /* if del_old, the preferred normal direction is exact * opposite as for keep old faces */ @@ -1168,34 +1200,14 @@ static short extrudeflag_edge(short flag, float *nor) /* step 3: make new faces from faces */ for(efa= em->faces.last; efa; efa= efa->prev) { if(efa->f & SELECT) { - if (efa->v1->tmp.v == NULL){ - efa->v1->tmp.v = addvertlist(efa->v1->co); - if(efa->v1->totweight){ - efa->v1->tmp.v->dw = MEM_dupallocN(efa->v1->dw); - efa->v1->tmp.v->totweight = efa->v1->totweight; - } - } - if (efa->v2->tmp.v ==NULL){ - efa->v2->tmp.v = addvertlist(efa->v2->co); - if(efa->v2->totweight){ - efa->v2->tmp.v->dw = MEM_dupallocN(efa->v2->dw); - efa->v2->tmp.v->totweight = efa->v2->totweight; - } - } - if (efa->v3->tmp.v ==NULL){ - efa->v3->tmp.v = addvertlist(efa->v3->co); - if(efa->v3->totweight){ - efa->v3->tmp.v->dw = MEM_dupallocN(efa->v3->dw); - efa->v3->tmp.v->totweight = efa->v3->totweight; - } - } - if (efa->v4 && (efa->v4->tmp.v == NULL)){ - efa->v4->tmp.v = addvertlist(efa->v4->co); - if(efa->v4->totweight){ - efa->v4->tmp.v->dw = MEM_dupallocN(efa->v4->dw); - efa->v4->tmp.v->totweight = efa->v4->totweight; - } - } + if (efa->v1->tmp.v == NULL) + efa->v1->tmp.v = addvertlist(efa->v1->co, efa->v1); + if (efa->v2->tmp.v ==NULL) + efa->v2->tmp.v = addvertlist(efa->v2->co, efa->v2); + if (efa->v3->tmp.v ==NULL) + efa->v3->tmp.v = addvertlist(efa->v3->co, efa->v3); + if (efa->v4 && (efa->v4->tmp.v == NULL)) + efa->v4->tmp.v = addvertlist(efa->v4->co, efa->v4); if(del_old==0) { // keep old faces means flipping normal if(efa->v4) @@ -1425,7 +1437,7 @@ short extrudeflag_vert(short flag, float *nor) eve->f &= ~128; /* clear, for later test for loose verts */ if(eve->f & flag) { sel= 1; - v1= addvertlist(0); + v1= addvertlist(0, NULL); VECCOPY(v1->co, eve->co); v1->f= eve->f; @@ -1482,7 +1494,7 @@ short extrudeflag_vert(short flag, float *nor) efa = eed->tmp.f; efa2->mat_nr= efa->mat_nr; efa2->flag= efa->flag; - CustomData_em_copy_data(&em->fdata, &efa->data, &efa2->data); + CustomData_em_copy_data(&em->fdata, &em->fdata, &efa->data, &efa2->data); } /* Needs smarter adaption of existing creases. @@ -1621,7 +1633,8 @@ void translateflag(short flag, float *vec) /* helper call for below */ static EditVert *adduplicate_vertex(EditVert *eve, int flag) { - EditVert *v1= addvertlist(eve->co); + /* FIXME: copy deformation weight from eve ok here? */ + EditVert *v1= addvertlist(eve->co, eve); v1->f= eve->f; eve->f-= flag; @@ -1629,15 +1642,6 @@ static EditVert *adduplicate_vertex(EditVert *eve, int flag) eve->tmp.v = v1; - /* FIXME: Copy deformation weight ? */ - v1->totweight = eve->totweight; - if (eve->totweight){ - v1->dw = MEM_mallocN (eve->totweight * sizeof(MDeformWeight), "deformWeight"); - memcpy (v1->dw, eve->dw, eve->totweight * sizeof(MDeformWeight)); - } - else - v1->dw=NULL; - return v1; } @@ -1800,13 +1804,13 @@ void flipface(EditFace *efa) SWAP(EditVert *, efa->v2, efa->v4); SWAP(EditEdge *, efa->e1, efa->e4); SWAP(EditEdge *, efa->e2, efa->e3); - EM_interp_from_faces(efa, NULL, efa, 0, 3, 2, 1); + EM_data_interp_from_faces(efa, NULL, efa, 0, 3, 2, 1); } else { SWAP(EditVert *, efa->v2, efa->v3); SWAP(EditEdge *, efa->e1, efa->e3); efa->e2->dir= 1-efa->e2->dir; - EM_interp_from_faces(efa, NULL, efa, 0, 2, 1, 3); + EM_data_interp_from_faces(efa, NULL, efa, 0, 2, 1, 3); } if(efa->v4) CalcNormFloat4(efa->v1->co, efa->v2->co, efa->v3->co, efa->v4->co, efa->n); diff --git a/source/blender/src/editmesh_mods.c b/source/blender/src/editmesh_mods.c index c5958be912b..52befe8a64c 100644 --- a/source/blender/src/editmesh_mods.c +++ b/source/blender/src/editmesh_mods.c @@ -1167,20 +1167,26 @@ int vertgroup_select(short mode) return selcount; } } - } else if (mode==3 && base_eve->totweight != 0) { /* vertex groups */ - short i,j; /*weight index*/ + } else if (mode==3) { /* vertex groups */ + MDeformVert *dvert, *base_dvert; + short i, j; /* weight index */ + + base_dvert= CustomData_em_get(&em->vdata, base_eve->data, + LAYERTYPE_MDEFORMVERT); + + if (!base_dvert || base_dvert->totweight == 0) + return selcount; for(eve= em->verts.first; eve; eve= eve->next) { - if ( - !(eve->f & SELECT) && - !eve->h && - eve->totweight - ) { + dvert= CustomData_em_get(&em->vdata, eve->data, + LAYERTYPE_MDEFORMVERT); + + if (dvert && !(eve->f & SELECT) && !eve->h && dvert->totweight) { /* do the extra check for selection in the following if, so were not checking verts that may be alredy selected */ - for (i=0; base_eve->totweight >i && !(eve->f & SELECT); i++) { - for (j=0; eve->totweight >j; j++) { - if (base_eve->dw[i].def_nr==eve->dw[j].def_nr) { + for (i=0; base_dvert->totweight >i && !(eve->f & SELECT); i++) { + for (j=0; dvert->totweight >j; j++) { + if (base_dvert->dw[i].def_nr==dvert->dw[j].def_nr) { eve->f |= SELECT; selcount++; deselcount--; diff --git a/source/blender/src/editmesh_tools.c b/source/blender/src/editmesh_tools.c index 2d10f93ef1c..8b7bf72b434 100644 --- a/source/blender/src/editmesh_tools.c +++ b/source/blender/src/editmesh_tools.c @@ -203,8 +203,7 @@ int removedoublesflag(short flag, float limit) /* return amount */ xvertsort *sortblock, *sb, *sb1; struct facesort *vlsortblock, *vsb, *vsb1; float dist; - int a, b, test, amount, currweight, doubweight, targetweight; - MDeformWeight *newdw; + int a, b, test, amount; /* flag 128 is cleared, count */ eve= em->verts.first; @@ -263,50 +262,9 @@ int removedoublesflag(short flag, float limit) /* return amount */ } MEM_freeN(sortblock); - - for(eve = em->verts.first; eve; eve=eve->next){ - - if(eve->f & flag) { - if(eve->f & 128) { - - v1 = eve->tmp.v; - - - if(v1->dw && eve->dw){ - for(doubweight=0; doubweight < eve->totweight; doubweight++){ - targetweight = -1; - for(currweight = 0; currweight < v1->totweight; currweight++){ - if(v1->dw[currweight].def_nr == eve->dw[doubweight].def_nr){ - targetweight = currweight; - break; - } - } - - if(targetweight != -1){ /*average*/ - v1->dw[targetweight].weight = (v1->dw[targetweight].weight + eve->dw[doubweight].weight) / 2; - } - else{ /*append*/ - newdw = MEM_callocN(sizeof(MDeformWeight)*(v1->totweight+1), "MDeformWeight Append"); - memcpy(newdw, v1->dw, sizeof(MDeformWeight)*v1->totweight); - MEM_freeN(v1->dw); - - v1->dw= newdw; - v1->dw[v1->totweight].weight = eve->dw[doubweight].weight; - v1->dw[v1->totweight].def_nr = eve->dw[doubweight].def_nr; - v1->totweight++; - } - } - } - else if(eve->dw){ /*just straight copy vert weights*/ - - newdw = MEM_mallocN(sizeof(MDeformWeight) * (eve->totweight), "MDeformWeight Copy"); - memcpy(newdw, eve->dw, sizeof(MDeformWeight)*eve->totweight); - v1->dw= newdw; - - } - } - } - } + for(eve = em->verts.first; eve; eve=eve->next) + if((eve->f & flag) && (eve->f & 128)) + EM_data_interp_from_verts(eve, eve->tmp.v, eve->tmp.v, 0.5f); /* test edges and insert again */ eed= em->edges.first; @@ -373,7 +331,7 @@ int removedoublesflag(short flag, float limit) /* return amount */ efa->v3= efa->v4; efa->v4= 0; - EM_interp_from_faces(efa, NULL, efa, 0, 2, 3, 3); + EM_data_interp_from_faces(efa, NULL, efa, 0, 2, 3, 3); test= 0; } @@ -1208,59 +1166,6 @@ void fill_mesh(void) /*used by faceloop cut to select only edges valid for edge slide*/ #define DOUBLEOPFILL 16 -/* Mostly mirrored from editdeform.c, here only used for the function below */ -/* Only to be used to add new weights in eve, the value of weight has been premultiplied with subdiv factor, so is added only */ -static void subdiv_add_defweight (EditVert *eve, int defgroup, float weight) -{ - MDeformWeight *newdw; - int i; - - if (defgroup<0) - return; - - for (i=0; i<eve->totweight; i++) { - if (eve->dw[i].def_nr == defgroup) { - eve->dw[i].weight += weight; - return; - } - } - - newdw = MEM_callocN (sizeof(MDeformWeight)*(eve->totweight+1), "subdiv deformWeight"); - if (eve->dw) { - memcpy (newdw, eve->dw, sizeof(MDeformWeight)*eve->totweight); - MEM_freeN (eve->dw); - } - eve->dw= newdw; - - eve->dw[eve->totweight].weight= weight; - eve->dw[eve->totweight].def_nr= defgroup; - - eve->totweight++; - -} - - -/* the new vertex *eve will get vertex groups as defined in eed, based on fac subdivide */ -static void subdivide_edge_vgroups(EditEdge *eed, EditVert *eve, float fac) -{ - EditVert *v1= eed->v1, *v2= eed->v2; - int i; - - /* let's first check of there are groups */ - if(v1->totweight==0 && v2->totweight==0) - return; - - /* now add the weights of v1 into the new vertex */ - for (i=0; i<v1->totweight; i++) { - subdiv_add_defweight(eve, v1->dw[i].def_nr, v1->dw[i].weight*(1.0f-fac)); - } - - /* now add the weights of v2 into the new vertex */ - for (i=0; i<v2->totweight; i++) { - subdiv_add_defweight(eve, v2->dw[i].def_nr, v2->dw[i].weight*fac); - } -} - /* calculates offset for co, based on fractal, sphere or smooth settings */ static void alter_co(float *co, EditEdge *edge, float rad, int beauty, float perc) { @@ -1331,10 +1236,10 @@ static EditVert *subdivide_edge_addvert(EditEdge *edge, float rad, int beauty, f /* offset for smooth or sphere or fractal */ alter_co(co, edge, rad, beauty, percent); - ev = addvertlist(co); + ev = addvertlist(co, NULL); - /* vgroups */ - subdivide_edge_vgroups(edge, ev, percent); + /* vert data (vgroups, ..) */ + EM_data_interp_from_verts(edge->v1, edge->v2, ev, percent); /* normal */ ev->no[0] = (edge->v2->no[0]-edge->v1->no[0])*percent + edge->v1->no[0]; @@ -1393,11 +1298,12 @@ void interp_uv_vcol(float *v1, float *v2, float *v3, float *v4, float *co, TFace static void facecopy(EditFace *source, EditFace *target) { + EditMesh *em= G.editMesh; float *v1 = source->v1->co, *v2 = source->v2->co, *v3 = source->v3->co; float *v4 = source->v4? source->v4->co: NULL; float w[4][4]; - CustomData_em_copy_data(&G.editMesh->fdata, source->data, &target->data); + CustomData_em_copy_data(&em->fdata, &em->fdata, source->data, &target->data); target->mat_nr = source->mat_nr; target->flag = source->flag; @@ -1408,8 +1314,7 @@ static void facecopy(EditFace *source, EditFace *target) if (target->v4) InterpWeightsQ3Dfl(v1, v2, v3, v4, target->v4->co, w[3]); - CustomData_em_interp(&G.editMesh->fdata, &source->data, NULL, - (float*)w, 1, target->data); + CustomData_em_interp(&em->fdata, &source->data, NULL, (float*)w, 1, target->data); } static void fill_quad_single(EditFace *efa, struct GHash *gh, int numcuts, int seltype) @@ -1831,11 +1736,13 @@ static void fill_quad_double_adj_inner(EditFace *efa, struct GHash *gh, int numc inner = MEM_mallocN(sizeof(EditVert*)*numcuts,"New inner verts"); for(i=0;i<numcuts;i++) { - co[0] = (verts[0][numcuts-i]->co[0] + verts[1][i+1]->co[0] ) / 2 ; - co[1] = (verts[0][numcuts-i]->co[1] + verts[1][i+1]->co[1] ) / 2 ; - co[2] = (verts[0][numcuts-i]->co[2] + verts[1][i+1]->co[2] ) / 2 ; - inner[i] = addvertlist(co); - inner[i]->f2 |= EDGEINNER; + co[0] = (verts[0][numcuts-i]->co[0] + verts[1][i+1]->co[0] ) / 2 ; + co[1] = (verts[0][numcuts-i]->co[1] + verts[1][i+1]->co[1] ) / 2 ; + co[2] = (verts[0][numcuts-i]->co[2] + verts[1][i+1]->co[2] ) / 2 ; + inner[i] = addvertlist(co, NULL); + inner[i]->f2 |= EDGEINNER; + + EM_data_interp_from_verts(verts[0][numcuts-i], verts[1][i+1], inner[i], 0.5f); } // Add Corner Quad @@ -4299,55 +4206,22 @@ static void bevel_mesh(float bsize, int allfaces) while (efa) { if (efa->f1 & 1) { efa->f1-= 1; - v1= addvertlist(efa->v1->co); + v1= addvertlist(efa->v1->co, efa->v1); v1->f= efa->v1->f & ~128; efa->v1->tmp.v = v1; -#ifdef __NLA - v1->totweight = efa->v1->totweight; - if (efa->v1->totweight) { - v1->dw = MEM_mallocN (efa->v1->totweight * sizeof(MDeformWeight), "deformWeight"); - memcpy (v1->dw, efa->v1->dw, efa->v1->totweight * sizeof(MDeformWeight)); - } - else - v1->dw=NULL; -#endif - v1= addvertlist(efa->v2->co); + + v1= addvertlist(efa->v2->co, efa->v2); v1->f= efa->v2->f & ~128; efa->v2->tmp.v = v1; -#ifdef __NLA - v1->totweight = efa->v2->totweight; - if (efa->v2->totweight) { - v1->dw = MEM_mallocN (efa->v2->totweight * sizeof(MDeformWeight), "deformWeight"); - memcpy (v1->dw, efa->v2->dw, efa->v2->totweight * sizeof(MDeformWeight)); - } - else - v1->dw=NULL; -#endif - v1= addvertlist(efa->v3->co); + + v1= addvertlist(efa->v3->co, efa->v3); v1->f= efa->v3->f & ~128; efa->v3->tmp.v = v1; -#ifdef __NLA - v1->totweight = efa->v3->totweight; - if (efa->v3->totweight) { - v1->dw = MEM_mallocN (efa->v3->totweight * sizeof(MDeformWeight), "deformWeight"); - memcpy (v1->dw, efa->v3->dw, efa->v3->totweight * sizeof(MDeformWeight)); - } - else - v1->dw=NULL; -#endif + if (efa->v4) { - v1= addvertlist(efa->v4->co); + v1= addvertlist(efa->v4->co, efa->v4); v1->f= efa->v4->f & ~128; efa->v4->tmp.v = v1; -#ifdef __NLA - v1->totweight = efa->v4->totweight; - if (efa->v4->totweight) { - v1->dw = MEM_mallocN (efa->v4->totweight * sizeof(MDeformWeight), "deformWeight"); - memcpy (v1->dw, efa->v4->dw, efa->v4->totweight * sizeof(MDeformWeight)); - } - else - v1->dw=NULL; -#endif } /* Needs better adaption of creases? */ @@ -4595,7 +4469,7 @@ static void bevel_mesh(float bsize, int allfaces) cent[0]= (min[0]+max[0])/2; cent[1]= (min[1]+max[1])/2; cent[2]= (min[2]+max[2])/2; - eve2= addvertlist(cent); + eve2= addvertlist(cent, NULL); eve2->f |= 1; eed= em->edges.first; while (eed) { @@ -5494,7 +5368,7 @@ void mesh_rip(void) for(eve = em->verts.last; eve; eve= eve->prev) { eve->tmp.v = NULL; if(eve->f & SELECT) { - eve->tmp.v = addvertlist(eve->co); + eve->tmp.v = addvertlist(eve->co, eve); eve->f &= ~SELECT; eve->tmp.v->f |= SELECT; } diff --git a/source/blender/src/editobject.c b/source/blender/src/editobject.c index 57802d3eb3e..280ca5be08b 100644 --- a/source/blender/src/editobject.c +++ b/source/blender/src/editobject.c @@ -95,6 +95,7 @@ #include "BKE_anim.h" #include "BKE_armature.h" #include "BKE_constraint.h" +#include "BKE_customdata.h" #include "BKE_blender.h" #include "BKE_booleanops.h" #include "BKE_curve.h" @@ -360,19 +361,24 @@ static int return_editmesh_indexar(int *tot, int **indexar, float *cent) static int return_editmesh_vgroup(char *name, float *cent) { EditMesh *em = G.editMesh; + MDeformVert *dvert; EditVert *eve; int i, totvert=0; cent[0]= cent[1]= cent[2]= 0.0; - if (G.obedit->actdef) { + if(G.obedit->actdef) { /* find the vertices */ for(eve= em->verts.first; eve; eve= eve->next) { - for (i=0; i<eve->totweight; i++){ - if(eve->dw[i].def_nr == (G.obedit->actdef-1)) { - totvert++; - VecAddf(cent, cent, eve->co); + dvert= CustomData_em_get(&em->vdata, eve->data, LAYERTYPE_MDEFORMVERT); + + if(dvert) { + for(i=0; i<dvert->totweight; i++){ + if(dvert->dw[i].def_nr == (G.obedit->actdef-1)) { + totvert++; + VecAddf(cent, cent, eve->co); + } } } } diff --git a/source/blender/src/retopo.c b/source/blender/src/retopo.c index 164823693a0..0c78d858f29 100644 --- a/source/blender/src/retopo.c +++ b/source/blender/src/retopo.c @@ -290,7 +290,7 @@ void retopo_paint_apply() for(i=0; i<hitcount; ++i) { RetopoPaintPoint *intersection= BLI_findlink(&rpd->intersections,i); retopo_do_2d(G.vd,&intersection->loc.x, hitco, 1); - intersection->eve= addvertlist(hitco); + intersection->eve= addvertlist(hitco, NULL); intersection->eve->f= SELECT; } diff --git a/source/blender/src/verse_mesh.c b/source/blender/src/verse_mesh.c index 851c2dcc77c..1445c5471d1 100644 --- a/source/blender/src/verse_mesh.c +++ b/source/blender/src/verse_mesh.c @@ -684,7 +684,7 @@ void post_vertex_create(VerseVert *vvert) * vertexes, because addvertlist() sends new vertex to verse * server if em->vnode isn't NULL */ em->vnode = NULL; - eve = addvertlist(vvert->co); + eve = addvertlist(vvert->co, NULL); em->vnode = (void*)geom_vnode; eve->vvert = (void*)vvert; @@ -1557,11 +1557,11 @@ void create_edit_mesh_from_geom_node(VNode *vnode) /* create all EditVerts */ while(vvert) { - eve = addvertlist(vvert->co); + eve = addvertlist(vvert->co, NULL); eve->f = 0; eve->h = 0; - eve->dw = NULL; + eve->data = NULL; eve->keyindex = keyindex; eve->vvert = (void*)vvert; |