Mercurial > hgrepos > Python2 > PyMuPDF
diff mupdf-source/source/fitz/draw-rasterize.c @ 3:2c135c81b16c
MERGE: upstream PyMuPDF 1.26.4 with MuPDF 1.26.7
| author | Franz Glasner <fzglas.hg@dom66.de> |
|---|---|
| date | Mon, 15 Sep 2025 11:44:09 +0200 |
| parents | b50eed0cc0ef |
| children |
line wrap: on
line diff
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/mupdf-source/source/fitz/draw-rasterize.c Mon Sep 15 11:44:09 2025 +0200 @@ -0,0 +1,311 @@ +// Copyright (C) 2004-2021 Artifex Software, Inc. +// +// This file is part of MuPDF. +// +// MuPDF is free software: you can redistribute it and/or modify it under the +// terms of the GNU Affero General Public License as published by the Free +// Software Foundation, either version 3 of the License, or (at your option) +// any later version. +// +// MuPDF is distributed in the hope that it will be useful, but WITHOUT ANY +// WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS +// FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for more +// details. +// +// You should have received a copy of the GNU Affero General Public License +// along with MuPDF. If not, see <https://www.gnu.org/licenses/agpl-3.0.en.html> +// +// Alternative licensing terms are available from the licensor. +// For commercial licensing, see <https://www.artifex.com/> or contact +// Artifex Software, Inc., 39 Mesa Street, Suite 108A, San Francisco, +// CA 94129, USA, for further information. + +#include "mupdf/fitz.h" + +#include "draw-imp.h" +#include "pixmap-imp.h" + +#include <string.h> + +void fz_init_aa_context(fz_context *ctx) +{ +#ifndef AA_BITS + ctx->aa.hscale = 17; + ctx->aa.vscale = 15; + ctx->aa.scale = 256; + ctx->aa.bits = 8; + ctx->aa.text_bits = 8; +#endif +} + +int +fz_aa_level(fz_context *ctx) +{ + return fz_aa_bits; +} + +int +fz_graphics_aa_level(fz_context *ctx) +{ + return fz_aa_bits; +} + +int +fz_text_aa_level(fz_context *ctx) +{ + return fz_aa_text_bits; +} + +int +fz_rasterizer_graphics_aa_level(fz_rasterizer *ras) +{ + return fz_rasterizer_aa_bits(ras); +} + +int +fz_rasterizer_text_aa_level(fz_rasterizer *ras) +{ + return fz_rasterizer_aa_text_bits(ras); +} + +void +fz_set_rasterizer_text_aa_level(fz_context *ctx, fz_aa_context *aa, int level) +{ +#ifdef AA_BITS + if (level != fz_aa_bits) + { + if (fz_aa_bits == 10) + fz_warn(ctx, "Only the Any-part-of-a-pixel rasterizer was compiled in"); + else if (fz_aa_bits == 9) + fz_warn(ctx, "Only the Centre-of-a-pixel rasterizer was compiled in"); + else + fz_warn(ctx, "Only the %d bit anti-aliasing rasterizer was compiled in", fz_aa_bits); + } +#else + if (level > 8) + aa->text_bits = 0; + else if (level > 6) + aa->text_bits = 8; + else if (level > 4) + aa->text_bits = 6; + else if (level > 2) + aa->text_bits = 4; + else if (level > 0) + aa->text_bits = 2; + else + aa->text_bits = 0; +#endif +} + +void +fz_set_rasterizer_graphics_aa_level(fz_context *ctx, fz_aa_context *aa, int level) +{ +#ifdef AA_BITS + if (level != fz_aa_bits) + { + if (fz_aa_bits == 10) + fz_warn(ctx, "Only the Any-part-of-a-pixel rasterizer was compiled in"); + else if (fz_aa_bits == 9) + fz_warn(ctx, "Only the Centre-of-a-pixel rasterizer was compiled in"); + else + fz_warn(ctx, "Only the %d bit anti-aliasing rasterizer was compiled in", fz_aa_bits); + } +#else + if (level == 9 || level == 10) + { + aa->hscale = 1; + aa->vscale = 1; + aa->bits = level; + } + else if (level > 6) + { + aa->hscale = 17; + aa->vscale = 15; + aa->bits = 8; + } + else if (level > 4) + { + aa->hscale = 8; + aa->vscale = 8; + aa->bits = 6; + } + else if (level > 2) + { + aa->hscale = 5; + aa->vscale = 3; + aa->bits = 4; + } + else if (level > 0) + { + aa->hscale = 2; + aa->vscale = 2; + aa->bits = 2; + } + else + { + aa->hscale = 1; + aa->vscale = 1; + aa->bits = 0; + } + aa->scale = 0xFF00 / (aa->hscale * aa->vscale); +#endif +} + +void +fz_set_aa_level(fz_context *ctx, int level) +{ + fz_set_rasterizer_graphics_aa_level(ctx, &ctx->aa, level); + fz_set_rasterizer_text_aa_level(ctx, &ctx->aa, level); +} + +void +fz_set_text_aa_level(fz_context *ctx, int level) +{ + fz_set_rasterizer_text_aa_level(ctx, &ctx->aa, level); +} + +void +fz_set_graphics_aa_level(fz_context *ctx, int level) +{ + fz_set_rasterizer_graphics_aa_level(ctx, &ctx->aa, level); +} + +void +fz_set_graphics_min_line_width(fz_context *ctx, float min_line_width) +{ + ctx->aa.min_line_width = min_line_width; +} + +float +fz_graphics_min_line_width(fz_context *ctx) +{ + return ctx->aa.min_line_width; +} + +float +fz_rasterizer_graphics_min_line_width(fz_rasterizer *ras) +{ + return ras->aa.min_line_width; +} + +fz_irect +fz_bound_rasterizer(fz_context *ctx, const fz_rasterizer *rast) +{ + fz_irect bbox; + const int hscale = fz_rasterizer_aa_hscale(rast); + const int vscale = fz_rasterizer_aa_vscale(rast); + + if (rast->bbox.x1 < rast->bbox.x0 || rast->bbox.y1 < rast->bbox.y0) + { + bbox = fz_empty_irect; + } + else + { + bbox.x0 = fz_idiv(rast->bbox.x0, hscale); + bbox.y0 = fz_idiv(rast->bbox.y0, vscale); + bbox.x1 = fz_idiv_up(rast->bbox.x1, hscale); + bbox.y1 = fz_idiv_up(rast->bbox.y1, vscale); + } + return bbox; +} + +fz_rect fz_scissor_rasterizer(fz_context *ctx, const fz_rasterizer *rast) +{ + fz_rect r; + const int hscale = fz_rasterizer_aa_hscale(rast); + const int vscale = fz_rasterizer_aa_vscale(rast); + + r.x0 = ((float)rast->clip.x0) / hscale; + r.y0 = ((float)rast->clip.y0) / vscale; + r.x1 = ((float)rast->clip.x1) / hscale; + r.y1 = ((float)rast->clip.y1) / vscale; + + return r; +} + +static fz_irect fz_clip_rasterizer(fz_context *ctx, const fz_rasterizer *rast) +{ + fz_irect r; + const int hscale = fz_rasterizer_aa_hscale(rast); + const int vscale = fz_rasterizer_aa_vscale(rast); + + r.x0 = fz_idiv(rast->clip.x0, hscale); + r.y0 = fz_idiv(rast->clip.y0, vscale); + r.x1 = fz_idiv_up(rast->clip.x1, hscale); + r.y1 = fz_idiv_up(rast->clip.y1, vscale); + + return r; +} + +int fz_reset_rasterizer(fz_context *ctx, fz_rasterizer *rast, fz_irect clip) +{ + const int hscale = fz_rasterizer_aa_hscale(rast); + const int vscale = fz_rasterizer_aa_vscale(rast); + + if (fz_is_infinite_irect(clip)) + { + rast->clip.x0 = rast->clip.y0 = BBOX_MIN; + rast->clip.x1 = rast->clip.y1 = BBOX_MAX; + } + else { + rast->clip.x0 = clip.x0 * hscale; + rast->clip.x1 = clip.x1 * hscale; + rast->clip.y0 = clip.y0 * vscale; + rast->clip.y1 = clip.y1 * vscale; + } + + rast->bbox.x0 = rast->bbox.y0 = BBOX_MAX; + rast->bbox.x1 = rast->bbox.y1 = BBOX_MIN; + + if (rast->fns.reset) + return rast->fns.reset(ctx, rast); + return 0; +} + +void *fz_new_rasterizer_of_size(fz_context *ctx, int size, const fz_rasterizer_fns *fns) +{ + fz_rasterizer *rast = fz_calloc(ctx, 1, size); + + rast->fns = *fns; + rast->clip.x0 = rast->clip.y0 = BBOX_MIN; + rast->clip.x1 = rast->clip.y1 = BBOX_MAX; + + rast->bbox.x0 = rast->bbox.y0 = BBOX_MAX; + rast->bbox.x1 = rast->bbox.y1 = BBOX_MIN; + + return rast; +} + +fz_rasterizer *fz_new_rasterizer(fz_context *ctx, const fz_aa_context *aa) +{ + fz_rasterizer *r; + int bits; + +#ifdef AA_BITS + bits = AA_BITS; +#else + if (aa == NULL) + aa = &ctx->aa; + bits = aa->bits; +#endif + if (bits == 10) + r = fz_new_edgebuffer(ctx, FZ_EDGEBUFFER_ANY_PART_OF_PIXEL); + else if (bits == 9) + r = fz_new_edgebuffer(ctx, FZ_EDGEBUFFER_CENTER_OF_PIXEL); + else + r = fz_new_gel(ctx); +#ifndef AA_BITS + r->aa = *aa; +#endif + + return r; +} + +void fz_convert_rasterizer(fz_context *ctx, fz_rasterizer *r, int eofill, fz_pixmap *pix, unsigned char *colorbv, fz_overprint *eop) +{ + fz_irect clip = fz_bound_rasterizer(ctx, r); + clip = fz_intersect_irect(clip, fz_pixmap_bbox_no_ctx(pix)); + clip = fz_intersect_irect(clip, fz_clip_rasterizer(ctx, r)); + if (!fz_is_empty_irect(clip)) + r->fns.convert(ctx, r, eofill, &clip, pix, colorbv, eop); +}
