diff options
author | Tor Andersson <tor@ghostscript.com> | 2010-07-10 22:46:39 +0200 |
---|---|---|
committer | Tor Andersson <tor@ghostscript.com> | 2010-07-10 22:46:39 +0200 |
commit | f387dd1ec51d53b9439ef91894e56a4a163384d7 (patch) | |
tree | 716e938e0f2cc0d13f9d027495f1a647681922bf | |
parent | 021329447f940512267171aa64c1288e45498c6e (diff) | |
download | mupdf-f387dd1ec51d53b9439ef91894e56a4a163384d7.tar.xz |
Clamp floats to representable numbers before converting to int. Clip lines against horizontal edges. Return empty bbox when the edge list is empty.
-rw-r--r-- | draw/pathscan.c | 82 |
1 files changed, 63 insertions, 19 deletions
diff --git a/draw/pathscan.c b/draw/pathscan.c index a667a33a..5833ed59 100644 --- a/draw/pathscan.c +++ b/draw/pathscan.c @@ -70,6 +70,8 @@ fz_bbox fz_boundgel(fz_gel *gel) { fz_bbox bbox; + if (gel->len == 0) + return fz_emptybbox; bbox.x0 = fz_idiv(gel->bbox.x0, HSCALE); bbox.y0 = fz_idiv(gel->bbox.y0, VSCALE); bbox.x1 = fz_idiv(gel->bbox.x1, HSCALE) + 1; @@ -106,31 +108,14 @@ cliplerpx(int val, int m, int x0, int y0, int x1, int y1, int *out) } } -void -fz_insertgel(fz_gel *gel, float fx0, float fy0, float fx1, float fy1) +static void +fz_insertgelraw(fz_gel *gel, int x0, int y0, int x1, int y1) { fz_edge *edge; int dx, dy; int winding; int width; int tmp; - int v; - int d; - - int x0 = floorf(fx0 * HSCALE); - int y0 = floorf(fy0 * VSCALE); - int x1 = floorf(fx1 * HSCALE); - int y1 = floorf(fy1 * VSCALE); - - d = cliplerpy(gel->clip.y0, 0, x0, y0, x1, y1, &v); - if (d == OUTSIDE) return; - if (d == LEAVE) { y1 = gel->clip.y0; x1 = v; } - if (d == ENTER) { y0 = gel->clip.y0; x0 = v; } - - d = cliplerpy(gel->clip.y1, 1, x0, y0, x1, y1, &v); - if (d == OUTSIDE) return; - if (d == LEAVE) { y1 = gel->clip.y1; x1 = v; } - if (d == ENTER) { y0 = gel->clip.y1; x0 = v; } if (y0 == y1) return; @@ -189,6 +174,65 @@ fz_insertgel(fz_gel *gel, float fx0, float fy0, float fx1, float fy1) } void +fz_insertgel(fz_gel *gel, float fx0, float fy0, float fx1, float fy1) +{ + int x0, y0, x1, y1; + int d, v; + + fx0 = floorf(fx0 * HSCALE); + fx1 = floorf(fx1 * HSCALE); + fy0 = floorf(fy0 * VSCALE); + fy1 = floorf(fy1 * VSCALE); + + x0 = CLAMP(fx0, BBOX_MIN, BBOX_MAX); + y0 = CLAMP(fy0, BBOX_MIN, BBOX_MAX); + x1 = CLAMP(fx1, BBOX_MIN, BBOX_MAX); + y1 = CLAMP(fy1, BBOX_MIN, BBOX_MAX); + + d = cliplerpy(gel->clip.y0, 0, x0, y0, x1, y1, &v); + if (d == OUTSIDE) return; + if (d == LEAVE) { y1 = gel->clip.y0; x1 = v; } + if (d == ENTER) { y0 = gel->clip.y0; x0 = v; } + + d = cliplerpy(gel->clip.y1, 1, x0, y0, x1, y1, &v); + if (d == OUTSIDE) return; + if (d == LEAVE) { y1 = gel->clip.y1; x1 = v; } + if (d == ENTER) { y0 = gel->clip.y1; x0 = v; } + + d = cliplerpx(gel->clip.x0, 0, x0, y0, x1, y1, &v); + if (d == OUTSIDE) { + x0 = x1 = gel->clip.x0; + } + if (d == LEAVE) { + fz_insertgelraw(gel, gel->clip.x0, v, gel->clip.x0, y1); + x1 = gel->clip.x0; + y1 = v; + } + if (d == ENTER) { + fz_insertgelraw(gel, gel->clip.x0, y0, gel->clip.x0, v); + x0 = gel->clip.x0; + y0 = v; + } + + d = cliplerpx(gel->clip.x1, 1, x0, y0, x1, y1, &v); + if (d == OUTSIDE) { + x0 = x1 = gel->clip.x1; + } + if (d == LEAVE) { + fz_insertgelraw(gel, gel->clip.x1, v, gel->clip.x1, y1); + x1 = gel->clip.x0; + y1 = v; + } + if (d == ENTER) { + fz_insertgelraw(gel, gel->clip.x1, y0, gel->clip.x1, v); + x0 = gel->clip.x1; + y0 = v; + } + + fz_insertgelraw(gel, x0, y0, x1, y1); +} + +void fz_sortgel(fz_gel *gel) { fz_edge *a = gel->edges; |