[Bf-blender-cvs] SVN commit: /data/svn/bf-blender [11980] branches/bmesh/source/blender: -> Duplicate tool
Geoffrey Bantle
hairbat at yahoo.com
Sat Sep 8 22:46:31 CEST 2007
Revision: 11980
http://projects.blender.org/plugins/scmsvn/viewcvs.php?view=rev&root=bf-blender&revision=11980
Author: briggs
Date: 2007-09-08 22:46:31 +0200 (Sat, 08 Sep 2007)
Log Message:
-----------
-> Duplicate tool
Shift-D, Duplicate tool in editmode ported over.
This should work for mixed selections as well when
multiselect is fixed later....
Modified Paths:
--------------
branches/bmesh/source/blender/blenkernel/BKE_bmesh.h
branches/bmesh/source/blender/blenkernel/intern/BME_tools.c
branches/bmesh/source/blender/include/editbmesh.h
branches/bmesh/source/blender/src/edit.c
branches/bmesh/source/blender/src/editbmesh_interface.c
branches/bmesh/source/blender/src/editbmesh_tools.c
Modified: branches/bmesh/source/blender/blenkernel/BKE_bmesh.h
===================================================================
--- branches/bmesh/source/blender/blenkernel/BKE_bmesh.h 2007-09-08 12:50:10 UTC (rev 11979)
+++ branches/bmesh/source/blender/blenkernel/BKE_bmesh.h 2007-09-08 20:46:31 UTC (rev 11980)
@@ -134,9 +134,9 @@
{
struct BME_Poly *next, *prev;
int EID;
+ unsigned short flag, h;
int eflag1, eflag2; /*reserved for use by eulers*/
int tflag1, tflag2; /*reserved for use by tools*/
- unsigned short flag, h;
unsigned short mat_nr;
struct BME_Loop *loopbase; /*First editloop around Polygon.*/
struct ListBase holes; /*list of inner loops in the face*/
@@ -218,4 +218,6 @@
struct BME_Poly *BME_inset_poly(struct BME_Mesh *bm, struct BME_Poly *f);
void BME_split_face(struct BME_Mesh *bm, struct BME_Poly *f);
void BME_delete_polys(struct BME_Mesh *bm);
+/*mixed tools*/
+void BME_duplicate(struct BME_Mesh *bm);
#endif
Modified: branches/bmesh/source/blender/blenkernel/intern/BME_tools.c
===================================================================
--- branches/bmesh/source/blender/blenkernel/intern/BME_tools.c 2007-09-08 12:50:10 UTC (rev 11979)
+++ branches/bmesh/source/blender/blenkernel/intern/BME_tools.c 2007-09-08 20:46:31 UTC (rev 11980)
@@ -47,12 +47,12 @@
#include "BKE_bmesh.h"
#include "BLI_blenlib.h"
#include "BLI_arithb.h"
+#include "BLI_ghash.h"
-
/*Vertex Tools*/
void BME_connect_verts(BME_Mesh *bm)
{
@@ -496,5 +496,158 @@
}
+static BME_Vert *BME_dupevert(BME_Mesh *bm, BME_Vert *ov){
+ BME_Vert *nv = BME_MV(bm,ov->co);
+ /*copy info about ov*/
+ if(BME_SELECTED(ov))BME_select_vert(bm,nv,1);
+ return nv;
+}
+static BME_Edge *BME_dupedge(BME_Mesh *bm, BME_Edge *oe,BME_Vert *v1, BME_Vert *v2){
+ BME_Edge *ne = BME_ME(bm,v1,v2);
+ if(BME_SELECTED(oe))BME_select_edge(bm,ne,1);
+ /*copy info about oe*/
+ return ne;
+}
+static BME_Poly *BME_dupepoly(BME_Mesh *bm, BME_Poly *of, BME_Vert *v1, BME_Vert *v2, BME_Edge **edar){
+ BME_Poly *nf = NULL;
+ nf = BME_MF(bm,v1,v2,edar,of->len);
+ /*copy info about of*/
+ if(BME_SELECTED(of))BME_select_poly(bm,nf,1);
+ return nf;
+}
+void BME_duplicate(BME_Mesh *bm){
+
+ BME_Vert *v, *nv, *ev1, *ev2;
+ BME_Edge *e, *ne, **edar;
+ BME_Loop *l;
+ BME_Poly *f;
+ struct GHash *vhash, *ehash;//pointer hashes
+ int edarlength, i;
+
+ /*Build a hash table of old pointers and new pointers.*/
+ vhash = BLI_ghash_new(BLI_ghashutil_ptrhash, BLI_ghashutil_ptrcmp);
+ ehash = BLI_ghash_new(BLI_ghashutil_ptrhash, BLI_ghashutil_ptrcmp);
+
+ /*Edge pointer array, realloc if too small (unlikely)*/
+ edarlength = 4096;
+ edar = MEM_callocN(sizeof(BME_Edge*)*edarlength,"Mesh duplicate tool \n");
+
+ /*first search for selected faces, dupe all verts*/
+ for(f=BME_first(bm,BME_POLY);f;f=BME_next(bm,BME_POLY,f)){
+ if(BME_SELECTED(f)){
+ /*dupe each vertex*/
+ l=f->loopbase;
+ do{
+ if(!(BME_ISVISITED(l->v))){
+ nv = BME_dupevert(bm,l->v);
+ BLI_ghash_insert(vhash,l->v,nv);
+ BME_VISIT(l->v);
+ }
+ l=l->next;
+ }while(l!=f->loopbase);
+ }
+ }
+
+ /*now search for selected edges, dupe all verts (if nessecary)*/
+ for(e=BME_first(bm,BME_EDGE);e;e=BME_next(bm,BME_EDGE,e)){
+ if(BME_SELECTED(e)){
+ if(!(BME_ISVISITED(e->v1))){
+ nv = BME_dupevert(bm,e->v1);
+ BLI_ghash_insert(vhash,e->v1,nv);
+ BME_VISIT(e->v1);
+ }
+ if(!(BME_ISVISITED(e->v2))){
+ nv = BME_dupevert(bm,e->v2);
+ BLI_ghash_insert(vhash,e->v2,nv);
+ BME_VISIT(e->v2);
+ }
+ }
+ }
+ /*finally, any unvisited vertices should be duped (loose)*/
+ for(v=BME_first(bm,BME_VERT);v;v=BME_next(bm,BME_VERT,v)){
+ if(BME_SELECTED(v) && (!(BME_NEWELEM(v)))){
+ if(!(BME_ISVISITED(v))){
+ nv = BME_dupevert(bm,v);
+ BLI_ghash_insert(vhash,v,nv);
+ BME_VISIT(v);
+ }
+ }
+ }
+
+ /*go through selected edges and dupe using vert hash as lookup.*/
+ for(e=BME_first(bm,BME_EDGE);e;e=BME_next(bm,BME_EDGE,e)){
+ if(BME_SELECTED(e) && (!(BME_NEWELEM(e)))){
+ ev1 = ev2 = NULL;
+ ev1 = BLI_ghash_lookup(vhash,e->v1);
+ ev2 = BLI_ghash_lookup(vhash,e->v2);
+
+ ne = BME_dupedge(bm,e,ev1,ev2);
+ BLI_ghash_insert(ehash,e,ne);
+ BME_VISIT(e);
+ }
+ }
+ /*go through selected faces and dupe edges*/
+ for(f=BME_first(bm,BME_POLY);f;f=BME_next(bm,BME_POLY,f)){
+ if(BME_SELECTED(f)){
+ l=f->loopbase;
+ do{
+ if(!(BME_ISVISITED(l->e))){
+ ev1 = ev2 = NULL;
+ ev1 = BLI_ghash_lookup(vhash,l->e->v1);
+ ev2 = BLI_ghash_lookup(vhash,l->e->v2);
+
+ ne = BME_dupedge(bm,l->e,ev1,ev2);
+ BLI_ghash_insert(ehash,l->e,ne);
+ BME_VISIT(l->e);
+ }
+ l=l->next;
+ }while(l!=f->loopbase);
+ }
+ }
+
+
+ /*go through faces and dupe using edge hash as lookup*/
+ for(f=BME_first(bm,BME_POLY);f;f=BME_next(bm,BME_POLY,f)){
+ if(BME_SELECTED(f) && (!(BME_NEWELEM(f)))){
+ /*first check facelen and see if edar needs to be reallocated. Highly unlikely.*/
+ if(f->len > edarlength){
+ MEM_freeN(edar);
+ edarlength = edarlength * 2;
+ edar = MEM_callocN(sizeof(BME_Edge*)*edarlength,"Mesh duplicate tool");
+ }
+ /*now loop through face, looking up the edge that should go in edar, and placing in there.*/
+ l = f->loopbase;
+ i = 0;
+ do{
+ edar[i] = BLI_ghash_lookup(ehash, l->e);
+ BME_VISIT(l->e);
+ i++;
+ l=l->next;
+ }while(l!=f->loopbase);
+ ev1=ev2=NULL;
+ ev1 = BLI_ghash_lookup(vhash,f->loopbase->v);
+ ev2 = BLI_ghash_lookup(vhash,f->loopbase->next->v);
+
+ BME_VISIT(f);
+ BME_dupepoly(bm,f,ev1,ev2,edar);
+ }
+ }
+
+ /*finally go through and unselect all 'visited' elements*/
+ for(v=BME_first(bm,BME_VERT);v;v=BME_next(bm,BME_VERT,v)){
+ if(BME_ISVISITED(v)) BME_select_vert(bm,v,0);
+ }
+ for(e=BME_first(bm,BME_EDGE);e;e=BME_next(bm,BME_EDGE,e)){
+ if(BME_ISVISITED(e)) BME_select_edge(bm,e,0);
+ }
+ for(f=BME_first(bm,BME_POLY);f;f=BME_next(bm,BME_POLY,f)){
+ if(BME_ISVISITED(f)) BME_select_poly(bm,f,0);
+ }
+
+ /*free memory*/
+ if(edar) MEM_freeN(edar);
+ BLI_ghash_free(vhash,NULL, NULL); //check usage!
+ BLI_ghash_free(ehash,NULL, NULL); //check usage!
+}
Modified: branches/bmesh/source/blender/include/editbmesh.h
===================================================================
--- branches/bmesh/source/blender/include/editbmesh.h 2007-09-08 12:50:10 UTC (rev 11979)
+++ branches/bmesh/source/blender/include/editbmesh.h 2007-09-08 20:46:31 UTC (rev 11980)
@@ -30,6 +30,7 @@
void EM_dissolve_edges(void);
void EM_delete_context(void);
void EM_extrude_mesh(void);
+void EM_clone_mesh(void);
/*editbmesh_select.c*/
Modified: branches/bmesh/source/blender/src/edit.c
===================================================================
--- branches/bmesh/source/blender/src/edit.c 2007-09-08 12:50:10 UTC (rev 11979)
+++ branches/bmesh/source/blender/src/edit.c 2007-09-08 20:46:31 UTC (rev 11980)
@@ -1807,8 +1807,8 @@
void duplicate_context_selected(void)
{
if(G.obedit) {
- /*//EDITBMESHGREP if(G.obedit->type==OB_MESH) adduplicate_mesh();
- else */if(G.obedit->type==OB_ARMATURE) adduplicate_armature();
+ if(G.obedit->type==OB_MESH)EM_clone_mesh();
+ else if(G.obedit->type==OB_ARMATURE) adduplicate_armature();
else if(G.obedit->type==OB_MBALL) adduplicate_mball();
else if ELEM(G.obedit->type, OB_CURVE, OB_SURF) adduplicate_nurb();
}
Modified: branches/bmesh/source/blender/src/editbmesh_interface.c
===================================================================
--- branches/bmesh/source/blender/src/editbmesh_interface.c 2007-09-08 12:50:10 UTC (rev 11979)
+++ branches/bmesh/source/blender/src/editbmesh_interface.c 2007-09-08 20:46:31 UTC (rev 11980)
@@ -369,6 +369,7 @@
for(eve=BME_first(G.editMesh,BME_VERT);eve;eve=BME_next(G.editMesh,BME_VERT,eve)) BME_select_vert(G.editMesh,eve,0);
BME_select_vert(G.editMesh,vert,1);
}
+
allqueue(REDRAWVIEW3D, 1);
}
} else if (G.scene->selectmode == SCE_SELECT_EDGE) {
Modified: branches/bmesh/source/blender/src/editbmesh_tools.c
===================================================================
--- branches/bmesh/source/blender/src/editbmesh_tools.c 2007-09-08 12:50:10 UTC (rev 11979)
+++ branches/bmesh/source/blender/src/editbmesh_tools.c 2007-09-08 20:46:31 UTC (rev 11980)
@@ -152,4 +152,11 @@
DAG_object_flush_update(G.scene,G.obedit,OB_RECALC_DATA);
allqueue(REDRAWVIEW3D,0);
}
+void EM_clone_mesh(void){
+ BME_model_begin(G.editMesh);
+ BME_duplicate(G.editMesh);
+ BME_model_end(G.editMesh);
+ DAG_object_flush_update(G.scene,G.obedit,OB_RECALC_DATA);
+ allqueue(REDRAWVIEW3D,0);
+}
More information about the Bf-blender-cvs
mailing list