📄 pdf_colorspace1.c.svn-base
字号:
#include "fitz.h"#include "mupdf.h"#define noUSECALstatic void initcs(fz_colorspace *cs, char *name, int n, void(*to)(fz_colorspace*,float*,float*), void(*from)(fz_colorspace*,float*,float*), void(*drop)(fz_colorspace*)){ strlcpy(cs->name, name, sizeof cs->name); cs->refs = 1; cs->convpixmap = pdf_convpixmap; cs->convcolor = pdf_convcolor; cs->toxyz = to; cs->fromxyz = from; cs->drop = drop; cs->n = n;}/* * CalGray */struct calgray{ fz_colorspace super; float white[3]; float black[3]; float gamma;};static void graytoxyz(fz_colorspace *fzcs, float *gray, float *xyz){ struct calgray *cs = (struct calgray *) fzcs; xyz[0] = pow(gray[0], cs->gamma) * cs->white[0]; xyz[1] = pow(gray[0], cs->gamma) * cs->white[1]; xyz[2] = pow(gray[0], cs->gamma) * cs->white[2];}static void xyztogray(fz_colorspace *fzcs, float *xyz, float *gray){ struct calgray *cs = (struct calgray *) fzcs; float r = pow(xyz[0], 1.0 / cs->gamma) / cs->white[0]; float g = pow(xyz[1], 1.0 / cs->gamma) / cs->white[1]; float b = pow(xyz[2], 1.0 / cs->gamma) / cs->white[2]; gray[0] = r * 0.3 + g * 0.59 + b * 0.11;}/* * CalRGB */struct calrgb{ fz_colorspace super; float white[3]; float black[3]; float gamma[3]; float matrix[9]; float invmat[9];};static void rgbtoxyz(fz_colorspace *fzcs, float *rgb, float *xyz){ struct calrgb *cs = (struct calrgb *) fzcs; float a = pow(rgb[0], cs->gamma[0]) * cs->white[0]; float b = pow(rgb[1], cs->gamma[1]) * cs->white[1]; float c = pow(rgb[2], cs->gamma[2]) * cs->white[2]; xyz[0] = a * cs->matrix[0] + b * cs->matrix[1] + c * cs->matrix[2]; xyz[1] = a * cs->matrix[3] + b * cs->matrix[4] + c * cs->matrix[5]; xyz[2] = a * cs->matrix[6] + b * cs->matrix[7] + c * cs->matrix[8];}static void xyztorgb(fz_colorspace *fzcs, float *xyz, float *rgb){ struct calrgb *cs = (struct calrgb *) fzcs; float a = xyz[0] * cs->invmat[0] + xyz[1] * cs->invmat[1] + xyz[2] * cs->invmat[2]; float b = xyz[0] * cs->invmat[3] + xyz[1] * cs->invmat[4] + xyz[2] * cs->invmat[5]; float c = xyz[0] * cs->invmat[6] + xyz[1] * cs->invmat[7] + xyz[2] * cs->invmat[8]; rgb[0] = pow(a, 1.0 / cs->gamma[0]) / cs->white[0]; rgb[1] = pow(b, 1.0 / cs->gamma[1]) / cs->white[1]; rgb[2] = pow(c, 1.0 / cs->gamma[2]) / cs->white[2];}/* * DeviceCMYK piggybacks on DeviceRGB */static void devicecmyktoxyz(fz_colorspace *cs, float *cmyk, float *xyz){ float rgb[3]; rgb[0] = 1.0 - MIN(1.0, cmyk[0] + cmyk[3]); rgb[1] = 1.0 - MIN(1.0, cmyk[1] + cmyk[3]); rgb[2] = 1.0 - MIN(1.0, cmyk[2] + cmyk[3]); rgbtoxyz(pdf_devicergb, rgb, xyz);}static void xyztodevicecmyk(fz_colorspace *cs, float *xyz, float *cmyk){ float rgb[3]; float c, m, y, k; xyztorgb(pdf_devicergb, xyz, rgb); c = 1.0 - rgb[0]; m = 1.0 - rgb[0]; y = 1.0 - rgb[0]; k = MIN(c, MIN(m, y)); cmyk[0] = c - k; cmyk[1] = m - k; cmyk[2] = y - k; cmyk[3] = k;}/* * CIE Lab */struct cielab{ fz_colorspace super; float white[3]; float black[3]; float range[4];};static inline float fung(float x){ if (x >= 6.0 / 29.0) return x * x * x; return (108.0 / 841.0) * (x - (4.0 / 29.0));}static inline float invg(float x){ if (x > 0.008856) return pow(x, 1.0 / 3.0); return (7.787 * x) + (16.0 / 116.0);}static void labtoxyz(fz_colorspace *fzcs, float *lab, float *xyz){ struct cielab *cs = (struct cielab *) fzcs; float lstar, astar, bstar, l, m, n; float tmp[3]; tmp[0] = lab[0] * 100; tmp[1] = lab[1] * 200 - 100; tmp[2] = lab[2] * 200 - 100; lstar = tmp[0]; astar = MAX(MIN(tmp[1], cs->range[1]), cs->range[0]); bstar = MAX(MIN(tmp[2], cs->range[3]), cs->range[2]); l = (lstar + 16.0) / 116.0 + astar / 500.0; m = (lstar + 16.0) / 116.0; n = (lstar + 16.0) / 116.0 - bstar / 200.0; xyz[0] = fung(l) * cs->white[0]; xyz[1] = fung(m) * cs->white[1]; xyz[2] = fung(n) * cs->white[2];}static void xyztolab(fz_colorspace *fzcs, float *xyz, float *lab){ struct cielab *cs = (struct cielab *) fzcs; float tmp[3]; float yyn = xyz[1] / cs->white[1]; if (yyn < 0.008856) tmp[0] = 116.0 * yyn * (1.0 / 3.0) - 16.0; else tmp[0] = 903.3 * yyn; tmp[1] = 500 * (invg(xyz[0]/cs->white[0]) - invg(xyz[1]/cs->white[1])); tmp[2] = 200 * (invg(xyz[1]/cs->white[1]) - invg(xyz[2]/cs->white[2])); lab[0] = tmp[0] / 100.0; lab[1] = (tmp[1] + 100) / 200.0; lab[2] = (tmp[2] + 100) / 200.0;}/* * Define global Device* colorspaces as Cal* */static struct calgray kdevicegray ={ { -1, "DeviceGray", 1, pdf_convpixmap, pdf_convcolor, graytoxyz, xyztogray, nil }, { 1.0000, 1.0000, 1.0000 }, { 0.0000, 0.0000, 0.0000 }, 1.0000};static struct calrgb kdevicergb ={ { -1, "DeviceRGB", 3, pdf_convpixmap, pdf_convcolor, rgbtoxyz, xyztorgb, nil }, { 1.0000, 1.0000, 1.0000 }, { 0.0000, 0.0000, 0.0000 }, { 1.0000, 1.0000, 1.0000 }, { 1,0,0, 0,1,0, 0,0,1 }, { 1,0,0, 0,1,0, 0,0,1 },};static fz_colorspace kdevicecmyk ={ -1, "DeviceCMYK", 4, pdf_convpixmap, pdf_convcolor, devicecmyktoxyz, xyztodevicecmyk, nil};static struct cielab kdevicelab ={ { -1, "Lab", 3, pdf_convpixmap, fz_stdconvcolor, labtoxyz, xyztolab, nil }, { 1.0000, 1.0000, 1.0000 }, { 0.0000, 0.0000, 0.0000 }, { -100, 100, -100, 100 },};static fz_colorspace kdevicepattern ={ -1, "Pattern", 0, nil, nil, nil, nil, nil};fz_colorspace *pdf_devicegray = &kdevicegray.super;fz_colorspace *pdf_devicergb = &kdevicergb.super;fz_colorspace *pdf_devicecmyk = &kdevicecmyk;fz_colorspace *pdf_devicelab = &kdevicelab.super;fz_colorspace *pdf_devicepattern = &kdevicepattern;/* * Colorspace parsing */#ifdef USECALstatic fz_error *loadcalgray(fz_colorspace **csp, pdf_xref *xref, fz_obj *dict){ fz_error *error; struct calgray *cs; fz_obj *tmp; error = pdf_resolve(&dict, xref); if (error) return fz_rethrow(error, "cannot find colorspace"); cs = fz_malloc(sizeof(struct calgray)); if (!cs) return fz_throw("outofmem: gray colorspace struct"); pdf_logrsrc("load CalGray\n"); initcs((fz_colorspace*)cs, "CalGray", 1, graytoxyz, xyztogray, nil); cs->white[0] = 1.0; cs->white[1] = 1.0; cs->white[2] = 1.0; cs->black[0] = 0.0; cs->black[1] = 0.0; cs->black[2] = 0.0; cs->gamma = 1.0; tmp = fz_dictgets(dict, "WhitePoint"); if (fz_isarray(tmp)) { cs->white[0] = fz_toreal(fz_arrayget(tmp, 0)); cs->white[1] = fz_toreal(fz_arrayget(tmp, 1)); cs->white[2] = fz_toreal(fz_arrayget(tmp, 2)); } tmp = fz_dictgets(dict, "BlackPoint"); if (fz_isarray(tmp)) { cs->black[0] = fz_toreal(fz_arrayget(tmp, 0)); cs->black[1] = fz_toreal(fz_arrayget(tmp, 1)); cs->black[2] = fz_toreal(fz_arrayget(tmp, 2)); } tmp = fz_dictgets(dict, "Gamma"); if (fz_isreal(tmp)) cs->gamma = fz_toreal(tmp); fz_dropobj(dict); *csp = (fz_colorspace*) cs; return fz_okay;}static fz_error *loadcalrgb(fz_colorspace **csp, pdf_xref *xref, fz_obj *dict){ fz_error *error; struct calrgb *cs; fz_obj *tmp; int i; error = pdf_resolve(&dict, xref); if (error) return fz_rethrow(error, "cannot find colorspace"); cs = fz_malloc(sizeof(struct calrgb)); if (!cs) return fz_throw("outofmem: RGB colorspace struct"); pdf_logrsrc("load CalRGB\n"); initcs((fz_colorspace*)cs, "CalRGB", 3, rgbtoxyz, xyztorgb, nil); cs->white[0] = 1.0; cs->white[1] = 1.0; cs->white[2] = 1.0; cs->black[0] = 0.0; cs->black[1] = 0.0; cs->black[2] = 0.0; cs->gamma[0] = 1.0; cs->gamma[1] = 1.0; cs->gamma[2] = 1.0; cs->matrix[0] = 1.0; cs->matrix[1] = 0.0; cs->matrix[2] = 0.0; cs->matrix[3] = 0.0; cs->matrix[4] = 1.0; cs->matrix[5] = 0.0; cs->matrix[6] = 0.0; cs->matrix[7] = 0.0; cs->matrix[8] = 1.0; tmp = fz_dictgets(dict, "WhitePoint"); if (fz_isarray(tmp)) { cs->white[0] = fz_toreal(fz_arrayget(tmp, 0)); cs->white[1] = fz_toreal(fz_arrayget(tmp, 1)); cs->white[2] = fz_toreal(fz_arrayget(tmp, 2)); } tmp = fz_dictgets(dict, "BlackPoint"); if (fz_isarray(tmp)) { cs->black[0] = fz_toreal(fz_arrayget(tmp, 0)); cs->black[1] = fz_toreal(fz_arrayget(tmp, 1)); cs->black[2] = fz_toreal(fz_arrayget(tmp, 2)); } tmp = fz_dictgets(dict, "Gamma"); if (fz_isarray(tmp)) { cs->gamma[0] = fz_toreal(fz_arrayget(tmp, 0)); cs->gamma[1] = fz_toreal(fz_arrayget(tmp, 1)); cs->gamma[2] = fz_toreal(fz_arrayget(tmp, 2)); } tmp = fz_dictgets(dict, "Matrix"); if (fz_isarray(tmp)) { for (i = 0; i < 9; i++) cs->matrix[i] = fz_toreal(fz_arrayget(tmp, i)); } fz_invert3x3(cs->invmat, cs->matrix); fz_dropobj(dict); *csp = (fz_colorspace*) cs; return fz_okay;}static fz_error *loadlab(fz_colorspace **csp, pdf_xref *xref, fz_obj *dict){ fz_error *error; struct cielab *cs; fz_obj *tmp; error = pdf_resolve(&dict, xref); if (error) return fz_rethrow(error, "cannot find colorspace"); cs = fz_malloc(sizeof(struct cielab)); if (!cs) return fz_throw("outofmem: L*a*b colorspace struct"); pdf_logrsrc("load Lab\n"); initcs((fz_colorspace*)cs, "Lab", 3, labtoxyz, xyztolab, nil); cs->white[0] = 1.0; cs->white[1] = 1.0; cs->white[2] = 1.0; cs->black[0] = 0.0; cs->black[1] = 0.0; cs->black[2] = 0.0; cs->range[0] = -100; cs->range[1] = 100; cs->range[2] = -100; cs->range[3] = 100;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -