e138631e5482120b6c0e6d388b6259f17e062ea8
[blender.git] / source / blender / src / editmesh.c
1 /**
2  * $Id$
3  *
4  * ***** BEGIN GPL/BL DUAL LICENSE BLOCK *****
5  *
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. The Blender
10  * Foundation also sells licenses for use in proprietary software under
11  * the Blender License.  See http://www.blender.org/BL/ for information
12  * about this.
13  *
14  * This program is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17  * GNU General Public License for more details.
18  *
19  * You should have received a copy of the GNU General Public License
20  * along with this program; if not, write to the Free Software Foundation,
21  * Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
22  *
23  * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
24  * All rights reserved.
25  *
26  * The Original Code is: all of this file.
27  *
28  * Contributor(s): none yet.
29  *
30  * ***** END GPL/BL DUAL LICENSE BLOCK *****
31  */
32
33
34 #include <stdlib.h>
35 #include <string.h>
36 #include <math.h>
37
38 #ifdef HAVE_CONFIG_H
39 #include <config.h>
40 #endif
41
42 #include "MEM_guardedalloc.h"
43
44 #include "PIL_time.h"
45
46 #include "DNA_mesh_types.h"
47 #include "DNA_meshdata_types.h"
48 #include "DNA_object_types.h"
49 #include "DNA_object_force.h"
50 #include "DNA_screen_types.h"
51 #include "DNA_key_types.h"
52 #include "DNA_scene_types.h"
53 #include "DNA_view3d_types.h"
54 #include "DNA_material_types.h"
55 #include "DNA_modifier_types.h"
56 #include "DNA_texture_types.h"
57 #include "DNA_userdef_types.h"
58
59 #include "BLI_blenlib.h"
60 #include "BLI_arithb.h"
61 #include "BLI_editVert.h"
62 #include "BLI_dynstr.h"
63 #include "BLI_rand.h"
64
65 #include "BKE_DerivedMesh.h"
66 #include "BKE_depsgraph.h"
67 #include "BKE_global.h"
68 #include "BKE_key.h"
69 #include "BKE_library.h"
70 #include "BKE_main.h"
71 #include "BKE_material.h"
72 #include "BKE_mesh.h"
73 #include "BKE_object.h"
74 #include "BKE_texture.h"
75 #include "BKE_utildefines.h"
76
77 #ifdef WITH_VERSE
78 #include "BKE_verse.h"
79 #endif
80
81 #include "BIF_editkey.h"
82 #include "BIF_editmesh.h"
83 #include "BIF_editmode_undo.h"
84 #include "BIF_interface.h"
85 #include "BIF_meshtools.h"
86 #include "BIF_mywindow.h"
87 #include "BIF_retopo.h"
88 #include "BIF_space.h"
89 #include "BIF_screen.h"
90 #include "BIF_toolbox.h"
91
92 #ifdef WITH_VERSE
93 #include "BIF_verse.h"
94 #endif
95
96 #include "BSE_view.h"
97 #include "BSE_edit.h"
98 #include "BSE_trans_types.h"
99
100 #include "BDR_drawobject.h"
101 #include "BDR_editobject.h"
102 #include "BDR_editface.h"
103 #include "BDR_vpaint.h"
104
105 #include "mydevice.h"
106 #include "blendef.h"
107
108 /* own include */
109 #include "editmesh.h"
110
111 /* 
112
113 editmesh.c:
114 - add/alloc/free data
115 - hashtables
116 - enter/exit editmode
117
118 */
119
120
121 /* ***************** HASH ********************* */
122
123
124 #define EDHASHSIZE              (512*512)
125 #define EDHASH(a, b)    (a % EDHASHSIZE)
126
127
128 /* ************ ADD / REMOVE / FIND ****************** */
129
130 /* used to bypass normal calloc with fast one */
131 static void *(*callocvert)(size_t, size_t) = calloc;
132 static void *(*callocedge)(size_t, size_t) = calloc;
133 static void *(*callocface)(size_t, size_t) = calloc;
134
135 EditVert *addvertlist(float *vec)
136 {
137         EditMesh *em = G.editMesh;
138         EditVert *eve;
139         static int hashnr= 0;
140
141         eve= callocvert(sizeof(EditVert), 1);
142         BLI_addtail(&em->verts, eve);
143         
144         if(vec) VECCOPY(eve->co, vec);
145
146         eve->hash= hashnr++;
147         if( hashnr>=EDHASHSIZE) hashnr= 0;
148
149         /* new verts get keyindex of -1 since they did not
150          * have a pre-editmode vertex order
151          */
152         eve->keyindex = -1;
153
154 #ifdef WITH_VERSE
155         createVerseVert(eve);
156 #endif
157
158         return eve;
159 }
160
161 void free_editvert (EditVert *eve)
162 {
163 #ifdef WITH_VERSE
164         if(eve->vvert) {
165                 /* it prevents from removing all verse vertexes
166                  * during entering edit mode ... messy solution */
167                 if(G.editMesh->vnode)
168                         b_verse_send_vertex_delete(eve);
169                 else
170                         ((VerseVert*)eve->vvert)->vertex = NULL;
171         }
172 #endif
173
174         if(eve->dw) MEM_freeN(eve->dw);
175         EM_remove_selection(eve, EDITVERT);
176         if(eve->fast==0){ 
177                 free(eve);
178         }
179 }
180
181
182 EditEdge *findedgelist(EditVert *v1, EditVert *v2)
183 {
184         EditVert *v3;
185         struct HashEdge *he;
186
187         /* swap ? */
188         if( v1 > v2) {
189                 v3= v2; 
190                 v2= v1; 
191                 v1= v3;
192         }
193         
194         if(G.editMesh->hashedgetab==NULL)
195                 G.editMesh->hashedgetab= MEM_callocN(EDHASHSIZE*sizeof(struct HashEdge), "hashedgetab");
196
197         he= G.editMesh->hashedgetab + EDHASH(v1->hash, v2->hash);
198         
199         while(he) {
200                 
201                 if(he->eed && he->eed->v1==v1 && he->eed->v2==v2) return he->eed;
202                 
203                 he= he->next;
204         }
205         return 0;
206 }
207
208 static void insert_hashedge(EditEdge *eed)
209 {
210         /* assuming that eed is not in the list yet, and that a find has been done before */
211         
212         struct HashEdge *first, *he;
213
214         first= G.editMesh->hashedgetab + EDHASH(eed->v1->hash, eed->v2->hash);
215
216         if( first->eed==0 ) {
217                 first->eed= eed;
218         }
219         else {
220                 he= &eed->hash; 
221                 he->eed= eed;
222                 he->next= first->next;
223                 first->next= he;
224         }
225 }
226
227 static void remove_hashedge(EditEdge *eed)
228 {
229         /* assuming eed is in the list */
230         
231         struct HashEdge *first, *he, *prev=NULL;
232
233         he=first= G.editMesh->hashedgetab + EDHASH(eed->v1->hash, eed->v2->hash);
234
235         while(he) {
236                 if(he->eed == eed) {
237                         /* remove from list */
238                         if(he==first) {
239                                 if(first->next) {
240                                         he= first->next;
241                                         first->eed= he->eed;
242                                         first->next= he->next;
243                                 }
244                                 else he->eed= 0;
245                         }
246                         else {
247                                 prev->next= he->next;
248                         }
249                         return;
250                 }
251                 prev= he;
252                 he= he->next;
253         }
254 }
255
256 EditEdge *addedgelist(EditVert *v1, EditVert *v2, EditEdge *example)
257 {
258         EditMesh *em = G.editMesh;
259         EditVert *v3;
260         EditEdge *eed;
261         int swap= 0;
262         
263         if(v1==v2) return NULL;
264         if(v1==NULL || v2==NULL) return NULL;
265
266         /* swap ? */
267         if(v1>v2) {
268                 v3= v2; 
269                 v2= v1; 
270                 v1= v3;
271                 swap= 1;
272         }
273         
274         /* find in hashlist */
275         eed= findedgelist(v1, v2);
276
277         if(eed==NULL) {
278         
279                 eed= (EditEdge *)callocedge(sizeof(EditEdge), 1);
280                 eed->v1= v1;
281                 eed->v2= v2;
282                 BLI_addtail(&em->edges, eed);
283                 eed->dir= swap;
284                 insert_hashedge(eed);
285                 
286                 /* copy edge data:
287                    rule is to do this with addedgelist call, before addfacelist */
288                 if(example) {
289                         eed->crease= example->crease;
290                         eed->sharp = example->sharp;
291                         eed->seam = example->seam;
292                         eed->h |= (example->h & EM_FGON);
293                 }
294         }
295
296         return eed;
297 }
298
299 void remedge(EditEdge *eed)
300 {
301         EditMesh *em = G.editMesh;
302
303         BLI_remlink(&em->edges, eed);
304         remove_hashedge(eed);
305 }
306
307 void free_editedge(EditEdge *eed)
308 {
309         EM_remove_selection(eed, EDITEDGE);
310         if(eed->fast==0){ 
311                 free(eed);
312         }
313 }
314
315 void free_editface(EditFace *efa)
316 {
317 #ifdef WITH_VERSE
318         if(efa->vface) {
319                 /* it prevents from removing all verse faces
320                  * during entering edit mode ... messy solution */
321                 if(G.editMesh->vnode)
322                         b_verse_send_face_delete(efa);
323                 else
324                         ((VerseFace*)efa->vface)->face = NULL;
325         }
326 #endif
327         EM_remove_selection(efa, EDITFACE);
328         if(efa->fast==0){ 
329                 free(efa);
330         }
331 }
332
333 void free_vertlist(ListBase *edve) 
334 {
335         EditVert *eve, *next;
336
337         if (!edve) return;
338
339         eve= edve->first;
340         while(eve) {
341                 next= eve->next;
342                 free_editvert(eve);
343                 eve= next;
344         }
345         edve->first= edve->last= NULL;
346 }
347
348 void free_edgelist(ListBase *lb)
349 {
350         EditEdge *eed, *next;
351         
352         eed= lb->first;
353         while(eed) {
354                 next= eed->next;
355                 free_editedge(eed);
356                 eed= next;
357         }
358         lb->first= lb->last= NULL;
359 }
360
361 void free_facelist(ListBase *lb)
362 {
363         EditFace *efa, *next;
364         
365         efa= lb->first;
366         while(efa) {
367                 next= efa->next;
368                 free_editface(efa);
369                 efa= next;
370         }
371         lb->first= lb->last= NULL;
372 }
373
374 EditFace *addfacelist(EditVert *v1, EditVert *v2, EditVert *v3, EditVert *v4, EditFace *example, EditFace *exampleEdges)
375 {
376         EditMesh *em = G.editMesh;
377         EditFace *efa;
378         EditEdge *e1, *e2=0, *e3=0, *e4=0;
379
380         /* add face to list and do the edges */
381         if(exampleEdges) {
382                 e1= addedgelist(v1, v2, exampleEdges->e1);
383                 e2= addedgelist(v2, v3, exampleEdges->e2);
384                 if(v4) e3= addedgelist(v3, v4, exampleEdges->e3); 
385                 else e3= addedgelist(v3, v1, exampleEdges->e3);
386                 if(v4) e4= addedgelist(v4, v1, exampleEdges->e4);
387         }
388         else {
389                 e1= addedgelist(v1, v2, NULL);
390                 e2= addedgelist(v2, v3, NULL);
391                 if(v4) e3= addedgelist(v3, v4, NULL); 
392                 else e3= addedgelist(v3, v1, NULL);
393                 if(v4) e4= addedgelist(v4, v1, NULL);
394         }
395         
396         if(v1==v2 || v2==v3 || v1==v3) return NULL;
397         if(e2==0) return NULL;
398
399         efa= (EditFace *)callocface(sizeof(EditFace), 1);
400         efa->v1= v1;
401         efa->v2= v2;
402         efa->v3= v3;
403         efa->v4= v4;
404
405         efa->e1= e1;
406         efa->e2= e2;
407         efa->e3= e3;
408         efa->e4= e4;
409
410         if(example) {
411                 efa->mat_nr= example->mat_nr;
412                 efa->tf= example->tf;
413                 efa->tf.flag &= ~TF_ACTIVE;
414                 efa->flag= example->flag;
415         }
416         else {
417                 if (G.obedit && G.obedit->actcol)
418                         efa->mat_nr= G.obedit->actcol-1;
419                 default_uv(efa->tf.uv, 1.0);
420
421                 /* Initialize colors */
422                 efa->tf.col[0]= efa->tf.col[1]= efa->tf.col[2]= efa->tf.col[3]= vpaint_get_current_col();
423         }
424
425         BLI_addtail(&em->faces, efa);
426
427         if(efa->v4) {
428                 CalcNormFloat4(efa->v1->co, efa->v2->co, efa->v3->co, efa->v4->co, efa->n);
429                 CalcCent4f(efa->cent, efa->v1->co, efa->v2->co, efa->v3->co, efa->v4->co);
430         }
431         else {
432                 CalcNormFloat(efa->v1->co, efa->v2->co, efa->v3->co, efa->n);
433                 CalcCent3f(efa->cent, efa->v1->co, efa->v2->co, efa->v3->co);
434         }
435
436 #ifdef WITH_VERSE
437         createVerseFace(efa);
438 #endif
439
440         return efa;
441 }
442
443 /* ************************ end add/new/find ************  */
444
445 /* ************************ Edit{Vert,Edge,Face} utilss ***************************** */
446
447 /* some nice utility functions */
448
449 EditVert *editedge_getOtherVert(EditEdge *eed, EditVert *eve)
450 {
451         if (eve==eed->v1) {
452                 return eed->v2;
453         } else if (eve==eed->v2) {
454                 return eed->v1;
455         } else {
456                 return NULL;
457         }
458 }
459
460 EditVert *editedge_getSharedVert(EditEdge *eed, EditEdge *eed2) 
461 {
462         if (eed->v1==eed2->v1 || eed->v1==eed2->v2) {
463                 return eed->v1;
464         } else if (eed->v2==eed2->v1 || eed->v2==eed2->v2) {
465                 return eed->v2;
466         } else {
467                 return NULL;
468         }
469 }
470
471 int editedge_containsVert(EditEdge *eed, EditVert *eve) 
472 {
473         return (eed->v1==eve || eed->v2==eve);
474 }
475
476 int editface_containsVert(EditFace *efa, EditVert *eve) 
477 {
478         return (efa->v1==eve || efa->v2==eve || efa->v3==eve || (efa->v4 && efa->v4==eve));
479 }
480
481 int editface_containsEdge(EditFace *efa, EditEdge *eed) 
482 {
483         return (efa->e1==eed || efa->e2==eed || efa->e3==eed || (efa->e4 && efa->e4==eed));
484 }
485
486
487 /* ************************ stuct EditMesh manipulation ***************************** */
488
489 /* fake callocs for fastmalloc below */
490 static void *calloc_fastvert(size_t size, size_t nr)
491 {
492         EditVert *eve= G.editMesh->curvert++;
493         eve->fast= 1;
494         return eve;
495 }
496 static void *calloc_fastedge(size_t size, size_t nr)
497 {
498         EditEdge *eed= G.editMesh->curedge++;
499         eed->fast= 1;
500         return eed;
501 }
502 static void *calloc_fastface(size_t size, size_t nr)
503 {
504         EditFace *efa= G.editMesh->curface++;
505         efa->fast= 1;
506         return efa;
507 }
508
509 /* allocate 1 chunk for all vertices, edges, faces. These get tagged to
510    prevent it from being freed
511 */
512 static void init_editmesh_fastmalloc(EditMesh *em, int totvert, int totedge, int totface)
513 {
514         
515         if(totvert) em->allverts= MEM_callocN(totvert*sizeof(EditVert), "allverts");
516         else em->allverts= NULL;
517         em->curvert= em->allverts;
518         
519         if(totedge==0) totedge= 4*totface;      // max possible
520
521         if(totedge) em->alledges= MEM_callocN(totedge*sizeof(EditEdge), "alledges");
522         else em->alledges= NULL;
523         em->curedge= em->alledges;
524         
525         if(totface) em->allfaces= MEM_callocN(totface*sizeof(EditFace), "allfaces");
526         else em->allfaces= NULL;
527         em->curface= em->allfaces;
528
529         callocvert= calloc_fastvert;
530         callocedge= calloc_fastedge;
531         callocface= calloc_fastface;
532 }
533
534 static void end_editmesh_fastmalloc(void)
535 {
536         callocvert= calloc;
537         callocedge= calloc;
538         callocface= calloc;
539 }
540
541 void free_editMesh(EditMesh *em)
542 {
543 #ifdef WITH_VERSE
544         struct VNode *vnode=NULL;
545 #endif
546         if(em==NULL) return;
547
548 #ifdef WITH_VERSE
549         if(em->vnode) {
550                 vnode = (VNode*)em->vnode;
551                 em->vnode = NULL;
552         }
553 #endif
554
555         if(em->verts.first) free_vertlist(&em->verts);
556         if(em->edges.first) free_edgelist(&em->edges);
557         if(em->faces.first) free_facelist(&em->faces);
558         if(em->selected.first) BLI_freelistN(&(em->selected));
559         if(em->derivedFinal) {
560                 if (em->derivedFinal!=em->derivedCage) {
561                         em->derivedFinal->release(em->derivedFinal);
562                 }
563                 em->derivedFinal= NULL;
564         }
565         if(em->derivedCage) {
566                 em->derivedCage->release(em->derivedCage);
567                 em->derivedCage= NULL;
568         }
569
570 #ifdef WITH_VERSE
571         if(vnode) {
572                 em->vnode = (void*)vnode;
573         }
574 #endif
575
576         /* DEBUG: hashtabs are slowest part of enter/exit editmode. here a testprint */
577 #if 0
578         if(em->hashedgetab) {
579                 HashEdge *he, *hen;
580                 int a, used=0, max=0, nr;
581                 he= em->hashedgetab;
582                 for(a=0; a<EDHASHSIZE; a++, he++) {
583                         if(he->eed) used++;
584                         hen= he->next;
585                         nr= 0;
586                         while(hen) {
587                                 nr++;
588                                 hen= hen->next;
589                         }
590                         if(max<nr) max= nr;
591                 }
592                 printf("hastab used %d max %d\n", used, max);
593         }
594 #endif
595         if(em->hashedgetab) MEM_freeN(em->hashedgetab);
596         em->hashedgetab= NULL;
597         
598         if(em->allverts) MEM_freeN(em->allverts);
599         if(em->alledges) MEM_freeN(em->alledges);
600         if(em->allfaces) MEM_freeN(em->allfaces);
601         
602         em->allverts= em->curvert= NULL;
603         em->alledges= em->curedge= NULL;
604         em->allfaces= em->curface= NULL;
605         
606         mesh_octree_table(NULL, NULL, 'e');
607         
608         G.totvert= G.totface= 0;
609
610         if(em->retopo_paint_data) retopo_free_paint_data(em->retopo_paint_data);
611 }
612
613 /* on G.editMesh */
614 static void editMesh_set_hash(void)
615 {
616         EditEdge *eed;
617
618         G.editMesh->hashedgetab= NULL;
619         
620         for(eed=G.editMesh->edges.first; eed; eed= eed->next)  {
621                 if( findedgelist(eed->v1, eed->v2)==NULL )
622                         insert_hashedge(eed);
623         }
624
625 }
626
627
628 /* ************************ IN & OUT EDITMODE ***************************** */
629
630
631 static void edge_normal_compare(EditEdge *eed, EditFace *efa1)
632 {
633         EditFace *efa2;
634         float cent1[3], cent2[3];
635         float inp;
636         
637         efa2 = eed->tmp.f;
638         if(efa1==efa2) return;
639         
640         inp= efa1->n[0]*efa2->n[0] + efa1->n[1]*efa2->n[1] + efa1->n[2]*efa2->n[2];
641         if(inp<0.999 && inp >-0.999) eed->f2= 1;
642                 
643         if(efa1->v4) CalcCent4f(cent1, efa1->v1->co, efa1->v2->co, efa1->v3->co, efa1->v4->co);
644         else CalcCent3f(cent1, efa1->v1->co, efa1->v2->co, efa1->v3->co);
645         if(efa2->v4) CalcCent4f(cent2, efa2->v1->co, efa2->v2->co, efa2->v3->co, efa2->v4->co);
646         else CalcCent3f(cent2, efa2->v1->co, efa2->v2->co, efa2->v3->co);
647         
648         VecSubf(cent1, cent2, cent1);
649         Normalise(cent1);
650         inp= cent1[0]*efa1->n[0] + cent1[1]*efa1->n[1] + cent1[2]*efa1->n[2]; 
651
652         if(inp < -0.001 ) eed->f1= 1;
653 }
654
655 #if 0
656 typedef struct {
657         EditEdge *eed;
658         float noLen,no[3];
659         int adjCount;
660 } EdgeDrawFlagInfo;
661
662 static int edgeDrawFlagInfo_cmp(const void *av, const void *bv)
663 {
664         const EdgeDrawFlagInfo *a = av;
665         const EdgeDrawFlagInfo *b = bv;
666
667         if (a->noLen<b->noLen) return -1;
668         else if (a->noLen>b->noLen) return 1;
669         else return 0;
670 }
671 #endif
672
673 static void edge_drawflags(void)
674 {
675         EditMesh *em = G.editMesh;
676         EditVert *eve;
677         EditEdge *eed, *e1, *e2, *e3, *e4;
678         EditFace *efa;
679         
680         /* - count number of times edges are used in faces: 0 en 1 time means draw edge
681          * - edges more than 1 time used: in *tmp.f is pointer to first face
682          * - check all faces, when normal differs to much: draw (flag becomes 1)
683          */
684
685         /* later on: added flags for 'cylinder' and 'sphere' intersection tests in old
686            game engine (2.04)
687          */
688         
689         recalc_editnormals();
690         
691         /* init */
692         eve= em->verts.first;
693         while(eve) {
694                 eve->f1= 1;             /* during test it's set at zero */
695                 eve= eve->next;
696         }
697         eed= em->edges.first;
698         while(eed) {
699                 eed->f2= eed->f1= 0;
700                 eed->tmp.f = 0;
701                 eed= eed->next;
702         }
703
704         efa= em->faces.first;
705         while(efa) {
706                 e1= efa->e1;
707                 e2= efa->e2;
708                 e3= efa->e3;
709                 e4= efa->e4;
710                 if(e1->f2<4) e1->f2+= 1;
711                 if(e2->f2<4) e2->f2+= 1;
712                 if(e3->f2<4) e3->f2+= 1;
713                 if(e4 && e4->f2<4) e4->f2+= 1;
714                 
715                 if(e1->tmp.f == 0) e1->tmp.f = (void *) efa;
716                 if(e2->tmp.f == 0) e2->tmp.f = (void *) efa;
717                 if(e3->tmp.f ==0) e3->tmp.f = (void *) efa;
718                 if(e4 && (e4->tmp.f == 0)) e4->tmp.f = (void *) efa;
719                 
720                 efa= efa->next;
721         }
722
723         if(G.f & G_ALLEDGES) {
724                 efa= em->faces.first;
725                 while(efa) {
726                         if(efa->e1->f2>=2) efa->e1->f2= 1;
727                         if(efa->e2->f2>=2) efa->e2->f2= 1;
728                         if(efa->e3->f2>=2) efa->e3->f2= 1;
729                         if(efa->e4 && efa->e4->f2>=2) efa->e4->f2= 1;
730                         
731                         efa= efa->next;
732                 }               
733         }       
734         else {
735                 
736                 /* handle single-edges for 'test cylinder flag' (old engine) */
737                 
738                 eed= em->edges.first;
739                 while(eed) {
740                         if(eed->f2==1) eed->f1= 1;
741                         eed= eed->next;
742                 }
743
744                 /* all faces, all edges with flag==2: compare normal */
745                 efa= em->faces.first;
746                 while(efa) {
747                         if(efa->e1->f2==2) edge_normal_compare(efa->e1, efa);
748                         else efa->e1->f2= 1;
749                         if(efa->e2->f2==2) edge_normal_compare(efa->e2, efa);
750                         else efa->e2->f2= 1;
751                         if(efa->e3->f2==2) edge_normal_compare(efa->e3, efa);
752                         else efa->e3->f2= 1;
753                         if(efa->e4) {
754                                 if(efa->e4->f2==2) edge_normal_compare(efa->e4, efa);
755                                 else efa->e4->f2= 1;
756                         }
757                         efa= efa->next;
758                 }
759                 
760                 /* sphere collision flag */
761                 
762                 eed= em->edges.first;
763                 while(eed) {
764                         if(eed->f1!=1) {
765                                 eed->v1->f1= eed->v2->f1= 0;
766                         }
767                         eed= eed->next;
768                 }
769                 
770         }
771 }
772
773 /* turns Mesh into editmesh */
774 void make_editMesh()
775 {
776         Mesh *me= G.obedit->data;
777         MFace *mface;
778         TFace *tface;
779         MVert *mvert;
780         MSelect *mselect;
781         KeyBlock *actkey;
782         EditVert *eve, **evlist, *eve1, *eve2, *eve3, *eve4;
783         EditFace *efa;
784         EditEdge *eed;
785         EditSelection *ese;
786         int tot, a, eekadoodle= 0;
787
788 #ifdef WITH_VERSE
789         if(me->vnode){
790                 create_edit_mesh_from_geom_node(me->vnode);
791                 return;
792         }
793 #endif
794
795         /* because of reload */
796         free_editMesh(G.editMesh);
797         
798         G.totvert= tot= me->totvert;
799         G.totedge= me->totedge;
800         G.totface= me->totface;
801
802         if(tot==0) {
803                 countall();
804                 return;
805         }
806         
807
808         /* initialize fastmalloc for editmesh */
809         init_editmesh_fastmalloc(G.editMesh, me->totvert, me->totedge, me->totface);
810
811         actkey = ob_get_keyblock(G.obedit);
812         if(actkey) {
813                 strcpy(G.editModeTitleExtra, "(Key) ");
814                 key_to_mesh(actkey, me);
815                 tot= actkey->totelem;
816         }
817
818         /* make editverts */
819         mvert= me->mvert;
820
821         evlist= (EditVert **)MEM_mallocN(tot*sizeof(void *),"evlist");
822         for(a=0; a<tot; a++, mvert++) {
823                 eve= addvertlist(mvert->co);
824                 evlist[a]= eve;
825                 
826                 // face select sets selection in next loop
827                 if( (G.f & G_FACESELECT)==0 )
828                         eve->f |= (mvert->flag & 1);
829                 
830                 if (mvert->flag & ME_HIDE) eve->h= 1;           
831                 eve->no[0]= mvert->no[0]/32767.0;
832                 eve->no[1]= mvert->no[1]/32767.0;
833                 eve->no[2]= mvert->no[2]/32767.0;
834
835                 /* lets overwrite the keyindex of the editvert
836                  * with the order it used to be in before
837                  * editmode
838                  */
839                 eve->keyindex = a;
840
841                 if (me->dvert){
842                         eve->totweight = me->dvert[a].totweight;
843                         if (me->dvert[a].dw){
844                                 eve->dw = MEM_callocN (sizeof(MDeformWeight) * me->dvert[a].totweight, "deformWeight");
845                                 memcpy (eve->dw, me->dvert[a].dw, sizeof(MDeformWeight) * me->dvert[a].totweight);
846                         }
847                 }
848
849         }
850         
851         if(actkey && actkey->totelem!=me->totvert);
852         else {
853                 unsigned int *mcol;
854                 MEdge *medge= me->medge;
855                 
856                 /* make edges */
857                 for(a=0; a<me->totedge; a++, medge++) {
858                         eed= addedgelist(evlist[medge->v1], evlist[medge->v2], NULL);
859                         /* eed can be zero when v1 and v2 are identical, dxf import does this... */
860                         if(eed) {
861                                 eed->crease= ((float)medge->crease)/255.0;
862                                 
863                                 if(medge->flag & ME_SEAM) eed->seam= 1;
864                                 if(medge->flag & ME_SHARP) eed->sharp = 1;
865                                 if(medge->flag & SELECT) eed->f |= SELECT;
866                                 if(medge->flag & ME_FGON) eed->h= EM_FGON;      // 2 different defines!
867                                 if(medge->flag & ME_HIDE) eed->h |= 1;
868                                 if(G.scene->selectmode==SCE_SELECT_EDGE) 
869                                         EM_select_edge(eed, eed->f & SELECT);           // force edge selection to vertices, seems to be needed ...
870                         }
871                 }
872                 
873                 /* make faces */
874                 mface= me->mface;
875                 tface= me->tface;
876                 mcol= (unsigned int *)me->mcol;
877                 
878                 for(a=0; a<me->totface; a++, mface++) {
879                         eve1= evlist[mface->v1];
880                         eve2= evlist[mface->v2];
881                         if(!mface->v3) eekadoodle= 1;
882                         eve3= evlist[mface->v3];
883                         if(mface->v4) eve4= evlist[mface->v4]; else eve4= NULL;
884                         
885                         efa= addfacelist(eve1, eve2, eve3, eve4, NULL, NULL);
886
887                         if(efa) {
888                         
889                                 if(mcol) memcpy(efa->tf.col, mcol, 4*sizeof(int));
890
891                                 if(me->tface) {
892                                         efa->tf= *tface;
893                                 }
894                         
895                                 efa->mat_nr= mface->mat_nr;
896                                 efa->flag= mface->flag & ~ME_HIDE;
897                                 
898                                 if((G.f & G_FACESELECT)==0) {
899                                         /* select face flag, if no edges we flush down */
900                                         if(mface->flag & ME_FACE_SEL) {
901                                                 efa->f |= SELECT;
902                                         }
903                                         if(mface->flag & ME_HIDE) efa->h= 1;
904                                 }
905                                 else if (tface) {
906                                         if( tface->flag & TF_HIDE) 
907                                                 efa->h= 1;
908                                         else if( tface->flag & TF_SELECT) {
909                                                 EM_select_face(efa, 1);
910                                         }
911                                 }
912                         }
913
914                         if(me->tface) tface++;
915                         if(mcol) mcol+=4;
916                 }
917         }
918         
919         if(eekadoodle)
920                 error("This Mesh has old style edgecodes, please put it in the bugtracker!");
921         
922         MEM_freeN(evlist);
923
924         end_editmesh_fastmalloc();      // resets global function pointers
925         
926         if(me->mselect){
927                 //restore editselections
928                 EM_init_index_arrays(1,1,1);
929                 mselect = me->mselect;
930                 
931                 for(a=0; a<me->totselect; a++, mselect++){
932                         /*check if recorded selection is still valid, if so copy into editmesh*/
933                         if( (mselect->type == EDITVERT && me->mvert[mselect->index].flag & SELECT) || (mselect->type == EDITEDGE && me->medge[mselect->index].flag & SELECT) || (mselect->type == EDITFACE && me->mface[mselect->index].flag & SELECT) ){
934                                 ese = MEM_callocN(sizeof(EditSelection), "Edit Selection");
935                                 ese->type = mselect->type;      
936                                 if(ese->type == EDITVERT) ese->data = EM_get_vert_for_index(mselect->index); else
937                                 if(ese->type == EDITEDGE) ese->data = EM_get_edge_for_index(mselect->index); else
938                                 if(ese->type == EDITFACE) ese->data = EM_get_face_for_index(mselect->index);
939                                 BLI_addtail(&(G.editMesh->selected),ese);
940                         }
941                 }
942                 EM_free_index_arrays();
943         }
944         /* this creates coherent selections. also needed for older files */
945         EM_selectmode_set();
946         /* paranoia check to enforce hide rules */
947         EM_hide_reset();
948         /* sets helper flags which arent saved */
949         EM_fgon_flags();
950         
951         countall();
952         
953 }
954
955 /* makes Mesh out of editmesh */
956 void load_editMesh(void)
957 {
958         EditMesh *em = G.editMesh;
959         Mesh *me= G.obedit->data;
960         MVert *mvert, *oldverts;
961         MEdge *medge;
962         MFace *mface;
963         MSticky *ms;
964         MSelect *mselect;
965         EditVert *eve;
966         EditFace *efa;
967         EditEdge *eed;
968         EditSelection *ese;
969         float *fp, *newkey, *oldkey, nor[3];
970         int i, a, ototvert, totedge=0;
971         MDeformVert *dvert;
972
973
974 #ifdef WITH_VERSE
975         if(em->vnode) {
976                 struct VNode *vnode = (VNode*)em->vnode;
977                 ((VGeomData*)vnode->data)->editmesh = NULL;
978                 em->vnode = NULL;
979         }
980 #endif
981
982         countall();
983
984         /* this one also tests of edges are not in faces: */
985         /* eed->f2==0: not in face, f2==1: draw it */
986         /* eed->f1 : flag for dynaface (cylindertest, old engine) */
987         /* eve->f1 : flag for dynaface (sphere test, old engine) */
988         /* eve->f2 : being used in vertexnormals */
989         edge_drawflags();
990         
991         eed= em->edges.first;
992         while(eed) {
993                 totedge++;
994                 eed= eed->next;
995         }
996         
997         /* new Vertex block */
998         if(G.totvert==0) mvert= NULL;
999         else mvert= MEM_callocN(G.totvert*sizeof(MVert), "loadeditMesh vert");
1000
1001         /* new Edge block */
1002         if(totedge==0) medge= NULL;
1003         else medge= MEM_callocN(totedge*sizeof(MEdge), "loadeditMesh edge");
1004         
1005         /* new Face block */
1006         if(G.totface==0) mface= NULL;
1007         else mface= MEM_callocN(G.totface*sizeof(MFace), "loadeditMesh face");
1008         
1009         /* are we adding dverts? */
1010         if (G.totvert==0) dvert= NULL;
1011         else if(G.obedit->defbase.first==NULL) dvert= NULL;
1012         else dvert = MEM_callocN(G.totvert*sizeof(MDeformVert), "loadeditMesh3");
1013
1014         if (me->dvert) free_dverts(me->dvert, me->totvert);
1015         me->dvert=dvert;
1016
1017         /* lets save the old verts just in case we are actually working on
1018          * a key ... we now do processing of the keys at the end */
1019         oldverts = me->mvert;
1020         ototvert= me->totvert;
1021
1022         /* put new data in Mesh */
1023         me->mvert= mvert;
1024         me->totvert= G.totvert;
1025
1026         if(me->medge) MEM_freeN(me->medge);
1027         me->medge= medge;
1028         me->totedge= totedge;
1029         
1030         if(me->mface) MEM_freeN(me->mface);
1031         me->mface= mface;
1032         me->totface= G.totface;
1033                 
1034         /* the vertices, use ->tmp.l as counter */
1035         eve= em->verts.first;
1036         a= 0;
1037
1038         while(eve) {
1039                 VECCOPY(mvert->co, eve->co);
1040                 mvert->mat_nr= 255;  /* what was this for, halos? */
1041                 
1042                 /* vertex normal */
1043                 VECCOPY(nor, eve->no);
1044                 VecMulf(nor, 32767.0);
1045                 VECCOPY(mvert->no, nor);
1046
1047                 /* note: it used to remove me->dvert when it was not in use, cancelled that... annoying when you have a fresh vgroup */
1048                 if (dvert){
1049                         dvert->totweight=eve->totweight;
1050                         if (eve->dw){
1051                                 dvert->dw = MEM_callocN (sizeof(MDeformWeight)*eve->totweight,
1052                                                                                  "deformWeight");
1053                                 memcpy (dvert->dw, eve->dw, 
1054                                                 sizeof(MDeformWeight)*eve->totweight);
1055                         }
1056                 }
1057
1058                 eve->tmp.l = a++;  /* counter */
1059                         
1060                 mvert->flag= 0;
1061                 if(eve->f1==1) mvert->flag |= ME_SPHERETEST;
1062                 mvert->flag |= (eve->f & SELECT);
1063                 if (eve->h) mvert->flag |= ME_HIDE;                     
1064
1065 #ifdef WITH_VERSE
1066                 if(eve->vvert) {
1067                         ((VerseVert*)eve->vvert)->vertex = NULL;
1068                         eve->vvert = NULL;
1069                 }
1070 #endif                  
1071                 eve= eve->next;
1072                 mvert++;
1073                 if(dvert) dvert++;
1074         }
1075
1076         /* the edges */
1077         a= 0;
1078         eed= em->edges.first;
1079         while(eed) {
1080                 medge->v1= (unsigned int) eed->v1->tmp.l;
1081                 medge->v2= (unsigned int) eed->v2->tmp.l;
1082                 
1083                 medge->flag= (eed->f & SELECT) | ME_EDGERENDER;
1084                 if(eed->f2<2) medge->flag |= ME_EDGEDRAW;
1085                 if(eed->f2==0) medge->flag |= ME_LOOSEEDGE;
1086                 if(eed->sharp) medge->flag |= ME_SHARP;
1087                 if(eed->seam) medge->flag |= ME_SEAM;
1088                 if(eed->h & EM_FGON) medge->flag |= ME_FGON;    // different defines yes
1089                 if(eed->h & 1) medge->flag |= ME_HIDE;
1090                 
1091                 medge->crease= (char)(255.0*eed->crease);
1092                 
1093                 eed->tmp.l = a++;
1094                 
1095                 medge++;
1096                 eed= eed->next;
1097         }
1098
1099         /* the faces */
1100         a = 0;
1101         efa= em->faces.first;
1102         i = 0;
1103         while(efa) {
1104                 mface= &((MFace *) me->mface)[i];
1105                 
1106                 mface->v1= (unsigned int) efa->v1->tmp.l;
1107                 mface->v2= (unsigned int) efa->v2->tmp.l;
1108                 mface->v3= (unsigned int) efa->v3->tmp.l;
1109                 if (efa->v4) mface->v4 = (unsigned int) efa->v4->tmp.l;
1110                         
1111                 mface->mat_nr= efa->mat_nr;
1112                 
1113                 mface->flag= efa->flag;
1114                 /* bit 0 of flag is already taken for smooth... */
1115                 if(efa->f & 1) mface->flag |= ME_FACE_SEL;
1116                 else mface->flag &= ~ME_FACE_SEL;
1117                 if(efa->h) mface->flag |= ME_HIDE;
1118                 
1119                 /* mat_nr in vertex */
1120                 if(me->totcol>1) {
1121                         mvert= me->mvert+mface->v1;
1122                         if(mvert->mat_nr == (char)255) mvert->mat_nr= mface->mat_nr;
1123                         mvert= me->mvert+mface->v2;
1124                         if(mvert->mat_nr == (char)255) mvert->mat_nr= mface->mat_nr;
1125                         mvert= me->mvert+mface->v3;
1126                         if(mvert->mat_nr == (char)255) mvert->mat_nr= mface->mat_nr;
1127                         if(mface->v4) {
1128                                 mvert= me->mvert+mface->v4;
1129                                 if(mvert->mat_nr == (char)255) mvert->mat_nr= mface->mat_nr;
1130                         }
1131                 }
1132                         
1133                 /* watch: efa->e1->f2==0 means loose edge */ 
1134                         
1135                 if(efa->e1->f2==1) {
1136                         efa->e1->f2= 2;
1137                 }                       
1138                 if(efa->e2->f2==1) {
1139                         efa->e2->f2= 2;
1140                 }
1141                 if(efa->e3->f2==1) {
1142                         efa->e3->f2= 2;
1143                 }
1144                 if(efa->e4 && efa->e4->f2==1) {
1145                         efa->e4->f2= 2;
1146                 }
1147
1148
1149                 /* no index '0' at location 3 or 4 */
1150                 test_index_face(mface, NULL, &efa->tf, efa->v4?4:3);
1151
1152 #ifdef WITH_VERSE
1153                 if(efa->vface) {
1154                         ((VerseFace*)efa->vface)->face = NULL;
1155                         efa->vface = NULL;
1156                 }
1157 #endif          
1158                 efa->tmp.l = a++;
1159                 i++;
1160                 efa= efa->next;
1161         }
1162         
1163         /* tface block */
1164         if( me->tface && me->totface ) {
1165                 TFace *tfn, *tf;
1166                         
1167                 tf=tfn= MEM_callocN(sizeof(TFace)*me->totface, "tface");
1168                 efa= em->faces.first;
1169                 while(efa) {
1170                                 
1171                         *tf= efa->tf;
1172                                 
1173                         if(G.f & G_FACESELECT) {
1174                                 if( efa->h) tf->flag |= TF_HIDE;
1175                                 else tf->flag &= ~TF_HIDE;
1176                                 if( efa->f & SELECT)  tf->flag |= TF_SELECT;
1177                                 else tf->flag &= ~TF_SELECT;
1178                         }
1179                                 
1180                         tf++;
1181                         efa= efa->next;
1182                 }
1183
1184                 if(me->tface) MEM_freeN(me->tface);
1185                 me->tface= tfn;
1186         }
1187         else if(me->tface) {
1188                 MEM_freeN(me->tface);
1189                 me->tface= NULL;
1190         }
1191                 
1192         /* mcol: same as tface... */
1193         if(me->mcol && me->totface) {
1194                 unsigned int *mcn, *mc;
1195
1196                 mc=mcn= MEM_mallocN(4*sizeof(int)*me->totface, "mcol");
1197                 efa= em->faces.first;
1198                 while(efa) {
1199                         memcpy(mc, efa->tf.col, 4*sizeof(int));
1200                                 
1201                         mc+=4;
1202                         efa= efa->next;
1203                 }
1204                 if(me->mcol) MEM_freeN(me->mcol);
1205                         me->mcol= (MCol *)mcn;
1206         }
1207         else if(me->mcol) {
1208                 MEM_freeN(me->mcol);
1209                 me->mcol= 0;
1210         }
1211
1212         /* patch hook indices */
1213         {
1214                 Object *ob;
1215                 ModifierData *md;
1216                 EditVert *eve, **vertMap = NULL;
1217                 int i,j;
1218
1219                 for (ob=G.main->object.first; ob; ob=ob->id.next) {
1220                         if (ob->data==me) {
1221                                 for (md=ob->modifiers.first; md; md=md->next) {
1222                                         if (md->type==eModifierType_Hook) {
1223                                                 HookModifierData *hmd = (HookModifierData*) md;
1224
1225                                                 if (!vertMap) {
1226                                                         vertMap = MEM_callocN(sizeof(*vertMap)*ototvert, "vertMap");
1227
1228                                                         for (eve=em->verts.first; eve; eve=eve->next) {
1229                                                                 if (eve->keyindex!=-1)
1230                                                                         vertMap[eve->keyindex] = eve;
1231                                                         }
1232                                                 }
1233                                                 
1234                                                 for (i=j=0; i<hmd->totindex; i++) {
1235                                                         if(hmd->indexar[i] < ototvert) {
1236                                                                 eve = vertMap[hmd->indexar[i]];
1237                                                                 
1238                                                                 if (eve) {
1239                                                                         hmd->indexar[j++] = eve->tmp.l;
1240                                                                 }
1241                                                         }
1242                                                         else j++;
1243                                                 }
1244
1245                                                 hmd->totindex = j;
1246                                         }
1247                                 }
1248                         }
1249                 }
1250
1251                 if (vertMap) MEM_freeN(vertMap);
1252         }
1253
1254         /* are there keys? */
1255         if(me->key) {
1256                 KeyBlock *currkey, *actkey = ob_get_keyblock(G.obedit);
1257
1258                 /* Lets reorder the key data so that things line up roughly
1259                  * with the way things were before editmode */
1260                 currkey = me->key->block.first;
1261                 while(currkey) {
1262                         
1263                         fp= newkey= MEM_callocN(me->key->elemsize*G.totvert,  "currkey->data");
1264                         oldkey = currkey->data;
1265
1266                         eve= em->verts.first;
1267
1268                         i = 0;
1269                         mvert = me->mvert;
1270                         while(eve) {
1271                                 if (eve->keyindex >= 0 && eve->keyindex < currkey->totelem) { // valid old vertex
1272                                         if(currkey == actkey) {
1273                                                 if (actkey == me->key->refkey) {
1274                                                         VECCOPY(fp, mvert->co);
1275                                                 }
1276                                                 else {
1277                                                         VECCOPY(fp, mvert->co);
1278                                                         if(oldverts) {
1279                                                                 VECCOPY(mvert->co, oldverts[eve->keyindex].co);
1280                                                         }
1281                                                 }
1282                                         }
1283                                         else {
1284                                                 if(oldkey) {
1285                                                         VECCOPY(fp, oldkey + 3 * eve->keyindex);
1286                                                 }
1287                                         }
1288                                 }
1289                                 else {
1290                                         VECCOPY(fp, mvert->co);
1291                                 }
1292                                 fp+= 3;
1293                                 ++i;
1294                                 ++mvert;
1295                                 eve= eve->next;
1296                         }
1297                         currkey->totelem= G.totvert;
1298                         if(currkey->data) MEM_freeN(currkey->data);
1299                         currkey->data = newkey;
1300                         
1301                         currkey= currkey->next;
1302                 }
1303         }
1304
1305         if(oldverts) MEM_freeN(oldverts);
1306         
1307         i = 0;
1308         for(ese=em->selected.first; ese; ese=ese->next) i++;
1309         me->totselect = i;
1310         if(i==0) mselect= NULL;
1311         else mselect= MEM_callocN(i*sizeof(MSelect), "loadeditMesh selections");
1312         
1313         if(me->mselect) MEM_freeN(me->mselect);
1314         me->mselect= mselect;
1315         
1316         for(ese=em->selected.first; ese; ese=ese->next){
1317                 mselect->type = ese->type;
1318                 if(ese->type == EDITVERT) mselect->index = ((EditVert*)ese->data)->tmp.l;
1319                 else if(ese->type == EDITEDGE) mselect->index = ((EditEdge*)ese->data)->tmp.l;
1320                 else if(ese->type == EDITFACE) mselect->index = ((EditFace*)ese->data)->tmp.l;
1321                 mselect++;
1322         }
1323         
1324         /* to be sure: clear ->tmp.l pointers */
1325         eve= em->verts.first;
1326         while(eve) {
1327                 eve->tmp.l = 0;
1328                 eve= eve->next;
1329         }
1330         
1331         eed= em->edges.first;
1332         while(eed) { 
1333                 eed->tmp.l = 0;
1334                 eed= eed->next;
1335         }
1336         
1337         efa= em->faces.first;
1338         while(efa) {
1339                 efa->tmp.l = 0;
1340                 efa= efa->next;
1341         }
1342         
1343         /* remake softbody of all users */
1344         if(me->id.us>1) {
1345                 Base *base;
1346                 for(base= G.scene->base.first; base; base= base->next) {
1347                         if(base->object->data==me) {
1348                                 base->object->softflag |= OB_SB_REDO;
1349                                 base->object->recalc |= OB_RECALC_DATA;
1350                         }
1351                 }
1352         }
1353         
1354         /* sticky */
1355         if(me->msticky) {
1356                 if (ototvert<me->totvert) {
1357                         ms= MEM_callocN(me->totvert*sizeof(MSticky), "msticky");
1358                         memcpy(ms, me->msticky, ototvert*sizeof(MSticky));
1359                         MEM_freeN(me->msticky);
1360                         me->msticky= ms;
1361                         error("Sticky was too small");
1362                 }
1363         }
1364
1365         mesh_calc_normals(me->mvert, me->totvert, me->mface, me->totface, NULL);
1366 }
1367
1368 void remake_editMesh(void)
1369 {
1370         make_editMesh();
1371         allqueue(REDRAWVIEW3D, 0);
1372         DAG_object_flush_update(G.scene, G.obedit, OB_RECALC_DATA);
1373         BIF_undo_push("Undo all changes");
1374 }
1375
1376 /* ***************              (partial exit editmode) *************/
1377
1378
1379 void separatemenu(void)
1380 {
1381         short event;
1382
1383         if(G.editMesh->verts.first==NULL) return;
1384            
1385         event = pupmenu("Separate %t|Selected%x1|All Loose Parts%x2|By Material%x3");
1386         
1387         if (event==0) return;
1388         waitcursor(1);
1389         
1390         switch (event) {
1391         case 1: 
1392                 separate_mesh();                    
1393                 break;
1394         case 2:                     
1395                 separate_mesh_loose();              
1396                 break;
1397         case 3:
1398                 separate_material();
1399                 break;
1400         }
1401         waitcursor(0);
1402 }
1403
1404 void separate_material(void)
1405 {
1406         EditMesh *em = G.editMesh;
1407         unsigned char curr_mat;
1408         Mesh *me;
1409         
1410         me= get_mesh(G.obedit);
1411         if(me->key) {
1412                 error("Can't separate with vertex keys");
1413                 return;
1414         }
1415
1416         if(G.obedit && em) {
1417                 if(G.obedit->type == OB_MESH) {
1418                         for (curr_mat = 1; curr_mat < G.obedit->totcol; ++curr_mat) {
1419                                 /* clear selection, we're going to use that to select material group */
1420                                 EM_clear_flag_all(SELECT);
1421                                 /* select the material */
1422                                 editmesh_select_by_material(curr_mat);
1423                                 /* and now separate */
1424                                 separate_mesh();
1425                         }
1426                 }
1427         }
1428         
1429         countall();
1430         allqueue(REDRAWVIEW3D, 0);
1431         DAG_object_flush_update(G.scene, G.obedit, OB_RECALC_DATA);
1432
1433 }
1434
1435 void separate_mesh(void)
1436 {
1437         EditMesh *em = G.editMesh;
1438         EditMesh emcopy;
1439         EditVert *eve, *v1;
1440         EditEdge *eed, *e1;
1441         EditFace *efa, *vl1;
1442         Object *oldob;
1443         Mesh *me, *men;
1444         Base *base, *oldbase;
1445         ListBase edve, eded, edvl;
1446 #ifdef WITH_VERSE
1447         struct VNode *vnode = NULL;
1448 #endif
1449         
1450         TEST_EDITMESH   
1451
1452         waitcursor(1);
1453         
1454         me= get_mesh(G.obedit);
1455         if(me->key) {
1456                 error("Can't separate with vertex keys");
1457                 return;
1458         }
1459         
1460         if(em->selected.first) BLI_freelistN(&(em->selected)); /* clear the selection order */
1461                 
1462         EM_selectmode_set();    // enforce full consistant selection flags 
1463         
1464         /* we are going to abuse the system as follows:
1465          * 1. add a duplicate object: this will be the new one, we remember old pointer
1466          * 2: then do a split if needed.
1467          * 3. put apart: all NOT selected verts, edges, faces
1468          * 4. call load_editMesh(): this will be the new object
1469          * 5. freelist and get back old verts, edges, facs
1470          */
1471         
1472         /* make only obedit selected */
1473         base= FIRSTBASE;
1474         while(base) {
1475                 if(base->lay & G.vd->lay) {
1476                         if(base->object==G.obedit) base->flag |= SELECT;
1477                         else base->flag &= ~SELECT;
1478                 }
1479                 base= base->next;
1480         }
1481         
1482 #ifdef WITH_VERSE
1483         if(G.editMesh->vnode) {
1484                 vnode = G.editMesh->vnode;
1485                 G.editMesh->vnode = NULL;
1486         }
1487 #endif
1488         /* no test for split, split doesn't split when a loose part is selected */
1489         /* SPLIT: first make duplicate */
1490         adduplicateflag(SELECT);
1491
1492 #ifdef WITH_VERSE
1493         if(vnode) {
1494                 G.editMesh->vnode = vnode;
1495         }
1496 #endif
1497         /* SPLIT: old faces have 3x flag 128 set, delete these ones */
1498         delfaceflag(128);
1499         
1500         /* since we do tricky things with verts/edges/faces, this makes sure all is selected coherent */
1501         EM_selectmode_set();
1502         
1503         /* set apart: everything that is not selected */
1504         edve.first= edve.last= eded.first= eded.last= edvl.first= edvl.last= 0;
1505         eve= em->verts.first;
1506         while(eve) {
1507                 v1= eve->next;
1508                 if((eve->f & SELECT)==0) {
1509                         BLI_remlink(&em->verts, eve);
1510                         BLI_addtail(&edve, eve);
1511 #ifdef WITH_VERSE
1512                         if(eve->vvert) {
1513                                 ((VerseVert*)eve->vvert)->vertex = NULL;
1514                                 eve->vvert = NULL;
1515                         }
1516 #endif
1517                 }
1518                 
1519                 eve= v1;
1520         }
1521         eed= em->edges.first;
1522         while(eed) {
1523                 e1= eed->next;
1524                 if((eed->f & SELECT)==0) {
1525                         BLI_remlink(&em->edges, eed);
1526                         BLI_addtail(&eded, eed);
1527                 }
1528                 eed= e1;
1529         }
1530         efa= em->faces.first;
1531         while(efa) {
1532                 vl1= efa->next;
1533                 if((efa->f & SELECT)==0) {
1534                         BLI_remlink(&em->faces, efa);
1535                         BLI_addtail(&edvl, efa);
1536 #ifdef WITH_VERSE
1537                         if(efa->vface) {
1538                                 ((VerseFace*)efa->vface)->face = NULL;
1539                                 efa->vface = NULL;
1540                         }
1541 #endif
1542                 }
1543                 efa= vl1;
1544         }
1545         
1546         oldob= G.obedit;
1547         oldbase= BASACT;
1548         
1549 #ifdef WITH_VERSE
1550         if(G.obedit->vnode) {
1551                 vnode = G.obedit->vnode;
1552                 G.obedit->vnode = NULL;
1553         }
1554 #endif
1555         adduplicate(1, 0); /* notrans and a linked duplicate*/
1556 #ifdef WITH_VERSE
1557         if(vnode) {
1558                 G.obedit->vnode = vnode;
1559         }
1560 #endif
1561         
1562         G.obedit= BASACT->object;       /* basact was set in adduplicate()  */
1563
1564         men= copy_mesh(me);
1565         set_mesh(G.obedit, men);
1566         /* because new mesh is a copy: reduce user count */
1567         men->id.us--;
1568         
1569         load_editMesh();
1570         
1571         BASACT->flag &= ~SELECT;
1572         
1573         /* we cannot free the original buffer... */
1574         emcopy= *G.editMesh;
1575         emcopy.allverts= NULL;
1576         emcopy.alledges= NULL;
1577         emcopy.allfaces= NULL;
1578         emcopy.derivedFinal= emcopy.derivedCage= NULL;
1579         free_editMesh(&emcopy);
1580         
1581         em->verts= edve;
1582         em->edges= eded;
1583         em->faces= edvl;
1584         
1585         /* hashedges are freed now, make new! */
1586         editMesh_set_hash();
1587
1588         DAG_object_flush_update(G.scene, G.obedit, OB_RECALC_DATA);     
1589         G.obedit= oldob;
1590         BASACT= oldbase;
1591         BASACT->flag |= SELECT;
1592         
1593         waitcursor(0);
1594
1595         countall();
1596         allqueue(REDRAWVIEW3D, 0);
1597         DAG_object_flush_update(G.scene, G.obedit, OB_RECALC_DATA);     
1598
1599 }
1600
1601 void separate_mesh_loose(void)
1602 {
1603         EditMesh *em = G.editMesh;
1604         EditMesh emcopy;
1605         EditVert *eve, *v1;
1606         EditEdge *eed, *e1;
1607         EditFace *efa, *vl1;
1608         Object *oldob=NULL;
1609         Mesh *me, *men;
1610         Base *base, *oldbase;
1611         ListBase edve, eded, edvl;
1612         int vertsep=0;  
1613         short done=0, check=1;
1614 #ifdef WITH_VERSE
1615         struct VNode *vnode = NULL;
1616 #endif
1617                         
1618         me= get_mesh(G.obedit);
1619 #ifdef WITH_VERSE
1620         if(me->vnode) {
1621                 error("Can't separate a mesh shared at verse server");
1622                 return;
1623         }
1624 #endif
1625         if(me->key) {
1626                 error("Can't separate a mesh with vertex keys");
1627                 return;
1628         }
1629         
1630         TEST_EDITMESH
1631         waitcursor(1);  
1632         
1633         /* we are going to abuse the system as follows:
1634          * 1. add a duplicate object: this will be the new one, we remember old pointer
1635          * 2: then do a split if needed.
1636          * 3. put apart: all NOT selected verts, edges, faces
1637          * 4. call load_editMesh(): this will be the new object
1638          * 5. freelist and get back old verts, edges, facs
1639          */
1640                         
1641         while(!done){           
1642                 vertsep=check=1;
1643                 
1644                 countall();
1645                 
1646                 /* make only obedit selected */
1647                 base= FIRSTBASE;
1648                 while(base) {
1649                         if(base->lay & G.vd->lay) {
1650                                 if(base->object==G.obedit) base->flag |= SELECT;
1651                                 else base->flag &= ~SELECT;
1652                         }
1653                         base= base->next;
1654                 }               
1655                 
1656                 /*--------- Select connected-----------*/               
1657                 
1658                 EM_clear_flag_all(SELECT);
1659
1660                 /* Select a random vert to start with */
1661                 eve= em->verts.first;
1662                 eve->f |= SELECT;
1663                 
1664                 while(check==1) {
1665                         check= 0;                       
1666                         eed= em->edges.first;                   
1667                         while(eed) {                            
1668                                 if(eed->h==0) {
1669                                         if(eed->v1->f & SELECT) {
1670                                                 if( (eed->v2->f & SELECT)==0 ) {
1671                                                         eed->v2->f |= SELECT;
1672                                                         vertsep++;
1673                                                         check= 1;
1674                                                 }
1675                                         }
1676                                         else if(eed->v2->f & SELECT) {
1677                                                 if( (eed->v1->f & SELECT)==0 ) {
1678                                                         eed->v1->f |= SELECT;
1679                                                         vertsep++;
1680                                                         check= SELECT;
1681                                                 }
1682                                         }
1683                                 }
1684                                 eed= eed->next;                         
1685                         }
1686                 }               
1687                 /*----------End of select connected--------*/
1688                 
1689                 
1690                 /* If the amount of vertices that is about to be split == the total amount 
1691                    of verts in the mesh, it means that there is only 1 unconnected object, so we don't have to separate
1692                 */
1693                 if(G.totvert==vertsep) done=1;                          
1694                 else{                   
1695                         /* No splitting: select connected goes fine */
1696                         
1697                         EM_select_flush();      // from verts->edges->faces
1698
1699                         /* set apart: everything that is not selected */
1700                         edve.first= edve.last= eded.first= eded.last= edvl.first= edvl.last= 0;
1701                         eve= em->verts.first;
1702                         while(eve) {
1703                                 v1= eve->next;
1704                                 if((eve->f & SELECT)==0) {
1705                                         BLI_remlink(&em->verts, eve);
1706                                         BLI_addtail(&edve, eve);
1707 #ifdef WITH_VERSE
1708                                         if(eve->vvert) {
1709                                                 b_verse_send_vertex_delete(eve);
1710                                         }
1711 #endif
1712                                 }
1713                                 eve= v1;
1714                         }
1715                         eed= em->edges.first;
1716                         while(eed) {
1717                                 e1= eed->next;
1718                                 if( (eed->f & SELECT)==0 ) {
1719                                         BLI_remlink(&em->edges, eed);
1720                                         BLI_addtail(&eded, eed);
1721                                 }
1722                                 eed= e1;
1723                         }
1724                         efa= em->faces.first;
1725                         while(efa) {
1726                                 vl1= efa->next;
1727                                 if( (efa->f & SELECT)==0 ) {
1728                                         BLI_remlink(&em->faces, efa);
1729                                         BLI_addtail(&edvl, efa);
1730 #ifdef WITH_VERSE
1731                                         if(efa->vface) {
1732                                                 b_verse_send_face_delete(efa);
1733                                         }
1734 #endif
1735                                 }
1736                                 efa= vl1;
1737                         }
1738                         
1739                         oldob= G.obedit;
1740                         oldbase= BASACT;
1741                         
1742 #ifdef WITH_VERSE
1743                         if(G.obedit->vnode) {
1744                                 vnode = G.obedit->vnode;
1745                                 G.obedit->vnode = NULL;
1746                         }
1747 #endif
1748                         adduplicate(1, 0); /* notrans and a linked duplicate*/
1749 #ifdef WITH_VERSE
1750                         if(vnode) {
1751                                 G.obedit->vnode = vnode;
1752                         }
1753 #endif
1754                         
1755                         G.obedit= BASACT->object;       /* basact was set in adduplicate()  */
1756
1757                         men= copy_mesh(me);
1758                         set_mesh(G.obedit, men);
1759                         /* because new mesh is a copy: reduce user count */
1760                         men->id.us--;
1761                         
1762                         load_editMesh();
1763                         
1764                         BASACT->flag &= ~SELECT;
1765                         
1766                         /* we cannot free the original buffer... */
1767                         emcopy= *G.editMesh;
1768                         emcopy.allverts= NULL;
1769                         emcopy.alledges= NULL;
1770                         emcopy.allfaces= NULL;
1771                         emcopy.derivedFinal= emcopy.derivedCage= NULL;
1772                         free_editMesh(&emcopy);
1773                         
1774                         em->verts= edve;
1775                         em->edges= eded;
1776                         em->faces= edvl;
1777                         
1778                         /* hashedges are freed now, make new! */
1779                         editMesh_set_hash();
1780                         
1781                         G.obedit= oldob;
1782                         BASACT= oldbase;
1783                         BASACT->flag |= SELECT; 
1784                                         
1785                 }               
1786         }
1787         
1788         /* unselect the vertices that we (ab)used for the separation*/
1789         EM_clear_flag_all(SELECT);
1790                 
1791         waitcursor(0);
1792         countall();
1793         allqueue(REDRAWVIEW3D, 0);
1794         DAG_object_flush_update(G.scene, G.obedit, OB_RECALC_DATA);     
1795 }
1796
1797 /* ******************************************** */
1798
1799 /* *************** UNDO ***************************** */
1800 /* new mesh undo, based on pushing editmesh data itself */
1801 /* reuses same code as for global and curve undo... unify that (ton) */
1802
1803 /* only one 'hack', to save memory it doesn't store the first push, but does a remake editmesh */
1804
1805 /* a compressed version of editmesh data */
1806
1807 typedef struct EditVertC
1808 {
1809         float no[3];
1810         float co[3];
1811         unsigned char f, h;
1812         short totweight;
1813         struct MDeformWeight *dw;
1814         int keyindex;
1815 } EditVertC;
1816
1817 typedef struct EditEdgeC
1818 {
1819         int v1, v2;
1820         unsigned char f, h, seam, sharp, pad;
1821         short crease, fgoni;
1822 } EditEdgeC;
1823
1824 typedef struct EditFaceC
1825 {
1826         int v1, v2, v3, v4;
1827         unsigned char mat_nr, flag, f, h, fgonf;
1828         short pad1;
1829 } EditFaceC;
1830
1831 typedef struct EditSelectionC{
1832         short type;
1833         int index;
1834 }EditSelectionC;
1835
1836
1837 typedef struct UndoMesh {
1838         EditVertC *verts;
1839         EditEdgeC *edges;
1840         EditFaceC *faces;
1841         EditSelectionC *selected;
1842         TFace *tfaces;
1843         int totvert, totedge, totface,totsel;
1844         short selectmode;
1845         RetopoPaintData *retopo_paint_data;
1846         char retopo_mode;
1847 } UndoMesh;
1848
1849
1850 /* for callbacks */
1851
1852 static void free_undoMesh(void *umv)
1853 {
1854         UndoMesh *um= umv;
1855         EditVertC *evec;
1856         int a;
1857         
1858         for(a=0, evec= um->verts; a<um->totvert; a++, evec++) {
1859                 if(evec->dw) MEM_freeN(evec->dw);
1860         }
1861         
1862         if(um->verts) MEM_freeN(um->verts);
1863         if(um->edges) MEM_freeN(um->edges);
1864         if(um->faces) MEM_freeN(um->faces);
1865         if(um->tfaces) MEM_freeN(um->tfaces);
1866         if(um->selected) MEM_freeN(um->selected);
1867         if(um->retopo_paint_data) retopo_free_paint_data(um->retopo_paint_data);
1868         MEM_freeN(um);
1869 }
1870
1871 static void *editMesh_to_undoMesh(void)
1872 {
1873         EditMesh *em= G.editMesh;
1874         UndoMesh *um;
1875         Mesh *me= G.obedit->data;
1876         EditVert *eve;
1877         EditEdge *eed;
1878         EditFace *efa;
1879         EditSelection *ese;
1880         EditVertC *evec=NULL;
1881         EditEdgeC *eedc=NULL;
1882         EditFaceC *efac=NULL;
1883         EditSelectionC *esec=NULL;
1884         TFace *tface= NULL;
1885         int a;
1886         
1887         um= MEM_callocN(sizeof(UndoMesh), "undomesh");
1888         
1889         um->selectmode = G.scene->selectmode;
1890         
1891         for(eve=em->verts.first; eve; eve= eve->next) um->totvert++;
1892         for(eed=em->edges.first; eed; eed= eed->next) um->totedge++;
1893         for(efa=em->faces.first; efa; efa= efa->next) um->totface++;
1894         for(ese=em->selected.first; ese; ese=ese->next) um->totsel++; 
1895         /* malloc blocks */
1896         
1897         if(um->totvert) evec= um->verts= MEM_callocN(um->totvert*sizeof(EditVertC), "allvertsC");
1898         if(um->totedge) eedc= um->edges= MEM_callocN(um->totedge*sizeof(EditEdgeC), "alledgesC");
1899         if(um->totface) efac= um->faces= MEM_callocN(um->totface*sizeof(EditFaceC), "allfacesC");
1900         if(um->totsel) esec= um->selected= MEM_callocN(um->totsel*sizeof(EditSelectionC), "allselections");
1901         
1902         if(me->tface || me->mcol) tface= um->tfaces= MEM_mallocN(um->totface*sizeof(TFace), "all tfacesC");
1903
1904                 //printf("copy editmesh %d\n", um->totvert*sizeof(EditVert) + um->totedge*sizeof(EditEdge) + um->totface*sizeof(EditFace));
1905                 //printf("copy undomesh %d\n", um->totvert*sizeof(EditVertC) + um->totedge*sizeof(EditEdgeC) + um->totface*sizeof(EditFaceC));
1906         
1907         /* now copy vertices */
1908         a = 0;
1909         for(eve=em->verts.first; eve; eve= eve->next, evec++, a++) {
1910                 VECCOPY(evec->co, eve->co);
1911                 VECCOPY(evec->no, eve->no);
1912
1913                 evec->f= eve->f;
1914                 evec->h= eve->h;
1915                 evec->keyindex= eve->keyindex;
1916                 evec->totweight= eve->totweight;
1917                 evec->dw= MEM_dupallocN(eve->dw);
1918                 eve->tmp.l = a; /*store index*/
1919         }
1920         
1921         /* copy edges */
1922         a = 0;
1923         for(eed=em->edges.first; eed; eed= eed->next, eedc++, a++)  {
1924                 eedc->v1= (int)eed->v1->tmp.l;
1925                 eedc->v2= (int)eed->v2->tmp.l;
1926                 eedc->f= eed->f;
1927                 eedc->h= eed->h;
1928                 eedc->seam= eed->seam;
1929                 eedc->sharp= eed->sharp;
1930                 eedc->crease= (short)(eed->crease*255.0);
1931                 eedc->fgoni= eed->fgoni;
1932                 eed->tmp.l = a; /*store index*/
1933         }
1934         
1935         /* copy faces */
1936         a = 0;
1937         for(efa=em->faces.first; efa; efa= efa->next, efac++, a++) {
1938                 efac->v1= (int)efa->v1->tmp.l;
1939                 efac->v2= (int)efa->v2->tmp.l;
1940                 efac->v3= (int)efa->v3->tmp.l;
1941                 if(efa->v4) efac->v4= (int)efa->v4->tmp.l;
1942                 else efac->v4= -1;
1943                 
1944                 efac->mat_nr= efa->mat_nr;
1945                 efac->flag= efa->flag;
1946                 efac->f= efa->f;
1947                 efac->h= efa->h;
1948                 efac->fgonf= efa->fgonf;
1949                 
1950                 if(tface) {
1951                         *tface= efa->tf;
1952                         tface++;
1953                 }
1954                 efa->tmp.l = a; /*store index*/
1955         }
1956         
1957         a = 0;
1958         for(ese=em->selected.first; ese; ese=ese->next, esec++){
1959                 esec->type = ese->type;
1960                 if(ese->type == EDITVERT) a = esec->index = ((EditVert*)ese->data)->tmp.l; 
1961                 else if(ese->type == EDITEDGE) a = esec->index = ((EditEdge*)ese->data)->tmp.l; 
1962                 else if(ese->type == EDITFACE) a = esec->index = ((EditFace*)ese->data)->tmp.l;
1963         }
1964
1965         um->retopo_paint_data= retopo_paint_data_copy(em->retopo_paint_data);
1966         um->retopo_mode= em->retopo_mode;
1967         
1968         return um;
1969 }
1970
1971 static void undoMesh_to_editMesh(void *umv)
1972 {
1973         UndoMesh *um= (UndoMesh*)umv;
1974         EditMesh *em= G.editMesh;
1975         EditVert *eve, **evar=NULL;
1976         EditEdge *eed;
1977         EditFace *efa;
1978         EditSelection *ese;
1979         EditVertC *evec;
1980         EditEdgeC *eedc;
1981         EditFaceC *efac;
1982         EditSelectionC *esec;
1983         TFace *tface;
1984         int a=0;
1985
1986 #ifdef WITH_VERSE
1987         struct VNode *vnode = G.editMesh->vnode;
1988         if(vnode) {
1989                 /* send delete command to all verse vertexes and verse face ...
1990                  * verse mesh will be recreated from new edit mesh */
1991                 destroy_versemesh(vnode);
1992         }
1993 #endif  
1994         G.scene->selectmode = um->selectmode;
1995         
1996         free_editMesh(G.editMesh);
1997         
1998         /* malloc blocks */
1999         memset(em, 0, sizeof(EditMesh));
2000                 
2001         init_editmesh_fastmalloc(em, um->totvert, um->totedge, um->totface);
2002
2003 #ifdef WITH_VERSE
2004         G.editMesh->vnode = vnode;
2005 #endif
2006
2007         /* now copy vertices */
2008         if(um->totvert) evar= MEM_mallocN(um->totvert*sizeof(EditVert *), "vertex ar");
2009         for(a=0, evec= um->verts; a<um->totvert; a++, evec++) {
2010                 eve= addvertlist(evec->co);
2011                 evar[a]= eve;
2012
2013                 VECCOPY(eve->no, evec->no);
2014                 eve->f= evec->f;
2015                 eve->h= evec->h;
2016                 eve->totweight= evec->totweight;
2017                 eve->keyindex= evec->keyindex;
2018                 eve->dw= MEM_dupallocN(evec->dw);
2019         }
2020
2021         /* copy edges */
2022         for(a=0, eedc= um->edges; a<um->totedge; a++, eedc++) {
2023                 eed= addedgelist(evar[eedc->v1], evar[eedc->v2], NULL);
2024
2025                 eed->f= eedc->f;
2026                 eed->h= eedc->h;
2027                 eed->seam= eedc->seam;
2028                 eed->sharp= eedc->sharp;
2029                 eed->fgoni= eedc->fgoni;
2030                 eed->crease= ((float)eedc->crease)/255.0;
2031         }
2032         
2033         /* copy faces */
2034         tface= um->tfaces;
2035         for(a=0, efac= um->faces; a<um->totface; a++, efac++) {
2036                 if(efac->v4 != -1)
2037                         efa= addfacelist(evar[efac->v1], evar[efac->v2], evar[efac->v3], evar[efac->v4], NULL, NULL);
2038                 else 
2039                         efa= addfacelist(evar[efac->v1], evar[efac->v2], evar[efac->v3], NULL, NULL ,NULL);
2040
2041                 efa->mat_nr= efac->mat_nr;
2042                 efa->flag= efac->flag;
2043                 efa->f= efac->f;
2044                 efa->h= efac->h;
2045                 efa->fgonf= efac->fgonf;
2046                 
2047                 if(tface) {
2048                         efa->tf= *tface;
2049                         tface++;
2050                 }
2051         }
2052         
2053         end_editmesh_fastmalloc();
2054         if(evar) MEM_freeN(evar);
2055         
2056         G.totvert = um->totvert;
2057         G.totedge = um->totedge;
2058         G.totface = um->totface;
2059         /*restore stored editselections*/
2060         if(um->totsel){
2061                 EM_init_index_arrays(1,1,1);
2062                 for(a=0, esec= um->selected; a<um->totsel; a++, esec++){
2063                         ese = MEM_callocN(sizeof(EditSelection), "Edit Selection");
2064                         ese->type = esec->type;
2065                         if(ese->type == EDITVERT) ese->data = EM_get_vert_for_index(esec->index); else
2066                         if(ese->type == EDITEDGE) ese->data = EM_get_edge_for_index(esec->index); else
2067                         if(ese->type == EDITFACE) ese->data = EM_get_face_for_index(esec->index);
2068                         BLI_addtail(&(em->selected),ese);
2069                 }
2070                 EM_free_index_arrays();
2071         }
2072
2073         retopo_free_paint();
2074         em->retopo_paint_data= retopo_paint_data_copy(um->retopo_paint_data);
2075         em->retopo_mode= um->retopo_mode;
2076 }
2077
2078
2079 /* and this is all the undo system needs to know */
2080 void undo_push_mesh(char *name)
2081 {
2082         undo_editmode_push(name, free_undoMesh, undoMesh_to_editMesh, editMesh_to_undoMesh);
2083 }
2084
2085
2086
2087 /* *************** END UNDO *************/
2088
2089 static EditVert **g_em_vert_array = NULL;
2090 static EditEdge **g_em_edge_array = NULL;
2091 static EditFace **g_em_face_array = NULL;
2092
2093 void EM_init_index_arrays(int forVert, int forEdge, int forFace)
2094 {
2095         EditVert *eve;
2096         EditEdge *eed;
2097         EditFace *efa;
2098         int i;
2099
2100         if (forVert) {
2101                 g_em_vert_array = MEM_mallocN(sizeof(*g_em_vert_array)*G.totvert, "em_v_arr");
2102
2103                 for (i=0,eve=G.editMesh->verts.first; eve; i++,eve=eve->next)
2104                         g_em_vert_array[i] = eve;
2105         }
2106
2107         if (forEdge) {
2108                 g_em_edge_array = MEM_mallocN(sizeof(*g_em_edge_array)*G.totedge, "em_e_arr");
2109
2110                 for (i=0,eed=G.editMesh->edges.first; eed; i++,eed=eed->next)
2111                         g_em_edge_array[i] = eed;
2112         }
2113
2114         if (forFace) {
2115                 g_em_face_array = MEM_mallocN(sizeof(*g_em_face_array)*G.totface, "em_f_arr");
2116
2117                 for (i=0,efa=G.editMesh->faces.first; efa; i++,efa=efa->next)
2118                         g_em_face_array[i] = efa;
2119         }
2120 }
2121
2122 void EM_free_index_arrays(void)
2123 {
2124         if (g_em_vert_array) MEM_freeN(g_em_vert_array);
2125         if (g_em_edge_array) MEM_freeN(g_em_edge_array);
2126         if (g_em_face_array) MEM_freeN(g_em_face_array);
2127         g_em_vert_array = NULL;
2128         g_em_edge_array = NULL;
2129         g_em_face_array = NULL;
2130 }
2131
2132 EditVert *EM_get_vert_for_index(int index)
2133 {
2134         return g_em_vert_array?g_em_vert_array[index]:NULL;
2135 }
2136
2137 EditEdge *EM_get_edge_for_index(int index)
2138 {
2139         return g_em_edge_array?g_em_edge_array[index]:NULL;
2140 }
2141
2142 EditFace *EM_get_face_for_index(int index)
2143 {
2144         return g_em_face_array?g_em_face_array[index]:NULL;
2145 }