4 * ***** BEGIN GPL LICENSE BLOCK *****
6 * This program is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU General Public License
8 * as published by the Free Software Foundation; either version 2
9 * of the License, or (at your option) any later version.
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software Foundation,
18 * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
20 * The Original Code is Copyright (C) 2004 by NaN Holding BV.
21 * All rights reserved.
23 * The Original Code is: all of this file.
25 * Contributor(s): Johnny Matthews, Geoffrey Bantle.
27 * ***** END GPL LICENSE BLOCK *****
32 editmesh_tool.c: UI called tools for editmesh, geometry changes here, otherwise in mods.c
45 #include "MEM_guardedalloc.h"
48 #include "DNA_mesh_types.h"
49 #include "DNA_material_types.h"
50 #include "DNA_meshdata_types.h"
51 #include "DNA_modifier_types.h"
52 #include "DNA_object_types.h"
53 #include "DNA_scene_types.h"
54 #include "DNA_screen_types.h"
55 #include "DNA_view3d_types.h"
56 #include "DNA_key_types.h"
58 #include "BLI_blenlib.h"
60 #include "BLI_editVert.h"
62 #include "BLI_ghash.h"
63 #include "BLI_linklist.h"
66 #include "BKE_depsgraph.h"
67 #include "BKE_customdata.h"
68 #include "BKE_global.h"
69 #include "BKE_library.h"
71 #include "BKE_object.h"
72 #include "BKE_utildefines.h"
73 #include "BKE_bmesh.h"
76 #include "BKE_verse.h"
79 #include "BIF_cursors.h"
80 #include "BIF_editmesh.h"
82 #include "BIF_glutil.h"
83 #include "BIF_graphics.h"
84 #include "BIF_interface.h"
85 #include "BIF_mywindow.h"
86 #include "BIF_screen.h"
87 #include "BIF_space.h"
88 #include "BIF_resources.h"
89 #include "BIF_toolbox.h"
90 #include "BIF_transform.h"
91 #include "transform.h"
94 #include "BIF_verse.h"
97 #include "BDR_drawobject.h"
98 #include "BDR_editobject.h"
100 #include "BSE_view.h"
101 #include "BSE_edit.h"
104 #include "multires.h"
105 #include "mydevice.h"
107 #include "editmesh.h"
109 #include "MTC_vectorops.h"
111 #include "PIL_time.h"
113 #include "BLO_sys_types.h" // for intptr_t support
115 /* local prototypes ---------------*/
116 void bevel_menu(void);
117 static void free_tagged_edges_faces(EditEdge *eed, EditFace *efa);
119 /********* qsort routines *********/
122 typedef struct xvertsort {
127 static int vergxco(const void *v1, const void *v2)
129 const xvertsort *x1=v1, *x2=v2;
131 if( x1->x > x2->x ) return 1;
132 else if( x1->x < x2->x) return -1;
138 struct EditFace *efa;
142 static int vergface(const void *v1, const void *v2)
144 const struct facesort *x1=v1, *x2=v2;
146 if( x1->x > x2->x ) return 1;
147 else if( x1->x < x2->x) return -1;
152 /* *********************************** */
154 void convert_to_triface(int direction)
156 EditMesh *em = G.editMesh;
157 EditFace *efa, *efan, *next;
160 if(multires_test()) return;
166 if(efa->f & SELECT) {
167 /* choose shortest diagonal for split */
168 fac= len_v3v3(efa->v1->co, efa->v3->co) - len_v3v3(efa->v2->co, efa->v4->co);
169 /* this makes sure exact squares get split different in both cases */
170 if( (direction==0 && fac<FLT_EPSILON) || (direction && fac>0.0f) ) {
171 efan= EM_face_from_faces(efa, NULL, 0, 1, 2, -1);
172 if(efa->f & SELECT) EM_select_face(efan, 1);
173 efan= EM_face_from_faces(efa, NULL, 0, 2, 3, -1);
174 if(efa->f & SELECT) EM_select_face(efan, 1);
177 efan= EM_face_from_faces(efa, NULL, 0, 1, 3, -1);
178 if(efa->f & SELECT) EM_select_face(efan, 1);
179 efan= EM_face_from_faces(efa, NULL, 1, 2, 3, -1);
180 if(efa->f & SELECT) EM_select_face(efan, 1);
183 BLI_remlink(&em->faces, efa);
190 EM_fgon_flags(); // redo flags and indices for fgons
193 if(G.editMesh->vnode)
194 sync_all_versefaces_with_editfaces((VNode*)G.editMesh->vnode);
196 BIF_undo_push("Convert Quads to Triangles");
200 int removedoublesflag(short flag, short automerge, float limit) /* return amount */
203 flag - Test with vert->flags
204 automerge - Alternative operation, merge unselected into selected.
205 Used for "Auto Weld" mode. warning.
206 limit - Quick manhattan distance between verts.
209 EditMesh *em = G.editMesh;
210 /* all verts with (flag & 'flag') are being evaluated */
211 EditVert *eve, *v1, *nextve;
212 EditEdge *eed, *e1, *nexted;
213 EditFace *efa, *nextvl;
214 xvertsort *sortblock, *sb, *sb1;
215 struct facesort *vlsortblock, *vsb, *vsb1;
216 int a, b, test, amount;
218 if(multires_test()) return 0;
221 /* flag 128 is cleared, count */
223 /* Normal non weld operation */
224 eve= em->verts.first;
228 if(eve->h==0 && (automerge || (eve->f & flag))) amount++;
231 if(amount==0) return 0;
233 /* allocate memory and qsort */
234 sb= sortblock= MEM_mallocN(sizeof(xvertsort)*amount,"sortremovedoub");
235 eve= em->verts.first;
237 if(eve->h==0 && (automerge || (eve->f & flag))) {
238 sb->x= eve->co[0]+eve->co[1]+eve->co[2];
244 qsort(sortblock, amount, sizeof(xvertsort), vergxco);
247 /* test for doubles */
250 for(a=0; a<amount; a++, sb++) {
252 if( (eve->f & 128)==0 ) {
254 for(b=a+1; b<amount && (eve->f & 128)==0; b++, sb1++) {
255 if(sb1->x - sb->x > limit) break;
257 /* when automarge, only allow unselected->selected */
259 if( (v1->f & 128)==0 ) {
260 if ((eve->f & flag)==0 && (v1->f & flag)==1) {
261 if( (float)fabs(v1->co[0]-eve->co[0])<=limit &&
262 (float)fabs(v1->co[1]-eve->co[1])<=limit &&
263 (float)fabs(v1->co[2]-eve->co[2])<=limit)
268 } else if( (eve->f & flag)==1 && (v1->f & flag)==0 ) {
269 if( (float)fabs(v1->co[0]-eve->co[0])<=limit &&
270 (float)fabs(v1->co[1]-eve->co[1])<=limit &&
271 (float)fabs(v1->co[2]-eve->co[2])<=limit)
282 for(a=0; a<amount; a++, sb++) {
284 if( (eve->f & 128)==0 ) {
286 for(b=a+1; b<amount; b++, sb1++) {
287 /* first test: simpel dist */
288 if(sb1->x - sb->x > limit) break;
291 /* second test: is vertex allowed */
292 if( (v1->f & 128)==0 ) {
293 if( (float)fabs(v1->co[0]-eve->co[0])<=limit &&
294 (float)fabs(v1->co[1]-eve->co[1])<=limit &&
295 (float)fabs(v1->co[2]-eve->co[2])<=limit)
305 MEM_freeN(sortblock);
308 for(eve = em->verts.first; eve; eve=eve->next)
309 if((eve->f & flag) && (eve->f & 128))
310 EM_data_interp_from_verts(eve, eve->tmp.v, eve->tmp.v, 0.5f);
312 /* test edges and insert again */
313 eed= em->edges.first;
323 if( (eed->v1->f & 128) || (eed->v2->f & 128) ) {
326 if(eed->v1->f & 128) eed->v1 = eed->v1->tmp.v;
327 if(eed->v2->f & 128) eed->v2 = eed->v2->tmp.v;
328 e1= addedgelist(eed->v1, eed->v2, eed);
335 if(e1!=eed) free_editedge(eed);
341 /* first count amount of test faces */
342 efa= (struct EditFace *)em->faces.first;
346 if(efa->v1->f & 128) efa->f1= 1;
347 else if(efa->v2->f & 128) efa->f1= 1;
348 else if(efa->v3->f & 128) efa->f1= 1;
349 else if(efa->v4 && (efa->v4->f & 128)) efa->f1= 1;
351 if(efa->f1==1) amount++;
355 /* test faces for double vertices, and if needed remove them */
356 efa= (struct EditFace *)em->faces.first;
361 if(efa->v1->f & 128) efa->v1= efa->v1->tmp.v;
362 if(efa->v2->f & 128) efa->v2= efa->v2->tmp.v;
363 if(efa->v3->f & 128) efa->v3= efa->v3->tmp.v;
364 if(efa->v4 && (efa->v4->f & 128)) efa->v4= efa->v4->tmp.v;
367 if(efa->v1==efa->v2) test+=1;
368 if(efa->v2==efa->v3) test+=2;
369 if(efa->v3==efa->v1) test+=4;
370 if(efa->v4==efa->v1) test+=8;
371 if(efa->v3==efa->v4) test+=16;
372 if(efa->v2==efa->v4) test+=32;
376 if(test==1 || test==2) {
381 EM_data_interp_from_faces(efa, NULL, efa, 0, 2, 3, 3);
385 else if(test==8 || test==16) {
390 BLI_remlink(&em->faces, efa);
396 BLI_remlink(&em->faces, efa);
403 /* set edge pointers */
404 efa->e1= findedgelist(efa->v1, efa->v2);
405 efa->e2= findedgelist(efa->v2, efa->v3);
407 efa->e3= findedgelist(efa->v3, efa->v1);
411 efa->e3= findedgelist(efa->v3, efa->v4);
412 efa->e4= findedgelist(efa->v4, efa->v1);
419 /* double faces: sort block */
420 /* count again, now all selected faces */
422 efa= em->faces.first;
425 if(faceselectedOR(efa, 1)) {
433 /* double faces: sort block */
434 vsb= vlsortblock= MEM_mallocN(sizeof(struct facesort)*amount, "sortremovedoub");
435 efa= em->faces.first;
438 if(efa->v4) vsb->x= (uintptr_t) MIN4( (uintptr_t)efa->v1, (uintptr_t)efa->v2, (uintptr_t)efa->v3, (uintptr_t)efa->v4);
439 else vsb->x= (uintptr_t) MIN3( (uintptr_t)efa->v1, (uintptr_t)efa->v2, (uintptr_t)efa->v3);
447 qsort(vlsortblock, amount, sizeof(struct facesort), vergface);
450 for(a=0; a<amount; a++) {
452 if( (efa->f1 & 128)==0 ) {
455 for(b=a+1; b<amount; b++) {
457 /* first test: same pointer? */
458 if(vsb->x != vsb1->x) break;
460 /* second test: is test permitted? */
462 if( (efa->f1 & 128)==0 ) {
463 if( compareface(efa, vsb->efa)) efa->f1 |= 128;
472 MEM_freeN(vlsortblock);
474 /* remove double faces */
475 efa= (struct EditFace *)em->faces.first;
479 BLI_remlink(&em->faces, efa);
486 /* remove double vertices */
488 eve= (struct EditVert *)em->verts.first;
491 if(automerge || eve->f & flag) {
494 BLI_remlink(&em->verts, eve);
502 if((a>0) && (G.editMesh->vnode)) {
503 sync_all_verseverts_with_editverts((VNode*)G.editMesh->vnode);
504 sync_all_versefaces_with_editfaces((VNode*)G.editMesh->vnode);
508 return a; /* amount */
511 /* called from buttons */
512 static void xsortvert_flag__doSetX(void *userData, EditVert *eve, int x, int y, int index)
514 xvertsort *sortblock = userData;
516 sortblock[index].x = x;
518 void xsortvert_flag(int flag)
520 EditMesh *em = G.editMesh;
521 /* all verts with (flag & 'flag') are sorted */
523 xvertsort *sortblock;
525 int i, amount = BLI_countlist(&em->verts);
527 if(multires_test()) return;
529 sortblock = MEM_callocN(sizeof(xvertsort)*amount,"xsort");
530 for (i=0,eve=em->verts.first; eve; i++,eve=eve->next)
532 sortblock[i].v1 = eve;
533 mesh_foreachScreenVert(xsortvert_flag__doSetX, sortblock, 0);
534 qsort(sortblock, amount, sizeof(xvertsort), vergxco);
536 /* make temporal listbase */
537 tbase.first= tbase.last= 0;
538 for (i=0; i<amount; i++) {
539 eve = sortblock[i].v1;
542 BLI_remlink(&em->verts, eve);
543 BLI_addtail(&tbase, eve);
547 addlisttolist(&em->verts, &tbase);
549 MEM_freeN(sortblock);
552 if(G.editMesh->vnode)
553 sync_all_versefaces_with_editfaces((VNode*)G.editMesh->vnode);
556 BIF_undo_push("Xsort");
560 /* called from buttons */
561 void hashvert_flag(int flag)
563 /* switch vertex order using hash table */
564 EditMesh *em = G.editMesh;
566 struct xvertsort *sortblock, *sb, onth, *newsort;
570 if(multires_test()) return;
573 eve= em->verts.first;
576 if(eve->f & flag) amount++;
579 if(amount==0) return;
581 /* allocate memory */
582 sb= sortblock= (struct xvertsort *)MEM_mallocN(sizeof(struct xvertsort)*amount,"sortremovedoub");
583 eve= em->verts.first;
595 for(a=0; a<amount; a++, sb++) {
596 b= (int)(amount*BLI_drand());
597 if(b>=0 && b<amount) {
598 newsort= sortblock+b;
605 /* make temporal listbase */
606 tbase.first= tbase.last= 0;
610 BLI_remlink(&em->verts, eve);
611 BLI_addtail(&tbase, eve);
615 addlisttolist(&em->verts, &tbase);
617 MEM_freeN(sortblock);
619 if(G.editMesh->vnode)
620 sync_all_versefaces_with_editfaces((VNode*)G.editMesh->vnode);
622 BIF_undo_push("Hash");
626 /* generic extern called extruder */
627 void extrude_mesh(void)
629 float nor[3]= {0.0, 0.0, 0.0};
630 short nr, transmode= 0;
633 if(multires_test()) return;
635 if(G.scene->selectmode & SCE_SELECT_VERTEX) {
636 if(G.totvertsel==0) nr= 0;
637 else if(G.totvertsel==1) nr= 4;
638 else if(G.totedgesel==0) nr= 4;
639 else if(G.totfacesel==0)
640 nr= pupmenu("Extrude %t|Only Edges%x3|Only Vertices%x4");
641 else if(G.totfacesel==1)
642 nr= pupmenu("Extrude %t|Region %x1|Only Edges%x3|Only Vertices%x4");
644 nr= pupmenu("Extrude %t|Region %x1||Individual Faces %x2|Only Edges%x3|Only Vertices%x4");
646 else if(G.scene->selectmode & SCE_SELECT_EDGE) {
647 if (G.totedgesel==0) nr = 0;
648 else if (G.totedgesel==1) nr = 3;
649 else if(G.totfacesel==0) nr = 3;
650 else if(G.totfacesel==1)
651 nr= pupmenu("Extrude %t|Region %x1|Only Edges%x3");
653 nr= pupmenu("Extrude %t|Region %x1||Individual Faces %x2|Only Edges%x3");
656 if (G.totfacesel == 0) nr = 0;
657 else if (G.totfacesel == 1) nr = 1;
659 nr= pupmenu("Extrude %t|Region %x1||Individual Faces %x2");
664 if(nr==1) transmode= extrudeflag(SELECT, nor);
665 else if(nr==4) transmode= extrudeflag_verts_indiv(SELECT, nor);
666 else if(nr==3) transmode= extrudeflag_edges_indiv(SELECT, nor);
667 else transmode= extrudeflag_face_indiv(SELECT, nor);
670 error("No valid selection");
676 /* We need to force immediate calculation here because
677 * transform may use derived objects (which are now stale).
679 * This shouldn't be necessary, derived queries should be
680 * automatically building this data if invalid. Or something.
682 DAG_object_flush_update(G.scene, G.obedit, OB_RECALC_DATA);
683 object_handle_update(G.obedit);
685 /* individual faces? */
686 BIF_TransformSetUndo("Extrude");
688 initTransform(TFM_SHRINKFATTEN, CTX_NO_PET|CTX_NO_MIRROR);
692 initTransform(TFM_TRANSLATION, CTX_NO_PET|CTX_NO_MIRROR);
694 mul_m4_v3(G.obedit->obmat, nor);
695 sub_v3_v3v3(nor, nor, G.obedit->obmat[3]);
696 BIF_setSingleAxisConstraint(nor, "along normal");
704 void split_mesh(void)
708 if(multires_test()) return;
710 if(okee(" Split ")==0) return;
714 /* make duplicate first */
715 adduplicateflag(SELECT);
716 /* old faces have flag 128 set, delete them */
718 recalc_editnormals();
723 allqueue(REDRAWVIEW3D, 0);
724 DAG_object_flush_update(G.scene, G.obedit, OB_RECALC_DATA);
727 if(G.editMesh->vnode)
728 sync_all_versefaces_with_editfaces((VNode*)G.editMesh->vnode);
731 BIF_undo_push("Split");
735 void extrude_repeat_mesh(int steps, float offs)
737 float dvec[3], tmat[3][3], bmat[3][3], nor[3]= {0.0, 0.0, 0.0};
741 if(multires_test()) return;
744 dvec[0]= G.vd->persinv[2][0];
745 dvec[1]= G.vd->persinv[2][1];
746 dvec[2]= G.vd->persinv[2][2];
752 /* base correction */
753 copy_m3_m4(bmat, G.obedit->obmat);
754 invert_m3_m3(tmat, bmat);
755 mul_m3_v3(tmat, dvec);
757 for(a=0; a<steps; a++) {
758 extrudeflag(SELECT, nor);
759 translateflag(SELECT, dvec);
762 recalc_editnormals();
767 allqueue(REDRAWVIEW3D, 0);
768 DAG_object_flush_update(G.scene, G.obedit, OB_RECALC_DATA);
770 BIF_undo_push("Extrude Repeat");
773 void spin_mesh(int steps, float degr, float *dvec, int mode)
775 EditMesh *em = G.editMesh;
776 EditVert *eve,*nextve;
777 float nor[3]= {0.0, 0.0, 0.0};
778 float *curs, si,n[3],q[4],cmat[3][3],imat[3][3], tmat[3][3];
779 float cent[3],bmat[3][3];
784 if(multires_test()) return;
786 /* imat and center and size */
787 copy_m3_m4(bmat, G.obedit->obmat);
788 invert_m3_m3(imat,bmat);
792 cent[0]-= G.obedit->obmat[3][0];
793 cent[1]-= G.obedit->obmat[3][1];
794 cent[2]-= G.obedit->obmat[3][2];
795 mul_m3_v3(imat, cent);
797 phi= degr*M_PI/360.0;
799 if(G.scene->toolsettings->editbutflag & B_CLOCKWISE) phi= -phi;
802 n[0]= G.vd->viewinv[1][0];
803 n[1]= G.vd->viewinv[1][1];
804 n[2]= G.vd->viewinv[1][2];
806 n[0]= G.vd->viewinv[2][0];
807 n[1]= G.vd->viewinv[2][1];
808 n[2]= G.vd->viewinv[2][2];
812 q[0]= (float)cos(phi);
817 quat_to_mat3( cmat,q);
819 mul_m3_m3m3(tmat,cmat,bmat);
820 mul_m3_m3m3(bmat,imat,tmat);
822 if(mode==0) if(G.scene->toolsettings->editbutflag & B_KEEPORIG) adduplicateflag(1);
825 for(a=0;a<steps;a++) {
826 if(mode==0) ok= extrudeflag(SELECT, nor);
827 else adduplicateflag(SELECT);
829 error("No valid vertices are selected");
832 rotateflag(SELECT, cent, bmat);
834 mul_m3_v3(bmat,dvec);
835 translateflag(SELECT, dvec);
840 /* no vertices or only loose ones selected, remove duplicates */
841 eve= em->verts.first;
844 if(eve->f & SELECT) {
845 BLI_remlink(&em->verts,eve);
851 recalc_editnormals();
855 allqueue(REDRAWVIEW3D, 0);
856 DAG_object_flush_update(G.scene, G.obedit, OB_RECALC_DATA);
859 if(dvec==NULL) BIF_undo_push("Spin");
862 void screw_mesh(int steps, int turns)
864 EditMesh *em = G.editMesh;
865 EditVert *eve,*v1=0,*v2=0;
867 float dvec[3], nor[3];
870 if(multires_test()) return;
873 eve= em->verts.first;
878 /* edges set flags in verts */
879 eed= em->edges.first;
881 if(eed->v1->f & SELECT) {
882 if(eed->v2->f & SELECT) {
883 /* watch: f1 is a byte */
884 if(eed->v1->f1<2) eed->v1->f1++;
885 if(eed->v2->f1<2) eed->v2->f1++;
890 /* find two vertices with eve->f1==1, more or less is wrong */
891 eve= em->verts.first;
895 else if(v2==0) v2= eve;
904 error("You have to select a string of connected vertices too");
909 dvec[0]= ( (v1->co[0]- v2->co[0]) )/(steps);
910 dvec[1]= ( (v1->co[1]- v2->co[1]) )/(steps);
911 dvec[2]= ( (v1->co[2]- v2->co[2]) )/(steps);
913 VECCOPY(nor, G.obedit->obmat[2]);
915 if(nor[0]*dvec[0]+nor[1]*dvec[1]+nor[2]*dvec[2]>0.000) {
921 spin_mesh(turns*steps, turns*360, dvec, 0);
923 BIF_undo_push("Spin");
927 static void erase_edges(ListBase *l)
929 EditEdge *ed, *nexted;
931 ed = (EditEdge *) l->first;
934 if( (ed->v1->f & SELECT) || (ed->v2->f & SELECT) ) {
942 static void erase_faces(ListBase *l)
946 f = (EditFace *) l->first;
950 if( faceselectedOR(f, SELECT) ) {
958 static void erase_vertices(ListBase *l)
962 v = (EditVert *) l->first;
973 void delete_mesh(void)
975 EditMesh *em = G.editMesh;
976 EditFace *efa, *nextvl;
977 EditVert *eve,*nextve;
978 EditEdge *eed,*nexted;
984 if(multires_test()) return;
986 event= pupmenu("Erase %t|Vertices%x10|Edges%x1|Faces%x2|All%x3|Edges & Faces%x4|Only Faces%x5|Edge Loop%x6");
990 str= "Erase Vertices";
991 erase_edges(&em->edges);
992 erase_faces(&em->faces);
993 erase_vertices(&em->verts);
996 if(!EdgeLoopDelete())
999 str= "Erase Edge Loop";
1002 str= "Erase Edges & Faces";
1003 efa= em->faces.first;
1006 /* delete only faces with 1 or more edges selected */
1008 if(efa->e1->f & SELECT) count++;
1009 if(efa->e2->f & SELECT) count++;
1010 if(efa->e3->f & SELECT) count++;
1011 if(efa->e4 && (efa->e4->f & SELECT)) count++;
1013 BLI_remlink(&em->faces, efa);
1018 eed= em->edges.first;
1021 if(eed->f & SELECT) {
1027 efa= em->faces.first;
1031 if( efa->v1->f & SELECT) event++;
1032 if( efa->v2->f & SELECT) event++;
1033 if( efa->v3->f & SELECT) event++;
1034 if(efa->v4 && (efa->v4->f & SELECT)) event++;
1037 BLI_remlink(&em->faces, efa);
1046 efa= em->faces.first;
1050 if( efa->e1->f & SELECT) event++;
1051 if( efa->e2->f & SELECT) event++;
1052 if( efa->e3->f & SELECT) event++;
1053 if(efa->e4 && (efa->e4->f & SELECT)) event++;
1056 BLI_remlink(&em->faces, efa);
1061 eed= em->edges.first;
1064 if(eed->f & SELECT) {
1070 /* to remove loose vertices: */
1071 eed= em->edges.first;
1073 if( eed->v1->f & SELECT) eed->v1->f-=SELECT;
1074 if( eed->v2->f & SELECT) eed->v2->f-=SELECT;
1077 eve= em->verts.first;
1080 if(eve->f & SELECT) {
1081 BLI_remlink(&em->verts,eve);
1090 delfaceflag(SELECT);
1094 if(em->verts.first) free_vertlist(&em->verts);
1095 if(em->edges.first) free_edgelist(&em->edges);
1096 if(em->faces.first) free_facelist(&em->faces);
1097 if(em->selected.first) BLI_freelistN(&(em->selected));
1100 str= "Erase Only Faces";
1101 efa= em->faces.first;
1104 if(efa->f & SELECT) {
1105 BLI_remlink(&em->faces, efa);
1112 EM_fgon_flags(); // redo flags and indices for fgons
1115 allqueue(REDRAWVIEW3D, 0);
1116 DAG_object_flush_update(G.scene, G.obedit, OB_RECALC_DATA);
1121 /* Got this from scanfill.c. You will need to juggle around the
1122 * callbacks for the scanfill.c code a bit for this to work. */
1123 void fill_mesh(void)
1125 EditMesh *em = G.editMesh;
1127 EditEdge *eed,*e1,*nexted;
1128 EditFace *efa,*nextvl, *efan;
1131 if(G.obedit==0 || (G.obedit->type!=OB_MESH)) return;
1132 if(multires_test()) return;
1136 /* copy all selected vertices */
1137 eve= em->verts.first;
1139 if(eve->f & SELECT) {
1140 v1= BLI_addfillvert(eve->co);
1143 v1->xs= 0; // used for counting edges
1147 /* copy all selected edges */
1148 eed= em->edges.first;
1150 if( (eed->v1->f & SELECT) && (eed->v2->f & SELECT) ) {
1151 e1= BLI_addfilledge(eed->v1->tmp.v, eed->v2->tmp.v);
1157 /* from all selected faces: remove vertices and edges to prevent doubles */
1158 /* all edges add values, faces subtract,
1159 then remove edges with vertices ->xs<2 */
1160 efa= em->faces.first;
1164 if( faceselectedAND(efa, 1) ) {
1165 efa->v1->tmp.v->xs--;
1166 efa->v2->tmp.v->xs--;
1167 efa->v3->tmp.v->xs--;
1168 if(efa->v4) efa->v4->tmp.v->xs--;
1174 if(ok) { /* there are faces selected */
1175 eed= filledgebase.first;
1178 if(eed->v1->xs<2 || eed->v2->xs<2) {
1179 BLI_remlink(&filledgebase,eed);
1185 if(BLI_edgefill(0, (G.obedit && G.obedit->actcol)?(G.obedit->actcol-1):0)) {
1186 efa= fillfacebase.first;
1188 /* normals default pointing up */
1189 efan= addfacelist(efa->v3->tmp.v, efa->v2->tmp.v,
1190 efa->v1->tmp.v, 0, NULL, NULL);
1191 if(efan) EM_select_face(efan, 1);
1201 allqueue(REDRAWVIEW3D, 0);
1202 DAG_object_flush_update(G.scene, G.obedit, OB_RECALC_DATA);
1205 if(G.editMesh->vnode)
1206 sync_all_versefaces_with_editfaces((VNode*)G.editMesh->vnode);
1209 BIF_undo_push("Fill");
1212 /*-------------------------------------------------------------------------------*/
1213 /*--------------------------- Edge Based Subdivide ------------------------------*/
1220 /*used by faceloop cut to select only edges valid for edge slide*/
1221 #define DOUBLEOPFILL 16
1223 /* calculates offset for co, based on fractal, sphere or smooth settings */
1224 static void alter_co(float *co, EditEdge *edge, float rad, int beauty, float perc)
1228 if(beauty & B_SMOOTH) {
1229 /* we calculate an offset vector vec1[], to be added to *co */
1230 float len, fac, nor[3], nor1[3], nor2[3];
1232 sub_v3_v3v3(nor, edge->v1->co, edge->v2->co);
1233 len= 0.5f*normalize_v3(nor);
1235 VECCOPY(nor1, edge->v1->no);
1236 VECCOPY(nor2, edge->v2->no);
1239 fac= nor[0]*nor1[0] + nor[1]*nor1[1] + nor[2]*nor1[2] ;
1241 vec1[0]= fac*nor1[0];
1242 vec1[1]= fac*nor1[1];
1243 vec1[2]= fac*nor1[2];
1246 fac= -nor[0]*nor2[0] - nor[1]*nor2[1] - nor[2]*nor2[2] ;
1248 vec1[0]+= fac*nor2[0];
1249 vec1[1]+= fac*nor2[1];
1250 vec1[2]+= fac*nor2[2];
1261 if(rad > 0.0) { /* subdivide sphere */
1267 else if(rad< 0.0) { /* fractal subdivide */
1268 fac= rad* len_v3v3(edge->v1->co, edge->v2->co);
1269 vec1[0]= fac*(float)(0.5-BLI_drand());
1270 vec1[1]= fac*(float)(0.5-BLI_drand());
1271 vec1[2]= fac*(float)(0.5-BLI_drand());
1272 add_v3_v3v3(co, co, vec1);
1278 /* assumes in the edge is the correct interpolated vertices already */
1279 /* percent defines the interpolation, rad and beauty are for special options */
1280 /* results in new vertex with correct coordinate, vertex normal and weight group info */
1281 static EditVert *subdivide_edge_addvert(EditEdge *edge, float rad, int beauty, float percent)
1286 co[0] = (edge->v2->co[0]-edge->v1->co[0])*percent + edge->v1->co[0];
1287 co[1] = (edge->v2->co[1]-edge->v1->co[1])*percent + edge->v1->co[1];
1288 co[2] = (edge->v2->co[2]-edge->v1->co[2])*percent + edge->v1->co[2];
1290 /* offset for smooth or sphere or fractal */
1291 alter_co(co, edge, rad, beauty, percent);
1293 /* clip if needed by mirror modifier */
1295 if ( edge->v1->f2 & edge->v2->f2 & 1) {
1298 if ( edge->v1->f2 & edge->v2->f2 & 2) {
1301 if ( edge->v1->f2 & edge->v2->f2 & 4) {
1306 ev = addvertlist(co, NULL);
1308 /* vert data (vgroups, ..) */
1309 EM_data_interp_from_verts(edge->v1, edge->v2, ev, percent);
1312 ev->no[0] = (edge->v2->no[0]-edge->v1->no[0])*percent + edge->v1->no[0];
1313 ev->no[1] = (edge->v2->no[1]-edge->v1->no[1])*percent + edge->v1->no[1];
1314 ev->no[2] = (edge->v2->no[2]-edge->v1->no[2])*percent + edge->v1->no[2];
1315 normalize_v3(ev->no);
1320 static void flipvertarray(EditVert** arr, short size)
1325 for(i=0; i<size/2; i++) {
1327 arr[i] = arr[size-i-1];
1328 arr[size-i-1] = hold;
1332 static void facecopy(EditFace *source, EditFace *target)
1334 EditMesh *em= G.editMesh;
1335 float *v1 = source->v1->co, *v2 = source->v2->co, *v3 = source->v3->co;
1336 float *v4 = source->v4? source->v4->co: NULL;
1339 CustomData_em_copy_data(&em->fdata, &em->fdata, source->data, &target->data);
1341 target->mat_nr = source->mat_nr;
1342 target->flag = source->flag;
1343 target->h = source->h;
1345 interp_weights_face_v3( w[0],v1, v2, v3, v4, target->v1->co);
1346 interp_weights_face_v3( w[1],v1, v2, v3, v4, target->v2->co);
1347 interp_weights_face_v3( w[2],v1, v2, v3, v4, target->v3->co);
1349 interp_weights_face_v3( w[3],v1, v2, v3, v4, target->v4->co);
1351 CustomData_em_interp(&em->fdata, &source->data, NULL, (float*)w, 1, target->data);
1354 static void fill_quad_single(EditFace *efa, struct GHash *gh, int numcuts, int seltype)
1356 EditEdge *cedge=NULL;
1357 EditVert *v[4], **verts;
1359 short start=0, end, left, right, vertsize,i;
1366 if(efa->e1->f & SELECT) { cedge = efa->e1; start = 0;}
1367 else if(efa->e2->f & SELECT) { cedge = efa->e2; start = 1;}
1368 else if(efa->e3->f & SELECT) { cedge = efa->e3; start = 2;}
1369 else if(efa->e4->f & SELECT) { cedge = efa->e4; start = 3;}
1371 // Point verts to the array of new verts for cedge
1372 verts = BLI_ghash_lookup(gh, cedge);
1373 //This is the index size of the verts array
1374 vertsize = numcuts+2;
1376 // Is the original v1 the same as the first vert on the selected edge?
1377 // if not, the edge is running the opposite direction in this face so flip
1378 // the array to the correct direction
1380 if(verts[0] != v[start]) {flipvertarray(verts,numcuts+2);}
1383 right = (start+3)%4;
1386 We should have something like this now
1397 where start,end,left, right are indexes of EditFace->v1, etc (stored in v)
1398 and 0,1,2... are the indexes of the new verts stored in verts
1400 We will fill this case like this or this depending on even or odd cuts
1402 |---*---*---| |---*---|
1406 ------------- ---------
1410 if(vertsize % 2 == 0) {
1411 hold = addfacelist(verts[(vertsize-1)/2],verts[((vertsize-1)/2)+1],v[left],v[right], NULL,NULL);
1412 hold->e2->f2 |= EDGEINNER;
1413 hold->e4->f2 |= EDGEINNER;
1415 hold = addfacelist(verts[(vertsize-1)/2],v[left],v[right],NULL, NULL,NULL);
1416 hold->e1->f2 |= EDGEINNER;
1417 hold->e3->f2 |= EDGEINNER;
1422 for(i=0;i<(vertsize-1)/2;i++) {
1423 hold = addfacelist(verts[i],verts[i+1],v[right],NULL,NULL,NULL);
1425 if(i+1 != (vertsize-1)/2) {
1426 if(seltype == SUBDIV_SELECT_INNER) {
1427 hold->e2->f2 |= EDGEINNER;
1430 hold = addfacelist(verts[vertsize-2-i],verts[vertsize-1-i],v[left],NULL,NULL,NULL);
1432 if(i+1 != (vertsize-1)/2) {
1433 if(seltype == SUBDIV_SELECT_INNER) {
1434 hold->e3->f2 |= EDGEINNER;
1440 static void fill_tri_single(EditFace *efa, struct GHash *gh, int numcuts, int seltype)
1442 EditEdge *cedge=NULL;
1443 EditVert *v[3], **verts;
1445 short start=0, end, op, vertsize,i;
1451 if(efa->e1->f & SELECT) { cedge = efa->e1; start = 0;}
1452 else if(efa->e2->f & SELECT) { cedge = efa->e2; start = 1;}
1453 else if(efa->e3->f & SELECT) { cedge = efa->e3; start = 2;}
1455 // Point verts to the array of new verts for cedge
1456 verts = BLI_ghash_lookup(gh, cedge);
1457 //This is the index size of the verts array
1458 vertsize = numcuts+2;
1460 // Is the original v1 the same as the first vert on the selected edge?
1461 // if not, the edge is running the opposite direction in this face so flip
1462 // the array to the correct direction
1464 if(verts[0] != v[start]) {flipvertarray(verts,numcuts+2);}
1469 We should have something like this now
1482 where start,end,op are indexes of EditFace->v1, etc (stored in v)
1483 and 0,1,2... are the indexes of the new verts stored in verts
1485 We will fill this case like this or this depending on even or odd cuts
1499 for(i=0;i<(vertsize-1);i++) {
1500 hold = addfacelist(verts[i],verts[i+1],v[op],NULL,NULL,NULL);
1501 if(i+1 != vertsize-1) {
1502 if(seltype == SUBDIV_SELECT_INNER) {
1503 hold->e2->f2 |= EDGEINNER;
1510 static void fill_quad_double_op(EditFace *efa, struct GHash *gh, int numcuts)
1512 EditEdge *cedge[2]={NULL, NULL};
1513 EditVert *v[4], **verts[2];
1515 short start=0, end, left, right, vertsize,i;
1522 if(efa->e1->f & SELECT) { cedge[0] = efa->e1; cedge[1] = efa->e3; start = 0;}
1523 else if(efa->e2->f & SELECT) { cedge[0] = efa->e2; cedge[1] = efa->e4; start = 1;}
1525 // Point verts[0] and [1] to the array of new verts for cedge[0] and cedge[1]
1526 verts[0] = BLI_ghash_lookup(gh, cedge[0]);
1527 verts[1] = BLI_ghash_lookup(gh, cedge[1]);
1528 //This is the index size of the verts array
1529 vertsize = numcuts+2;
1531 // Is the original v1 the same as the first vert on the selected edge?
1532 // if not, the edge is running the opposite direction in this face so flip
1533 // the array to the correct direction
1535 if(verts[0][0] != v[start]) {flipvertarray(verts[0],numcuts+2);}
1538 right = (start+3)%4;
1539 if(verts[1][0] != v[left]) {flipvertarray(verts[1],numcuts+2);}
1541 We should have something like this now
1553 We will fill this case like this or this depending on even or odd cuts
1563 for(i=0;i<vertsize-1;i++) {
1564 hold = addfacelist(verts[0][i],verts[0][i+1],verts[1][vertsize-2-i],verts[1][vertsize-1-i],NULL,NULL);
1565 if(i < vertsize-2) {
1566 hold->e2->f2 |= EDGEINNER;
1567 hold->e2->f2 |= DOUBLEOPFILL;
1573 static void fill_quad_double_adj_path(EditFace *efa, struct GHash *gh, int numcuts)
1575 EditEdge *cedge[2]={NULL, NULL};
1576 EditVert *v[4], **verts[2];
1578 short start=0, start2=0, vertsize,i;
1585 if(efa->e1->f & SELECT && efa->e2->f & SELECT) {cedge[0] = efa->e1; cedge[1] = efa->e2; start = 0; start2 = 1;}
1586 if(efa->e2->f & SELECT && efa->e3->f & SELECT) {cedge[0] = efa->e2; cedge[1] = efa->e3; start = 1; start2 = 2;}
1587 if(efa->e3->f & SELECT && efa->e4->f & SELECT) {cedge[0] = efa->e3; cedge[1] = efa->e4; start = 2; start2 = 3;}
1588 if(efa->e4->f & SELECT && efa->e1->f & SELECT) {cedge[0] = efa->e4; cedge[1] = efa->e1; start = 3; start2 = 0;}
1590 // Point verts[0] and [1] to the array of new verts for cedge[0] and cedge[1]
1591 verts[0] = BLI_ghash_lookup(gh, cedge[0]);
1592 verts[1] = BLI_ghash_lookup(gh, cedge[1]);
1593 //This is the index size of the verts array
1594 vertsize = numcuts+2;
1596 // Is the original v1 the same as the first vert on the selected edge?
1597 // if not, the edge is running the opposite direction in this face so flip
1598 // the array to the correct direction
1600 if(verts[0][0] != v[start]) {flipvertarray(verts[0],numcuts+2);}
1601 if(verts[1][0] != v[start2]) {flipvertarray(verts[1],numcuts+2);}
1603 We should have something like this now
1607 start2 0|---*---*---|
1615 We will fill this case like this or this depending on even or odd cuts
1625 // Make outside tris
1626 hold = addfacelist(verts[0][vertsize-2],verts[0][vertsize-1],verts[1][1],NULL,NULL,NULL);
1627 /* when ctrl is depressed, only want verts on the cutline selected */
1628 if (G.qual != LR_CTRLKEY)
1629 hold->e3->f2 |= EDGEINNER;
1631 hold = addfacelist(verts[0][0],verts[1][vertsize-1],v[(start2+2)%4],NULL,NULL,NULL);
1632 /* when ctrl is depressed, only want verts on the cutline selected */
1633 if (G.qual != LR_CTRLKEY)
1634 hold->e1->f2 |= EDGEINNER;
1636 //if(G.scene->toolsettings->editbutflag & B_AUTOFGON) {
1637 // hold->e1->h |= EM_FGON;
1641 for(i=0;i<numcuts;i++) {
1642 hold = addfacelist(verts[0][i],verts[0][i+1],verts[1][vertsize-1-(i+1)],verts[1][vertsize-1-i],NULL,NULL);
1643 hold->e2->f2 |= EDGEINNER;
1650 static void fill_quad_double_adj_fan(EditFace *efa, struct GHash *gh, int numcuts)
1652 EditEdge *cedge[2]={NULL, NULL};
1653 EditVert *v[4], *op=NULL, **verts[2];
1655 short start=0, start2=0, vertsize,i;
1662 if(efa->e1->f & SELECT && efa->e2->f & SELECT) {cedge[0] = efa->e1; cedge[1] = efa->e2; start = 0; start2 = 1; op = efa->v4;}
1663 if(efa->e2->f & SELECT && efa->e3->f & SELECT) {cedge[0] = efa->e2; cedge[1] = efa->e3; start = 1; start2 = 2; op = efa->v1;}
1664 if(efa->e3->f & SELECT && efa->e4->f & SELECT) {cedge[0] = efa->e3; cedge[1] = efa->e4; start = 2; start2 = 3; op = efa->v2;}
1665 if(efa->e4->f & SELECT && efa->e1->f & SELECT) {cedge[0] = efa->e4; cedge[1] = efa->e1; start = 3; start2 = 0; op = efa->v3;}
1668 // Point verts[0] and [1] to the array of new verts for cedge[0] and cedge[1]
1669 verts[0] = BLI_ghash_lookup(gh, cedge[0]);
1670 verts[1] = BLI_ghash_lookup(gh, cedge[1]);
1671 //This is the index size of the verts array
1672 vertsize = numcuts+2;
1674 // Is the original v1 the same as the first vert on the selected edge?
1675 // if not, the edge is running the opposite direction in this face so flip
1676 // the array to the correct direction
1678 if(verts[0][0] != v[start]) {flipvertarray(verts[0],numcuts+2);}
1679 if(verts[1][0] != v[start2]) {flipvertarray(verts[1],numcuts+2);}
1681 We should have something like this now
1685 start2 0|---*---*---|
1691 end2 3|-----------|op
1693 We will fill this case like this or this (warning horrible ascii art follows)
1703 for(i=0;i<=numcuts;i++) {
1704 hold = addfacelist(op,verts[1][numcuts-i],verts[1][numcuts-i+1],NULL,NULL,NULL);
1705 hold->e1->f2 |= EDGEINNER;
1708 hold = addfacelist(op,verts[0][i],verts[0][i+1],NULL,NULL,NULL);
1709 hold->e3->f2 |= EDGEINNER;
1714 static void fill_quad_double_adj_inner(EditFace *efa, struct GHash *gh, int numcuts)
1716 EditEdge *cedge[2]={NULL, NULL};
1717 EditVert *v[4], *op=NULL, **verts[2],**inner;
1719 short start=0, start2=0, vertsize,i;
1727 if(efa->e1->f & SELECT && efa->e2->f & SELECT) {cedge[0] = efa->e1; cedge[1] = efa->e2; start = 0; start2 = 1; op = efa->v4;}
1728 if(efa->e2->f & SELECT && efa->e3->f & SELECT) {cedge[0] = efa->e2; cedge[1] = efa->e3; start = 1; start2 = 2; op = efa->v1;}
1729 if(efa->e3->f & SELECT && efa->e4->f & SELECT) {cedge[0] = efa->e3; cedge[1] = efa->e4; start = 2; start2 = 3; op = efa->v2;}
1730 if(efa->e4->f & SELECT && efa->e1->f & SELECT) {cedge[0] = efa->e4; cedge[1] = efa->e1; start = 3; start2 = 0; op = efa->v3;}
1733 // Point verts[0] and [1] to the array of new verts for cedge[0] and cedge[1]
1734 verts[0] = BLI_ghash_lookup(gh, cedge[0]);
1735 verts[1] = BLI_ghash_lookup(gh, cedge[1]);
1736 //This is the index size of the verts array
1737 vertsize = numcuts+2;
1739 // Is the original v1 the same as the first vert on the selected edge?
1740 // if not, the edge is running the opposite direction in this face so flip
1741 // the array to the correct direction
1743 if(verts[0][0] != v[start]) {flipvertarray(verts[0],numcuts+2);}
1744 if(verts[1][0] != v[start2]) {flipvertarray(verts[1],numcuts+2);}
1746 We should have something like this now
1750 start2 0|---*---*---|
1756 end2 3|-----------|op
1758 We will fill this case like this or this (warning horrible ascii art follows)
1769 // Add Inner Vert(s)
1770 inner = MEM_mallocN(sizeof(EditVert*)*numcuts,"New inner verts");
1772 for(i=0;i<numcuts;i++) {
1773 co[0] = (verts[0][numcuts-i]->co[0] + verts[1][i+1]->co[0] ) / 2 ;
1774 co[1] = (verts[0][numcuts-i]->co[1] + verts[1][i+1]->co[1] ) / 2 ;
1775 co[2] = (verts[0][numcuts-i]->co[2] + verts[1][i+1]->co[2] ) / 2 ;
1776 inner[i] = addvertlist(co, NULL);
1777 inner[i]->f2 |= EDGEINNER;
1779 EM_data_interp_from_verts(verts[0][numcuts-i], verts[1][i+1], inner[i], 0.5f);
1783 hold = addfacelist(verts[0][numcuts+1],verts[1][1],inner[0],verts[0][numcuts],NULL,NULL);
1784 hold->e2->f2 |= EDGEINNER;
1785 hold->e3->f2 |= EDGEINNER;
1788 hold = addfacelist(verts[0][0],verts[0][1],inner[numcuts-1],op,NULL,NULL);
1789 hold->e2->f2 |= EDGEINNER;
1792 hold = addfacelist(op,inner[numcuts-1],verts[1][numcuts],verts[1][numcuts+1],NULL,NULL);
1793 hold->e2->f2 |= EDGEINNER;
1796 //if(G.scene->toolsettings->editbutflag & B_AUTOFGON) {
1797 // hold->e1->h |= EM_FGON;
1799 // Add Fill Quads (if # cuts > 1)
1801 for(i=0;i<numcuts-1;i++) {
1802 hold = addfacelist(inner[i],verts[1][i+1],verts[1][i+2],inner[i+1],NULL,NULL);
1803 hold->e1->f2 |= EDGEINNER;
1804 hold->e3->f2 |= EDGEINNER;
1807 hold = addfacelist(inner[i],inner[i+1],verts[0][numcuts-1-i],verts[0][numcuts-i],NULL,NULL);
1808 hold->e2->f2 |= EDGEINNER;
1809 hold->e4->f2 |= EDGEINNER;
1812 //if(G.scene->toolsettings->editbutflag & B_AUTOFGON) {
1813 // hold->e1->h |= EM_FGON;
1822 static void fill_tri_double(EditFace *efa, struct GHash *gh, int numcuts)
1824 EditEdge *cedge[2]={NULL, NULL};
1825 EditVert *v[3], **verts[2];
1827 short start=0, start2=0, vertsize,i;
1833 if(efa->e1->f & SELECT && efa->e2->f & SELECT) {cedge[0] = efa->e1; cedge[1] = efa->e2; start = 0; start2 = 1;}
1834 if(efa->e2->f & SELECT && efa->e3->f & SELECT) {cedge[0] = efa->e2; cedge[1] = efa->e3; start = 1; start2 = 2;}
1835 if(efa->e3->f & SELECT && efa->e1->f & SELECT) {cedge[0] = efa->e3; cedge[1] = efa->e1; start = 2; start2 = 0;}
1837 // Point verts[0] and [1] to the array of new verts for cedge[0] and cedge[1]
1838 verts[0] = BLI_ghash_lookup(gh, cedge[0]);
1839 verts[1] = BLI_ghash_lookup(gh, cedge[1]);
1840 //This is the index size of the verts array
1841 vertsize = numcuts+2;
1843 // Is the original v1 the same as the first vert on the selected edge?
1844 // if not, the edge is running the opposite direction in this face so flip
1845 // the array to the correct direction
1847 if(verts[0][0] != v[start]) {flipvertarray(verts[0],numcuts+2);}
1848 if(verts[1][0] != v[start2]) {flipvertarray(verts[1],numcuts+2);}
1850 We should have something like this now
1854 start2 0|---*---*---|
1862 We will fill this case like this or this depending on even or odd cuts
1873 hold = addfacelist(verts[0][vertsize-2],verts[0][vertsize-1],verts[1][1],NULL,NULL,NULL);
1874 hold->e3->f2 |= EDGEINNER;
1878 for(i=0;i<numcuts;i++) {
1879 hold = addfacelist(verts[0][i],verts[0][i+1],verts[1][vertsize-1-(i+1)],verts[1][vertsize-1-i],NULL,NULL);
1880 hold->e2->f2 |= EDGEINNER;
1885 static void fill_quad_triple(EditFace *efa, struct GHash *gh, int numcuts)
1887 EditEdge *cedge[3]={0};
1888 EditVert *v[4], **verts[3];
1890 short start=0, start2=0, start3=0, vertsize, i, repeats;
1897 if(!(efa->e1->f & SELECT)) {
1901 start = 1;start2 = 2;start3 = 3;
1903 if(!(efa->e2->f & SELECT)) {
1907 start = 2;start2 = 3;start3 = 0;
1909 if(!(efa->e3->f & SELECT)) {
1913 start = 3;start2 = 0;start3 = 1;
1915 if(!(efa->e4->f & SELECT)) {
1919 start = 0;start2 = 1;start3 = 2;
1921 // Point verts[0] and [1] to the array of new verts for cedge[0] and cedge[1]
1922 verts[0] = BLI_ghash_lookup(gh, cedge[0]);
1923 verts[1] = BLI_ghash_lookup(gh, cedge[1]);
1924 verts[2] = BLI_ghash_lookup(gh, cedge[2]);
1925 //This is the index size of the verts array
1926 vertsize = numcuts+2;
1928 // Is the original v1 the same as the first vert on the selected edge?
1929 // if not, the edge is running the opposite direction in this face so flip
1930 // the array to the correct direction
1932 if(verts[0][0] != v[start]) {flipvertarray(verts[0],numcuts+2);}
1933 if(verts[1][0] != v[start2]) {flipvertarray(verts[1],numcuts+2);}
1934 if(verts[2][0] != v[start3]) {flipvertarray(verts[2],numcuts+2);}
1936 We should have something like this now
1940 start3 0|---*---*---|3
1946 3|-----------|0 start
1948 We will fill this case like this or this depending on even or odd cuts
1949 there are a couple of differences. For odd cuts, there is a tri in the
1950 middle as well as 1 quad at the bottom (not including the extra quads
1953 For even cuts, there is a quad in the middle and 2 quads on the bottom
1955 they are numbered here for clarity
1957 1 outer tris and bottom quads
1976 |---*---*---*---*---|
1984 *-------------------*
1988 *-------------------*
1992 *-------------------*
1996 |-------------------|
2000 // Make outside tris
2001 hold = addfacelist(verts[0][vertsize-2],verts[0][vertsize-1],verts[1][1],NULL,NULL,NULL);
2002 hold->e3->f2 |= EDGEINNER;
2004 hold = addfacelist(verts[1][vertsize-2],verts[1][vertsize-1],verts[2][1],NULL,NULL,NULL);
2005 hold->e3->f2 |= EDGEINNER;
2008 hold = addfacelist(verts[0][0],verts[0][1],verts[2][vertsize-2],verts[2][vertsize-1],NULL,NULL);
2009 hold->e2->f2 |= EDGEINNER;
2011 //If it is even cuts, add the 2nd lower quad
2012 if(numcuts % 2 == 0) {
2013 hold = addfacelist(verts[0][1],verts[0][2],verts[2][vertsize-3],verts[2][vertsize-2],NULL,NULL);
2014 hold->e2->f2 |= EDGEINNER;
2016 // Also Make inner quad
2017 hold = addfacelist(verts[1][numcuts/2],verts[1][(numcuts/2)+1],verts[2][numcuts/2],verts[0][(numcuts/2)+1],NULL,NULL);
2018 hold->e3->f2 |= EDGEINNER;
2019 //if(G.scene->toolsettings->editbutflag & B_AUTOFGON) {
2020 // hold->e3->h |= EM_FGON;
2023 repeats = (numcuts / 2) -1;
2026 hold = addfacelist(verts[1][(numcuts/2)+1],verts[2][(numcuts/2)+1],verts[0][(numcuts/2)+1],NULL,NULL,NULL);
2027 hold->e2->f2 |= EDGEINNER;
2028 //if(G.scene->toolsettings->editbutflag & B_AUTOFGON) {
2029 // hold->e2->h |= EM_FGON;
2032 repeats = ((numcuts+1) / 2)-1;
2035 // cuts for 1 and 2 do not have the repeating quads
2036 if(numcuts < 3) {repeats = 0;}
2037 for(i=0;i<repeats;i++) {
2038 //Make side repeating Quads
2039 hold = addfacelist(verts[1][i+1],verts[1][i+2],verts[0][vertsize-i-3],verts[0][vertsize-i-2],NULL,NULL);
2040 hold->e2->f2 |= EDGEINNER;
2042 hold = addfacelist(verts[1][vertsize-i-3],verts[1][vertsize-i-2],verts[2][i+1],verts[2][i+2],NULL,NULL);
2043 hold->e4->f2 |= EDGEINNER;
2046 // Do repeating bottom quads
2047 for(i=0;i<repeats;i++) {
2048 if(numcuts % 2 == 1) {
2049 hold = addfacelist(verts[0][1+i],verts[0][2+i],verts[2][vertsize-3-i],verts[2][vertsize-2-i],NULL,NULL);
2051 hold = addfacelist(verts[0][2+i],verts[0][3+i],verts[2][vertsize-4-i],verts[2][vertsize-3-i],NULL,NULL);
2053 hold->e2->f2 |= EDGEINNER;
2059 static void fill_quad_quadruple(EditFace *efa, struct GHash *gh, int numcuts, float rad, int beauty)
2061 EditVert **verts[4], ***innerverts;
2064 short vertsize, i, j;
2066 // Point verts[0] and [1] to the array of new verts for cedge[0] and cedge[1]
2067 verts[0] = BLI_ghash_lookup(gh, efa->e1);
2068 verts[1] = BLI_ghash_lookup(gh, efa->e2);
2069 verts[2] = BLI_ghash_lookup(gh, efa->e3);
2070 verts[3] = BLI_ghash_lookup(gh, efa->e4);
2072 //This is the index size of the verts array
2073 vertsize = numcuts+2;
2075 // Is the original v1 the same as the first vert on the selected edge?
2076 // if not, the edge is running the opposite direction in this face so flip
2077 // the array to the correct direction
2079 if(verts[0][0] != efa->v1) {flipvertarray(verts[0],numcuts+2);}
2080 if(verts[1][0] != efa->v2) {flipvertarray(verts[1],numcuts+2);}
2081 if(verts[2][0] == efa->v3) {flipvertarray(verts[2],numcuts+2);}
2082 if(verts[3][0] == efa->v4) {flipvertarray(verts[3],numcuts+2);}
2084 We should have something like this now
2098 // we will fill a 2 dim array of editvert*s to make filling easier
2099 // the innervert order is shown
2110 innerverts = MEM_mallocN(sizeof(EditVert*)*(numcuts+2),"quad-quad subdiv inner verts outer array");
2111 for(i=0;i<numcuts+2;i++) {
2112 innerverts[i] = MEM_mallocN(sizeof(EditVert*)*(numcuts+2),"quad-quad subdiv inner verts inner array");
2115 // first row is e1 last row is e3
2116 for(i=0;i<numcuts+2;i++) {
2117 innerverts[0][i] = verts[0][(numcuts+1)-i];
2118 innerverts[numcuts+1][i] = verts[2][(numcuts+1)-i];
2121 for(i=1;i<=numcuts;i++) {
2122 /* we create a fake edge for the next loop */
2123 temp.v2 = innerverts[i][0] = verts[1][i];
2124 temp.v1 = innerverts[i][numcuts+1] = verts[3][i];
2126 for(j=1;j<=numcuts;j++) {
2127 float percent= (float)j/(float)(numcuts+1);
2129 innerverts[i][(numcuts+1)-j]= subdivide_edge_addvert(&temp, rad, beauty, percent);
2133 for(i=0;i<numcuts+1;i++) {
2134 for(j=0;j<numcuts+1;j++) {
2135 hold = addfacelist(innerverts[i][j+1],innerverts[i][j],innerverts[i+1][j],innerverts[i+1][j+1],NULL,NULL);
2136 hold->e1->f2 = EDGENEW;
2137 hold->e2->f2 = EDGENEW;
2138 hold->e3->f2 = EDGENEW;
2139 hold->e4->f2 = EDGENEW;
2141 if(i != 0) { hold->e1->f2 |= EDGEINNER; }
2142 if(j != 0) { hold->e2->f2 |= EDGEINNER; }
2143 if(i != numcuts) { hold->e3->f2 |= EDGEINNER; }
2144 if(j != numcuts) { hold->e4->f2 |= EDGEINNER; }
2149 // Clean up our dynamic multi-dim array
2150 for(i=0;i<numcuts+2;i++) {
2151 MEM_freeN(innerverts[i]);
2153 MEM_freeN(innerverts);
2156 static void fill_tri_triple(EditFace *efa, struct GHash *gh, int numcuts, float rad, int beauty)
2158 EditVert **verts[3], ***innerverts;
2159 short vertsize, i, j;
2163 // Point verts[0] and [1] to the array of new verts for cedge[0] and cedge[1]
2164 verts[0] = BLI_ghash_lookup(gh, efa->e1);
2165 verts[1] = BLI_ghash_lookup(gh, efa->e2);
2166 verts[2] = BLI_ghash_lookup(gh, efa->e3);
2168 //This is the index size of the verts array
2169 vertsize = numcuts+2;
2171 // Is the original v1 the same as the first vert on the selected edge?
2172 // if not, the edge is running the opposite direction in this face so flip
2173 // the array to the correct direction
2175 if(verts[0][0] != efa->v1) {flipvertarray(verts[0],numcuts+2);}
2176 if(verts[1][0] != efa->v2) {flipvertarray(verts[1],numcuts+2);}
2177 if(verts[2][0] != efa->v3) {flipvertarray(verts[2],numcuts+2);}
2179 We should have something like this now
2192 we will fill a 2 dim array of editvert*s to make filling easier
2210 innerverts = MEM_mallocN(sizeof(EditVert*)*(numcuts+2),"tri-tri subdiv inner verts outer array");
2211 for(i=0;i<numcuts+2;i++) {
2212 innerverts[i] = MEM_mallocN(sizeof(EditVert*)*((numcuts+2)-i),"tri-tri subdiv inner verts inner array");
2214 //top row is e3 backwards
2215 for(i=0;i<numcuts+2;i++) {
2216 innerverts[0][i] = verts[2][(numcuts+1)-i];
2219 for(i=1;i<=numcuts+1;i++) {
2220 //fake edge, first vert is from e1, last is from e2
2221 temp.v1= innerverts[i][0] = verts[0][i];
2222 temp.v2= innerverts[i][(numcuts+1)-i] = verts[1][(numcuts+1)-i];
2224 for(j=1;j<(numcuts+1)-i;j++) {
2225 float percent= (float)j/(float)((numcuts+1)-i);
2227 innerverts[i][((numcuts+1)-i)-j]= subdivide_edge_addvert(&temp, rad, beauty, 1-percent);
2231 // Now fill the verts with happy little tris :)
2232 for(i=0;i<=numcuts+1;i++) {
2233 for(j=0;j<(numcuts+1)-i;j++) {
2234 //We always do the first tri
2235 hold = addfacelist(innerverts[i][j+1],innerverts[i][j],innerverts[i+1][j],NULL,NULL,NULL);
2236 hold->e1->f2 |= EDGENEW;
2237 hold->e2->f2 |= EDGENEW;
2238 hold->e3->f2 |= EDGENEW;
2239 if(i != 0) { hold->e1->f2 |= EDGEINNER; }
2240 if(j != 0) { hold->e2->f2 |= EDGEINNER; }
2241 if(j+1 != (numcuts+1)-i) {hold->e3->f2 |= EDGEINNER;}
2244 //if there are more to come, we do the 2nd
2245 if(j+1 <= numcuts-i) {
2246 hold = addfacelist(innerverts[i+1][j],innerverts[i+1][j+1],innerverts[i][j+1],NULL,NULL,NULL);
2248 hold->e1->f2 |= EDGENEW;
2249 hold->e2->f2 |= EDGENEW;
2250 hold->e3->f2 |= EDGENEW;
2255 // Clean up our dynamic multi-dim array
2256 for(i=0;i<numcuts+2;i++) {
2257 MEM_freeN(innerverts[i]);
2259 MEM_freeN(innerverts);
2262 //Next two fill types are for knife exact only and are provided to allow for knifing through vertices
2263 //This means there is no multicut!
2264 static void fill_quad_doublevert(EditFace *efa, int v1, int v2){
2267 Depending on which two vertices have been knifed through (v1 and v2), we
2268 triangulate like the patterns below.
2276 if(v1 == 1 && v2 == 3){
2277 hold= addfacelist(efa->v1, efa->v2, efa->v3, 0, efa, NULL);
2278 hold->e1->f2 |= EDGENEW;
2279 hold->e2->f2 |= EDGENEW;
2280 hold->e3->f2 |= EDGENEW;
2281 hold->e3->f2 |= EDGEINNER;
2282 facecopy(efa, hold);
2284 hold= addfacelist(efa->v1, efa->v3, efa->v4, 0, efa, NULL);
2285 hold->e1->f2 |= EDGENEW;
2286 hold->e2->f2 |= EDGENEW;
2287 hold->e3->f2 |= EDGENEW;
2288 hold->e1->f2 |= EDGEINNER;
2289 facecopy(efa, hold);
2292 hold= addfacelist(efa->v1, efa->v2, efa->v4, 0, efa, NULL);
2293 hold->e1->f2 |= EDGENEW;
2294 hold->e2->f2 |= EDGENEW;
2295 hold->e3->f2 |= EDGENEW;
2296 hold->e2->f2 |= EDGEINNER;
2297 facecopy(efa, hold);
2299 hold= addfacelist(efa->v2, efa->v3, efa->v4, 0, efa, NULL);
2300 hold->e1->f2 |= EDGENEW;
2301 hold->e2->f2 |= EDGENEW;
2302 hold->e3->f2 |= EDGENEW;
2303 hold->e3->f2 |= EDGEINNER;
2304 facecopy(efa, hold);
2308 static void fill_quad_singlevert(EditFace *efa, struct GHash *gh)
2310 EditEdge *cedge=NULL;
2311 EditVert *v[4], **verts;
2313 short start=0, end, left, right, vertsize;
2320 if(efa->e1->f & SELECT) { cedge = efa->e1; start = 0;}
2321 else if(efa->e2->f & SELECT) { cedge = efa->e2; start = 1;}
2322 else if(efa->e3->f & SELECT) { cedge = efa->e3; start = 2;}
2323 else if(efa->e4->f & SELECT) { cedge = efa->e4; start = 3;}
2325 // Point verts to the array of new verts for cedge
2326 verts = BLI_ghash_lookup(gh, cedge);
2327 //This is the index size of the verts array
2330 // Is the original v1 the same as the first vert on the selected edge?
2331 // if not, the edge is running the opposite direction in this face so flip
2332 // the array to the correct direction
2334 if(verts[0] != v[start]) {flipvertarray(verts,3);}
2337 right = (start+3)%4;
2340 We should have something like this now
2351 where start,end,left, right are indexes of EditFace->v1, etc (stored in v)
2352 and 0,1,2 are the indexes of the new verts stored in verts. We fill like
2353 this, depending on whether its vertex 'left' or vertex 'right' thats
2354 been knifed through...
2364 //triangle is composed of cutvert, end and left
2365 hold = addfacelist(verts[1],v[end],v[left],NULL, NULL,NULL);
2366 hold->e1->f2 |= EDGENEW;
2367 hold->e2->f2 |= EDGENEW;
2368 hold->e3->f2 |= EDGENEW;
2369 hold->e3->f2 |= EDGEINNER;
2370 facecopy(efa, hold);
2372 //quad is composed of cutvert, left, right and start
2373 hold = addfacelist(verts[1],v[left],v[right],v[start], NULL, NULL);
2374 hold->e1->f2 |= EDGENEW;
2375 hold->e2->f2 |= EDGENEW;
2376 hold->e3->f2 |= EDGENEW;
2377 hold->e4->f2 |= EDGENEW;
2378 hold->e1->f2 |= EDGEINNER;
2379 facecopy(efa, hold);
2381 else if(v[right]->f1){
2382 //triangle is composed of cutvert, right and start
2383 hold = addfacelist(verts[1],v[right],v[start], NULL, NULL, NULL);
2384 hold->e1->f2 |= EDGENEW;
2385 hold->e2->f2 |= EDGENEW;
2386 hold->e3->f2 |= EDGENEW;
2387 hold->e1->f2 |= EDGEINNER;
2388 facecopy(efa, hold);
2389 //quad is composed of cutvert, end, left, right
2390 hold = addfacelist(verts[1],v[end], v[left], v[right], NULL, NULL);
2391 hold->e1->f2 |= EDGENEW;
2392 hold->e2->f2 |= EDGENEW;
2393 hold->e3->f2 |= EDGENEW;
2394 hold->e4->f2 |= EDGENEW;
2395 hold->e4->f2 |= EDGEINNER;
2396 facecopy(efa, hold);
2401 // This function takes an example edge, the current point to create and
2402 // the total # of points to create, then creates the point and return the
2403 // editvert pointer to it.
2404 static EditVert *subdivideedgenum(EditEdge *edge, int curpoint, int totpoint, float rad, int beauty)
2409 if (beauty & (B_PERCENTSUBD) && totpoint == 1)
2410 //percent=(float)(edge->tmp.l)/32768.0f;
2411 percent= edge->tmp.fp;
2413 percent= (float)curpoint/(float)(totpoint+1);
2415 ev= subdivide_edge_addvert(edge, rad, beauty, percent);
2416 ev->f = edge->v1->f;
2424 void esubdivideflag(int flag, float rad, int beauty, int numcuts, int seltype)
2427 BMOperator subdop, conv;
2428 EditMesh *em = G.editMesh;
2429 BMEdge **list, *bed;
2433 /*convert from editmesh*/
2434 bm = editmesh_to_bmesh(G.editMesh);
2436 BMO_Init_Op(&subdop, BMOP_ESUBDIVIDE);
2437 for (tot=0, bed=BMIter_New(&iter, bm, BM_EDGES, NULL); bed; bed=BMIter_Step(&iter)) {
2438 if (BM_Selected(bm, bed)) tot++;
2441 list = MEM_callocN(sizeof(void*)*tot, "vert ptr list");
2443 for (tot=0, bed=BMIter_New(&iter, bm, BM_EDGES, NULL); bed; bed=BMIter_Step(&iter)) {
2444 if (BM_Selected(bm, bed)) list[tot++] = bed;
2447 BMO_Set_PntBuf(&subdop, BMOP_ESUBDIVIDE_EDGES, list, tot);
2448 BMO_Exec_Op(bm, &subdop);
2449 BMO_Finish_Op(bm, &subdop);
2451 free_editMesh(G.editMesh);
2452 bmesh_to_editmesh(bm);
2455 if (list) MEM_freeN(list);
2458 void esubdivideflag(int flag, float rad, int beauty, int numcuts, int seltype)
2460 EditMesh *em = G.editMesh;
2462 EditEdge *eed, *cedge, *sort[4];
2463 EditVert *eve, **templist;
2465 float length[4], v1mat[3], v2mat[3], v3mat[3], v4mat[3];
2466 int i, j, edgecount, touchcount, facetype,hold;
2467 ModifierData *md= G.obedit->modifiers.first;
2469 if(multires_test()) return;
2471 //Set faces f1 to 0 cause we need it later
2472 for(ef=em->faces.first;ef;ef = ef->next) ef->f1 = 0;
2473 for(eve=em->verts.first; eve; eve=eve->next) {
2474 if(!(beauty & B_KNIFE)) /* knife sets this flag for vertex cuts */
2479 for (; md; md=md->next) {
2480 if (md->type==eModifierType_Mirror) {
2481 MirrorModifierData *mmd = (MirrorModifierData*) md;
2483 if(mmd->flag & MOD_MIR_CLIPPING) {
2484 for (eve= em->verts.first; eve; eve= eve->next) {
2488 if (fabs(eve->co[0]) < mmd->tolerance)
2492 if (fabs(eve->co[1]) < mmd->tolerance)
2496 if (fabs(eve->co[2]) < mmd->tolerance)
2505 //Flush vertex flags upward to the edges
2506 for(eed = em->edges.first;eed;eed = eed->next) {
2507 //if(eed->f & flag && eed->v1->f == eed->v2->f) {
2508 // eed->f |= eed->v1->f;
2516 // We store an array of verts for each edge that is subdivided,
2517 // we put this array as a value in a ghash which is keyed by the EditEdge*
2519 // Now for beauty subdivide deselect edges based on length
2520 if(beauty & B_BEAUTY) {
2521 for(ef = em->faces.first;ef;ef = ef->next) {
2525 if(ef->f & SELECT) {
2526 VECCOPY(v1mat, ef->v1->co);
2527 VECCOPY(v2mat, ef->v2->co);
2528 VECCOPY(v3mat, ef->v3->co);
2529 VECCOPY(v4mat, ef->v4->co);
2530 mul_mat3_m4_v3(G.obedit->obmat, v1mat);
2531 mul_mat3_m4_v3(G.obedit->obmat, v2mat);
2532 mul_mat3_m4_v3(G.obedit->obmat, v3mat);
2533 mul_mat3_m4_v3(G.obedit->obmat, v4mat);
2535 length[0] = len_v3v3(v1mat, v2mat);
2536 length[1] = len_v3v3(v2mat, v3mat);
2537 length[2] = len_v3v3(v3mat, v4mat);
2538 length[3] = len_v3v3(v4mat, v1mat);
2545 // Beauty Short Edges
2546 if(beauty & B_BEAUTY_SHORT) {
2552 } else if(hold == -1) {
2555 if(length[hold] < length[i]) {
2560 sort[hold]->f &= ~SELECT;
2561 sort[hold]->f2 |= EDGENEW;
2566 // Beauty Long Edges
2573 } else if(hold == -1) {
2576 if(length[hold] > length[i]) {
2581 sort[hold]->f &= ~SELECT;
2582 sort[hold]->f2 |= EDGENEW;
2590 gh = BLI_ghash_new(BLI_ghashutil_ptrhash, BLI_ghashutil_ptrcmp);
2592 // If we are knifing, We only need the selected edges that were cut, so deselect if it was not cut
2593 if(beauty & B_KNIFE) {
2594 for(eed= em->edges.first;eed;eed=eed->next) {
2595 if( eed->tmp.fp == 0 ) {
2596 EM_select_edge(eed,0);
2600 // So for each edge, if it is selected, we allocate an array of size cuts+2
2601 // so we can have a place for the v1, the new verts and v2
2602 for(eed=em->edges.first;eed;eed = eed->next) {
2604 templist = MEM_mallocN(sizeof(EditVert*)*(numcuts+2),"vertlist");
2605 templist[0] = eed->v1;
2606 for(i=0;i<numcuts;i++) {
2607 // This function creates the new vert and returns it back
2609 templist[i+1] = subdivideedgenum(eed, i+1, numcuts, rad, beauty);
2610 //while we are here, we can copy edge info from the original edge
2611 cedge = addedgelist(templist[i],templist[i+1],eed);
2612 // Also set the edge f2 to EDGENEW so that we can use this info later
2613 cedge->f2 = EDGENEW;
2615 templist[i+1] = eed->v2;
2616 //Do the last edge too
2617 cedge = addedgelist(templist[i],templist[i+1],eed);
2618 cedge->f2 = EDGENEW;
2619 // Now that the edge is subdivided, we can put its verts in the ghash
2620 BLI_ghash_insert(gh, eed, templist);
2624 DAG_object_flush_update(G.scene, G.obedit, OB_RECALC_DATA);
2625 // Now for each face in the mesh we need to figure out How many edges were cut
2626 // and which filling method to use for that face
2627 for(ef = em->faces.first;ef;ef = ef->next) {
2630 if(ef->e1->f & flag) {edgecount++;}
2631 if(ef->e2->f & flag) {edgecount++;}
2632 if(ef->e3->f & flag) {edgecount++;}
2635 if(ef->e4->f & flag) {edgecount++;}
2640 if(beauty & B_KNIFE && numcuts == 1){
2641 /*Test for when knifing through two opposite verts but no edges*/
2643 if(ef->v1->f1) touchcount++;
2644 if(ef->v2->f1) touchcount++;
2645 if(ef->v3->f1) touchcount++;
2646 if(ef->v4->f1) touchcount++;
2647 if(touchcount == 2){
2648 if(ef->v1->f1 && ef->v3->f1){
2650 fill_quad_doublevert(ef, 1, 3);
2652 else if(ef->v2->f1 && ef->v4->f1){
2654 fill_quad_doublevert(ef, 2, 4);
2661 if(beauty & B_KNIFE && numcuts == 1){
2662 /*Test for when knifing through an edge and one vert*/
2664 if(ef->v1->f1) touchcount++;
2665 if(ef->v2->f1) touchcount++;
2666 if(ef->v3->f1) touchcount++;
2667 if(ef->v4->f1) touchcount++;
2669 if(touchcount == 1){
2670 if( (ef->e1->f & flag && ( !ef->e1->v1->f1 && !ef->e1->v2->f1 )) ||
2671 (ef->e2->f & flag && ( !ef->e2->v1->f1 && !ef->e2->v2->f1 )) ||
2672 (ef->e3->f & flag && ( !ef->e3->v1->f1 && !ef->e3->v2->f1 )) ||
2673 (ef->e4->f & flag && ( !ef->e4->v1->f1 && !ef->e4->v2->f1 )) ){
2676 fill_quad_singlevert(ef, gh);
2680 fill_quad_single(ef, gh, numcuts, seltype);
2685 fill_quad_single(ef, gh, numcuts, seltype);
2690 fill_quad_single(ef, gh, numcuts, seltype);
2693 case 2: ef->f1 = SELECT;
2694 // if there are 2, we check if edge 1 and 3 are either both on or off that way
2695 // we can tell if the selected pair is Adjacent or Opposite of each other
2696 if((ef->e1->f & flag && ef->e3->f & flag) ||
2697 (ef->e2->f & flag && ef->e4->f & flag)) {
2698 fill_quad_double_op(ef, gh, numcuts);
2700 switch(G.scene->toolsettings->cornertype) {
2701 case 0: fill_quad_double_adj_path(ef, gh, numcuts); break;
2702 case 1: fill_quad_double_adj_inner(ef, gh, numcuts); break;
2703 case 2: fill_quad_double_adj_fan(ef, gh, numcuts); break;
2708 case 3: ef->f1 = SELECT;
2709 fill_quad_triple(ef, gh, numcuts);
2711 case 4: ef->f1 = SELECT;
2712 fill_quad_quadruple(ef, gh, numcuts, rad, beauty);
2718 case 1: ef->f1 = SELECT;
2719 fill_tri_single(ef, gh, numcuts, seltype);
2721 case 2: ef->f1 = SELECT;
2722 fill_tri_double(ef, gh, numcuts);
2724 case 3: ef->f1 = SELECT;
2725 fill_tri_triple(ef, gh, numcuts, rad, beauty);
2731 // Delete Old Edges and Faces
2732 for(eed = em->edges.first;eed;eed = eed->next) {
2733 if(BLI_ghash_haskey(gh,eed)) {
2739 free_tagged_edges_faces(em->edges.first, em->faces.first);
2741 if(seltype == SUBDIV_SELECT_ORIG && G.qual != LR_CTRLKEY) {
2742 /* bugfix: vertex could get flagged as "not-selected"
2743 // solution: clear flags before, not at the same time as setting SELECT flag -dg
2745 for(eed = em->edges.first;eed;eed = eed->next) {
2746 if(!(eed->f2 & EDGENEW || eed->f2 & EDGEOLD)) {
2748 EM_select_edge(eed,0);
2751 for(eed = em->edges.first;eed;eed = eed->next) {
2752 if(eed->f2 & EDGENEW || eed->f2 & EDGEOLD) {
2754 EM_select_edge(eed,1);
2757 } else if ((seltype == SUBDIV_SELECT_INNER || seltype == SUBDIV_SELECT_INNER_SEL)|| G.qual == LR_CTRLKEY) {
2758 for(eed = em->edges.first;eed;eed = eed->next) {
2759 if(eed->f2 & EDGEINNER) {
2761 EM_select_edge(eed,1);
2762 if(eed->v1->f & EDGEINNER) eed->v1->f |= SELECT;
2763 if(eed->v2->f & EDGEINNER) eed->v2->f |= SELECT;
2766 EM_select_edge(eed,0);
2769 } else if(seltype == SUBDIV_SELECT_LOOPCUT){
2770 for(eed = em->edges.first;eed;eed = eed->next) {
2771 if(eed->f2 & DOUBLEOPFILL){
2773 EM_select_edge(eed,1);
2776 EM_select_edge(eed,0);
2780 if(G.scene->selectmode & SCE_SELECT_VERTEX) {
2781 for(eed = em->edges.first;eed;eed = eed->next) {
2782 if(eed->f & SELECT) {
2783 eed->v1->f |= SELECT;
2784 eed->v2->f |= SELECT;
2789 //fix hide flags for edges. First pass, hide edges of hidden faces
2790 for(ef=em->faces.first; ef; ef=ef->next){
2795 if(ef->e4) ef->e4->h |= 1;
2798 //second pass: unhide edges of visible faces adjacent to hidden faces
2799 for(ef=em->faces.first; ef; ef=ef->next){
2804 if(ef->e4) ef->e4->h &= ~1;
2808 // Free the ghash and call MEM_freeN on all the value entries to return
2810 BLI_ghash_free(gh, NULL, (GHashValFreeFP)MEM_freeN);
2812 EM_selectmode_flush();
2813 for(ef=em->faces.first;ef;ef = ef->next) {
2815 if( (ef->e1->f & SELECT && ef->e2->f & SELECT) &&
2816 (ef->e3->f & SELECT && ef->e4->f & SELECT) ) {
2820 if( (ef->e1->f & SELECT && ef->e2->f & SELECT) && ef->e3->f & SELECT) {
2826 recalc_editnormals();
2828 allqueue(REDRAWVIEW3D, 0);
2829 DAG_object_flush_update(G.scene, G.obedit, OB_RECALC_DATA);
2833 static int count_selected_edges(EditEdge *ed)
2838 if( ed->f & SELECT ) totedge++;
2844 /* hurms, as if this makes code readable! It's pointerpointer hiding... (ton) */
2845 typedef EditFace *EVPtr;
2846 typedef EVPtr EVPTuple[2];
2848 /** builds EVPTuple array efaa of face tuples (in fact pointers to EditFaces)
2850 arguments: selected edge list, face list.
2851 Edges will also be tagged accordingly (see eed->f2) */
2853 static int collect_quadedges(EVPTuple *efaa, EditEdge *eed, EditFace *efa)
2855 EditEdge *e1, *e2, *e3;
2859 /* run through edges, if selected, set pointer edge-> facearray */
2863 if( eed->f & SELECT ) {
2864 eed->tmp.p = (EditVert *) (&efaa[i]);
2867 else eed->tmp.p = NULL;
2873 /* find edges pointing to 2 faces by procedure:
2875 - run through faces and their edges, increase
2876 face counter e->f1 for each face
2881 if(efa->v4==0 && (efa->f & SELECT)) { /* if selected triangle */
2885 if(e1->f2<3 && e1->tmp.p) {
2887 evp= (EVPtr *) e1->tmp.p;
2888 evp[(int)e1->f2] = efa;
2892 if(e2->f2<3 && e2->tmp.p) {
2894 evp= (EVPtr *) e2->tmp.p;
2895 evp[(int)e2->f2]= efa;
2899 if(e3->f2<3 && e3->tmp.p) {
2901 evp= (EVPtr *) e3->tmp.p;
2902 evp[(int)e3->f2]= efa;
2908 /* set to 3 to make sure these are not flipped or joined */
2912 if (efa->e4) efa->e4->f2= 3;
2921 /* returns vertices of two adjacent triangles forming a quad
2922 - can be righthand or lefthand
2933 #define VTEST(face, num, other) \
2934 (face->v##num != other->v1 && face->v##num != other->v2 && face->v##num != other->v3)
2936 static void givequadverts(EditFace *efa, EditFace *efa1, EditVert **v1, EditVert **v2, EditVert **v3, EditVert **v4, int *vindex)
2938 if VTEST(efa, 1, efa1) {
2944 else if VTEST(efa, 2, efa1) {
2950 else if VTEST(efa, 3, efa1) {
2957 if VTEST(efa1, 1, efa) {
2963 else if VTEST(efa1, 2, efa) {
2969 else if VTEST(efa1, 3, efa) {
2979 /* Helper functions for edge/quad edit features*/
2980 static void untag_edges(EditFace *f)
2985 if (f->e4) f->e4->f1 = 0;
2988 /** remove and free list of tagged edges and faces */
2989 static void free_tagged_edges_faces(EditEdge *eed, EditFace *efa)
2991 EditMesh *em= G.editMesh;