Browse Source

Do bevels only at control points

shared-context
Mikko Mononen 11 years ago
parent
commit
4a1e66a515
1 changed files with 17 additions and 11 deletions
  1. +17
    -11
      src/nanovg.c

+ 17
- 11
src/nanovg.c View File

@@ -46,6 +46,7 @@ enum NVGpointFlags
NVG_PT_BEVEL = 0x01,
NVG_PT_LEFT = 0x02,
NVG_PT_CUSP = 0x04,
NVG_PT_CORNER = 0x08,
};

enum NVGexpandFeatures {
@@ -833,7 +834,7 @@ static struct NVGpoint* nvg__lastPoint(struct NVGcontext* ctx)
return NULL;
}

static void nvg__addPoint(struct NVGcontext* ctx, float x, float y)
static void nvg__addPoint(struct NVGcontext* ctx, float x, float y, int flags)
{
struct NVGpath* path = nvg__lastPath(ctx);
struct NVGpoint* pt;
@@ -841,8 +842,10 @@ static void nvg__addPoint(struct NVGcontext* ctx, float x, float y)

if (ctx->cache->npoints > 0) {
pt = nvg__lastPoint(ctx);
if (nvg__ptEquals(pt->x,pt->y, x,y, ctx->distTol))
if (nvg__ptEquals(pt->x,pt->y, x,y, ctx->distTol)) {
pt->flags |= flags;
return;
}
}

if (ctx->cache->npoints+1 > ctx->cache->cpoints) {
@@ -855,6 +858,7 @@ static void nvg__addPoint(struct NVGcontext* ctx, float x, float y)
memset(pt, 0, sizeof(*pt));
pt->x = x;
pt->y = y;
pt->flags = flags;

ctx->cache->npoints++;
path->count++;
@@ -940,14 +944,14 @@ static void nvg__vset(struct NVGvertex* vtx, float x, float y, float u, float v)
static void nvg__tesselateBezier(struct NVGcontext* ctx,
float x1, float y1, float x2, float y2,
float x3, float y3, float x4, float y4,
int level)
int level, int type)
{
float x12,y12,x23,y23,x34,y34,x123,y123,x234,y234,x1234,y1234;
if (level > 10) return;

if (nvg__absf(x1+x3-x2-x2) + nvg__absf(y1+y3-y2-y2) + nvg__absf(x2+x4-x3-x3) + nvg__absf(y2+y4-y3-y3) < ctx->tessTol) {
nvg__addPoint(ctx, x4, y4);
nvg__addPoint(ctx, x4, y4, type);
return;
}

@@ -964,8 +968,8 @@ static void nvg__tesselateBezier(struct NVGcontext* ctx,
x1234 = (x123+x234)*0.5f;
y1234 = (y123+y234)*0.5f;

nvg__tesselateBezier(ctx, x1,y1, x12,y12, x123,y123, x1234,y1234, level+1);
nvg__tesselateBezier(ctx, x1234,y1234, x234,y234, x34,y34, x4,y4, level+1);
nvg__tesselateBezier(ctx, x1,y1, x12,y12, x123,y123, x1234,y1234, level+1, 0);
nvg__tesselateBezier(ctx, x1234,y1234, x234,y234, x34,y34, x4,y4, level+1, type);
}

static void nvg__flattenPaths(struct NVGcontext* ctx, int lineCap, int lineJoin, float miterLimit)
@@ -994,12 +998,12 @@ static void nvg__flattenPaths(struct NVGcontext* ctx, int lineCap, int lineJoin,
case NVG_MOVETO:
nvg__addPath(ctx);
p = &ctx->commands[i+1];
nvg__addPoint(ctx, p[0], p[1]);
nvg__addPoint(ctx, p[0], p[1], NVG_PT_CORNER);
i += 3;
break;
case NVG_LINETO:
p = &ctx->commands[i+1];
nvg__addPoint(ctx, p[0], p[1]);
nvg__addPoint(ctx, p[0], p[1], NVG_PT_CORNER);
i += 3;
break;
case NVG_BEZIERTO:
@@ -1008,7 +1012,7 @@ static void nvg__flattenPaths(struct NVGcontext* ctx, int lineCap, int lineJoin,
cp1 = &ctx->commands[i+1];
cp2 = &ctx->commands[i+3];
p = &ctx->commands[i+5];
nvg__tesselateBezier(ctx, last->x,last->y, cp1[0],cp1[1], cp2[0],cp2[1], p[0],p[1], 0);
nvg__tesselateBezier(ctx, last->x,last->y, cp1[0],cp1[1], cp2[0],cp2[1], p[0],p[1], 0, NVG_PT_CORNER);
}
i += 7;
break;
@@ -1107,8 +1111,10 @@ static void nvg__flattenPaths(struct NVGcontext* ctx, int lineCap, int lineJoin,
}

// Check to see if the corner needs to be beveled.
if ((dmr2 * miterLimit*miterLimit) < 1.0f || lineJoin == NVG_BEVEL || lineJoin == NVG_ROUND) {
p1->flags |= NVG_PT_BEVEL;
if (p1->flags & NVG_PT_CORNER) {
if ((dmr2 * miterLimit*miterLimit) < 1.0f || lineJoin == NVG_BEVEL || lineJoin == NVG_ROUND) {
p1->flags |= NVG_PT_BEVEL;
}
}

if ((p1->flags & (NVG_PT_BEVEL | NVG_PT_CUSP)) != 0)


Loading…
Cancel
Save