svn merge ^/trunk/blender -r40379:40381
[blender-staging.git] / source / blender / blenkernel / intern / subsurf_ccg.c
1 /*
2  * $Id$
3  *
4  * ***** BEGIN GPL 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.
10  *
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.
15  *
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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
19  *
20  * The Original Code is Copyright (C) 2005 Blender Foundation.
21  * All rights reserved.
22  *
23  * The Original Code is: all of this file.
24  *
25  * Contributor(s): none yet.
26  *
27  * ***** END GPL LICENSE BLOCK *****
28  */
29
30 /** \file blender/blenkernel/intern/subsurf_ccg.c
31  *  \ingroup bke
32  */
33
34
35 #include <stdlib.h>
36 #include <string.h>
37 #include <stdio.h>
38 #include <math.h>
39 #include <float.h>
40
41 #include "MEM_guardedalloc.h"
42
43 #include "DNA_mesh_types.h"
44 #include "DNA_meshdata_types.h"
45 #include "DNA_modifier_types.h"
46 #include "DNA_object_types.h"
47 #include "DNA_scene_types.h"
48
49 #include "BLI_utildefines.h"
50 #include "BLI_blenlib.h"
51 #include "BLI_edgehash.h"
52 #include "BLI_math.h"
53 #include "BLI_memarena.h"
54 #include "BLI_pbvh.h"
55
56 #include "BKE_cdderivedmesh.h"
57 #include "BKE_global.h"
58 #include "BKE_mesh.h"
59 #include "BKE_modifier.h"
60 #include "BKE_paint.h"
61 #include "BKE_scene.h"
62 #include "BKE_subsurf.h"
63 #include "BKE_tessmesh.h"
64
65 #include "PIL_time.h"
66 #include "BLI_array.h"
67
68 #include "GL/glew.h"
69
70 #include "GPU_draw.h"
71 #include "GPU_extensions.h"
72 #include "GPU_material.h"
73
74 #include "CCGSubSurf.h"
75
76 extern GLubyte stipple_quarttone[128]; /* glutil.c, bad level data */
77
78 static CCGDerivedMesh *getCCGDerivedMesh(CCGSubSurf *ss,
79                                          int drawInteriorEdges,
80                                          int useSubsurfUv,
81                                          DerivedMesh *dm);
82 static int ccgDM_use_grid_pbvh(CCGDerivedMesh *ccgdm);
83
84 ///
85
86 static void *arena_alloc(CCGAllocatorHDL a, int numBytes) {
87         return BLI_memarena_alloc(a, numBytes);
88 }
89 static void *arena_realloc(CCGAllocatorHDL a, void *ptr, int newSize, int oldSize) {
90         void *p2 = BLI_memarena_alloc(a, newSize);
91         if (ptr) {
92                 memcpy(p2, ptr, oldSize);
93         }
94         return p2;
95 }
96 static void arena_free(CCGAllocatorHDL UNUSED(a), void *UNUSED(ptr)) {
97 }
98 static void arena_release(CCGAllocatorHDL a) {
99         BLI_memarena_free(a);
100 }
101
102 static CCGSubSurf *_getSubSurf(CCGSubSurf *prevSS, int subdivLevels, int useAging, int useArena, int UNUSED(useFlatSubdiv)) {
103         CCGMeshIFC ifc;
104         CCGSubSurf *ccgSS;
105
106                 /* subdivLevels==0 is not allowed */
107         subdivLevels = MAX2(subdivLevels, 1);
108
109         if (prevSS) {
110                 int oldUseAging;
111
112                 useAging = !!useAging;
113                 ccgSubSurf_getUseAgeCounts(prevSS, &oldUseAging, NULL, NULL, NULL);
114
115                 if (oldUseAging!=useAging) {
116                         ccgSubSurf_free(prevSS);
117                 } else {
118                         ccgSubSurf_setSubdivisionLevels(prevSS, subdivLevels);
119
120                         return prevSS;
121                 }
122         }
123
124         if (useAging) {
125                 ifc.vertUserSize = ifc.edgeUserSize = ifc.faceUserSize = 12;
126         } else {
127                 ifc.vertUserSize = ifc.edgeUserSize = ifc.faceUserSize = 8;
128         }
129         ifc.vertDataSize = sizeof(DMGridData);
130
131         if (useArena) {
132                 CCGAllocatorIFC allocatorIFC;
133                 CCGAllocatorHDL allocator = BLI_memarena_new((1<<16), "subsurf arena");
134
135                 allocatorIFC.alloc = arena_alloc;
136                 allocatorIFC.realloc = arena_realloc;
137                 allocatorIFC.free = arena_free;
138                 allocatorIFC.release = arena_release;
139
140                 ccgSS = ccgSubSurf_new(&ifc, subdivLevels, &allocatorIFC, allocator);
141         } else {
142                 ccgSS = ccgSubSurf_new(&ifc, subdivLevels, NULL, NULL);
143         }
144
145         if (useAging) {
146                 ccgSubSurf_setUseAgeCounts(ccgSS, 1, 8, 8, 8);
147         }
148
149         ccgSubSurf_setCalcVertexNormals(ccgSS, 1, BLI_STRUCT_OFFSET(DMGridData, no));
150
151         return ccgSS;
152 }
153
154 static int getEdgeIndex(CCGSubSurf *ss, CCGEdge *e, int x, int edgeSize) {
155         CCGVert *v0 = ccgSubSurf_getEdgeVert0(e);
156         CCGVert *v1 = ccgSubSurf_getEdgeVert1(e);
157         int v0idx = *((int*) ccgSubSurf_getVertUserData(ss, v0));
158         int v1idx = *((int*) ccgSubSurf_getVertUserData(ss, v1));
159         int edgeBase = *((int*) ccgSubSurf_getEdgeUserData(ss, e));
160
161         if (x==0) {
162                 return v0idx;
163         } else if (x==edgeSize-1) {
164                 return v1idx;
165         } else {
166                 return edgeBase + x-1;
167         }
168 }
169
170 BM_INLINE int getFaceIndex(CCGSubSurf *ss, CCGFace *f, int S, int x, int y, int edgeSize, int gridSize) {
171         int faceBase = *((int*) ccgSubSurf_getFaceUserData(ss, f));
172         int numVerts = ccgSubSurf_getFaceNumVerts(f);
173
174         if (x==gridSize-1 && y==gridSize-1) {
175                 CCGVert *v = ccgSubSurf_getFaceVert(ss, f, S);
176                 return *((int*) ccgSubSurf_getVertUserData(ss, v));
177         } else if (x==gridSize-1) {
178                 CCGVert *v = ccgSubSurf_getFaceVert(ss, f, S);
179                 CCGEdge *e = ccgSubSurf_getFaceEdge(ss, f, S);
180                 int edgeBase = *((int*) ccgSubSurf_getEdgeUserData(ss, e));
181                 if (v==ccgSubSurf_getEdgeVert0(e)) {
182                         return edgeBase + (gridSize-1-y)-1;
183                 } else {
184                         return edgeBase + (edgeSize-2-1)-((gridSize-1-y)-1);
185                 }
186         } else if (y==gridSize-1) {
187                 CCGVert *v = ccgSubSurf_getFaceVert(ss, f, S);
188                 CCGEdge *e = ccgSubSurf_getFaceEdge(ss, f, (S+numVerts-1)%numVerts);
189                 int edgeBase = *((int*) ccgSubSurf_getEdgeUserData(ss, e));
190                 if (v==ccgSubSurf_getEdgeVert0(e)) {
191                         return edgeBase + (gridSize-1-x)-1;
192                 } else {
193                         return edgeBase + (edgeSize-2-1)-((gridSize-1-x)-1);
194                 }
195         } else if (x==0 && y==0) {
196                 return faceBase;
197         } else if (x==0) {
198                 S = (S+numVerts-1)%numVerts;
199                 return faceBase + 1 + (gridSize-2)*S + (y-1);
200         } else if (y==0) {
201                 return faceBase + 1 + (gridSize-2)*S + (x-1);
202         } else {
203                 return faceBase + 1 + (gridSize-2)*numVerts + S*(gridSize-2)*(gridSize-2) + (y-1)*(gridSize-2) + (x-1);
204         }
205 }
206
207 static void get_face_uv_map_vert(UvVertMap *vmap, struct MFace *mf, int fi, CCGVertHDL *fverts) {
208         unsigned int *fv = &mf->v1;
209         UvMapVert *v, *nv;
210         int j, nverts= mf->v4? 4: 3;
211
212         for (j=0; j<nverts; j++, fv++) {
213                 for (nv=v=get_uv_map_vert(vmap, *fv); v; v=v->next) {
214                         if (v->separate)
215                                 nv= v;
216                         if (v->f == fi)
217                                 break;
218                 }
219
220                 fverts[j]= SET_INT_IN_POINTER(nv->f*4 + nv->tfindex);
221         }
222 }
223
224 static int ss_sync_from_uv(CCGSubSurf *ss, CCGSubSurf *origss, DerivedMesh *dm, MTFace *tface) {
225 #if 1 /*BMESH_TODO*/
226         (void)ss;
227         (void)origss;
228         (void)dm;
229         (void)tface;
230 #else
231         MFace *mface = dm->getTessFaceArray(dm);
232         MVert *mvert = dm->getVertArray(dm);
233         int totvert = dm->getNumVerts(dm);
234         int totface = dm->getNumTessFaces(dm);
235         int i, j, seam;
236         UvMapVert *v;
237         UvVertMap *vmap;
238         float limit[2];
239         CCGVertHDL fverts[4];
240         EdgeHash *ehash;
241         float creaseFactor = (float)ccgSubSurf_getSubdivisionLevels(ss);
242
243         limit[0]= limit[1]= STD_UV_CONNECT_LIMIT;
244         vmap= make_uv_vert_map(mface, tface, totface, totvert, 0, limit);
245         if (!vmap)
246                 return 0;
247         
248         ccgSubSurf_initFullSync(ss);
249
250         /* create vertices */
251         for (i=0; i<totvert; i++) {
252                 if (!get_uv_map_vert(vmap, i))
253                         continue;
254
255                 for (v=get_uv_map_vert(vmap, i)->next; v; v=v->next)
256                         if (v->separate)
257                                 break;
258
259                 seam = (v != NULL) || ((mvert+i)->flag & ME_VERT_MERGED);
260
261                 for (v=get_uv_map_vert(vmap, i); v; v=v->next) {
262                         if (v->separate) {
263                                 CCGVert *ssv;
264                                 CCGVertHDL vhdl = SET_INT_IN_POINTER(v->f*4 + v->tfindex);
265                                 float uv[3];
266
267                                 uv[0]= (tface+v->f)->uv[v->tfindex][0];
268                                 uv[1]= (tface+v->f)->uv[v->tfindex][1];
269                                 uv[2]= 0.0f;
270
271                                 ccgSubSurf_syncVert(ss, vhdl, uv, seam, &ssv);
272                         }
273                 }
274         }
275
276         /* create edges */
277         ehash = BLI_edgehash_new();
278
279         for (i=0; i<totface; i++) {
280                 MFace *mf = &((MFace*) mface)[i];
281                 int nverts= mf->v4? 4: 3;
282                 CCGFace *origf= ccgSubSurf_getFace(origss, SET_INT_IN_POINTER(i));
283                 unsigned int *fv = &mf->v1;
284
285                 get_face_uv_map_vert(vmap, mf, i, fverts);
286
287                 for (j=0; j<nverts; j++) {
288                         int v0 = GET_INT_FROM_POINTER(fverts[j]);
289                         int v1 = GET_INT_FROM_POINTER(fverts[(j+1)%nverts]);
290                         MVert *mv0 = mvert + *(fv+j);
291                         MVert *mv1 = mvert + *(fv+((j+1)%nverts));
292
293                         if (!BLI_edgehash_haskey(ehash, v0, v1)) {
294                                 CCGEdge *e, *orige= ccgSubSurf_getFaceEdge(origss, origf, j);
295                                 CCGEdgeHDL ehdl= SET_INT_IN_POINTER(i*4 + j);
296                                 float crease;
297
298                                 if ((mv0->flag&mv1->flag) & ME_VERT_MERGED)
299                                         crease = creaseFactor;
300                                 else
301                                         crease = ccgSubSurf_getEdgeCrease(orige);
302
303                                 ccgSubSurf_syncEdge(ss, ehdl, fverts[j], fverts[(j+1)%nverts], crease, &e);
304                                 BLI_edgehash_insert(ehash, v0, v1, NULL);
305                         }
306                 }
307         }
308
309         BLI_edgehash_free(ehash, NULL);
310
311         /* create faces */
312         for (i=0; i<totface; i++) {
313                 MFace *mf = &((MFace*) mface)[i];
314                 int nverts= mf->v4? 4: 3;
315                 CCGFace *f;
316
317                 get_face_uv_map_vert(vmap, mf, i, fverts);
318                 ccgSubSurf_syncFace(ss, SET_INT_IN_POINTER(i), nverts, fverts, &f);
319         }
320
321         free_uv_vert_map(vmap);
322         ccgSubSurf_processSync(ss);
323
324 #endif
325         return 1;
326 }
327
328 static void set_subsurf_uv(CCGSubSurf *ss, DerivedMesh *dm, DerivedMesh *result, int n)
329 {
330         CCGSubSurf *uvss;
331         CCGFace **faceMap;
332         MTFace *tf;
333         CCGFaceIterator *fi;
334         int index, gridSize, gridFaces, /*edgeSize,*/ totface, x, y, S;
335         MTFace *dmtface = CustomData_get_layer_n(&dm->faceData, CD_MTFACE, n);
336         MTFace *tface = CustomData_get_layer_n(&result->faceData, CD_MTFACE, n);
337
338         if(!dmtface || !tface)
339                 return;
340
341         /* create a CCGSubSurf from uv's */
342         uvss = _getSubSurf(NULL, ccgSubSurf_getSubdivisionLevels(ss), 0, 1, 0);
343
344         if(!ss_sync_from_uv(uvss, ss, dm, dmtface)) {
345                 ccgSubSurf_free(uvss);
346                 return;
347         }
348
349         /* get some info from CCGSubSurf */
350         totface = ccgSubSurf_getNumFaces(uvss);
351         /* edgeSize = ccgSubSurf_getEdgeSize(uvss); */ /*UNUSED*/
352         gridSize = ccgSubSurf_getGridSize(uvss);
353         gridFaces = gridSize - 1;
354
355         /* make a map from original faces to CCGFaces */
356         faceMap = MEM_mallocN(totface*sizeof(*faceMap), "facemapuv");
357
358         fi = ccgSubSurf_getFaceIterator(uvss);
359         for(; !ccgFaceIterator_isStopped(fi); ccgFaceIterator_next(fi)) {
360                 CCGFace *f = ccgFaceIterator_getCurrent(fi);
361                 faceMap[GET_INT_FROM_POINTER(ccgSubSurf_getFaceFaceHandle(uvss, f))] = f;
362         }
363         ccgFaceIterator_free(fi);
364
365         /* load coordinates from uvss into tface */
366         tf= tface;
367
368         for(index = 0; index < totface; index++) {
369                 CCGFace *f = faceMap[index];
370                 int numVerts = ccgSubSurf_getFaceNumVerts(f);
371
372                 for (S=0; S<numVerts; S++) {
373                         DMGridData *faceGridData= ccgSubSurf_getFaceGridDataArray(uvss, f, S);
374
375                         for(y = 0; y < gridFaces; y++) {
376                                 for(x = 0; x < gridFaces; x++) {
377                                         float *a = faceGridData[(y + 0)*gridSize + x + 0].co;
378                                         float *b = faceGridData[(y + 0)*gridSize + x + 1].co;
379                                         float *c = faceGridData[(y + 1)*gridSize + x + 1].co;
380                                         float *d = faceGridData[(y + 1)*gridSize + x + 0].co;
381
382                                         tf->uv[0][0] = a[0]; tf->uv[0][1] = a[1];
383                                         tf->uv[1][0] = d[0]; tf->uv[1][1] = d[1];
384                                         tf->uv[2][0] = c[0]; tf->uv[2][1] = c[1];
385                                         tf->uv[3][0] = b[0]; tf->uv[3][1] = b[1];
386
387                                         tf++;
388                                 }
389                         }
390                 }
391         }
392
393         ccgSubSurf_free(uvss);
394         MEM_freeN(faceMap);
395 }
396
397 /* face weighting */
398 typedef struct FaceVertWeightEntry {
399         FaceVertWeight *weight;
400         float *w;
401         int valid;
402 } FaceVertWeightEntry;
403
404 typedef struct WeightTable {
405         FaceVertWeightEntry *weight_table;
406         int len;
407 } WeightTable;
408
409 static float *get_ss_weights(WeightTable *wtable, int gridCuts, int faceLen)
410 {
411         int x, y, i, j;
412         float *w, w1, w2, w4, fac, fac2, fx, fy;
413
414         if (wtable->len <= faceLen) {
415                 void *tmp = MEM_callocN(sizeof(FaceVertWeightEntry)*(faceLen+1), "weight table alloc 2");
416                 
417                 if (wtable->len) {
418                         memcpy(tmp, wtable->weight_table, sizeof(FaceVertWeightEntry)*wtable->len);
419                         MEM_freeN(wtable->weight_table);
420                 }
421                 
422                 wtable->weight_table = tmp;
423                 wtable->len = faceLen+1;
424         }
425
426         if (!wtable->weight_table[faceLen].valid) {
427                 wtable->weight_table[faceLen].valid = 1;
428                 wtable->weight_table[faceLen].w = w = MEM_callocN(sizeof(float)*faceLen*faceLen*(gridCuts+2)*(gridCuts+2), "weight table alloc");
429                 fac = 1.0f / (float)faceLen;
430
431                 for (i=0; i<faceLen; i++) {
432                         for (x=0; x<gridCuts+2; x++) {
433                                 for (y=0; y<gridCuts+2; y++) {
434                                         fx = 0.5f - (float)x / (float)(gridCuts+1) / 2.0f;
435                                         fy = 0.5f - (float)y / (float)(gridCuts+1) / 2.0f;
436                                 
437                                         fac2 = faceLen - 4;
438                                         w1 = (1.0f - fx) * (1.0f - fy) + (-fac2*fx*fy*fac);
439                                         w2 = (1.0f - fx + fac2*fx*-fac) * (fy);
440                                         w4 = (fx) * (1.0f - fy + -fac2*fy*fac);
441                                         
442                                         fac2 = 1.0f - (w1+w2+w4);
443                                         fac2 = fac2 / (float)(faceLen-3);
444                                         for (j=0; j<faceLen; j++)
445                                                 w[j] = fac2;
446                                         
447                                         w[i] = w1;
448                                         w[(i-1+faceLen)%faceLen] = w2;
449                                         w[(i+1)%faceLen] = w4;
450
451                                         w += faceLen;
452                                 }
453                         }
454                 }
455         }
456
457         return wtable->weight_table[faceLen].w;
458 }
459
460 static void free_ss_weights(WeightTable *wtable)
461 {
462         int i;
463
464         for (i=0; i<wtable->len; i++) {
465                 if (wtable->weight_table[i].valid)
466                         MEM_freeN(wtable->weight_table[i].w);
467         }
468         
469         if (wtable->weight_table)
470                 MEM_freeN(wtable->weight_table);
471 }
472
473 #if 0
474 static DerivedMesh *ss_to_cdderivedmesh(CCGSubSurf *ss, int ssFromEditmesh,
475                                                                  int drawInteriorEdges, int useSubsurfUv,
476                                                                  DerivedMesh *dm, struct MultiresSubsurf *ms)
477 {
478         DerivedMesh *cgdm, *result;
479         double curt = PIL_check_seconds_timer();
480
481         cgdm = getCCGDerivedMesh(ss, drawInteriorEdges, useSubsurfUv, dm);
482         result = CDDM_copy(cgdm, 1);
483
484         printf("subsurf conversion time: %.6lf\n", PIL_check_seconds_timer() - curt);
485
486         cgdm->needsFree = 1;
487         cgdm->release(cgdm);
488
489         CDDM_calc_normals(result);
490
491         return result;
492 }
493 #endif
494
495 static int ss_sync_from_derivedmesh(CCGSubSurf *ss, DerivedMesh *dm,
496                                                                          float (*vertexCos)[3], int useFlatSubdiv)
497 {
498         float creaseFactor = (float) ccgSubSurf_getSubdivisionLevels(ss);
499         CCGVertHDL *fVerts = NULL;
500         BLI_array_declare(fVerts);
501         MVert *mvert = dm->getVertArray(dm);
502         MEdge *medge = dm->getEdgeArray(dm);
503         /* MFace *mface = dm->getTessFaceArray(dm); */ /* UNUSED */
504         MVert *mv;
505         MEdge *me;
506         MLoop *mloop = dm->getLoopArray(dm), *ml;
507         MPoly *mpoly = dm->getPolyArray(dm), *mp;
508         /*MFace *mf;*/ /*UNUSED*/
509         int totvert = dm->getNumVerts(dm);
510         int totedge = dm->getNumEdges(dm);
511         /*int totface = dm->getNumTessFaces(dm);*/ /*UNUSED*/
512         /*int totpoly = dm->getNumFaces(dm);*/ /*UNUSED*/
513         int i, j;
514         int *index;
515
516         ccgSubSurf_initFullSync(ss);
517
518         mv = mvert;
519         index = (int *)dm->getVertDataArray(dm, CD_ORIGINDEX);
520         for(i = 0; i < totvert; i++, mv++) {
521                 CCGVert *v;
522
523                 if(vertexCos) {
524                         ccgSubSurf_syncVert(ss, SET_INT_IN_POINTER(i), vertexCos[i], 0, &v);
525                 } else {
526                         ccgSubSurf_syncVert(ss, SET_INT_IN_POINTER(i), mv->co, 0, &v);
527                 }
528
529                 ((int*)ccgSubSurf_getVertUserData(ss, v))[1] = (index)? *index++: i;
530         }
531
532         me = medge;
533         index = (int *)dm->getEdgeDataArray(dm, CD_ORIGINDEX);
534         for(i = 0; i < totedge; i++, me++) {
535                 CCGEdge *e;
536                 float crease;
537
538                 crease = useFlatSubdiv ? creaseFactor :
539                                                                  me->crease * creaseFactor / 255.0f;
540
541                 ccgSubSurf_syncEdge(ss, SET_INT_IN_POINTER(i), SET_INT_IN_POINTER(me->v1),
542                                                         SET_INT_IN_POINTER(me->v2), crease, &e);
543
544                 ((int*)ccgSubSurf_getEdgeUserData(ss, e))[1] = (index)? *index++: i;
545         }
546
547         mp = mpoly;
548         index = DM_get_face_data_layer(dm, CD_ORIGINDEX);
549         for (i=0; i<dm->numPolyData; i++, mp++) {
550                 CCGFace *f=NULL;
551
552                 BLI_array_empty(fVerts);
553
554                 ml = mloop + mp->loopstart;
555                 for (j=0; j<mp->totloop; j++, ml++) {
556                         BLI_array_append(fVerts, SET_INT_IN_POINTER(ml->v));
557                 }
558
559                 /* this is very bad, means mesh is internally inconsistent.
560                  * it is not really possible to continue without modifying
561                  * other parts of code significantly to handle missing faces.
562                  * since this really shouldn't even be possible we just bail.*/
563                 if(ccgSubSurf_syncFace(ss, SET_INT_IN_POINTER(i), mp->totloop,
564                                                            fVerts, &f) == eCCGError_InvalidValue) {
565                         static int hasGivenError = 0;
566
567                         if(!hasGivenError) {
568                                 printf("Unrecoverable error in SubSurf calculation,"
569                                            " mesh is inconsistent.\n");
570
571                                 hasGivenError = 1;
572                         }
573
574                         return 0;
575                 }
576
577                 ((int*)ccgSubSurf_getFaceUserData(ss, f))[1] = index ? *index++: i;
578         }
579
580         ccgSubSurf_processSync(ss);
581
582         BLI_array_free(fVerts);
583         return 1;
584 }
585
586 /***/
587
588 static int ccgDM_getVertMapIndex(CCGSubSurf *ss, CCGVert *v) {
589         return ((int*) ccgSubSurf_getVertUserData(ss, v))[1];
590 }
591
592 static int ccgDM_getEdgeMapIndex(CCGSubSurf *ss, CCGEdge *e) {
593         return ((int*) ccgSubSurf_getEdgeUserData(ss, e))[1];
594 }
595
596 static int ccgDM_getFaceMapIndex(CCGSubSurf *ss, CCGFace *f) {
597         return ((int*) ccgSubSurf_getFaceUserData(ss, f))[1];
598 }
599
600 static void cgdm_getMinMax(DerivedMesh *dm, float min_r[3], float max_r[3]) {
601         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
602         CCGSubSurf *ss = cgdm->ss;
603         CCGVertIterator *vi = ccgSubSurf_getVertIterator(ss);
604         CCGEdgeIterator *ei = ccgSubSurf_getEdgeIterator(ss);
605         CCGFaceIterator *fi = ccgSubSurf_getFaceIterator(ss);
606         int i, edgeSize = ccgSubSurf_getEdgeSize(ss);
607         int gridSize = ccgSubSurf_getGridSize(ss);
608
609         if (!ccgSubSurf_getNumVerts(ss))
610                 min_r[0] = min_r[1] = min_r[2] = max_r[0] = max_r[1] = max_r[2] = 0.0;
611
612         for (; !ccgVertIterator_isStopped(vi); ccgVertIterator_next(vi)) {
613                 CCGVert *v = ccgVertIterator_getCurrent(vi);
614                 float *co = ccgSubSurf_getVertData(ss, v);
615
616                 DO_MINMAX(co, min_r, max_r);
617         }
618
619         for (; !ccgEdgeIterator_isStopped(ei); ccgEdgeIterator_next(ei)) {
620                 CCGEdge *e = ccgEdgeIterator_getCurrent(ei);
621                 DMGridData *edgeData = ccgSubSurf_getEdgeDataArray(ss, e);
622
623                 for (i=0; i<edgeSize; i++)
624                         DO_MINMAX(edgeData[i].co, min_r, max_r);
625         }
626
627         for (; !ccgFaceIterator_isStopped(fi); ccgFaceIterator_next(fi)) {
628                 CCGFace *f = ccgFaceIterator_getCurrent(fi);
629                 int S, x, y, numVerts = ccgSubSurf_getFaceNumVerts(f);
630
631                 for (S=0; S<numVerts; S++) {
632                         DMGridData *faceGridData = ccgSubSurf_getFaceGridDataArray(ss, f, S);
633
634                         for (y=0; y<gridSize; y++)
635                                 for (x=0; x<gridSize; x++)
636                                         DO_MINMAX(faceGridData[y*gridSize + x].co, min_r, max_r);
637                 }
638         }
639
640         ccgFaceIterator_free(fi);
641         ccgEdgeIterator_free(ei);
642         ccgVertIterator_free(vi);
643 }
644 static int cgdm_getNumVerts(DerivedMesh *dm) {
645         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
646
647         return ccgSubSurf_getNumFinalVerts(cgdm->ss);
648 }
649 static int cgdm_getNumEdges(DerivedMesh *dm) {
650         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
651
652         return ccgSubSurf_getNumFinalEdges(cgdm->ss);
653 }
654 static int cgdm_getNumTessFaces(DerivedMesh *dm) {
655         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
656
657         return ccgSubSurf_getNumFinalFaces(cgdm->ss);
658 }
659
660 static void ccgDM_getFinalVert(DerivedMesh *dm, int vertNum, MVert *mv)
661 {
662         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
663         CCGSubSurf *ss = cgdm->ss;
664         DMGridData *vd;
665         int i;
666
667         memset(mv, 0, sizeof(*mv));
668
669         if((vertNum < cgdm->edgeMap[0].startVert) && (ccgSubSurf_getNumFaces(ss) > 0)) {
670                 /* this vert comes from face data */
671                 int lastface = ccgSubSurf_getNumFaces(ss) - 1;
672                 CCGFace *f;
673                 int x, y, grid, numVerts;
674                 int offset;
675                 int gridSize = ccgSubSurf_getGridSize(ss);
676                 int gridSideVerts;
677                 int gridInternalVerts;
678                 int gridSideEnd;
679                 int gridInternalEnd;
680
681                 i = 0;
682                 while(i < lastface && vertNum >= cgdm->faceMap[i + 1].startVert)
683                         ++i;
684
685                 f = cgdm->faceMap[i].face;
686                 numVerts = ccgSubSurf_getFaceNumVerts(f);
687
688                 gridSideVerts = gridSize - 2;
689                 gridInternalVerts = gridSideVerts * gridSideVerts;
690
691                 gridSideEnd = 1 + numVerts * gridSideVerts;
692                 gridInternalEnd = gridSideEnd + numVerts * gridInternalVerts;
693
694                 offset = vertNum - cgdm->faceMap[i].startVert;
695                 if(offset < 1) {
696                         vd = ccgSubSurf_getFaceCenterData(f);
697                         copy_v3_v3(mv->co, vd->co);
698                         normal_float_to_short_v3(mv->no, vd->no);
699                 } else if(offset < gridSideEnd) {
700                         offset -= 1;
701                         grid = offset / gridSideVerts;
702                         x = offset % gridSideVerts + 1;
703                         vd = ccgSubSurf_getFaceGridEdgeData(ss, f, grid, x);
704                         copy_v3_v3(mv->co, vd->co);
705                         normal_float_to_short_v3(mv->no, vd->no);
706                 } else if(offset < gridInternalEnd) {
707                         offset -= gridSideEnd;
708                         grid = offset / gridInternalVerts;
709                         offset %= gridInternalVerts;
710                         y = offset / gridSideVerts + 1;
711                         x = offset % gridSideVerts + 1;
712                         vd = ccgSubSurf_getFaceGridData(ss, f, grid, x, y);
713                         copy_v3_v3(mv->co, vd->co);
714                         normal_float_to_short_v3(mv->no, vd->no);
715                 }
716         } else if((vertNum < cgdm->vertMap[0].startVert) && (ccgSubSurf_getNumEdges(ss) > 0)) {
717                 /* this vert comes from edge data */
718                 CCGEdge *e;
719                 int lastedge = ccgSubSurf_getNumEdges(ss) - 1;
720                 int x;
721
722                 i = 0;
723                 while(i < lastedge && vertNum >= cgdm->edgeMap[i + 1].startVert)
724                         ++i;
725
726                 e = cgdm->edgeMap[i].edge;
727
728                 x = vertNum - cgdm->edgeMap[i].startVert + 1;
729                 vd = ccgSubSurf_getEdgeData(ss, e, x);
730                 copy_v3_v3(mv->co, vd->co);
731                 normal_float_to_short_v3(mv->no, vd->no);
732         } else {
733                 /* this vert comes from vert data */
734                 CCGVert *v;
735                 i = vertNum - cgdm->vertMap[0].startVert;
736
737                 v = cgdm->vertMap[i].vert;
738                 vd = ccgSubSurf_getVertData(ss, v);
739                 copy_v3_v3(mv->co, vd->co);
740                 normal_float_to_short_v3(mv->no, vd->no);
741         }
742 }
743
744 static void ccgDM_getFinalVertCo(DerivedMesh *dm, int vertNum, float co_r[3])
745 {
746         MVert mvert;
747
748         ccgDM_getFinalVert(dm, vertNum, &mvert);
749         VECCOPY(co_r, mvert.co);
750 }
751
752 static void ccgDM_getFinalVertNo(DerivedMesh *dm, int vertNum, float no_r[3])
753 {
754         MVert mvert;
755
756         ccgDM_getFinalVert(dm, vertNum, &mvert);
757         normal_short_to_float_v3(no_r, mvert.no);
758 }
759
760 static void ccgDM_getFinalEdge(DerivedMesh *dm, int edgeNum, MEdge *med)
761 {
762         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
763         CCGSubSurf *ss = cgdm->ss;
764         int i;
765
766         memset(med, 0, sizeof(*med));
767
768         if(edgeNum < cgdm->edgeMap[0].startEdge) {
769                 /* this edge comes from face data */
770                 int lastface = ccgSubSurf_getNumFaces(ss) - 1;
771                 CCGFace *f;
772                 int x, y, grid /*, numVerts*/;
773                 int offset;
774                 int gridSize = ccgSubSurf_getGridSize(ss);
775                 int edgeSize = ccgSubSurf_getEdgeSize(ss);
776                 int gridSideEdges;
777                 int gridInternalEdges;
778                                 int lasti, previ;
779
780                                 i = lastface;
781                                 lasti = 0;
782                                 while (1) {
783                                         previ = i;
784                                         if (cgdm->faceMap[i].startEdge >= edgeNum) {
785                                                 i -= fabsf(i-lasti)/2.0f;
786                                         } else if (cgdm->faceMap[i].startEdge < edgeNum) {
787                                                 i += fabsf(i-lasti)/2.0f;
788                                         } else {
789                                                 break;
790                                         }
791
792                                         if (i < 0) {
793                                                 i = 0;
794                                                 break;
795                                         }
796
797                                         if (i > lastface) {
798                                                 i = lastface;
799                                                 break;
800
801                                         }
802
803                                         if (i == lasti)
804                                            break;
805
806                                         lasti = previ;
807                                 }
808
809                                 i = i > 0 ? i - 1 : i;
810                 while(i < lastface && edgeNum >= cgdm->faceMap[i + 1].startEdge)
811                         ++i;
812
813                 f = cgdm->faceMap[i].face;
814                 /* numVerts = ccgSubSurf_getFaceNumVerts(f); */ /*UNUSED*/
815
816                 gridSideEdges = gridSize - 1;
817                 gridInternalEdges = (gridSideEdges - 1) * gridSideEdges * 2; 
818
819                 offset = edgeNum - cgdm->faceMap[i].startEdge;
820                 grid = offset / (gridSideEdges + gridInternalEdges);
821                 offset %= (gridSideEdges + gridInternalEdges);
822
823                 if(offset < gridSideEdges) {
824                         x = offset;
825                         med->v1 = getFaceIndex(ss, f, grid, x, 0, edgeSize, gridSize);
826                         med->v2 = getFaceIndex(ss, f, grid, x+1, 0, edgeSize, gridSize);
827                 } else {
828                         offset -= gridSideEdges;
829                         x = (offset / 2) / gridSideEdges + 1;
830                         y = (offset / 2) % gridSideEdges;
831                         if(offset % 2 == 0) {
832                                 med->v1 = getFaceIndex(ss, f, grid, x, y, edgeSize, gridSize);
833                                 med->v2 = getFaceIndex(ss, f, grid, x, y+1, edgeSize, gridSize);
834                         } else {
835                                 med->v1 = getFaceIndex(ss, f, grid, y, x, edgeSize, gridSize);
836                                 med->v2 = getFaceIndex(ss, f, grid, y+1, x, edgeSize, gridSize);
837                         }
838                 }
839         } else {
840                 /* this vert comes from edge data */
841                 CCGEdge *e;
842                 int edgeSize = ccgSubSurf_getEdgeSize(ss);
843                 int x;
844                 short *edgeFlag;
845                 unsigned int flags = 0;
846
847                 i = (edgeNum - cgdm->edgeMap[0].startEdge) / (edgeSize - 1);
848
849                 e = cgdm->edgeMap[i].edge;
850
851                 if(!ccgSubSurf_getEdgeNumFaces(e)) flags |= ME_LOOSEEDGE;
852
853                 x = edgeNum - cgdm->edgeMap[i].startEdge;
854
855                 med->v1 = getEdgeIndex(ss, e, x, edgeSize);
856                 med->v2 = getEdgeIndex(ss, e, x+1, edgeSize);
857
858                 edgeFlag = (cgdm->edgeFlags)? &cgdm->edgeFlags[i]: NULL;
859                 if(edgeFlag)
860                         flags |= (*edgeFlag & (ME_SEAM | ME_SHARP))
861                                          | ME_EDGEDRAW | ME_EDGERENDER;
862                 else
863                         flags |= ME_EDGEDRAW | ME_EDGERENDER;
864
865                 med->flag = flags;
866         }
867 }
868
869 static void ccgDM_getFinalFace(DerivedMesh *dm, int faceNum, MFace *mf)
870 {
871         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
872         CCGSubSurf *ss = cgdm->ss;
873         int gridSize = ccgSubSurf_getGridSize(ss);
874         int edgeSize = ccgSubSurf_getEdgeSize(ss);
875         int gridSideEdges = gridSize - 1;
876         int gridFaces = gridSideEdges * gridSideEdges;
877         int i;
878         CCGFace *f;
879         /*int numVerts;*/
880         int offset;
881         int grid;
882         int x, y;
883         /*int lastface = ccgSubSurf_getNumFaces(ss) - 1;*/ /*UNUSED*/
884         char *faceFlags = cgdm->faceFlags;
885
886         memset(mf, 0, sizeof(*mf));
887         if (faceNum >= cgdm->dm.numFaceData)
888                 return;
889
890         i = cgdm->reverseFaceMap[faceNum];
891
892         f = cgdm->faceMap[i].face;
893         /*numVerts = ccgSubSurf_getFaceNumVerts(f);*/ /*UNUSED*/
894
895         offset = faceNum - cgdm->faceMap[i].startFace;
896         grid = offset / gridFaces;
897         offset %= gridFaces;
898         y = offset / gridSideEdges;
899         x = offset % gridSideEdges;
900
901         mf->v1 = getFaceIndex(ss, f, grid, x+0, y+0, edgeSize, gridSize);
902         mf->v2 = getFaceIndex(ss, f, grid, x+0, y+1, edgeSize, gridSize);
903         mf->v3 = getFaceIndex(ss, f, grid, x+1, y+1, edgeSize, gridSize);
904         mf->v4 = getFaceIndex(ss, f, grid, x+1, y+0, edgeSize, gridSize);
905
906         if(faceFlags) {
907                 mf->flag = faceFlags[i*2];
908                 mf->mat_nr = faceFlags[i*2+1];
909         }
910         else mf->flag = ME_SMOOTH;
911 }
912
913 static void ccgDM_copyFinalVertArray(DerivedMesh *dm, MVert *mvert)
914 {
915         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
916         CCGSubSurf *ss = cgdm->ss;
917         DMGridData *vd;
918         int index;
919         int totvert, totedge, totface;
920         int gridSize = ccgSubSurf_getGridSize(ss);
921         int edgeSize = ccgSubSurf_getEdgeSize(ss);
922         int i = 0;
923
924         totface = ccgSubSurf_getNumFaces(ss);
925         for(index = 0; index < totface; index++) {
926                 CCGFace *f = cgdm->faceMap[index].face;
927                 int x, y, S, numVerts = ccgSubSurf_getFaceNumVerts(f);
928
929                 vd= ccgSubSurf_getFaceCenterData(f);
930                 copy_v3_v3(mvert[i].co, vd->co);
931                 normal_float_to_short_v3(mvert[i].no, vd->no);
932                 i++;
933                 
934                 for(S = 0; S < numVerts; S++) {
935                         for(x = 1; x < gridSize - 1; x++, i++) {
936                                 vd= ccgSubSurf_getFaceGridEdgeData(ss, f, S, x);
937                                 copy_v3_v3(mvert[i].co, vd->co);
938                                 normal_float_to_short_v3(mvert[i].no, vd->no);
939                         }
940                 }
941
942                 for(S = 0; S < numVerts; S++) {
943                         for(y = 1; y < gridSize - 1; y++) {
944                                 for(x = 1; x < gridSize - 1; x++, i++) {
945                                         vd= ccgSubSurf_getFaceGridData(ss, f, S, x, y);
946                                         copy_v3_v3(mvert[i].co, vd->co);
947                                         normal_float_to_short_v3(mvert[i].no, vd->no);
948                                 }
949                         }
950                 }
951         }
952
953         totedge = ccgSubSurf_getNumEdges(ss);
954         for(index = 0; index < totedge; index++) {
955                 CCGEdge *e = cgdm->edgeMap[index].edge;
956                 int x;
957
958                 for(x = 1; x < edgeSize - 1; x++, i++) {
959                         vd= ccgSubSurf_getEdgeData(ss, e, x);
960                         copy_v3_v3(mvert[i].co, vd->co);
961                         /* This gives errors with -debug-fpe
962                          * the normals dont seem to be unit length.
963                          * this is most likely caused by edges with no
964                          * faces which are now zerod out, see comment in:
965                          * ccgSubSurf__calcVertNormals(), - campbell */
966                         normal_float_to_short_v3(mvert[i].no, vd->no);
967                 }
968         }
969
970         totvert = ccgSubSurf_getNumVerts(ss);
971         for(index = 0; index < totvert; index++) {
972                 CCGVert *v = cgdm->vertMap[index].vert;
973
974                 vd= ccgSubSurf_getVertData(ss, v);
975                 copy_v3_v3(mvert[i].co, vd->co);
976                 normal_float_to_short_v3(mvert[i].no, vd->no);
977                 i++;
978         }
979 }
980
981 static void ccgDM_copyFinalEdgeArray(DerivedMesh *dm, MEdge *medge)
982 {
983         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
984         CCGSubSurf *ss = cgdm->ss;
985         int index;
986         int totedge, totface;
987         int gridSize = ccgSubSurf_getGridSize(ss);
988         int edgeSize = ccgSubSurf_getEdgeSize(ss);
989         int i = 0;
990         short *edgeFlags = cgdm->edgeFlags;
991
992         totface = ccgSubSurf_getNumFaces(ss);
993         for(index = 0; index < totface; index++) {
994                 CCGFace *f = cgdm->faceMap[index].face;
995                 int x, y, S, numVerts = ccgSubSurf_getFaceNumVerts(f);
996
997                 for(S = 0; S < numVerts; S++) {
998                         for(x = 0; x < gridSize - 1; x++) {
999                                 MEdge *med = &medge[i];
1000
1001                                 if(cgdm->drawInteriorEdges)
1002                                         med->flag = ME_EDGEDRAW | ME_EDGERENDER;
1003                                 med->v1 = getFaceIndex(ss, f, S, x, 0, edgeSize, gridSize);
1004                                 med->v2 = getFaceIndex(ss, f, S, x + 1, 0, edgeSize, gridSize);
1005                                 i++;
1006                         }
1007
1008                         for(x = 1; x < gridSize - 1; x++) {
1009                                 for(y = 0; y < gridSize - 1; y++) {
1010                                         MEdge *med;
1011
1012                                         med = &medge[i];
1013                                         if(cgdm->drawInteriorEdges)
1014                                                 med->flag = ME_EDGEDRAW | ME_EDGERENDER;
1015                                         med->v1 = getFaceIndex(ss, f, S, x, y,
1016                                                                                    edgeSize, gridSize);
1017                                         med->v2 = getFaceIndex(ss, f, S, x, y + 1,
1018                                                                                    edgeSize, gridSize);
1019                                         i++;
1020
1021                                         med = &medge[i];
1022                                         if(cgdm->drawInteriorEdges)
1023                                                 med->flag = ME_EDGEDRAW | ME_EDGERENDER;
1024                                         med->v1 = getFaceIndex(ss, f, S, y, x,
1025                                                                                    edgeSize, gridSize);
1026                                         med->v2 = getFaceIndex(ss, f, S, y + 1, x,
1027                                                                                    edgeSize, gridSize);
1028                                         i++;
1029                                 }
1030                         }
1031                 }
1032         }
1033
1034         totedge = ccgSubSurf_getNumEdges(ss);
1035         for(index = 0; index < totedge; index++) {
1036                 CCGEdge *e = cgdm->edgeMap[index].edge;
1037                 unsigned int flags = 0;
1038                 int x;
1039                 int edgeIdx = GET_INT_FROM_POINTER(ccgSubSurf_getEdgeEdgeHandle(e));
1040
1041                 if(!ccgSubSurf_getEdgeNumFaces(e)) flags |= ME_LOOSEEDGE;
1042
1043                 if(edgeFlags) {
1044                         if(edgeIdx != -1) {
1045                                 flags |= (edgeFlags[index] & (ME_SEAM | ME_SHARP))
1046                                                  | ME_EDGEDRAW | ME_EDGERENDER;
1047                         }
1048                 } else {
1049                         flags |= ME_EDGEDRAW | ME_EDGERENDER;
1050                 }
1051
1052                 for(x = 0; x < edgeSize - 1; x++) {
1053                         MEdge *med = &medge[i];
1054                         med->v1 = getEdgeIndex(ss, e, x, edgeSize);
1055                         med->v2 = getEdgeIndex(ss, e, x + 1, edgeSize);
1056                         med->flag = flags;
1057                         i++;
1058                 }
1059         }
1060 }
1061
1062 static void ccgDM_copyFinalFaceArray(DerivedMesh *dm, MFace *mface)
1063 {
1064         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
1065         CCGSubSurf *ss = cgdm->ss;
1066         int index;
1067         int totface;
1068         int gridSize = ccgSubSurf_getGridSize(ss);
1069         int edgeSize = ccgSubSurf_getEdgeSize(ss);
1070         int i = 0;
1071         char *faceFlags = cgdm->faceFlags;
1072
1073         totface = ccgSubSurf_getNumFaces(ss);
1074         for(index = 0; index < totface; index++) {
1075                 CCGFace *f = cgdm->faceMap[index].face;
1076                 int x, y, S, numVerts = ccgSubSurf_getFaceNumVerts(f);
1077                 int flag = (faceFlags)? faceFlags[index*2]: ME_SMOOTH;
1078                 int mat_nr = (faceFlags)? faceFlags[index*2+1]: 0;
1079
1080                 for(S = 0; S < numVerts; S++) {
1081                         for(y = 0; y < gridSize - 1; y++) {
1082                                 for(x = 0; x < gridSize - 1; x++) {
1083                                         MFace *mf = &mface[i];
1084                                         mf->v1 = getFaceIndex(ss, f, S, x + 0, y + 0,
1085                                                                                   edgeSize, gridSize);
1086                                         mf->v2 = getFaceIndex(ss, f, S, x + 0, y + 1,
1087                                                                                   edgeSize, gridSize);
1088                                         mf->v3 = getFaceIndex(ss, f, S, x + 1, y + 1,
1089                                                                                   edgeSize, gridSize);
1090                                         mf->v4 = getFaceIndex(ss, f, S, x + 1, y + 0,
1091                                                                                   edgeSize, gridSize);
1092                                         if (faceFlags) {
1093                                                 mat_nr = faceFlags[index*2+1];
1094                                                 mf->flag = faceFlags[index*2];
1095                                         } else mf->flag = flag;
1096
1097                                         mf->mat_nr = mat_nr;
1098                                         mf->flag = flag;
1099
1100                                         i++;
1101                                 }
1102                         }
1103                 }
1104         }
1105 }
1106
1107 static void ccgDM_copyFinalLoopArray(DerivedMesh *dm, MLoop *mloop)
1108 {
1109         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
1110         CCGSubSurf *ss = cgdm->ss;
1111         int index;
1112         int totface;
1113         int gridSize = ccgSubSurf_getGridSize(ss);
1114         int edgeSize = ccgSubSurf_getEdgeSize(ss);
1115         int i = 0;
1116         MLoop *mv;
1117         /* char *faceFlags = cgdm->faceFlags; */ /* UNUSED */
1118
1119         if (!cgdm->ehash) {
1120                 MEdge *medge;
1121
1122                 cgdm->ehash = BLI_edgehash_new();
1123                 medge = cgdm->dm.getEdgeArray((DerivedMesh*)cgdm);
1124
1125                 for (i=0; i<cgdm->dm.numEdgeData; i++) {
1126                         BLI_edgehash_insert(cgdm->ehash, medge[i].v1, medge[i].v2, SET_INT_IN_POINTER(i));
1127                 }
1128         }
1129
1130         totface = ccgSubSurf_getNumFaces(ss);
1131         mv = mloop;
1132         for(index = 0; index < totface; index++) {
1133                 CCGFace *f = cgdm->faceMap[index].face;
1134                 int x, y, S, numVerts = ccgSubSurf_getFaceNumVerts(f);
1135                 /* int flag = (faceFlags)? faceFlags[index*2]: ME_SMOOTH; */ /* UNUSED */
1136                 /* int mat_nr = (faceFlags)? faceFlags[index*2+1]: 0; */ /* UNUSED */
1137
1138                 for(S = 0; S < numVerts; S++) {
1139                         for(y = 0; y < gridSize - 1; y++) {
1140                                 for(x = 0; x < gridSize - 1; x++) {
1141                                         int v1, v2, v3, v4;
1142
1143                                         v1 = getFaceIndex(ss, f, S, x + 0, y + 0,
1144                                                                                   edgeSize, gridSize);
1145
1146                                         v2 = getFaceIndex(ss, f, S, x + 0, y + 1,
1147                                                                                   edgeSize, gridSize);
1148                                         v3 = getFaceIndex(ss, f, S, x + 1, y + 1,
1149                                                                                   edgeSize, gridSize);
1150                                         v4 = getFaceIndex(ss, f, S, x + 1, y + 0,
1151                                                                                   edgeSize, gridSize);
1152
1153                                         mv->v = v1;
1154                                         mv->e = GET_INT_FROM_POINTER(BLI_edgehash_lookup(cgdm->ehash, v1, v2));
1155                                         mv++, i++;
1156
1157                                         mv->v = v2;
1158                                         mv->e = GET_INT_FROM_POINTER(BLI_edgehash_lookup(cgdm->ehash, v2, v3));
1159                                         mv++, i++;
1160
1161                                         mv->v = v3;
1162                                         mv->e = GET_INT_FROM_POINTER(BLI_edgehash_lookup(cgdm->ehash, v3, v4));
1163                                         mv++, i++;
1164
1165                                         mv->v = v4;
1166                                         mv->e = GET_INT_FROM_POINTER(BLI_edgehash_lookup(cgdm->ehash, v4, v1));
1167                                         mv++, i++;
1168                                 }
1169                         }
1170                 }
1171         }
1172 }
1173
1174
1175 static void ccgDM_copyFinalPolyArray(DerivedMesh *dm, MPoly *mface)
1176 {
1177         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
1178         CCGSubSurf *ss = cgdm->ss;
1179         int index;
1180         int totface;
1181         int gridSize = ccgSubSurf_getGridSize(ss);
1182         /* int edgeSize = ccgSubSurf_getEdgeSize(ss); */ /* UNUSED */
1183         int i = 0, k = 0;
1184         char *faceFlags = cgdm->faceFlags;
1185
1186         totface = ccgSubSurf_getNumFaces(ss);
1187         for(index = 0; index < totface; index++) {
1188                 CCGFace *f = cgdm->faceMap[index].face;
1189                 int x, y, S, numVerts = ccgSubSurf_getFaceNumVerts(f);
1190                 int flag = (faceFlags)? faceFlags[index*2]: ME_SMOOTH;
1191                 int mat_nr = (faceFlags)? faceFlags[index*2+1]: 0;
1192
1193                 for(S = 0; S < numVerts; S++) {
1194                         for(y = 0; y < gridSize - 1; y++) {
1195                                 for(x = 0; x < gridSize - 1; x++) {
1196                                         MPoly *mf = &mface[i];
1197
1198                                         if (faceFlags) {
1199                                                 mat_nr = faceFlags[index*2+1];
1200                                                 mf->flag = faceFlags[index*2];
1201                                         } else mf->flag = flag;
1202
1203                                         mf->mat_nr = mat_nr;
1204                                         mf->flag = flag;
1205                                         mf->loopstart = k;
1206                                         mf->totloop = 4;
1207
1208                                         k += 4;
1209                                         i++;
1210                                 }
1211                         }
1212                 }
1213         }
1214 }
1215
1216 static void cgdm_getVertCos(DerivedMesh *dm, float (*cos)[3]) {
1217         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
1218         CCGSubSurf *ss = cgdm->ss;
1219         int edgeSize = ccgSubSurf_getEdgeSize(ss);
1220         int gridSize = ccgSubSurf_getGridSize(ss);
1221         int i;
1222         CCGVertIterator *vi;
1223         CCGEdgeIterator *ei;
1224         CCGFaceIterator *fi;
1225         CCGFace **faceMap2;
1226         CCGEdge **edgeMap2;
1227         CCGVert **vertMap2;
1228         int index, totvert, totedge, totface;
1229         
1230         totvert = ccgSubSurf_getNumVerts(ss);
1231         vertMap2 = MEM_mallocN(totvert*sizeof(*vertMap2), "vertmap");
1232         vi = ccgSubSurf_getVertIterator(ss);
1233         for (; !ccgVertIterator_isStopped(vi); ccgVertIterator_next(vi)) {
1234                 CCGVert *v = ccgVertIterator_getCurrent(vi);
1235
1236                 vertMap2[GET_INT_FROM_POINTER(ccgSubSurf_getVertVertHandle(v))] = v;
1237         }
1238         ccgVertIterator_free(vi);
1239
1240         totedge = ccgSubSurf_getNumEdges(ss);
1241         edgeMap2 = MEM_mallocN(totedge*sizeof(*edgeMap2), "edgemap");
1242         ei = ccgSubSurf_getEdgeIterator(ss);
1243         for (i=0; !ccgEdgeIterator_isStopped(ei); i++,ccgEdgeIterator_next(ei)) {
1244                 CCGEdge *e = ccgEdgeIterator_getCurrent(ei);
1245
1246                 edgeMap2[GET_INT_FROM_POINTER(ccgSubSurf_getEdgeEdgeHandle(e))] = e;
1247         }
1248
1249         totface = ccgSubSurf_getNumFaces(ss);
1250         faceMap2 = MEM_mallocN(totface*sizeof(*faceMap2), "facemap");
1251         fi = ccgSubSurf_getFaceIterator(ss);
1252         for (; !ccgFaceIterator_isStopped(fi); ccgFaceIterator_next(fi)) {
1253                 CCGFace *f = ccgFaceIterator_getCurrent(fi);
1254
1255                 faceMap2[GET_INT_FROM_POINTER(ccgSubSurf_getFaceFaceHandle(ss, f))] = f;
1256         }
1257         ccgFaceIterator_free(fi);
1258
1259         i = 0;
1260         for (index=0; index<totface; index++) {
1261                 CCGFace *f = faceMap2[index];
1262                 int x, y, S, numVerts = ccgSubSurf_getFaceNumVerts(f);
1263
1264                 copy_v3_v3(cos[i++], ccgSubSurf_getFaceCenterData(f));
1265                 
1266                 for (S=0; S<numVerts; S++) {
1267                         for (x=1; x<gridSize-1; x++) {
1268                                 copy_v3_v3(cos[i++], ccgSubSurf_getFaceGridEdgeData(ss, f, S, x));
1269                         }
1270                 }
1271
1272                 for (S=0; S<numVerts; S++) {
1273                         for (y=1; y<gridSize-1; y++) {
1274                                 for (x=1; x<gridSize-1; x++) {
1275                                         copy_v3_v3(cos[i++], ccgSubSurf_getFaceGridData(ss, f, S, x, y));
1276                                 }
1277                         }
1278                 }
1279         }
1280
1281         for (index=0; index<totedge; index++) {
1282                 CCGEdge *e= edgeMap2[index];
1283                 int x;
1284
1285                 for (x=1; x<edgeSize-1; x++) {
1286                         copy_v3_v3(cos[i++], ccgSubSurf_getEdgeData(ss, e, x));
1287                 }
1288         }
1289
1290         for (index=0; index<totvert; index++) {
1291                 CCGVert *v = vertMap2[index];
1292                 copy_v3_v3(cos[i++], ccgSubSurf_getVertData(ss, v));
1293         }
1294
1295         MEM_freeN(vertMap2);
1296         MEM_freeN(edgeMap2);
1297         MEM_freeN(faceMap2);
1298 }
1299 static void cgdm_foreachMappedVert(DerivedMesh *dm, void (*func)(void *userData, int index, float *co, float *no_f, short *no_s), void *userData) {
1300         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
1301         CCGVertIterator *vi = ccgSubSurf_getVertIterator(cgdm->ss);
1302
1303         for (; !ccgVertIterator_isStopped(vi); ccgVertIterator_next(vi)) {
1304                 CCGVert *v = ccgVertIterator_getCurrent(vi);
1305                 DMGridData *vd = ccgSubSurf_getVertData(cgdm->ss, v);
1306                 int index = ccgDM_getVertMapIndex(cgdm->ss, v);
1307
1308                 if (index!=-1)
1309                         func(userData, index, vd->co, vd->no, NULL);
1310         }
1311
1312         ccgVertIterator_free(vi);
1313 }
1314 static void cgdm_foreachMappedEdge(DerivedMesh *dm, void (*func)(void *userData, int index, float *v0co, float *v1co), void *userData) {
1315         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
1316         CCGSubSurf *ss = cgdm->ss;
1317         CCGEdgeIterator *ei = ccgSubSurf_getEdgeIterator(ss);
1318         int i, edgeSize = ccgSubSurf_getEdgeSize(ss);
1319
1320         for (; !ccgEdgeIterator_isStopped(ei); ccgEdgeIterator_next(ei)) {
1321                 CCGEdge *e = ccgEdgeIterator_getCurrent(ei);
1322                 DMGridData *edgeData = ccgSubSurf_getEdgeDataArray(ss, e);
1323                 int index = ccgDM_getEdgeMapIndex(ss, e);
1324
1325                 if (index!=-1) {
1326                         for (i=0; i<edgeSize-1; i++)
1327                                 func(userData, index, edgeData[i].co, edgeData[i+1].co);
1328                 }
1329         }
1330
1331         ccgEdgeIterator_free(ei);
1332 }
1333
1334 static void ccgDM_drawVerts(DerivedMesh *dm) {
1335         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
1336         CCGSubSurf *ss = cgdm->ss;
1337         int edgeSize = ccgSubSurf_getEdgeSize(ss);
1338         int gridSize = ccgSubSurf_getGridSize(ss);
1339         CCGVertIterator *vi;
1340         CCGEdgeIterator *ei;
1341         CCGFaceIterator *fi;
1342
1343         glBegin(GL_POINTS);
1344         vi = ccgSubSurf_getVertIterator(ss);
1345         for (; !ccgVertIterator_isStopped(vi); ccgVertIterator_next(vi)) {
1346                 CCGVert *v = ccgVertIterator_getCurrent(vi);
1347                 glVertex3fv(ccgSubSurf_getVertData(ss, v));
1348         }
1349         ccgVertIterator_free(vi);
1350
1351         ei = ccgSubSurf_getEdgeIterator(ss);
1352         for (; !ccgEdgeIterator_isStopped(ei); ccgEdgeIterator_next(ei)) {
1353                 CCGEdge *e = ccgEdgeIterator_getCurrent(ei);
1354                 int x;
1355
1356                 for (x=1; x<edgeSize-1; x++)
1357                         glVertex3fv(ccgSubSurf_getEdgeData(ss, e, x));
1358         }
1359         ccgEdgeIterator_free(ei);
1360
1361         fi = ccgSubSurf_getFaceIterator(ss);
1362         for (; !ccgFaceIterator_isStopped(fi); ccgFaceIterator_next(fi)) {
1363                 CCGFace *f = ccgFaceIterator_getCurrent(fi);
1364                 int x, y, S, numVerts = ccgSubSurf_getFaceNumVerts(f);
1365
1366                 glVertex3fv(ccgSubSurf_getFaceCenterData(f));
1367                 for (S=0; S<numVerts; S++)
1368                         for (x=1; x<gridSize-1; x++)
1369                                 glVertex3fv(ccgSubSurf_getFaceGridEdgeData(ss, f, S, x));
1370                 for (S=0; S<numVerts; S++)
1371                         for (y=1; y<gridSize-1; y++)
1372                                 for (x=1; x<gridSize-1; x++)
1373                                         glVertex3fv(ccgSubSurf_getFaceGridData(ss, f, S, x, y));
1374         }
1375         ccgFaceIterator_free(fi);
1376         glEnd();
1377 }
1378
1379 static void ccgdm_pbvh_update(CCGDerivedMesh *ccgdm)
1380 {
1381         if(ccgdm->pbvh && ccgDM_use_grid_pbvh(ccgdm)) {
1382                 CCGFace **faces;
1383                 int totface;
1384
1385                 BLI_pbvh_get_grid_updates(ccgdm->pbvh, 1, (void***)&faces, &totface);
1386                 if(totface) {
1387                         ccgSubSurf_updateFromFaces(ccgdm->ss, 0, faces, totface);
1388                         ccgSubSurf_updateNormals(ccgdm->ss, faces, totface);
1389                         MEM_freeN(faces);
1390                 }
1391         }
1392 }
1393
1394 static void ccgDM_drawEdges(DerivedMesh *dm, int drawLooseEdges, int UNUSED(drawAllEdges)) {
1395         CCGDerivedMesh *ccgdm = (CCGDerivedMesh*) dm;
1396         CCGSubSurf *ss = ccgdm->ss;
1397         CCGEdgeIterator *ei = ccgSubSurf_getEdgeIterator(ss);
1398         CCGFaceIterator *fi = ccgSubSurf_getFaceIterator(ss);
1399         int i, j, edgeSize = ccgSubSurf_getEdgeSize(ss);
1400         int totedge = ccgSubSurf_getNumEdges(ss);
1401         int gridSize = ccgSubSurf_getGridSize(ss);
1402         int useAging;
1403
1404         ccgdm_pbvh_update(ccgdm);
1405
1406         ccgSubSurf_getUseAgeCounts(ss, &useAging, NULL, NULL, NULL);
1407
1408         for (j=0; j< totedge; j++) {
1409                 CCGEdge *e = ccgdm->edgeMap[j].edge;
1410                 DMGridData *edgeData = ccgSubSurf_getEdgeDataArray(ss, e);
1411
1412                 if (!drawLooseEdges && !ccgSubSurf_getEdgeNumFaces(e))
1413                         continue;
1414
1415                 if(ccgdm->edgeFlags && !(ccgdm->edgeFlags[j] & ME_EDGEDRAW))
1416                         continue;
1417
1418                 if (useAging && !(G.f&G_BACKBUFSEL)) {
1419                         int ageCol = 255-ccgSubSurf_getEdgeAge(ss, e)*4;
1420                         glColor3ub(0, ageCol>0?ageCol:0, 0);
1421                 }
1422
1423                 glBegin(GL_LINE_STRIP);
1424                 for (i=0; i<edgeSize-1; i++) {
1425                         glVertex3fv(edgeData[i].co);
1426                         glVertex3fv(edgeData[i+1].co);
1427                 }
1428                 glEnd();
1429         }
1430
1431         if (useAging && !(G.f&G_BACKBUFSEL)) {
1432                 glColor3ub(0, 0, 0);
1433         }
1434
1435         if (ccgdm->drawInteriorEdges) {
1436                 for (; !ccgFaceIterator_isStopped(fi); ccgFaceIterator_next(fi)) {
1437                         CCGFace *f = ccgFaceIterator_getCurrent(fi);
1438                         int S, x, y, numVerts = ccgSubSurf_getFaceNumVerts(f);
1439
1440                         for (S=0; S<numVerts; S++) {
1441                                 DMGridData *faceGridData = ccgSubSurf_getFaceGridDataArray(ss, f, S);
1442
1443                                 glBegin(GL_LINE_STRIP);
1444                                 for (x=0; x<gridSize; x++)
1445                                         glVertex3fv(faceGridData[x].co);
1446                                 glEnd();
1447                                 for (y=1; y<gridSize-1; y++) {
1448                                         glBegin(GL_LINE_STRIP);
1449                                         for (x=0; x<gridSize; x++)
1450                                                 glVertex3fv(faceGridData[y*gridSize + x].co);
1451                                         glEnd();
1452                                 }
1453                                 for (x=1; x<gridSize-1; x++) {
1454                                         glBegin(GL_LINE_STRIP);
1455                                         for (y=0; y<gridSize; y++)
1456                                                 glVertex3fv(faceGridData[y*gridSize + x].co);
1457                                         glEnd();
1458                                 }
1459                         }
1460                 }
1461         }
1462
1463         ccgFaceIterator_free(fi);
1464         ccgEdgeIterator_free(ei);
1465 }
1466 static void ccgDM_drawLooseEdges(DerivedMesh *dm) {
1467         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
1468         CCGSubSurf *ss = cgdm->ss;
1469         CCGEdgeIterator *ei = ccgSubSurf_getEdgeIterator(ss);
1470         int i, edgeSize = ccgSubSurf_getEdgeSize(ss);
1471
1472         for (; !ccgEdgeIterator_isStopped(ei); ccgEdgeIterator_next(ei)) {
1473                 CCGEdge *e = ccgEdgeIterator_getCurrent(ei);
1474                 DMGridData *edgeData = ccgSubSurf_getEdgeDataArray(ss, e);
1475
1476                 if (!ccgSubSurf_getEdgeNumFaces(e)) {
1477                         glBegin(GL_LINE_STRIP);
1478                         for (i=0; i<edgeSize-1; i++) {
1479                                 glVertex3fv(edgeData[i].co);
1480                                 glVertex3fv(edgeData[i+1].co);
1481                         }
1482                         glEnd();
1483                 }
1484         }
1485
1486         ccgEdgeIterator_free(ei);
1487 }
1488
1489 static void ccgDM_glNormalFast(float *a, float *b, float *c, float *d)
1490 {
1491         float a_cX = c[0]-a[0], a_cY = c[1]-a[1], a_cZ = c[2]-a[2];
1492         float b_dX = d[0]-b[0], b_dY = d[1]-b[1], b_dZ = d[2]-b[2];
1493         float no[3];
1494
1495         no[0] = b_dY*a_cZ - b_dZ*a_cY;
1496         no[1] = b_dZ*a_cX - b_dX*a_cZ;
1497         no[2] = b_dX*a_cY - b_dY*a_cX;
1498
1499         /* don't normalize, GL_NORMALIZE is enabled */
1500         glNormal3fv(no);
1501 }
1502
1503         /* Only used by non-editmesh types */
1504 static void ccgDM_drawFacesSolid(DerivedMesh *dm, float (*partial_redraw_planes)[4], int fast, int (*setMaterial)(int, void *attribs)) {
1505         CCGDerivedMesh *ccgdm = (CCGDerivedMesh*) dm;
1506         CCGSubSurf *ss = ccgdm->ss;
1507         CCGFaceIterator *fi;
1508         int gridSize = ccgSubSurf_getGridSize(ss);
1509         char *faceFlags = ccgdm->faceFlags;
1510         int step = (fast)? gridSize-1: 1;
1511
1512         ccgdm_pbvh_update(ccgdm);
1513
1514         if(ccgdm->pbvh && ccgdm->multires.mmd && !fast) {
1515                 if(dm->numFaceData) {
1516                         /* should be per face */
1517                         if(!setMaterial(faceFlags[1]+1, NULL))
1518                                 return;
1519
1520                         glShadeModel((faceFlags[0] & ME_SMOOTH)? GL_SMOOTH: GL_FLAT);
1521                         BLI_pbvh_draw(ccgdm->pbvh, partial_redraw_planes, NULL, (faceFlags[0] & ME_SMOOTH));
1522                         glShadeModel(GL_FLAT);
1523                 }
1524
1525                 return;
1526         }
1527
1528         fi = ccgSubSurf_getFaceIterator(ss);
1529         for (; !ccgFaceIterator_isStopped(fi); ccgFaceIterator_next(fi)) {
1530                 CCGFace *f = ccgFaceIterator_getCurrent(fi);
1531                 int S, x, y, numVerts = ccgSubSurf_getFaceNumVerts(f);
1532                 int index = GET_INT_FROM_POINTER(ccgSubSurf_getFaceFaceHandle(ss, f));
1533                 int drawSmooth, mat_nr;
1534
1535                 if(faceFlags) {
1536                         drawSmooth = (faceFlags[index*2] & ME_SMOOTH);
1537                         mat_nr= faceFlags[index*2 + 1];
1538                 }
1539                 else {
1540                         drawSmooth = 1;
1541                         mat_nr= 0;
1542                 }
1543                 
1544                 if (!setMaterial(mat_nr+1, NULL))
1545                         continue;
1546
1547                 glShadeModel(drawSmooth? GL_SMOOTH: GL_FLAT);
1548                 for (S=0; S<numVerts; S++) {
1549                         DMGridData *faceGridData = ccgSubSurf_getFaceGridDataArray(ss, f, S);
1550
1551                         if (drawSmooth) {
1552                                 for (y=0; y<gridSize-1; y+=step) {
1553                                         glBegin(GL_QUAD_STRIP);
1554                                         for (x=0; x<gridSize; x+=step) {
1555                                                 DMGridData *a = &faceGridData[(y+0)*gridSize + x];
1556                                                 DMGridData *b = &faceGridData[(y+step)*gridSize + x];
1557
1558                                                 glNormal3fv(a->no);
1559                                                 glVertex3fv(a->co);
1560                                                 glNormal3fv(b->no);
1561                                                 glVertex3fv(b->co);
1562                                         }
1563                                         glEnd();
1564                                 }
1565                         } else {
1566                                 glBegin(GL_QUADS);
1567                                 for (y=0; y<gridSize-1; y+=step) {
1568                                         for (x=0; x<gridSize-1; x+=step) {
1569                                                 float *a = faceGridData[(y+0)*gridSize + x].co;
1570                                                 float *b = faceGridData[(y+0)*gridSize + x + step].co;
1571                                                 float *c = faceGridData[(y+step)*gridSize + x + step].co;
1572                                                 float *d = faceGridData[(y+step)*gridSize + x].co;
1573
1574                                                 ccgDM_glNormalFast(a, b, c, d);
1575
1576                                                 glVertex3fv(d);
1577                                                 glVertex3fv(c);
1578                                                 glVertex3fv(b);
1579                                                 glVertex3fv(a);
1580                                         }
1581                                 }
1582                                 glEnd();
1583                         }
1584                 }
1585         }
1586
1587         ccgFaceIterator_free(fi);
1588 }
1589
1590         /* Only used by non-editmesh types */
1591 static void cgdm_drawMappedFacesGLSL(DerivedMesh *dm, int (*setMaterial)(int, void *attribs), int (*setDrawOptions)(void *userData, int index), void *userData) {
1592         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
1593         CCGSubSurf *ss = cgdm->ss;
1594         CCGFaceIterator *fi = ccgSubSurf_getFaceIterator(ss);
1595         GPUVertexAttribs gattribs;
1596         DMVertexAttribs attribs= {{{NULL}}};
1597         /* MTFace *tf = dm->getTessFaceDataArray(dm, CD_MTFACE); */ /* UNUSED */
1598         int gridSize = ccgSubSurf_getGridSize(ss);
1599         int gridFaces = gridSize - 1;
1600         int edgeSize = ccgSubSurf_getEdgeSize(ss);
1601         char *faceFlags = cgdm->faceFlags;
1602         int a, b, i, doDraw, numVerts, matnr, new_matnr, totface;
1603
1604         ccgdm_pbvh_update(cgdm);
1605
1606         doDraw = 0;
1607         matnr = -1;
1608
1609 #define PASSATTRIB(dx, dy, vert) {                                                                                              \
1610         if(attribs.totorco) {                                                                                                           \
1611                 index = getFaceIndex(ss, f, S, x+dx, y+dy, edgeSize, gridSize);                 \
1612                 glVertexAttrib3fvARB(attribs.orco.glIndex, attribs.orco.array[index]);  \
1613         }                                                                                                                                                       \
1614         for(b = 0; b < attribs.tottface; b++) {                                                                         \
1615                 MTFace *tf = &attribs.tface[b].array[a];                                                                \
1616                 glVertexAttrib2fvARB(attribs.tface[b].glIndex, tf->uv[vert]);                   \
1617         }                                                                                                                                                       \
1618         for(b = 0; b < attribs.totmcol; b++) {                                                                          \
1619                 MCol *cp = &attribs.mcol[b].array[a*4 + vert];                                                  \
1620                 GLubyte col[4];                                                                                                                 \
1621                 col[0]= cp->b; col[1]= cp->g; col[2]= cp->r; col[3]= cp->a;                             \
1622                 glVertexAttrib4ubvARB(attribs.mcol[b].glIndex, col);                                    \
1623         }                                                                                                                                                       \
1624         if(attribs.tottang) {                                                                                                           \
1625                 float *tang = attribs.tang.array[a*4 + vert];                                                   \
1626                 glVertexAttrib4fvARB(attribs.tang.glIndex, tang);                                               \
1627         }                                                                                                                                                       \
1628 }
1629
1630         totface = ccgSubSurf_getNumFaces(ss);
1631         for(a = 0, i = 0; i < totface; i++) {
1632                 CCGFace *f = cgdm->faceMap[i].face;
1633                 int S, x, y, drawSmooth;
1634                 int index = GET_INT_FROM_POINTER(ccgSubSurf_getFaceFaceHandle(ss, f));
1635                 int origIndex = ccgDM_getFaceMapIndex(ss, f);
1636                 
1637                 numVerts = ccgSubSurf_getFaceNumVerts(f);
1638
1639                 if(faceFlags) {
1640                         drawSmooth = (faceFlags[index*2] & ME_SMOOTH);
1641                         new_matnr= faceFlags[index*2 + 1] + 1;
1642                 }
1643                 else {
1644                         drawSmooth = 1;
1645                         new_matnr= 1;
1646                 }
1647
1648                 if(new_matnr != matnr) {
1649                         doDraw = setMaterial(matnr = new_matnr, &gattribs);
1650                         if(doDraw)
1651                                 DM_vertex_attributes_from_gpu(dm, &gattribs, &attribs);
1652                 }
1653
1654                 if(!doDraw || (setDrawOptions && (origIndex != ORIGINDEX_NONE) && !setDrawOptions(userData, origIndex))) {
1655                         a += gridFaces*gridFaces*numVerts;
1656                         continue;
1657                 }
1658
1659                 glShadeModel(drawSmooth? GL_SMOOTH: GL_FLAT);
1660                 for (S=0; S<numVerts; S++) {
1661                         DMGridData *faceGridData = ccgSubSurf_getFaceGridDataArray(ss, f, S);
1662                         DMGridData *vda, *vdb;
1663
1664                         if (drawSmooth) {
1665                                 for (y=0; y<gridFaces; y++) {
1666                                         glBegin(GL_QUAD_STRIP);
1667                                         for (x=0; x<gridFaces; x++) {
1668                                                 vda = &faceGridData[(y+0)*gridSize + x];
1669                                                 vdb = &faceGridData[(y+1)*gridSize + x];
1670                                                 
1671                                                 PASSATTRIB(0, 0, 0);
1672                                                 glNormal3fv(vda->no);
1673                                                 glVertex3fv(vda->co);
1674
1675                                                 PASSATTRIB(0, 1, 1);
1676                                                 glNormal3fv(vdb->no);
1677                                                 glVertex3fv(vdb->co);
1678
1679                                                 if(x != gridFaces-1)
1680                                                         a++;
1681                                         }
1682
1683                                         vda = &faceGridData[(y+0)*gridSize + x];
1684                                         vdb = &faceGridData[(y+1)*gridSize + x];
1685
1686                                         PASSATTRIB(0, 0, 3);
1687                                         glNormal3fv(vda->no);
1688                                         glVertex3fv(vda->co);
1689
1690                                         PASSATTRIB(0, 1, 2);
1691                                         glNormal3fv(vdb->no);
1692                                         glVertex3fv(vdb->co);
1693
1694                                         glEnd();
1695
1696                                         a++;
1697                                 }
1698                         } else {
1699                                 glBegin(GL_QUADS);
1700                                 for (y=0; y<gridFaces; y++) {
1701                                         for (x=0; x<gridFaces; x++) {
1702                                                 float *aco = faceGridData[(y+0)*gridSize + x].co;
1703                                                 float *bco = faceGridData[(y+0)*gridSize + x + 1].co;
1704                                                 float *cco = faceGridData[(y+1)*gridSize + x + 1].co;
1705                                                 float *dco = faceGridData[(y+1)*gridSize + x].co;
1706
1707                                                 ccgDM_glNormalFast(aco, bco, cco, dco);
1708
1709                                                 PASSATTRIB(0, 1, 1);
1710                                                 glVertex3fv(dco);
1711                                                 PASSATTRIB(1, 1, 2);
1712                                                 glVertex3fv(cco);
1713                                                 PASSATTRIB(1, 0, 3);
1714                                                 glVertex3fv(bco);
1715                                                 PASSATTRIB(0, 0, 0);
1716                                                 glVertex3fv(aco);
1717                                                 
1718                                                 a++;
1719                                         }
1720                                 }
1721                                 glEnd();
1722                         }
1723                 }
1724         }
1725
1726 #undef PASSATTRIB
1727
1728         ccgFaceIterator_free(fi);
1729 }
1730
1731 static void cgdm_drawFacesGLSL(DerivedMesh *dm, int (*setMaterial)(int, void *attribs)) {
1732         dm->drawMappedFacesGLSL(dm, setMaterial, NULL, NULL);
1733 }
1734
1735 static void cgdm_drawFacesColored(DerivedMesh *dm, int UNUSED(useTwoSided), unsigned char *col1, unsigned char *col2) {
1736         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
1737         CCGSubSurf *ss = cgdm->ss;
1738         CCGFaceIterator *fi = ccgSubSurf_getFaceIterator(ss);
1739         int gridSize = ccgSubSurf_getGridSize(ss);
1740         unsigned char *cp1, *cp2;
1741         int useTwoSide=1;
1742
1743         ccgdm_pbvh_update(cgdm);
1744
1745         cp1= col1;
1746         if(col2) {
1747                 cp2= col2;
1748         } else {
1749                 cp2= NULL;
1750                 useTwoSide= 0;
1751         }
1752
1753         glShadeModel(GL_SMOOTH);
1754
1755         if(col2) {
1756                 glEnable(GL_CULL_FACE);
1757         }
1758
1759         glBegin(GL_QUADS);
1760         for (; !ccgFaceIterator_isStopped(fi); ccgFaceIterator_next(fi)) {
1761                 CCGFace *f = ccgFaceIterator_getCurrent(fi);
1762                 int S, x, y, numVerts = ccgSubSurf_getFaceNumVerts(f);
1763
1764                 for (S=0; S<numVerts; S++) {
1765                         DMGridData *faceGridData = ccgSubSurf_getFaceGridDataArray(ss, f, S);
1766                         for (y=0; y<gridSize-1; y++) {
1767                                 for (x=0; x<gridSize-1; x++) {
1768                                         float *a = faceGridData[(y+0)*gridSize + x].co;
1769                                         float *b = faceGridData[(y+0)*gridSize + x + 1].co;
1770                                         float *c = faceGridData[(y+1)*gridSize + x + 1].co;
1771                                         float *d = faceGridData[(y+1)*gridSize + x].co;
1772
1773                                         glColor3ub(cp1[3], cp1[2], cp1[1]);
1774                                         glVertex3fv(d);
1775                                         glColor3ub(cp1[7], cp1[6], cp1[5]);
1776                                         glVertex3fv(c);
1777                                         glColor3ub(cp1[11], cp1[10], cp1[9]);
1778                                         glVertex3fv(b);
1779                                         glColor3ub(cp1[15], cp1[14], cp1[13]);
1780                                         glVertex3fv(a);
1781
1782                                         if (useTwoSide) {
1783                                                 glColor3ub(cp2[15], cp2[14], cp2[13]);
1784                                                 glVertex3fv(a);
1785                                                 glColor3ub(cp2[11], cp2[10], cp2[9]);
1786                                                 glVertex3fv(b);
1787                                                 glColor3ub(cp2[7], cp2[6], cp2[5]);
1788                                                 glVertex3fv(c);
1789                                                 glColor3ub(cp2[3], cp2[2], cp2[1]);
1790                                                 glVertex3fv(d);
1791                                         }
1792
1793                                         if (cp2) cp2+=16;
1794                                         cp1+=16;
1795                                 }
1796                         }
1797                 }
1798         }
1799         glEnd();
1800
1801         ccgFaceIterator_free(fi);
1802 }
1803
1804 static void cgdm_drawFacesTex_common(DerivedMesh *dm,
1805         int (*drawParams)(MTFace *tface, int has_vcol, int matnr),
1806         int (*drawParamsMapped)(void *userData, int index),
1807         void *userData) 
1808 {
1809         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
1810         CCGSubSurf *ss = cgdm->ss;
1811         MCol *mcol = dm->getTessFaceDataArray(dm, CD_WEIGHT_MCOL);
1812         MTFace *tf = DM_get_tessface_data_layer(dm, CD_MTFACE);
1813         char *faceFlags = cgdm->faceFlags;
1814         int i, totface, flag, gridSize = ccgSubSurf_getGridSize(ss);
1815         int gridFaces = gridSize - 1;
1816
1817         ccgdm_pbvh_update(cgdm);
1818
1819         if(!mcol)
1820                 mcol = dm->getTessFaceDataArray(dm, CD_MCOL);
1821
1822         totface = ccgSubSurf_getNumFaces(ss);
1823         for(i = 0; i < totface; i++) {
1824                 CCGFace *f = cgdm->faceMap[i].face;
1825                 int S, x, y, numVerts = ccgSubSurf_getFaceNumVerts(f);
1826                 int drawSmooth, index = ccgDM_getFaceMapIndex(ss, f);
1827                 int origIndex = GET_INT_FROM_POINTER(ccgSubSurf_getFaceFaceHandle(ss, f));
1828                 unsigned char *cp= NULL;
1829                 int mat_nr;
1830
1831                 if(faceFlags) {
1832                         drawSmooth = (faceFlags[origIndex*2] & ME_SMOOTH);
1833                         mat_nr= faceFlags[origIndex*2 + 1];
1834                 }
1835                 else {
1836                         drawSmooth = 1;
1837                         mat_nr= 0;
1838                 }
1839
1840                 if(drawParams)
1841                         flag = drawParams(tf, mcol!=NULL, mat_nr);
1842                 else if (index != ORIGINDEX_NONE)
1843                         flag= (drawParamsMapped)? drawParamsMapped(userData, index): 1;
1844                 else
1845                         flag= GPU_enable_material(mat_nr, NULL) ? 1:0;
1846
1847
1848                 if (flag == 0) { /* flag 0 == the face is hidden or invisible */
1849                         if(tf) tf += gridFaces*gridFaces*numVerts;
1850                         if(mcol) mcol += gridFaces*gridFaces*numVerts*4;
1851                         continue;
1852                 }
1853
1854                 /* flag 1 == use vertex colors */
1855                 if(mcol) {
1856                         if(flag==1) cp= (unsigned char*)mcol;
1857                         mcol += gridFaces*gridFaces*numVerts*4;
1858                 }
1859
1860                 for (S=0; S<numVerts; S++) {
1861                         DMGridData *faceGridData = ccgSubSurf_getFaceGridDataArray(ss, f, S);
1862                         DMGridData *a, *b;
1863
1864                         if (drawSmooth) {
1865                                 glShadeModel(GL_SMOOTH);
1866                                 for (y=0; y<gridFaces; y++) {
1867                                         glBegin(GL_QUAD_STRIP);
1868                                         for (x=0; x<gridFaces; x++) {
1869                                                 a = &faceGridData[(y+0)*gridSize + x];
1870                                                 b = &faceGridData[(y+1)*gridSize + x];
1871
1872                                                 if(tf) glTexCoord2fv(tf->uv[0]);
1873                                                 if(cp) glColor3ub(cp[3], cp[2], cp[1]);
1874                                                 glNormal3fv(a->no);
1875                                                 glVertex3fv(a->co);
1876
1877                                                 if(tf) glTexCoord2fv(tf->uv[1]);
1878                                                 if(cp) glColor3ub(cp[7], cp[6], cp[5]);
1879                                                 glNormal3fv(b->no);
1880                                                 glVertex3fv(b->co);
1881                                                 
1882                                                 if(x != gridFaces-1) {
1883                                                         if(tf) tf++;
1884                                                         if(cp) cp += 16;
1885                                                 }
1886                                         }
1887
1888                                         a = &faceGridData[(y+0)*gridSize + x];
1889                                         b = &faceGridData[(y+1)*gridSize + x];
1890
1891                                         if(tf) glTexCoord2fv(tf->uv[3]);
1892                                         if(cp) glColor3ub(cp[15], cp[14], cp[13]);
1893                                         glNormal3fv(a->no);
1894                                         glVertex3fv(a->co);
1895
1896                                         if(tf) glTexCoord2fv(tf->uv[2]);
1897                                         if(cp) glColor3ub(cp[11], cp[10], cp[9]);
1898                                         glNormal3fv(b->no);
1899                                         glVertex3fv(b->co);
1900
1901                                         if(tf) tf++;
1902                                         if(cp) cp += 16;
1903
1904                                         glEnd();
1905                                 }
1906                         } else {
1907                                 glShadeModel(GL_FLAT);
1908                                 glBegin(GL_QUADS);
1909                                 for (y=0; y<gridFaces; y++) {
1910                                         for (x=0; x<gridFaces; x++) {
1911                                                 float *a_co = faceGridData[(y+0)*gridSize + x].co;
1912                                                 float *b_co = faceGridData[(y+0)*gridSize + x + 1].co;
1913                                                 float *c_co = faceGridData[(y+1)*gridSize + x + 1].co;
1914                                                 float *d_co = faceGridData[(y+1)*gridSize + x].co;
1915
1916                                                 ccgDM_glNormalFast(a_co, b_co, c_co, d_co);
1917
1918                                                 if(tf) glTexCoord2fv(tf->uv[1]);
1919                                                 if(cp) glColor3ub(cp[7], cp[6], cp[5]);
1920                                                 glVertex3fv(d_co);
1921
1922                                                 if(tf) glTexCoord2fv(tf->uv[2]);
1923                                                 if(cp) glColor3ub(cp[11], cp[10], cp[9]);
1924                                                 glVertex3fv(c_co);
1925
1926                                                 if(tf) glTexCoord2fv(tf->uv[3]);
1927                                                 if(cp) glColor3ub(cp[15], cp[14], cp[13]);
1928                                                 glVertex3fv(b_co);
1929
1930                                                 if(tf) glTexCoord2fv(tf->uv[0]);
1931                                                 if(cp) glColor3ub(cp[3], cp[2], cp[1]);
1932                                                 glVertex3fv(a_co);
1933
1934                                                 if(tf) tf++;
1935                                                 if(cp) cp += 16;
1936                                         }
1937                                 }
1938                                 glEnd();
1939                         }
1940                 }
1941         }
1942 }
1943
1944 static void cgdm_drawFacesTex(DerivedMesh *dm, int (*setDrawOptions)(MTFace *tface, int has_vcol, int matnr))
1945 {
1946         cgdm_drawFacesTex_common(dm, setDrawOptions, NULL, NULL);
1947 }
1948
1949 static void cgdm_drawMappedFacesTex(DerivedMesh *dm, int (*setDrawOptions)(void *userData, int index), void *userData)
1950 {
1951         cgdm_drawFacesTex_common(dm, NULL, setDrawOptions, userData);
1952 }
1953
1954 static void cgdm_drawUVEdges(DerivedMesh *dm)
1955 {
1956
1957         MFace *mf = dm->getTessFaceArray(dm);
1958         MTFace *tf = DM_get_tessface_data_layer(dm, CD_MTFACE);
1959         int i;
1960         
1961         if (tf) {
1962                 glBegin(GL_LINES);
1963                 for(i = 0; i < dm->numFaceData; i++, mf++, tf++) {
1964                         if(!(mf->flag&ME_HIDE)) {
1965                                 glVertex2fv(tf->uv[0]);
1966                                 glVertex2fv(tf->uv[1]);
1967         
1968                                 glVertex2fv(tf->uv[1]);
1969                                 glVertex2fv(tf->uv[2]);
1970         
1971                                 if(!mf->v4) {
1972                                         glVertex2fv(tf->uv[2]);
1973                                         glVertex2fv(tf->uv[0]);
1974                                 } else {
1975                                         glVertex2fv(tf->uv[2]);
1976                                         glVertex2fv(tf->uv[3]);
1977         
1978                                         glVertex2fv(tf->uv[3]);
1979                                         glVertex2fv(tf->uv[0]);
1980                                 }
1981                         }
1982                 }
1983                 glEnd();
1984         }
1985 }
1986
1987 static void ccgDM_drawMappedFaces(DerivedMesh *dm, int (*setDrawOptions)(void *userData, int index, int *drawSmooth_r), void *userData, int useColors, int (*setMaterial)(int, void *attribs),
1988                         int (*compareDrawOptions)(void *userData, int cur_index, int next_index)) {
1989         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
1990         CCGSubSurf *ss = cgdm->ss;
1991         MCol *mcol= NULL;
1992         int i, gridSize = ccgSubSurf_getGridSize(ss);
1993         char *faceFlags = cgdm->faceFlags;
1994         int gridFaces = gridSize - 1, totface;
1995
1996         /* currently unused -- each original face is handled separately */
1997         (void)compareDrawOptions;
1998
1999         if(useColors) {
2000                 mcol = dm->getTessFaceDataArray(dm, CD_WEIGHT_MCOL);
2001                 if(!mcol)
2002                         mcol = dm->getTessFaceDataArray(dm, CD_MCOL);
2003         }
2004
2005         totface = ccgSubSurf_getNumFaces(ss);
2006         for(i = 0; i < totface; i++) {
2007                 CCGFace *f = cgdm->faceMap[i].face;
2008                 int S, x, y, numVerts = ccgSubSurf_getFaceNumVerts(f);
2009                 int drawSmooth, index = ccgDM_getFaceMapIndex(ss, f);
2010                 int origIndex;
2011                 unsigned char *cp= NULL;
2012
2013                 origIndex = GET_INT_FROM_POINTER(ccgSubSurf_getFaceFaceHandle(ss, f));
2014
2015                 if(faceFlags) drawSmooth = (faceFlags[origIndex*2] & ME_SMOOTH);
2016                 else drawSmooth = 1;
2017
2018                 if(mcol) {
2019                         cp= (unsigned char*)mcol;
2020                         mcol += gridFaces*gridFaces*numVerts*4;
2021                 }
2022
2023                 {
2024                         int draw= 1;
2025
2026                         if(index == ORIGINDEX_NONE)
2027                                 draw= setMaterial(faceFlags ? faceFlags[origIndex*2 + 1] + 1: 1, NULL); /* XXX, no faceFlags no material */
2028                         else if (setDrawOptions)
2029                                 draw= setDrawOptions(userData, index, &drawSmooth);
2030
2031                         if (draw) {
2032                                 if (draw==2) {
2033                                           glEnable(GL_POLYGON_STIPPLE);
2034                                           glPolygonStipple(stipple_quarttone);
2035                                 }
2036                                 
2037                                 for (S=0; S<numVerts; S++) {
2038                                         DMGridData *faceGridData = ccgSubSurf_getFaceGridDataArray(ss, f, S);
2039                                         if (drawSmooth) {
2040                                                 glShadeModel(GL_SMOOTH);
2041                                                 for (y=0; y<gridFaces; y++) {
2042                                                         DMGridData *a, *b;
2043                                                         glBegin(GL_QUAD_STRIP);
2044                                                         for (x=0; x<gridFaces; x++) {
2045                                                                 a = &faceGridData[(y+0)*gridSize + x];
2046                                                                 b = &faceGridData[(y+1)*gridSize + x];
2047         
2048                                                                 if(cp) glColor3ub(cp[3], cp[2], cp[1]);
2049                                                                 glNormal3fv(a->no);
2050                                                                 glVertex3fv(a->co);
2051                                                                 if(cp) glColor3ub(cp[7], cp[6], cp[5]);
2052                                                                 glNormal3fv(b->no);
2053                                                                 glVertex3fv(b->co);
2054
2055                                                                 if(x != gridFaces-1) {
2056                                                                         if(cp) cp += 16;
2057                                                                 }
2058                                                         }
2059
2060                                                         a = &faceGridData[(y+0)*gridSize + x];
2061                                                         b = &faceGridData[(y+1)*gridSize + x];
2062
2063                                                         if(cp) glColor3ub(cp[15], cp[14], cp[13]);
2064                                                         glNormal3fv(a->no);
2065                                                         glVertex3fv(a->co);
2066                                                         if(cp) glColor3ub(cp[11], cp[10], cp[9]);
2067                                                         glNormal3fv(b->no);
2068                                                         glVertex3fv(b->co);
2069
2070                                                         if(cp) cp += 16;
2071
2072                                                         glEnd();
2073                                                 }
2074                                         } else {
2075                                                 glShadeModel(GL_FLAT);
2076                                                 glBegin(GL_QUADS);
2077                                                 for (y=0; y<gridFaces; y++) {
2078                                                         for (x=0; x<gridFaces; x++) {
2079                                                                 float *a = faceGridData[(y+0)*gridSize + x].co;
2080                                                                 float *b = faceGridData[(y+0)*gridSize + x + 1].co;
2081                                                                 float *c = faceGridData[(y+1)*gridSize + x + 1].co;
2082                                                                 float *d = faceGridData[(y+1)*gridSize + x].co;
2083
2084                                                                 ccgDM_glNormalFast(a, b, c, d);
2085         
2086                                                                 if(cp) glColor3ub(cp[7], cp[6], cp[5]);
2087                                                                 glVertex3fv(d);
2088                                                                 if(cp) glColor3ub(cp[11], cp[10], cp[9]);
2089                                                                 glVertex3fv(c);
2090                                                                 if(cp) glColor3ub(cp[15], cp[14], cp[13]);
2091                                                                 glVertex3fv(b);
2092                                                                 if(cp) glColor3ub(cp[3], cp[2], cp[1]);
2093                                                                 glVertex3fv(a);
2094
2095                                                                 if(cp) cp += 16;
2096                                                         }
2097                                                 }
2098                                                 glEnd();
2099                                         }
2100                                 }
2101                                 if (draw==2)
2102                                         glDisable(GL_POLYGON_STIPPLE);
2103                         }
2104                 }
2105         }
2106 }
2107 static void cgdm_drawMappedEdges(DerivedMesh *dm, int (*setDrawOptions)(void *userData, int index), void *userData) {
2108         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
2109         CCGSubSurf *ss = cgdm->ss;
2110         CCGEdgeIterator *ei = ccgSubSurf_getEdgeIterator(ss);
2111         int i, useAging, edgeSize = ccgSubSurf_getEdgeSize(ss);
2112
2113         ccgSubSurf_getUseAgeCounts(ss, &useAging, NULL, NULL, NULL);
2114
2115         for (; !ccgEdgeIterator_isStopped(ei); ccgEdgeIterator_next(ei)) {
2116                 CCGEdge *e = ccgEdgeIterator_getCurrent(ei);
2117                 DMGridData *edgeData = ccgSubSurf_getEdgeDataArray(ss, e);
2118                 int index = ccgDM_getEdgeMapIndex(ss, e);
2119
2120                 glBegin(GL_LINE_STRIP);
2121                 if (index!=-1 && (!setDrawOptions || setDrawOptions(userData, index))) {
2122                         if (useAging && !(G.f&G_BACKBUFSEL)) {
2123                                 int ageCol = 255-ccgSubSurf_getEdgeAge(ss, e)*4;
2124                                 glColor3ub(0, ageCol>0?ageCol:0, 0);
2125                         }
2126
2127                         for (i=0; i<edgeSize-1; i++) {
2128                                 glVertex3fv(edgeData[i].co);
2129                                 glVertex3fv(edgeData[i+1].co);
2130                         }
2131                 }
2132                 glEnd();
2133         }
2134
2135         ccgEdgeIterator_free(ei);
2136 }
2137 static void cgdm_drawMappedEdgesInterp(DerivedMesh *dm, int (*setDrawOptions)(void *userData, int index), void (*setDrawInterpOptions)(void *userData, int index, float t), void *userData) {
2138         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
2139         CCGSubSurf *ss = cgdm->ss;
2140         CCGEdgeIterator *ei = ccgSubSurf_getEdgeIterator(ss);
2141         int i, useAging, edgeSize = ccgSubSurf_getEdgeSize(ss);
2142
2143         ccgSubSurf_getUseAgeCounts(ss, &useAging, NULL, NULL, NULL);
2144
2145         for (; !ccgEdgeIterator_isStopped(ei); ccgEdgeIterator_next(ei)) {
2146                 CCGEdge *e = ccgEdgeIterator_getCurrent(ei);
2147                 DMGridData *edgeData = ccgSubSurf_getEdgeDataArray(ss, e);
2148                 int index = ccgDM_getEdgeMapIndex(ss, e);
2149
2150                 glBegin(GL_LINE_STRIP);
2151                 if (index!=-1 && (!setDrawOptions || setDrawOptions(userData, index))) {
2152                         for (i=0; i<edgeSize; i++) {
2153                                 setDrawInterpOptions(userData, index, (float) i/(edgeSize-1));
2154
2155                                 if (useAging && !(G.f&G_BACKBUFSEL)) {
2156                                         int ageCol = 255-ccgSubSurf_getEdgeAge(ss, e)*4;
2157                                         glColor3ub(0, ageCol>0?ageCol:0, 0);
2158                                 }
2159
2160                                 glVertex3fv(edgeData[i].co);
2161                         }
2162                 }
2163                 glEnd();
2164         }
2165
2166         ccgEdgeIterator_free(ei);
2167 }
2168 static void cgdm_foreachMappedFaceCenter(DerivedMesh *dm, void (*func)(void *userData, int index, float *co, float *no), void *userData) {
2169         CCGDerivedMesh *cgdm = (CCGDerivedMesh*) dm;
2170         CCGSubSurf *ss = cgdm->ss;
2171         CCGFaceIterator *fi = ccgSubSurf_getFaceIterator(ss);
2172
2173         for (; !ccgFaceIterator_isStopped(fi); ccgFaceIterator_next(fi)) {
2174                 CCGFace *f = ccgFaceIterator_getCurrent(fi);
2175                 int index = ccgDM_getFaceMapIndex(ss, f);
2176
2177                 if (index!=-1) {
2178                                 /* Face center data normal isn't updated atm. */
2179                         DMGridData *vd = ccgSubSurf_getFaceGridData(ss, f, 0, 0, 0);
2180
2181                         func(userData, index, vd->co, vd->no);
2182                 }
2183         }
2184
2185         ccgFaceIterator_free(fi);
2186 }
2187
2188 static void cgdm_release(DerivedMesh *dm) {
2189         CCGDerivedMesh *ccgdm = (CCGDerivedMesh*) dm;
2190
2191         if (DM_release(dm)) {
2192                 /* Before freeing, need to update the displacement map */
2193                 if(ccgdm->multires.modified) {
2194                         /* Check that mmd still exists */
2195                         if(!ccgdm->multires.local_mmd && BLI_findindex(&ccgdm->multires.ob->modifiers, ccgdm->multires.mmd) < 0)
2196                                 ccgdm->multires.mmd = NULL;
2197                         if(ccgdm->multires.mmd)
2198                                 ccgdm->multires.update(dm);
2199                 }
2200
2201                 if (ccgdm->ehash)
2202                         BLI_edgehash_free(ccgdm->ehash, NULL);
2203
2204                 if(ccgdm->reverseFaceMap) MEM_freeN(ccgdm->reverseFaceMap);
2205                 if(ccgdm->gridFaces) MEM_freeN(ccgdm->gridFaces);
2206                 if(ccgdm->gridData) MEM_freeN(ccgdm->gridData);
2207                 if(ccgdm->gridAdjacency) MEM_freeN(ccgdm->gridAdjacency);
2208                 if(ccgdm->gridOffset) MEM_freeN(ccgdm->gridOffset);
2209                 if(ccgdm->freeSS) ccgSubSurf_free(ccgdm->ss);
2210                 if(ccgdm->fmap) MEM_freeN(ccgdm->fmap);
2211                 if(ccgdm->fmap_mem) MEM_freeN(ccgdm->fmap_mem);
2212                 MEM_freeN(ccgdm->edgeFlags);
2213                 MEM_freeN(ccgdm->faceFlags);
2214                 MEM_freeN(ccgdm->vertMap);
2215                 MEM_freeN(ccgdm->edgeMap);
2216                 MEM_freeN(ccgdm->faceMap);
2217                 MEM_freeN(ccgdm);
2218         }
2219 }
2220
2221 static void ccg_loops_to_corners(CustomData *fdata, CustomData *ldata, 
2222                           CustomData *pdata, int loopstart, int findex, 
2223                           int polyindex, int numTex, int numCol) 
2224 {
2225         MTFace *texface;
2226         MTexPoly *texpoly;
2227         MCol *mcol;
2228         MLoopCol *mloopcol;
2229         MLoopUV *mloopuv;
2230         int i, j, hasWCol = CustomData_has_layer(ldata, CD_WEIGHT_MLOOPCOL);
2231
2232         for(i=0; i < numTex; i++){
2233                 texface = CustomData_get_n(fdata, CD_MTFACE, findex, i);
2234                 texpoly = CustomData_get_n(pdata, CD_MTEXPOLY, polyindex, i);
2235                 
2236                 texface->tpage = texpoly->tpage;
2237                 texface->flag = texpoly->flag;
2238                 texface->transp = texpoly->transp;
2239                 texface->mode = texpoly->mode;
2240                 texface->tile = texpoly->tile;
2241                 texface->unwrap = texpoly->unwrap;
2242
2243                 mloopuv = CustomData_get_n(ldata, CD_MLOOPUV, loopstart, i);
2244                 for (j=0; j<4; j++, mloopuv++) {
2245                         texface->uv[j][0] = mloopuv->uv[0];
2246                         texface->uv[j][1] = mloopuv->uv[1];
2247                 }
2248         }
2249
2250         for(i=0; i < numCol; i++){
2251                 mloopcol = CustomData_get_n(ldata, CD_MLOOPCOL, loopstart, i);
2252                 mcol = CustomData_get_n(fdata, CD_MCOL, findex, i);
2253
2254                 for (j=0; j<4; j++, mloopcol++) {
2255                         mcol[j].r = mloopcol->r;
2256                         mcol[j].g = mloopcol->g;
2257                         mcol[j].b = mloopcol->b;
2258                         mcol[j].a = mloopcol->a;
2259                 }
2260         }
2261         
2262         if (hasWCol) {
2263                 mloopcol = CustomData_get(ldata, loopstart, CD_WEIGHT_MLOOPCOL);
2264                 mcol = CustomData_get(fdata, findex, CD_WEIGHT_MCOL);
2265
2266                 for (j=0; j<4; j++, mloopcol++) {
2267                         mcol[j].r = mloopcol->r;
2268                         mcol[j].g = mloopcol->g;
2269                         mcol[j].b = mloopcol->b;
2270                         mcol[j].a = mloopcol->a;
2271                 }
2272         }
2273 }
2274
2275 static void *ccgDM_get_vert_data_layer(DerivedMesh *dm, int type)
2276 {
2277         if(type == CD_ORIGINDEX) {
2278                 /* create origindex on demand to save memory */
2279                 CCGDerivedMesh *cgdm= (CCGDerivedMesh*)dm;
2280                 CCGSubSurf *ss= cgdm->ss;
2281                 int *origindex;
2282                 int a, index, totnone, totorig;
2283
2284                 DM_add_vert_layer(dm, CD_ORIGINDEX, CD_CALLOC, NULL);
2285                 origindex= DM_get_vert_data_layer(dm, CD_ORIGINDEX);
2286
2287                 totorig = ccgSubSurf_getNumVerts(ss);
2288                 totnone= dm->numVertData - totorig;
2289
2290                 /* original vertices are at the end */
2291                 for(a=0; a<totnone; a++)
2292                         origindex[a]= ORIGINDEX_NONE;
2293
2294                 for(index=0; index<totorig; index++, a++) {
2295                         CCGVert *v = cgdm->vertMap[index].vert;
2296                         origindex[a] = ccgDM_getVertMapIndex(cgdm->ss, v);
2297                 }
2298
2299                 return origindex;
2300         }
2301
2302         return DM_get_vert_data_layer(dm, type);
2303 }
2304
2305 static void *ccgDM_get_edge_data_layer(DerivedMesh *dm, int type)
2306 {
2307         if(type == CD_ORIGINDEX) {
2308                 /* create origindex on demand to save memory */
2309                 CCGDerivedMesh *cgdm= (CCGDerivedMesh*)dm;
2310                 CCGSubSurf *ss= cgdm->ss;
2311                 int *origindex;
2312                 int a, i, index, totnone, totorig, totedge;
2313                 int edgeSize= ccgSubSurf_getEdgeSize(ss);
2314
2315                 DM_add_edge_layer(dm, CD_ORIGINDEX, CD_CALLOC, NULL);
2316                 origindex= DM_get_edge_data_layer(dm, CD_ORIGINDEX);
2317
2318                 totedge= ccgSubSurf_getNumEdges(ss);
2319                 totorig= totedge*(edgeSize - 1);
2320                 totnone= dm->numEdgeData - totorig;
2321
2322                 /* original edges are at the end */
2323                 for(a=0; a<totnone; a++)
2324                         origindex[a]= ORIGINDEX_NONE;
2325
2326                 for(index=0; index<totedge; index++) {
2327                         CCGEdge *e= cgdm->edgeMap[index].edge;
2328                         int mapIndex= ccgDM_getEdgeMapIndex(ss, e);
2329
2330                         for(i = 0; i < edgeSize - 1; i++, a++)
2331                                 origindex[a]= mapIndex;
2332                 }
2333
2334                 return origindex;
2335         }
2336
2337         return DM_get_edge_data_layer(dm, type);
2338 }
2339
2340 static void *ccgDM_get_face_data_layer(DerivedMesh *dm, int type)
2341 {
2342         if(type == CD_ORIGINDEX) {
2343                 /* create origindex on demand to save memory */
2344                 CCGDerivedMesh *cgdm= (CCGDerivedMesh*)dm;
2345                 CCGSubSurf *ss= cgdm->ss;
2346                 int *origindex;
2347                 int a, i, index, totface;
2348                 int gridFaces = ccgSubSurf_getGridSize(ss) - 1;
2349
2350                 DM_add_face_layer(dm, CD_ORIGINDEX, CD_CALLOC, NULL);
2351                 origindex= DM_get_tessface_data_layer(dm, CD_ORIGINDEX);
2352
2353                 totface= ccgSubSurf_getNumFaces(ss);
2354
2355                 for(a=0, index=0; index<totface; index++) {
2356                         CCGFace *f = cgdm->faceMap[index].face;
2357                         int numVerts = ccgSubSurf_getFaceNumVerts(f);
2358                         int mapIndex = ccgDM_getFaceMapIndex(ss, f);
2359
2360                         for(i=0; i<gridFaces*gridFaces*numVerts; i++, a++)
2361                                 origindex[a]= mapIndex;
2362                 }
2363
2364                 return origindex;
2365         }
2366
2367         return DM_get_tessface_data_layer(dm, type);
2368 }
2369
2370 static int ccgDM_getNumGrids(DerivedMesh *dm)
2371 {
2372         CCGDerivedMesh *cgdm= (CCGDerivedMesh*)dm;
2373         int index, numFaces, numGrids;
2374
2375         numFaces= ccgSubSurf_getNumFaces(cgdm->ss);
2376         numGrids= 0;
2377
2378         for(index=0; index<numFaces; index++) {
2379                 CCGFace *f = cgdm->faceMap[index].face;
2380                 numGrids += ccgSubSurf_getFaceNumVerts(f);
2381         }
2382
2383         return numGrids;
2384 }
2385
2386 static int ccgDM_getGridSize(DerivedMesh *dm)
2387 {
2388         CCGDerivedMesh *cgdm= (CCGDerivedMesh*)dm;
2389         return ccgSubSurf_getGridSize(cgdm->ss);
2390 }
2391
2392 static int cgdm_adjacent_grid(CCGSubSurf *ss, int *gridOffset, CCGFace *f, int S, int offset)
2393 {
2394         CCGFace *adjf;
2395         CCGEdge *e;
2396         int i, j= 0, numFaces, fIndex, numEdges= 0;
2397
2398         e = ccgSubSurf_getFaceEdge(ss, f, S);
2399         numFaces = ccgSubSurf_getEdgeNumFaces(e);
2400
2401         if(numFaces != 2)
2402                 return -1;
2403
2404         for(i = 0; i < numFaces; i++) {
2405                 adjf = ccgSubSurf_getEdgeFace(e, i);
2406
2407                 if(adjf != f) {
2408                         numEdges = ccgSubSurf_getFaceNumVerts(adjf);
2409                         for(j = 0; j < numEdges; j++)
2410                                 if(ccgSubSurf_getFaceEdge(ss, adjf, j) == e)
2411                                         break;
2412
2413                         if(j != numEdges)
2414                                 break;
2415                 }
2416         }
2417         
2418         fIndex = GET_INT_FROM_POINTER(ccgSubSurf_getFaceFaceHandle(ss, adjf));
2419
2420         return gridOffset[fIndex] + (j + offset)%numEdges;
2421 }
2422
2423 static void ccgdm_create_grids(DerivedMesh *dm)
2424 {
2425         CCGDerivedMesh *cgdm= (CCGDerivedMesh*)dm;
2426         CCGSubSurf *ss= cgdm->ss;
2427         DMGridData **gridData;
2428         DMGridAdjacency *gridAdjacency, *adj;
2429         CCGFace **gridFaces;
2430         int *gridOffset;
2431         int index, numFaces, numGrids, S, gIndex /*, gridSize*/;
2432
2433         if(cgdm->gridData)
2434                 return;
2435         
2436         numGrids = ccgDM_getNumGrids(dm);
2437         numFaces = ccgSubSurf_getNumFaces(ss);
2438         /*gridSize = ccgDM_getGridSize(dm);*/  /*UNUSED*/
2439
2440         /* compute offset into grid array for each face */
2441         gridOffset = MEM_mallocN(sizeof(int)*numFaces, "cgdm.gridOffset");
2442
2443         for(gIndex = 0, index = 0; index < numFaces; index++) {
2444                 CCGFace *f = cgdm->faceMap[index].face;
2445                 int numVerts = ccgSubSurf_getFaceNumVerts(f);
2446
2447                 gridOffset[index] = gIndex;
2448                 gIndex += numVerts;
2449         }
2450
2451         /* compute grid data */
2452         gridData = MEM_mallocN(sizeof(DMGridData*)*numGrids, "cgdm.gridData");
2453         gridAdjacency = MEM_mallocN(sizeof(DMGridAdjacency)*numGrids, "cgdm.gridAdjacency");
2454         gridFaces = MEM_mallocN(sizeof(CCGFace*)*numGrids, "cgdm.gridFaces");
2455
2456         for(gIndex = 0, index = 0; index < numFaces; index++) {
2457                 CCGFace *f = cgdm->faceMap[index].face;
2458                 int numVerts = ccgSubSurf_getFaceNumVerts(f);
2459
2460                 for(S = 0; S < numVerts; S++, gIndex++) {
2461                         int prevS = (S - 1 + numVerts) % numVerts;
2462                         int nextS = (S + 1 + numVerts) % numVerts;
2463
2464                         gridData[gIndex] = ccgSubSurf_getFaceGridDataArray(ss, f, S);
2465                         gridFaces[gIndex] = f;
2466
2467                         adj = &gridAdjacency[gIndex];
2468
2469                         adj->index[0] = gIndex - S + nextS;
2470                         adj->rotation[0] = 3;
2471                         adj->index[1] = cgdm_adjacent_grid(ss, gridOffset, f, prevS, 0);
2472                         adj->rotation[1] = 1;
2473                         adj->index[2] = cgdm_adjacent_grid(ss, gridOffset, f, S, 1);
2474                         adj->rotation[2] = 3;
2475                         adj->index[3] = gIndex - S + prevS;
2476                         adj->rotation[3] = 1;
2477                 }
2478         }
2479
2480         cgdm->gridData = gridData;
2481         cgdm->gridFaces = gridFaces;
2482         cgdm->gridAdjacency = gridAdjacency;
2483         cgdm->gridOffset = gridOffset;
2484 }
2485
2486 static DMGridData **ccgDM_getGridData(DerivedMesh *dm)
2487 {
2488         CCGDerivedMesh *cgdm= (CCGDerivedMesh*)dm;
2489
2490         ccgdm_create_grids(dm);
2491         return cgdm->gridData;
2492 }
2493
2494 static DMGridAdjacency *ccgDM_getGridAdjacency(DerivedMesh *dm)
2495 {
2496         CCGDerivedMesh *cgdm= (CCGDerivedMesh*)dm;
2497
2498         ccgdm_create_grids(dm);
2499         return cgdm->gridAdjacency;
2500 }
2501
2502 static int *ccgDM_getGridOffset(DerivedMesh *dm)
2503 {
2504         CCGDerivedMesh *cgdm= (CCGDerivedMesh*)dm;
2505
2506         ccgdm_create_grids(dm);
2507         return cgdm->gridOffset;
2508 }
2509
2510 static ListBase *ccgDM_getFaceMap(Object *ob, DerivedMesh *dm)
2511 {
2512         CCGDerivedMesh *ccgdm= (CCGDerivedMesh*)dm;
2513
2514         if(!ccgdm->multires.mmd && !ccgdm->fmap && ob->type == OB_MESH) {
2515                 Mesh *me= ob->data;
2516
2517                 create_vert_face_map(&ccgdm->fmap, &ccgdm->fmap_mem, me->mface,
2518                                      me->totvert, me->totface);
2519         }
2520
2521         return ccgdm->fmap;
2522 }
2523
2524 static int ccgDM_use_grid_pbvh(CCGDerivedMesh *ccgdm)
2525 {
2526         MultiresModifierData *mmd= ccgdm->multires.mmd;
2527
2528         /* both of multires and subsurm modifiers are CCG, but
2529            grids should only be used when sculpting on multires */
2530         if(!mmd)
2531                 return 0;
2532
2533         return 1;
2534 }
2535
2536 static struct PBVH *ccgDM_getPBVH(Object *ob, DerivedMesh *dm)
2537 {
2538         CCGDerivedMesh *ccgdm= (CCGDerivedMesh*)dm;
2539         int gridSize, numGrids, grid_pbvh;
2540
2541         if(!ob) {
2542                 ccgdm->pbvh= NULL;
2543                 return NULL;
2544         }
2545
2546         if(!ob->sculpt)
2547                 return NULL;
2548
2549         grid_pbvh= ccgDM_use_grid_pbvh(ccgdm);
2550
2551         if(ob->sculpt->pbvh) {
2552                 if(grid_pbvh) {
2553                         /* pbvh's grids, gridadj and gridfaces points to data inside ccgdm
2554                            but this can be freed on ccgdm release, this updates the pointers
2555                            when the ccgdm gets remade, the assumption is that the topology
2556                            does not change. */
2557                         ccgdm_create_grids(dm);
2558                         BLI_pbvh_grids_update(ob->sculpt->pbvh, ccgdm->gridData, ccgdm->gridAdjacency, (void**)ccgdm->gridFaces);
2559                 }
2560
2561                 ccgdm->pbvh = ob->sculpt->pbvh;
2562         }
2563
2564         if(ccgdm->pbvh)
2565                 return ccgdm->pbvh;
2566
2567         /* no pbvh exists yet, we need to create one. only in case of multires
2568            we build a pbvh over the modified mesh, in other cases the base mesh
2569            is being sculpted, so we build a pbvh from that. */
2570         if(grid_pbvh) {
2571                 ccgdm_create_grids(dm);
2572
2573                 gridSize = ccgDM_getGridSize(dm);
2574                 numGrids = ccgDM_getNumGrids(dm);
2575
2576                 ob->sculpt->pbvh= ccgdm->pbvh = BLI_pbvh_new();
2577                 BLI_pbvh_build_grids(ccgdm->pbvh, ccgdm->gridData, ccgdm->gridAdjacency,
2578                         numGrids, gridSize, (void**)ccgdm->gridFaces);
2579         } else if(ob->type == OB_MESH) {
2580                 Mesh *me= ob->data;
2581                 ob->sculpt->pbvh= ccgdm->pbvh = BLI_pbvh_new();
2582                 BLI_pbvh_build_mesh(ccgdm->pbvh, me->mface, me->mvert,
2583                                    me->totface, me->totvert);
2584         }
2585
2586         return ccgdm->pbvh;
2587 }
2588
2589 static CCGDerivedMesh *getCCGDerivedMesh(CCGSubSurf *ss,
2590                                                                                  int drawInteriorEdges,
2591                                                                                  int useSubsurfUv,
2592                                                                                  DerivedMesh *dm)
2593 {
2594         CCGDerivedMesh *ccgdm = MEM_callocN(sizeof(*ccgdm), "cgdm");
2595         CCGVertIterator *vi;
2596         CCGEdgeIterator *ei;
2597         CCGFaceIterator *fi;
2598         int index, totvert, totedge, totface;
2599         int i;
2600         int vertNum, edgeNum, faceNum;
2601         int *vertOrigIndex, *faceOrigIndex, *polyOrigIndex, *base_polyOrigIndex; /* *edgeOrigIndex - as yet, unused  */
2602         short *edgeFlags;
2603         char *faceFlags;
2604         int *loopidx = NULL, *vertidx = NULL;
2605         BLI_array_declare(loopidx);
2606         BLI_array_declare(vertidx);
2607         int loopindex, loopindex2;
2608         int edgeSize, has_edge_origindex;
2609         int gridSize;
2610         int gridFaces, gridCuts;
2611         /*int gridSideVerts;*/
2612         int gridSideEdges;
2613         int numTex, numCol;
2614         int gridInternalEdges;
2615         float *w = NULL;
2616         WeightTable wtable = {0};
2617         MCol *mcol;
2618         MEdge *medge = NULL;
2619         /* MFace *mface = NULL; */
2620         MPoly *mpoly = NULL;
2621
2622         DM_from_template(&ccgdm->dm, dm, DM_TYPE_CCGDM,
2623                                          ccgSubSurf_getNumFinalVerts(ss),
2624                                          ccgSubSurf_getNumFinalEdges(ss),
2625                                          ccgSubSurf_getNumFinalFaces(ss),
2626                                          ccgSubSurf_getNumFinalFaces(ss)*4, 
2627                                          ccgSubSurf_getNumFinalFaces(ss));
2628         
2629         numTex = CustomData_number_of_layers(&ccgdm->dm.loopData, CD_MLOOPUV);
2630         numCol = CustomData_number_of_layers(&ccgdm->dm.loopData, CD_MLOOPCOL);
2631         
2632         if (numTex && CustomData_number_of_layers(&ccgdm->dm.faceData, CD_MTFACE) != numTex)
2633                 CustomData_from_bmeshpoly(&ccgdm->dm.faceData, &ccgdm->dm.polyData, &ccgdm->dm.loopData, ccgSubSurf_getNumFinalFaces(ss));
2634         else if (numCol && CustomData_number_of_layers(&ccgdm->dm.faceData, CD_MCOL) != numCol)
2635                 CustomData_from_bmeshpoly(&ccgdm->dm.faceData, &ccgdm->dm.polyData, &ccgdm->dm.loopData, ccgSubSurf_getNumFinalFaces(ss));
2636
2637         ccgdm->dm.getMinMax = cgdm_getMinMax;
2638         ccgdm->dm.getNumVerts = cgdm_getNumVerts;
2639         ccgdm->dm.getNumEdges = cgdm_getNumEdges;
2640         ccgdm->dm.getNumTessFaces = cgdm_getNumTessFaces;
2641         ccgdm->dm.getNumFaces = cgdm_getNumTessFaces;
2642
2643         ccgdm->dm.getNumGrids = ccgDM_getNumGrids;
2644         ccgdm->dm.getPBVH = ccgDM_getPBVH;
2645
2646         ccgdm->dm.getVert = ccgDM_getFinalVert;
2647         ccgdm->dm.getEdge = ccgDM_getFinalEdge;
2648         ccgdm->dm.getTessFace = ccgDM_getFinalFace;
2649         ccgdm->dm.getVertCo = ccgDM_getFinalVertCo;
2650         ccgdm->dm.getVertNo = ccgDM_getFinalVertNo;
2651         ccgdm->dm.copyVertArray = ccgDM_copyFinalVertArray;
2652         ccgdm->dm.copyEdgeArray = ccgDM_copyFinalEdgeArray;
2653         ccgdm->dm.copyTessFaceArray = ccgDM_copyFinalFaceArray;
2654         ccgdm->dm.copyLoopArray = ccgDM_copyFinalLoopArray;
2655         ccgdm->dm.copyPolyArray = ccgDM_copyFinalPolyArray;
2656         ccgdm->dm.getVertData = DM_get_vert_data;
2657         ccgdm->dm.getEdgeData = DM_get_edge_data;
2658         ccgdm->dm.getTessFaceData = DM_get_face_data;
2659         ccgdm->dm.getVertDataArray = ccgDM_get_vert_data_layer;
2660         ccgdm->dm.getEdgeDataArray = ccgDM_get_edge_data_layer;
2661         ccgdm->dm.getTessFaceDataArray = ccgDM_get_face_data_layer;
2662         ccgdm->dm.getNumGrids = ccgDM_getNumGrids;
2663         ccgdm->dm.getGridSize = ccgDM_getGridSize;
2664         ccgdm->dm.getGridData = ccgDM_getGridData;
2665         ccgdm->dm.getGridAdjacency = ccgDM_getGridAdjacency;
2666         ccgdm->dm.getGridOffset = ccgDM_getGridOffset;
2667         ccgdm->dm.getFaceMap = ccgDM_getFaceMap;
2668         ccgdm->dm.getPBVH = ccgDM_getPBVH;
2669
2670         ccgdm->dm.getTessFace = ccgDM_getFinalFace;
2671         ccgdm->dm.copyVertArray = ccgDM_copyFinalVertArray;
2672         ccgdm->dm.copyEdgeArray = ccgDM_copyFinalEdgeArray;
2673         ccgdm->dm.copyTessFaceArray = ccgDM_copyFinalFaceArray;
2674         ccgdm->dm.getVertData = DM_get_vert_data;
2675         ccgdm->dm.getEdgeData = DM_get_edge_data;
2676         ccgdm->dm.getTessFaceData = DM_get_face_data;
2677         ccgdm->dm.getVertDataArray = DM_get_vert_data_layer;
2678         ccgdm->dm.getEdgeDataArray = DM_get_edge_data_layer;
2679         ccgdm->dm.getTessFaceDataArray = DM_get_tessface_data_layer;
2680
2681         ccgdm->dm.getVertCos = cgdm_getVertCos;
2682         ccgdm->dm.foreachMappedVert = cgdm_foreachMappedVert;
2683         ccgdm->dm.foreachMappedEdge = cgdm_foreachMappedEdge;
2684         ccgdm->dm.foreachMappedFaceCenter = cgdm_foreachMappedFaceCenter;
2685         
2686         ccgdm->dm.drawVerts = ccgDM_drawVerts;
2687         ccgdm->dm.drawEdges = ccgDM_drawEdges;
2688         ccgdm->dm.drawLooseEdges = ccgDM_drawLooseEdges;
2689         ccgdm->dm.drawFacesSolid = ccgDM_drawFacesSolid;
2690         ccgdm->dm.drawFacesColored = cgdm_drawFacesColored;
2691         ccgdm->dm.drawFacesTex = cgdm_drawFacesTex;
2692         ccgdm->dm.drawFacesGLSL = cgdm_drawFacesGLSL;
2693         ccgdm->dm.drawMappedFaces = ccgDM_drawMappedFaces;
2694         ccgdm->dm.drawMappedFacesTex = cgdm_drawMappedFacesTex;
2695         ccgdm->dm.drawMappedFacesGLSL = cgdm_drawMappedFacesGLSL;
2696         ccgdm->dm.drawUVEdges = cgdm_drawUVEdges;
2697
2698         ccgdm->dm.drawMappedEdgesInterp = cgdm_drawMappedEdgesInterp;
2699         ccgdm->dm.drawMappedEdges = cgdm_drawMappedEdges;
2700         
2701         ccgdm->dm.release = cgdm_release;
2702         
2703         ccgdm->ss = ss;
2704         ccgdm->drawInteriorEdges = drawInteriorEdges;
2705         ccgdm->useSubsurfUv = useSubsurfUv;
2706
2707         totvert = ccgSubSurf_getNumVerts(ss);
2708         ccgdm->vertMap = MEM_callocN(totvert * sizeof(*ccgdm->vertMap), "vertMap");
2709         vi = ccgSubSurf_getVertIterator(ss);
2710         for(; !ccgVertIterator_isStopped(vi); ccgVertIterator_next(vi)) {
2711                 CCGVert *v = ccgVertIterator_getCurrent(vi);
2712
2713                 ccgdm->vertMap[GET_INT_FROM_POINTER(ccgSubSurf_getVertVertHandle(v))].vert = v;
2714         }
2715         ccgVertIterator_free(vi);
2716
2717         totedge = ccgSubSurf_getNumEdges(ss);
2718         ccgdm->edgeMap = MEM_callocN(totedge * sizeof(*ccgdm->edgeMap), "edgeMap");
2719         ei = ccgSubSurf_getEdgeIterator(ss);
2720         for(; !ccgEdgeIterator_isStopped(ei); ccgEdgeIterator_next(ei)) {
2721                 CCGEdge *e = ccgEdgeIterator_getCurrent(ei);
2722
2723                 ccgdm->edgeMap[GET_INT_FROM_POINTER(ccgSubSurf_getEdgeEdgeHandle(e))].edge = e;
2724         }
2725
2726         totface = ccgSubSurf_getNumFaces(ss);
2727         ccgdm->faceMap = MEM_callocN(totface * sizeof(*ccgdm->faceMap), "faceMap");
2728         fi = ccgSubSurf_getFaceIterator(ss);
2729         for(; !ccgFaceIterator_isStopped(fi); ccgFaceIterator_next(fi)) {
2730                 CCGFace *f = ccgFaceIterator_getCurrent(fi);
2731
2732                 ccgdm->faceMap[GET_INT_FROM_POINTER(ccgSubSurf_getFaceFaceHandle(ss, f))].face = f;
2733         }
2734         ccgFaceIterator_free(fi);
2735
2736         ccgdm->reverseFaceMap = MEM_callocN(sizeof(int)*ccgSubSurf_getNumFinalFaces(ss), "reverseFaceMap");
2737
2738         edgeSize = ccgSubSurf_getEdgeSize(ss);
2739         gridSize = ccgSubSurf_getGridSize(ss);
2740         gridFaces = gridSize - 1;
2741         gridCuts = gridSize - 2;
2742         /*gridInternalVerts = gridSideVerts * gridSideVerts; - as yet, unused */
2743         gridSideEdges = gridSize - 1;
2744         gridInternalEdges = (gridSideEdges - 1) * gridSideEdges * 2; 
2745
2746         vertNum = 0;
2747         edgeNum = 0;
2748         faceNum = 0;
2749
2750         /* mvert = dm->getVertArray(dm); */ /* UNUSED */
2751         medge = dm->getEdgeArray(dm);
2752         /* mface = dm->getTessFaceArray(dm); */ /* UNUSED */
2753
2754         mpoly = CustomData_get_layer(&dm->polyData, CD_MPOLY);
2755         base_polyOrigIndex = CustomData_get_layer(&dm->polyData, CD_ORIGINDEX);
2756         
2757         /*CDDM hack*/
2758         edgeFlags = ccgdm->edgeFlags = MEM_callocN(sizeof(short)*totedge, "faceFlags");
2759         faceFlags = ccgdm->faceFlags = MEM_callocN(sizeof(char)*2*totface, "faceFlags");
2760
2761         vertOrigIndex = DM_get_vert_data_layer(&ccgdm->dm, CD_ORIGINDEX);
2762         /*edgeOrigIndex = DM_get_edge_data_layer(&cgdm->dm, CD_ORIGINDEX);*/
2763         faceOrigIndex = DM_get_tessface_data_layer(&ccgdm->dm, CD_ORIGINDEX);
2764
2765         polyOrigIndex = DM_get_face_data_layer(&ccgdm->dm, CD_ORIGINDEX);
2766
2767         if (!CustomData_has_layer(&ccgdm->dm.faceData, CD_MCOL))
2768                 DM_add_tessface_layer(&ccgdm->dm, CD_MCOL, CD_CALLOC, NULL);
2769
2770         mcol = DM_get_tessface_data_layer(&ccgdm->dm, CD_MCOL);
2771         has_edge_origindex = CustomData_has_layer(&ccgdm->dm.edgeData, CD_ORIGINDEX);
2772
2773         faceNum = 0;
2774         loopindex = loopindex2 = 0; //current loop index
2775         for (index = 0; index < totface; index++) {
2776                 CCGFace *f = ccgdm->faceMap[index].face;
2777                 int numVerts = ccgSubSurf_getFaceNumVerts(f);
2778                 int numFinalEdges = numVerts * (gridSideEdges + gridInternalEdges);
2779                 int origIndex = GET_INT_FROM_POINTER(ccgSubSurf_getFaceFaceHandle(ss, f));
2780                 int g2_wid = gridCuts+2;
2781                 float *w2;
2782                 int s, x, y;
2783                 
2784                 origIndex = base_polyOrigIndex ? base_polyOrigIndex[origIndex] : origIndex;
2785                 
2786                 w = get_ss_weights(&wtable, gridCuts, numVerts);
2787
2788                 ccgdm->faceMap[index].startVert = vertNum;
2789                 ccgdm->faceMap[index].startEdge = edgeNum;
2790                 ccgdm->faceMap[index].startFace = faceNum;
2791                 
2792                 faceFlags[0] = mpoly ?  mpoly[origIndex].flag : 0;
2793                 faceFlags[1] = mpoly ? mpoly[origIndex].mat_nr : 0;
2794                 faceFlags += 2;
2795
2796                 /* set the face base vert */
2797                 *((int*)ccgSubSurf_getFaceUserData(ss, f)) = vertNum;
2798
2799                 BLI_array_empty(loopidx);               
2800                 for (s=0; s<numVerts; s++) {
2801                         BLI_array_growone(loopidx);
2802                         loopidx[s] = loopindex++;
2803                 }
2804                 
2805                 BLI_array_empty(vertidx);
2806                                 for(s = 0; s < numVerts; s++) {
2807                         CCGVert *v = ccgSubSurf_getFaceVert(ss, f, s);
2808                         
2809                         BLI_array_growone(vertidx);
2810                         vertidx[s] = GET_INT_FROM_POINTER(ccgSubSurf_getVertVertHandle(v));
2811                 }
2812                 
2813
2814                 /*I think this is for interpolating the center vert?*/
2815                 w2 = w; // + numVerts*(g2_wid-1)*(g2_wid-1); //numVerts*((g2_wid-1)*g2_wid+g2_wid-1);
2816                 DM_interp_vert_data(dm, &ccgdm->dm, vertidx, w2,
2817                                     numVerts, vertNum);
2818                 if (vertOrigIndex) {
2819                         *vertOrigIndex = ORIGINDEX_NONE;
2820                         ++vertOrigIndex;
2821                 }
2822
2823                 ++vertNum;
2824
2825                 /*interpolate per-vert data*/
2826                 for(s = 0; s < numVerts; s++) {
2827                         for(x = 1; x < gridFaces; x++) {
2828                                 w2 = w + s*numVerts*g2_wid*g2_wid + x*numVerts;
2829                                 DM_interp_vert_data(dm, &ccgdm->dm, vertidx, w2,
2830                                                     numVerts, vertNum);
2831
2832                                 if (vertOrigIndex) {
2833                                         *vertOrigIndex = ORIGINDEX_NONE;
2834                                         ++vertOrigIndex;
2835                                 }
2836
2837                                 ++vertNum;
2838                         }
2839                 }
2840
2841                 /*interpolate per-vert data*/
2842                 for(s = 0; s < numVerts; s++) {
2843                         for(y = 1; y < gridFaces; y++) {
2844                                 for(x = 1; x < gridFaces; x++) {
2845                                         w2 = w + s*numVerts*g2_wid*g2_wid + (y*g2_wid+x)*numVerts;
2846                                         DM_interp_vert_data(dm, &ccgdm->dm, vertidx, w2,
2847                                                             numVerts, vertNum);
2848
2849                                         if (vertOrigIndex) {
2850                                                 *vertOrigIndex = ORIGINDEX_NONE;
2851                                                 ++vertOrigIndex;
2852                                         }
2853
2854                                         ++vertNum;
2855                                 }
2856                         }
2857                 }
2858
2859                 if (has_edge_origindex) {
2860                         for(i = 0; i < numFinalEdges; ++i)
2861                                 *(int *)DM_get_edge_data(&ccgdm->dm, edgeNum + i,
2862                                                          CD_ORIGINDEX) = ORIGINDEX_NONE;
2863                 }
2864
2865                 for (s=0; s<numVerts; s++) {
2866                         /*interpolate per-face data*/
2867                         for (y=0; y<gridFaces; y++) {
2868                                 for (x=0; x<gridFaces; x++) {
2869                                         w2 = w + s*numVerts*g2_wid*g2_wid + (y*g2_wid+x)*numVerts;
2870                                         CustomData_interp(&dm->loopData, &ccgdm->dm.loopData,
2871                                                           loopidx, w2, NULL, numVerts, loopindex2);
2872                                         loopindex2++;
2873
2874                                         w2 = w + s*numVerts*g2_wid*g2_wid + ((y+1)*g2_wid+(x))*numVerts;
2875                                         CustomData_interp(&dm->loopData, &ccgdm->dm.loopData,
2876                                                           loopidx, w2, NULL, numVerts, loopindex2);
2877                                         loopindex2++;
2878
2879                                         w2 = w + s*numVerts*g2_wid*g2_wid + ((y+1)*g2_wid+(x+1))*numVerts;
2880                                         CustomData_interp(&dm->loopData, &ccgdm->dm.loopData,
2881