From 93bd1ff05bf315ed11b305d32eb510bd9a9a7e92 Mon Sep 17 00:00:00 2001 From: Tor Andersson Date: Thu, 16 May 2013 22:29:27 +0200 Subject: Add colorspace context. To prepare for color management, we have to make the device colorspaces per-context and able to be overridden by users. --- fitz/res_colorspace.c | 177 ++++++++++++++++++++++++++++++++++++++------------ 1 file changed, 134 insertions(+), 43 deletions(-) (limited to 'fitz/res_colorspace.c') diff --git a/fitz/res_colorspace.c b/fitz/res_colorspace.c index 5d8c3b02..faa6c3c1 100644 --- a/fitz/res_colorspace.c +++ b/fitz/res_colorspace.c @@ -169,31 +169,122 @@ static void rgb_to_cmyk(fz_context *ctx, fz_colorspace *cs, float *rgb, float *c cmyk[3] = k; } -static fz_colorspace k_device_gray = { {-1, fz_free_colorspace_imp}, 0, "DeviceGray", 1, gray_to_rgb, rgb_to_gray }; -static fz_colorspace k_device_rgb = { {-1, fz_free_colorspace_imp}, 0, "DeviceRGB", 3, rgb_to_rgb, rgb_to_rgb }; -static fz_colorspace k_device_bgr = { {-1, fz_free_colorspace_imp}, 0, "DeviceRGB", 3, bgr_to_rgb, rgb_to_bgr }; -static fz_colorspace k_device_cmyk = { {-1, fz_free_colorspace_imp}, 0, "DeviceCMYK", 4, cmyk_to_rgb, rgb_to_cmyk }; +static fz_colorspace k_default_gray = { {-1, fz_free_colorspace_imp}, 0, "DeviceGray", 1, gray_to_rgb, rgb_to_gray }; +static fz_colorspace k_default_rgb = { {-1, fz_free_colorspace_imp}, 0, "DeviceRGB", 3, rgb_to_rgb, rgb_to_rgb }; +static fz_colorspace k_default_bgr = { {-1, fz_free_colorspace_imp}, 0, "DeviceRGB", 3, bgr_to_rgb, rgb_to_bgr }; +static fz_colorspace k_default_cmyk = { {-1, fz_free_colorspace_imp}, 0, "DeviceCMYK", 4, cmyk_to_rgb, rgb_to_cmyk }; -fz_colorspace *fz_device_gray = &k_device_gray; -fz_colorspace *fz_device_rgb = &k_device_rgb; -fz_colorspace *fz_device_bgr = &k_device_bgr; -fz_colorspace *fz_device_cmyk = &k_device_cmyk; +static fz_colorspace *fz_default_gray = &k_default_gray; +static fz_colorspace *fz_default_rgb = &k_default_rgb; +static fz_colorspace *fz_default_bgr = &k_default_bgr; +static fz_colorspace *fz_default_cmyk = &k_default_cmyk; + +struct fz_colorspace_context_s +{ + int ctx_refs; + fz_colorspace *gray, *rgb, *bgr, *cmyk; +}; + +void fz_new_colorspace_context(fz_context *ctx) +{ + ctx->colorspace = fz_malloc_struct(ctx, fz_colorspace_context); + ctx->colorspace->ctx_refs = 1; + ctx->colorspace->gray = fz_default_gray; + ctx->colorspace->rgb = fz_default_rgb; + ctx->colorspace->bgr = fz_default_bgr; + ctx->colorspace->cmyk = fz_default_cmyk; +} + +fz_colorspace_context * +fz_keep_colorspace_context(fz_context *ctx) +{ + if (!ctx || !ctx->colorspace) + return NULL; + fz_lock(ctx, FZ_LOCK_ALLOC); + ctx->colorspace->ctx_refs++; + fz_unlock(ctx, FZ_LOCK_ALLOC); + return ctx->colorspace; +} + +void fz_drop_colorspace_context(fz_context *ctx) +{ + int drop; + if (!ctx || !ctx->colorspace) + return; + fz_lock(ctx, FZ_LOCK_ALLOC); + drop = --ctx->colorspace->ctx_refs; + fz_unlock(ctx, FZ_LOCK_ALLOC); + if (drop == 0) + fz_free(ctx, ctx->colorspace); +} + +fz_colorspace * +fz_device_gray(fz_context *ctx) +{ + return ctx->colorspace->gray; +} + +fz_colorspace * +fz_device_rgb(fz_context *ctx) +{ + return ctx->colorspace->rgb; +} + +fz_colorspace * +fz_device_bgr(fz_context *ctx) +{ + return ctx->colorspace->bgr; +} + +fz_colorspace * +fz_device_cmyk(fz_context *ctx) +{ + return ctx->colorspace->cmyk; +} fz_colorspace * fz_find_device_colorspace(fz_context *ctx, char *name) { if (!strcmp(name, "DeviceGray")) - return fz_device_gray; + return fz_device_gray(ctx); if (!strcmp(name, "DeviceRGB")) - return fz_device_rgb; + return fz_device_rgb(ctx); if (!strcmp(name, "DeviceBGR")) - return fz_device_bgr; + return fz_device_bgr(ctx); if (!strcmp(name, "DeviceCMYK")) - return fz_device_cmyk; + return fz_device_cmyk(ctx); assert(!"unknown device colorspace"); return NULL; } +void +fz_set_device_gray(fz_context *ctx, fz_colorspace *cs) +{ + fz_drop_colorspace(ctx, ctx->colorspace->gray); + ctx->colorspace->gray = fz_keep_colorspace(ctx, cs); +} + +void +fz_set_device_rgb(fz_context *ctx, fz_colorspace *cs) +{ + fz_drop_colorspace(ctx, ctx->colorspace->rgb); + ctx->colorspace->rgb = fz_keep_colorspace(ctx, cs); +} + +void +fz_set_device_bgr(fz_context *ctx, fz_colorspace *cs) +{ + fz_drop_colorspace(ctx, ctx->colorspace->bgr); + ctx->colorspace->bgr = fz_keep_colorspace(ctx, cs); +} + +void +fz_set_device_cmyk(fz_context *ctx, fz_colorspace *cs) +{ + fz_drop_colorspace(ctx, ctx->colorspace->cmyk); + ctx->colorspace->cmyk = fz_keep_colorspace(ctx, cs); +} + int fz_colorspace_is_indexed(fz_colorspace *cs) { @@ -861,35 +952,35 @@ fz_convert_pixmap(fz_context *ctx, fz_pixmap *dp, fz_pixmap *sp) dp->interpolate = sp->interpolate; - if (ss == fz_device_gray) + if (ss == fz_default_gray) { - if (ds == fz_device_rgb) fast_gray_to_rgb(dp, sp); - else if (ds == fz_device_bgr) fast_gray_to_rgb(dp, sp); /* bgr == rgb here */ - else if (ds == fz_device_cmyk) fast_gray_to_cmyk(dp, sp); + if (ds == fz_default_rgb) fast_gray_to_rgb(dp, sp); + else if (ds == fz_default_bgr) fast_gray_to_rgb(dp, sp); /* bgr == rgb here */ + else if (ds == fz_default_cmyk) fast_gray_to_cmyk(dp, sp); else fz_std_conv_pixmap(ctx, dp, sp); } - else if (ss == fz_device_rgb) + else if (ss == fz_default_rgb) { - if (ds == fz_device_gray) fast_rgb_to_gray(dp, sp); - else if (ds == fz_device_bgr) fast_rgb_to_bgr(dp, sp); - else if (ds == fz_device_cmyk) fast_rgb_to_cmyk(dp, sp); + if (ds == fz_default_gray) fast_rgb_to_gray(dp, sp); + else if (ds == fz_default_bgr) fast_rgb_to_bgr(dp, sp); + else if (ds == fz_default_cmyk) fast_rgb_to_cmyk(dp, sp); else fz_std_conv_pixmap(ctx, dp, sp); } - else if (ss == fz_device_bgr) + else if (ss == fz_default_bgr) { - if (ds == fz_device_gray) fast_bgr_to_gray(dp, sp); - else if (ds == fz_device_rgb) fast_rgb_to_bgr(dp, sp); /* bgr = rgb here */ - else if (ds == fz_device_cmyk) fast_bgr_to_cmyk(sp, dp); + if (ds == fz_default_gray) fast_bgr_to_gray(dp, sp); + else if (ds == fz_default_rgb) fast_rgb_to_bgr(dp, sp); /* bgr = rgb here */ + else if (ds == fz_default_cmyk) fast_bgr_to_cmyk(sp, dp); else fz_std_conv_pixmap(ctx, dp, sp); } - else if (ss == fz_device_cmyk) + else if (ss == fz_default_cmyk) { - if (ds == fz_device_gray) fast_cmyk_to_gray(dp, sp); - else if (ds == fz_device_bgr) fast_cmyk_to_bgr(ctx, dp, sp); - else if (ds == fz_device_rgb) fast_cmyk_to_rgb(ctx, dp, sp); + if (ds == fz_default_gray) fast_cmyk_to_gray(dp, sp); + else if (ds == fz_default_bgr) fast_cmyk_to_bgr(ctx, dp, sp); + else if (ds == fz_default_rgb) fast_cmyk_to_rgb(ctx, dp, sp); else fz_std_conv_pixmap(ctx, dp, sp); } @@ -1027,47 +1118,47 @@ void fz_find_color_converter(fz_color_converter *cc, fz_context *ctx, fz_colorsp cc->ctx = ctx; cc->ds = ds; cc->ss = ss; - if (ss == fz_device_gray) + if (ss == fz_default_gray) { - if ((ds == fz_device_rgb) || (ds == fz_device_bgr)) + if ((ds == fz_default_rgb) || (ds == fz_default_bgr)) cc->convert = g2rgb; - else if (ds == fz_device_cmyk) + else if (ds == fz_default_cmyk) cc->convert = g2cmyk; else cc->convert = std_conv_color; } - else if (ss == fz_device_rgb) + else if (ss == fz_default_rgb) { - if (ds == fz_device_gray) + if (ds == fz_default_gray) cc->convert = rgb2g; - else if (ds == fz_device_bgr) + else if (ds == fz_default_bgr) cc->convert = rgb2bgr; - else if (ds == fz_device_cmyk) + else if (ds == fz_default_cmyk) cc->convert = rgb2cmyk; else cc->convert = std_conv_color; } - else if (ss == fz_device_bgr) + else if (ss == fz_default_bgr) { - if (ds == fz_device_gray) + if (ds == fz_default_gray) cc->convert = bgr2g; - else if (ds == fz_device_rgb) + else if (ds == fz_default_rgb) cc->convert = rgb2bgr; - else if (ds == fz_device_cmyk) + else if (ds == fz_default_cmyk) cc->convert = bgr2cmyk; else cc->convert = std_conv_color; } - else if (ss == fz_device_cmyk) + else if (ss == fz_default_cmyk) { - if (ds == fz_device_gray) + if (ds == fz_default_gray) cc->convert = cmyk2g; - else if (ds == fz_device_rgb) + else if (ds == fz_default_rgb) cc->convert = cmyk2rgb; - else if (ds == fz_device_bgr) + else if (ds == fz_default_bgr) cc->convert = cmyk2bgr; else cc->convert = std_conv_color; -- cgit v1.2.3