diff options
-rw-r--r-- | source/blender/blenkernel/intern/CCGSubSurf.c | 344 | ||||
-rw-r--r-- | source/blender/blenkernel/intern/CCGSubSurf.h | 3 | ||||
-rw-r--r-- | source/blender/blenkernel/intern/subsurf_ccg.c | 50 |
3 files changed, 380 insertions, 17 deletions
diff --git a/source/blender/blenkernel/intern/CCGSubSurf.c b/source/blender/blenkernel/intern/CCGSubSurf.c index 8c2d0f6e80d..906e390d8fd 100644 --- a/source/blender/blenkernel/intern/CCGSubSurf.c +++ b/source/blender/blenkernel/intern/CCGSubSurf.c @@ -4,9 +4,12 @@ #include <stdlib.h> #include <string.h> +#include <math.h> #include "CCGSubSurf.h" +#define USE_CREASING + /***/ typedef unsigned char byte; @@ -462,6 +465,15 @@ static void _edge_unlinkMarkAndFree(CCGEdge *e, CCGSubSurf *ss) { _edge_free(e, ss); } +#ifdef USE_CREASING +float EDGE_getSharpness(CCGEdge *e, int lvl, CCGSubSurf *ss) { + float f,sharpness = f=(((float*) ccgSubSurf_getEdgeUserData(ss, e))[1]); + while ((sharpness>1.0) && lvl--) + sharpness -= 1.0; + return sharpness; +} +#endif + /***/ static CCGFace *_face_new(CCGFaceHDL fHDL, CCGVert **verts, CCGEdge **edges, int numVerts, int levels, int dataSize, CCGSubSurf *ss) { @@ -1098,17 +1110,45 @@ static void ccgSubSurf__sync(CCGSubSurf *ss) { for (ptrIdx=0; ptrIdx<numEffectedF; ptrIdx++) { CCGFace *f = effectedF[ptrIdx]; void *co = FACE_getCenterData(f); - f->flags = 0; ss->meshIFC.vertDataZero(ss->meshData, co); for (i=0; i<f->numVerts; i++) { ss->meshIFC.vertDataAdd(ss->meshData, co, VERT_getCo(FACE_getVerts(f)[i], curLvl)); } ss->meshIFC.vertDataMulN(ss->meshData, co, 1.0f/f->numVerts); + + f->flags = 0; } for (ptrIdx=0; ptrIdx<numEffectedE; ptrIdx++) { CCGEdge *e = effectedE[ptrIdx]; void *co = EDGE_getCo(e, nextLvl, 1); - e->flags = 0; +#ifdef USE_CREASING + float sharpness = EDGE_getSharpness(e, curLvl, ss); + + if (_edge_isBoundary(e) || sharpness>=1.0) { + ss->meshIFC.vertDataCopy(ss->meshData, co, VERT_getCo(e->v0, curLvl)); + ss->meshIFC.vertDataAdd(ss->meshData, co, VERT_getCo(e->v1, curLvl)); + ss->meshIFC.vertDataMulN(ss->meshData, co, 0.5f); + } else { + int numFaces = 0; + ss->meshIFC.vertDataCopy(ss->meshData, q, VERT_getCo(e->v0, curLvl)); + ss->meshIFC.vertDataAdd(ss->meshData, q, VERT_getCo(e->v1, curLvl)); + for (i=0; i<e->numFaces; i++) { + CCGFace *f = e->faces[i]; + ss->meshIFC.vertDataAdd(ss->meshData, q, FACE_getCenterData(f)); + numFaces++; + } + ss->meshIFC.vertDataMulN(ss->meshData, q, 1.0f/(2.0f+numFaces)); + + ss->meshIFC.vertDataCopy(ss->meshData, r, VERT_getCo(e->v0, curLvl)); + ss->meshIFC.vertDataAdd(ss->meshData, r, VERT_getCo(e->v1, curLvl)); + ss->meshIFC.vertDataMulN(ss->meshData, r, 0.5f); + + ss->meshIFC.vertDataCopy(ss->meshData, co, q); + ss->meshIFC.vertDataSub(ss->meshData, r, q); + ss->meshIFC.vertDataMulN(ss->meshData, r, sharpness); + ss->meshIFC.vertDataAdd(ss->meshData, co, r); + } +#else if (_edge_isBoundary(e)) { ss->meshIFC.vertDataCopy(ss->meshData, co, VERT_getCo(e->v0, curLvl)); ss->meshIFC.vertDataAdd(ss->meshData, co, VERT_getCo(e->v1, curLvl)); @@ -1124,13 +1164,95 @@ static void ccgSubSurf__sync(CCGSubSurf *ss) { } ss->meshIFC.vertDataMulN(ss->meshData, co, 1.0f/(2.0f+numFaces)); } +#endif + + e->flags = 0; } for (ptrIdx=0; ptrIdx<numEffectedV; ptrIdx++) { CCGVert *v = effectedV[ptrIdx]; void *co = VERT_getCo(v, curLvl); void *nCo = VERT_getCo(v, nextLvl); - v->flags = 0; +#ifdef USE_CREASING + int sharpCount = 0; + float avgSharpness = 0.0; + CCGVert *sharpV0 = NULL, *sharpV1 = NULL; + + for (i=0; i<v->numEdges; i++) { + CCGEdge *e = v->edges[i]; + float sharpness = EDGE_getSharpness(e, curLvl, ss); + + if (sharpness!=0.0f) { + sharpCount++; + avgSharpness += sharpness; + + if (!sharpV0) { + sharpV0 = _edge_getOtherVert(e, v); + } else if (!sharpV1) { + sharpV1 = _edge_getOtherVert(e, v); + } + } + } + + avgSharpness /= sharpCount; + if (avgSharpness>1.0) { + avgSharpness = 1.0; + } + + if (!v->numEdges || sharpCount>2) { + ss->meshIFC.vertDataCopy(ss->meshData, nCo, co); + } else if (_vert_isBoundary(v) && sharpCount<2) { + int numBoundary = 0; + + ss->meshIFC.vertDataZero(ss->meshData, r); + for (i=0; i<v->numEdges; i++) { + CCGEdge *e = v->edges[i]; + if (_edge_isBoundary(e)) { + ss->meshIFC.vertDataAdd(ss->meshData, r, VERT_getCo(_edge_getOtherVert(e, v), curLvl)); + numBoundary++; + } + } + ss->meshIFC.vertDataCopy(ss->meshData, nCo, co); + ss->meshIFC.vertDataMulN(ss->meshData, nCo, 0.75); + ss->meshIFC.vertDataMulN(ss->meshData, r, 0.25f/numBoundary); + ss->meshIFC.vertDataAdd(ss->meshData, nCo, r); + } else { + int numEdges = 0, numFaces = 0; + + ss->meshIFC.vertDataZero(ss->meshData, q); + for (i=0; i<v->numFaces; i++) { + CCGFace *f = v->faces[i]; + ss->meshIFC.vertDataAdd(ss->meshData, q, FACE_getCenterData(f)); + numFaces++; + } + ss->meshIFC.vertDataMulN(ss->meshData, q, 1.0f/numFaces); + ss->meshIFC.vertDataZero(ss->meshData, r); + for (i=0; i<v->numEdges; i++) { + CCGEdge *e = v->edges[i]; + ss->meshIFC.vertDataAdd(ss->meshData, r, VERT_getCo(_edge_getOtherVert(e, v), curLvl)); + numEdges++; + } + ss->meshIFC.vertDataMulN(ss->meshData, r, 1.0f/numEdges); + + ss->meshIFC.vertDataCopy(ss->meshData, nCo, co); + ss->meshIFC.vertDataMulN(ss->meshData, nCo, numEdges-2.0f); + ss->meshIFC.vertDataAdd(ss->meshData, nCo, q); + ss->meshIFC.vertDataAdd(ss->meshData, nCo, r); + ss->meshIFC.vertDataMulN(ss->meshData, nCo, 1.0f/numEdges); + + if (sharpCount==2) { + ss->meshIFC.vertDataCopy(ss->meshData, q, co); + ss->meshIFC.vertDataMulN(ss->meshData, q, 6.0f); + ss->meshIFC.vertDataAdd(ss->meshData, q, VERT_getCo(sharpV0, curLvl)); + ss->meshIFC.vertDataAdd(ss->meshData, q, VERT_getCo(sharpV1, curLvl)); + ss->meshIFC.vertDataMulN(ss->meshData, q, 1/8.0f); + + ss->meshIFC.vertDataSub(ss->meshData, q, nCo); + ss->meshIFC.vertDataMulN(ss->meshData, q, avgSharpness); + ss->meshIFC.vertDataAdd(ss->meshData, nCo, q); + } + } +#else if (!v->numEdges) { ss->meshIFC.vertDataCopy(ss->meshData, nCo, co); } else if (_vert_isBoundary(v)) { @@ -1172,6 +1294,9 @@ static void ccgSubSurf__sync(CCGSubSurf *ss) { ss->meshIFC.vertDataAdd(ss->meshData, nCo, r); ss->meshIFC.vertDataMulN(ss->meshData, nCo, 1.0f/numEdges); } +#endif + + v->flags = 0; } if (ss->useAgeCounts) { @@ -1302,6 +1427,50 @@ static void ccgSubSurf__sync(CCGSubSurf *ss) { for (ptrIdx=0; ptrIdx<numEffectedE; ptrIdx++) { CCGEdge *e = (CCGEdge*) effectedE[ptrIdx]; +#ifdef USE_CREASING + float sharpness = EDGE_getSharpness(e, curLvl, ss); + + if (_edge_isBoundary(e) || sharpness>1.0) { + for (x=0; x<edgeSize-1; x++) { + int fx = x*2 + 1; + void *co0 = EDGE_getCo(e, curLvl, x+0); + void *co1 = EDGE_getCo(e, curLvl, x+1); + void *co = EDGE_getCo(e, nextLvl, fx); + + ss->meshIFC.vertDataCopy(ss->meshData, co, co0); + ss->meshIFC.vertDataAdd(ss->meshData, co, co1); + ss->meshIFC.vertDataMulN(ss->meshData, co, 0.5); + } + } else { + for (x=0; x<edgeSize-1; x++) { + int fx = x*2 + 1; + void *co0 = EDGE_getCo(e, curLvl, x+0); + void *co1 = EDGE_getCo(e, curLvl, x+1); + void *co = EDGE_getCo(e, nextLvl, fx); + int numFaces = 0; + + ss->meshIFC.vertDataCopy(ss->meshData, q, co0); + ss->meshIFC.vertDataAdd(ss->meshData, q, co1); + + for (i=0; i<e->numFaces; i++) { + CCGFace *f = e->faces[i]; + ss->meshIFC.vertDataAdd(ss->meshData, q, _face_getIFCoEdge(f, e, nextLvl, fx, 1, subdivLevels, vertDataSize)); + numFaces++; + } + + ss->meshIFC.vertDataMulN(ss->meshData, q, 1.0f/(2.0f+numFaces)); + + ss->meshIFC.vertDataCopy(ss->meshData, r, co0); + ss->meshIFC.vertDataAdd(ss->meshData, r, co1); + ss->meshIFC.vertDataMulN(ss->meshData, r, 0.5); + + ss->meshIFC.vertDataCopy(ss->meshData, co, q); + ss->meshIFC.vertDataSub(ss->meshData, r, q); + ss->meshIFC.vertDataMulN(ss->meshData, r, sharpness); + ss->meshIFC.vertDataAdd(ss->meshData, co, r); + } + } +#else if (_edge_isBoundary(e)) { for (x=0; x<edgeSize-1; x++) { int fx = x*2 + 1; @@ -1333,6 +1502,7 @@ static void ccgSubSurf__sync(CCGSubSurf *ss) { ss->meshIFC.vertDataMulN(ss->meshData, co, 1.0f/(2.0f+numFaces)); } } +#endif } /* exterior vertex shift @@ -1345,6 +1515,88 @@ static void ccgSubSurf__sync(CCGSubSurf *ss) { void *co = VERT_getCo(v, curLvl); void *nCo = VERT_getCo(v, nextLvl); +#ifdef USE_CREASING + int sharpCount = 0; + float avgSharpness = 0.0; + CCGEdge *sharpE0 = NULL, *sharpE1 = NULL; + + for (i=0; i<v->numEdges; i++) { + CCGEdge *e = v->edges[i]; + float sharpness = EDGE_getSharpness(e, curLvl, ss); + + if (sharpness!=0.0f) { + sharpCount++; + avgSharpness += sharpness; + + if (!sharpE0) { + sharpE0 = e; + } else if (!sharpE1) { + sharpE1 = e; + } + } + } + + avgSharpness /= sharpCount; + if (avgSharpness>1.0) { + avgSharpness = 1.0; + } + + if (!v->numEdges || sharpCount>2) { + ss->meshIFC.vertDataCopy(ss->meshData, nCo, co); + } else if (_vert_isBoundary(v) && sharpCount<2) { + int numBoundary = 0; + + ss->meshIFC.vertDataZero(ss->meshData, r); + for (i=0; i<v->numEdges; i++) { + CCGEdge *e = v->edges[i]; + if (_edge_isBoundary(e)) { + ss->meshIFC.vertDataAdd(ss->meshData, r, _edge_getCoVert(e, v, curLvl, 1, vertDataSize)); + numBoundary++; + } + } + + ss->meshIFC.vertDataCopy(ss->meshData, nCo, co); + ss->meshIFC.vertDataMulN(ss->meshData, nCo, 0.75); + ss->meshIFC.vertDataMulN(ss->meshData, r, 0.25f/numBoundary); + ss->meshIFC.vertDataAdd(ss->meshData, nCo, r); + } else { + int cornerIdx = (1 + (1<<(curLvl))) - 2; + int numEdges = 0, numFaces = 0; + + ss->meshIFC.vertDataZero(ss->meshData, q); + for (i=0; i<v->numFaces; i++) { + CCGFace *f = v->faces[i]; + ss->meshIFC.vertDataAdd(ss->meshData, q, FACE_getIFCo(f, nextLvl, _face_getVertIndex(f,v), cornerIdx, cornerIdx)); + numFaces++; + } + ss->meshIFC.vertDataMulN(ss->meshData, q, 1.0f/numFaces); + ss->meshIFC.vertDataZero(ss->meshData, r); + for (i=0; i<v->numEdges; i++) { + CCGEdge *e = v->edges[i]; + ss->meshIFC.vertDataAdd(ss->meshData, r, _edge_getCoVert(e, v, curLvl, 1,vertDataSize)); + numEdges++; + } + ss->meshIFC.vertDataMulN(ss->meshData, r, 1.0f/numEdges); + + ss->meshIFC.vertDataCopy(ss->meshData, nCo, co); + ss->meshIFC.vertDataMulN(ss->meshData, nCo, numEdges-2.0f); + ss->meshIFC.vertDataAdd(ss->meshData, nCo, q); + ss->meshIFC.vertDataAdd(ss->meshData, nCo, r); + ss->meshIFC.vertDataMulN(ss->meshData, nCo, 1.0f/numEdges); + + if (sharpCount==2) { + ss->meshIFC.vertDataCopy(ss->meshData, q, co); + ss->meshIFC.vertDataMulN(ss->meshData, q, 6.0f); + ss->meshIFC.vertDataAdd(ss->meshData, q, _edge_getCoVert(sharpE0, v, curLvl, 1, vertDataSize)); + ss->meshIFC.vertDataAdd(ss->meshData, q, _edge_getCoVert(sharpE1, v, curLvl, 1, vertDataSize)); + ss->meshIFC.vertDataMulN(ss->meshData, q, 1/8.0f); + + ss->meshIFC.vertDataSub(ss->meshData, q, nCo); + ss->meshIFC.vertDataMulN(ss->meshData, q, avgSharpness); + ss->meshIFC.vertDataAdd(ss->meshData, nCo, q); + } + } +#else if (!v->numEdges) { ss->meshIFC.vertDataCopy(ss->meshData, nCo, co); } else if (_vert_isBoundary(v)) { @@ -1388,6 +1640,7 @@ static void ccgSubSurf__sync(CCGSubSurf *ss) { ss->meshIFC.vertDataAdd(ss->meshData, nCo, r); ss->meshIFC.vertDataMulN(ss->meshData, nCo, 1.0f/numEdges); } +#endif } /* exterior edge interior shift @@ -1398,6 +1651,80 @@ static void ccgSubSurf__sync(CCGSubSurf *ss) { for (ptrIdx=0; ptrIdx<numEffectedE; ptrIdx++) { CCGEdge *e = (CCGEdge*) effectedE[ptrIdx]; +#ifdef USE_CREASING + float sharpness = EDGE_getSharpness(e, curLvl, ss); + int sharpCount = 0; + float avgSharpness = 0.0; + CCGVert *sharpV0 = NULL, *sharpV1 = NULL; + + if (sharpness!=0.0f) { + sharpCount = 2; + avgSharpness += 2*sharpness; + } else { + sharpCount = 0; + avgSharpness = 0; + } + + avgSharpness /= sharpCount; + if (avgSharpness>1.0) { + avgSharpness = 1.0; + } + + if (_edge_isBoundary(e) && sharpCount<2) { + for (x=1; x<edgeSize-1; x++) { + int fx = x*2; + void *co = EDGE_getCo(e, curLvl, x); + void *nCo = EDGE_getCo(e, nextLvl, fx); + ss->meshIFC.vertDataCopy(ss->meshData, r, EDGE_getCo(e, curLvl, x-1)); + ss->meshIFC.vertDataAdd(ss->meshData, r, EDGE_getCo(e, curLvl, x+1)); + ss->meshIFC.vertDataMulN(ss->meshData, r, 0.5); + ss->meshIFC.vertDataCopy(ss->meshData, nCo, co); + ss->meshIFC.vertDataMulN(ss->meshData, nCo, 0.75); + ss->meshIFC.vertDataMulN(ss->meshData, r, 0.25); + ss->meshIFC.vertDataAdd(ss->meshData, nCo, r); + } + } else { + for (x=1; x<edgeSize-1; x++) { + int fx = x*2; + void *co = EDGE_getCo(e, curLvl, x); + void *nCo = EDGE_getCo(e, nextLvl, fx); + int numFaces = 0; + + ss->meshIFC.vertDataZero(ss->meshData, q); + ss->meshIFC.vertDataZero(ss->meshData, r); + ss->meshIFC.vertDataAdd(ss->meshData, r, EDGE_getCo(e, curLvl, x-1)); + ss->meshIFC.vertDataAdd(ss->meshData, r, EDGE_getCo(e, curLvl, x+1)); + for (i=0; i<e->numFaces; i++) { + CCGFace *f = e->faces[i]; + ss->meshIFC.vertDataAdd(ss->meshData, q, _face_getIFCoEdge(f, e, nextLvl, fx-1, 1, subdivLevels, vertDataSize)); + ss->meshIFC.vertDataAdd(ss->meshData, q, _face_getIFCoEdge(f, e, nextLvl, fx+1, 1, subdivLevels, vertDataSize)); + + ss->meshIFC.vertDataAdd(ss->meshData, r, _face_getIFCoEdge(f, e, curLvl, x, 1, subdivLevels, vertDataSize)); + numFaces++; + } + ss->meshIFC.vertDataMulN(ss->meshData, q, 1.0/(numFaces*2.0f)); + ss->meshIFC.vertDataMulN(ss->meshData, r, 1.0/(2.0f + numFaces)); + + ss->meshIFC.vertDataCopy(ss->meshData, nCo, co); + ss->meshIFC.vertDataMulN(ss->meshData, nCo, (float) numFaces); + ss->meshIFC.vertDataAdd(ss->meshData, nCo, q); + ss->meshIFC.vertDataAdd(ss->meshData, nCo, r); + ss->meshIFC.vertDataMulN(ss->meshData, nCo, 1.0f/(2+numFaces)); + + if (sharpCount==2) { + ss->meshIFC.vertDataCopy(ss->meshData, q, co); + ss->meshIFC.vertDataMulN(ss->meshData, q, 6.0f); + ss->meshIFC.vertDataAdd(ss->meshData, q, EDGE_getCo(e, curLvl, x-1)); + ss->meshIFC.vertDataAdd(ss->meshData, q, EDGE_getCo(e, curLvl, x+1)); + ss->meshIFC.vertDataMulN(ss->meshData, q, 1/8.0f); + + ss->meshIFC.vertDataSub(ss->meshData, q, nCo); + ss->meshIFC.vertDataMulN(ss->meshData, q, avgSharpness); + ss->meshIFC.vertDataAdd(ss->meshData, nCo, q); + } + } + } +#else if (_edge_isBoundary(e)) { for (x=1; x<edgeSize-1; x++) { int fx = x*2; @@ -1440,6 +1767,7 @@ static void ccgSubSurf__sync(CCGSubSurf *ss) { ss->meshIFC.vertDataMulN(ss->meshData, nCo, 1.0f/(2+numFaces)); } } +#endif } for (ptrIdx=0; ptrIdx<numEffectedF; ptrIdx++) { @@ -1580,6 +1908,16 @@ int ccgSubSurf_getNumFaces(CCGSubSurf *ss) { return ss->fMap->numEntries; } +CCGVert *ccgSubSurf_getVert(CCGSubSurf *ss, CCGVertHDL v) { + return (CCGVert*) _ehash_lookup(ss->vMap, v); +} +CCGEdge *ccgSubSurf_getEdge(CCGSubSurf *ss, CCGEdgeHDL e) { + return (CCGEdge*) _ehash_lookup(ss->eMap, e); +} +CCGFace *ccgSubSurf_getFace(CCGSubSurf *ss, CCGFaceHDL f) { + return (CCGFace*) _ehash_lookup(ss->fMap, f); +} + int ccgSubSurf_getSubdivisionLevels(CCGSubSurf *ss) { return ss->subdivLevels; } diff --git a/source/blender/blenkernel/intern/CCGSubSurf.h b/source/blender/blenkernel/intern/CCGSubSurf.h index e1f00ea1048..f9d8da6bf36 100644 --- a/source/blender/blenkernel/intern/CCGSubSurf.h +++ b/source/blender/blenkernel/intern/CCGSubSurf.h @@ -97,6 +97,7 @@ int ccgSubSurf_getEdgeLevelSize (CCGSubSurf *ss, int level); int ccgSubSurf_getGridSize (CCGSubSurf *ss); int ccgSubSurf_getGridLevelSize (CCGSubSurf *ss, int level); +CCGVert* ccgSubSurf_getVert (CCGSubSurf *ss, CCGVertHDL v); CCGVertHDL ccgSubSurf_getVertVertHandle (CCGSubSurf *ss, CCGVert *v); int ccgSubSurf_getVertNumFaces (CCGSubSurf *ss, CCGVert *v); CCGFace* ccgSubSurf_getVertFace (CCGSubSurf *ss, CCGVert *v, int index); @@ -108,6 +109,7 @@ void* ccgSubSurf_getVertUserData (CCGSubSurf *ss, CCGVert *v); void* ccgSubSurf_getVertData (CCGSubSurf *ss, CCGVert *v); void* ccgSubSurf_getVertLevelData (CCGSubSurf *ss, CCGVert *v, int level); +CCGEdge* ccgSubSurf_getEdge (CCGSubSurf *ss, CCGEdgeHDL e); CCGEdgeHDL ccgSubSurf_getEdgeEdgeHandle (CCGSubSurf *ss, CCGEdge *e); int ccgSubSurf_getEdgeNumFaces (CCGSubSurf *ss, CCGEdge *e); CCGFace* ccgSubSurf_getEdgeFace (CCGSubSurf *ss, CCGEdge *e, int index); @@ -120,6 +122,7 @@ void* ccgSubSurf_getEdgeDataArray (CCGSubSurf *ss, CCGEdge *e); void* ccgSubSurf_getEdgeData (CCGSubSurf *ss, CCGEdge *e, int x); void* ccgSubSurf_getEdgeLevelData (CCGSubSurf *ss, CCGEdge *e, int x, int level); +CCGFace* ccgSubSurf_getFace (CCGSubSurf *ss, CCGFaceHDL f); CCGFaceHDL ccgSubSurf_getFaceFaceHandle (CCGSubSurf *ss, CCGFace *f); int ccgSubSurf_getFaceNumVerts (CCGSubSurf *ss, CCGFace *f); CCGVert* ccgSubSurf_getFaceVert (CCGSubSurf *ss, CCGFace *f, int index); diff --git a/source/blender/blenkernel/intern/subsurf_ccg.c b/source/blender/blenkernel/intern/subsurf_ccg.c index 1fe71c74791..8a4c0c2064e 100644 --- a/source/blender/blenkernel/intern/subsurf_ccg.c +++ b/source/blender/blenkernel/intern/subsurf_ccg.c @@ -24,6 +24,8 @@ #include "CCGSubSurf.h" +#define USE_CREASING + typedef struct _SubSurf { CCGSubSurf *subSurf; @@ -102,7 +104,7 @@ static CCGSubSurf *_getSubSurf(SubSurf *ss, int subdivLevels) { CCGAllocatorHDL allocator; ifc.vertUserSize = 4; - ifc.edgeUserSize = 4; + ifc.edgeUserSize = 8; ifc.faceUserSize = 4; ifc.vertDataSize= 12; ifc.vertDataZero= _subsurfNew_meshIFC_vertDataZero; @@ -525,6 +527,8 @@ static DispListMesh *subSurf_createDispListMesh(SubSurf *ssm, int doOptEdges) { } static void subSurf_sync(SubSurf *ss) { + float creaseFactor = (float) ccgSubSurf_getSubdivisionLevels(ss->subSurf); + ccgSubSurf_initFullSync(ss->subSurf); if (ss->controlType==SUBSURF_CONTROLTYPE_MESH) { @@ -543,6 +547,15 @@ static void subSurf_sync(SubSurf *ss) { MEdge *med = &ss->me->medge[i]; ccgSubSurf_syncEdge(ss->subSurf, (CCGEdgeHDL) i, (CCGVertHDL) med->v1, (CCGVertHDL) med->v2); + +#ifdef USE_CREASING + { + CCGEdge *e = ccgSubSurf_getEdge(ss->subSurf, (CCGEdgeHDL) i); + float *userData = ccgSubSurf_getEdgeUserData(ss->subSurf, e); + + userData[1] = med->crease*creaseFactor/255.0f; + } +#endif } } else { for (i=0; i<ss->me->totface; i++) { @@ -567,25 +580,34 @@ static void subSurf_sync(SubSurf *ss) { } } } else { - EditVert *v, *fVerts[4]; - EditEdge *e; - EditFace *f; + EditVert *ev, *fVerts[4]; + EditEdge *ee; + EditFace *ef; - for (v=ss->em->verts.first; v; v=v->next) { - ccgSubSurf_syncVert(ss->subSurf, v, v->co); + for (ev=ss->em->verts.first; ev; ev=ev->next) { + ccgSubSurf_syncVert(ss->subSurf, ev, ev->co); } - for (e=ss->em->edges.first; e; e=e->next) { - ccgSubSurf_syncEdge(ss->subSurf, e, e->v1, e->v2); + for (ee=ss->em->edges.first; ee; ee=ee->next) { + ccgSubSurf_syncEdge(ss->subSurf, ee, ee->v1, ee->v2); + +#ifdef USE_CREASING + { + CCGEdge *e = ccgSubSurf_getEdge(ss->subSurf, ee); + float *userData = ccgSubSurf_getEdgeUserData(ss->subSurf, e); + + userData[1] = ee->crease*creaseFactor; + } +#endif } - for (f=ss->em->faces.first; f; f=f->next) { - fVerts[0] = f->v1; - fVerts[1] = f->v2; - fVerts[2] = f->v3; - fVerts[3] = f->v4; + for (ef=ss->em->faces.first; ef; ef=ef->next) { + fVerts[0] = ef->v1; + fVerts[1] = ef->v2; + fVerts[2] = ef->v3; + fVerts[3] = ef->v4; - ccgSubSurf_syncFace(ss->subSurf, f, f->v4?4:3, fVerts); + ccgSubSurf_syncFace(ss->subSurf, ef, ef->v4?4:3, fVerts); } } |