⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 tif_pixarlog.c

📁 一个国人自己实现图像库的程序(有参考价值)
💻 C
📖 第 1 页 / 共 3 页
字号:
/* * Copyright (c) 1996-1997 Sam Leffler * Copyright (c) 1996 Pixar * * Permission to use, copy, modify, distribute, and sell this software and  * its documentation for any purpose is hereby granted without fee, provided * that (i) the above copyright notices and this permission notice appear in * all copies of the software and related documentation, and (ii) the names of * Pixar, Sam Leffler and Silicon Graphics may not be used in any advertising or * publicity relating to the software without the specific, prior written * permission of Pixar, Sam Leffler and Silicon Graphics. *  * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND,  * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY  * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE.   *  * IN NO EVENT SHALL PIXAR, SAM LEFFLER OR SILICON GRAPHICS BE LIABLE FOR * ANY SPECIAL, INCIDENTAL, INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, * OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, * WHETHER OR NOT ADVISED OF THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF  * LIABILITY, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE  * OF THIS SOFTWARE. */#include "tiffiop.h"#ifdef PIXARLOG_SUPPORT/* * TIFF Library. * PixarLog Compression Support * * Contributed by Dan McCoy. * * PixarLog film support uses the TIFF library to store companded * 11 bit values into a tiff file, which are compressed using the  * zip compressor.   * * The codec can take as input and produce as output 32-bit IEEE float values  * as well as 16-bit or 8-bit unsigned integer values. * * On writing any of the above are converted into the internal * 11-bit log format.   In the case of  8 and 16 bit values, the * input is assumed to be unsigned linear color values that represent * the range 0-1.  In the case of IEEE values, the 0-1 range is assumed to * be the normal linear color range, in addition over 1 values are * accepted up to a value of about 25.0 to encode "hot" hightlights and such. * The encoding is lossless for 8-bit values, slightly lossy for the * other bit depths.  The actual color precision should be better * than the human eye can perceive with extra room to allow for * error introduced by further image computation.  As with any quantized * color format, it is possible to perform image calculations which * expose the quantization error. This format should certainly be less  * susceptable to such errors than standard 8-bit encodings, but more * susceptable than straight 16-bit or 32-bit encodings. * * On reading the internal format is converted to the desired output format. * The program can request which format it desires by setting the internal * pseudo tag TIFFTAG_PIXARLOGDATAFMT to one of these possible values: *  PIXARLOGDATAFMT_FLOAT     = provide IEEE float values. *  PIXARLOGDATAFMT_16BIT     = provide unsigned 16-bit integer values *  PIXARLOGDATAFMT_8BIT      = provide unsigned 8-bit integer values * * alternately PIXARLOGDATAFMT_8BITABGR provides unsigned 8-bit integer * values with the difference that if there are exactly three or four channels * (rgb or rgba) it swaps the channel order (bgr or abgr). * * PIXARLOGDATAFMT_11BITLOG provides the internal encoding directly * packed in 16-bit values.   However no tools are supplied for interpreting * these values. * * "hot" (over 1.0) areas written in floating point get clamped to * 1.0 in the integer data types. * * When the file is closed after writing, the bit depth and sample format * are set always to appear as if 8-bit data has been written into it. * That way a naive program unaware of the particulars of the encoding * gets the format it is most likely able to handle. * * The codec does it's own horizontal differencing step on the coded * values so the libraries predictor stuff should be turned off. * The codec also handle byte swapping the encoded values as necessary * since the library does not have the information necessary * to know the bit depth of the raw unencoded buffer. *  */#include "tif_predict.h"#include "zlib.h"#include "zutil.h"#include <stdio.h>#include <assert.h>#include <stdlib.h>#include <math.h>/* Tables for converting to/from 11 bit coded values */#define  TSIZE	 2048		/* decode table size (11-bit tokens) */#define  TSIZEP1 2049		/* Plus one for slop */#define  ONE	 1250		/* token value of 1.0 exactly */#define  RATIO	 1.004		/* nominal ratio for log part */#define CODE_MASK 0x7ff         /* 11 bits. */static float  Fltsize;static float  LogK1, LogK2;#define REPEAT(n, op)   { int i; i=n; do { i--; op; } while (i>0); }static voidhorizontalAccumulateF(uint16 *wp, int n, int stride, float *op, 	float *ToLinearF){    register unsigned int  cr, cg, cb, ca, mask;    register float  t0, t1, t2, t3;    if (n >= stride) {	mask = CODE_MASK;	if (stride == 3) {	    t0 = ToLinearF[cr = wp[0]];	    t1 = ToLinearF[cg = wp[1]];	    t2 = ToLinearF[cb = wp[2]];	    op[0] = t0;	    op[1] = t1;	    op[2] = t2;	    n -= 3;	    while (n > 0) {		wp += 3;		op += 3;		n -= 3;		t0 = ToLinearF[(cr += wp[0]) & mask];		t1 = ToLinearF[(cg += wp[1]) & mask];		t2 = ToLinearF[(cb += wp[2]) & mask];		op[0] = t0;		op[1] = t1;		op[2] = t2;	    }	} else if (stride == 4) {	    t0 = ToLinearF[cr = wp[0]];	    t1 = ToLinearF[cg = wp[1]];	    t2 = ToLinearF[cb = wp[2]];	    t3 = ToLinearF[ca = wp[3]];	    op[0] = t0;	    op[1] = t1;	    op[2] = t2;	    op[3] = t3;	    n -= 4;	    while (n > 0) {		wp += 4;		op += 4;		n -= 4;		t0 = ToLinearF[(cr += wp[0]) & mask];		t1 = ToLinearF[(cg += wp[1]) & mask];		t2 = ToLinearF[(cb += wp[2]) & mask];		t3 = ToLinearF[(ca += wp[3]) & mask];		op[0] = t0;		op[1] = t1;		op[2] = t2;		op[3] = t3;	    }	} else {	    REPEAT(stride, *op = ToLinearF[*wp&mask]; wp++; op++)	    n -= stride;	    while (n > 0) {		REPEAT(stride,		    wp[stride] += *wp; *op = ToLinearF[*wp&mask]; wp++; op++)		n -= stride;	    }	}    }}static voidhorizontalAccumulate12(uint16 *wp, int n, int stride, int16 *op,	float *ToLinearF){    register unsigned int  cr, cg, cb, ca, mask;    register float  t0, t1, t2, t3;#define SCALE12 2048.0#define CLAMP12(t) (((t) < 3071) ? (uint16) (t) : 3071)    if (n >= stride) {	mask = CODE_MASK;	if (stride == 3) {	    t0 = ToLinearF[cr = wp[0]] * SCALE12;	    t1 = ToLinearF[cg = wp[1]] * SCALE12;	    t2 = ToLinearF[cb = wp[2]] * SCALE12;	    op[0] = CLAMP12(t0);	    op[1] = CLAMP12(t1);	    op[2] = CLAMP12(t2);	    n -= 3;	    while (n > 0) {		wp += 3;		op += 3;		n -= 3;		t0 = ToLinearF[(cr += wp[0]) & mask] * SCALE12;		t1 = ToLinearF[(cg += wp[1]) & mask] * SCALE12;		t2 = ToLinearF[(cb += wp[2]) & mask] * SCALE12;		op[0] = CLAMP12(t0);		op[1] = CLAMP12(t1);		op[2] = CLAMP12(t2);	    }	} else if (stride == 4) {	    t0 = ToLinearF[cr = wp[0]] * SCALE12;	    t1 = ToLinearF[cg = wp[1]] * SCALE12;	    t2 = ToLinearF[cb = wp[2]] * SCALE12;	    t3 = ToLinearF[ca = wp[3]] * SCALE12;	    op[0] = CLAMP12(t0);	    op[1] = CLAMP12(t1);	    op[2] = CLAMP12(t2);	    op[3] = CLAMP12(t3);	    n -= 4;	    while (n > 0) {		wp += 4;		op += 4;		n -= 4;		t0 = ToLinearF[(cr += wp[0]) & mask] * SCALE12;		t1 = ToLinearF[(cg += wp[1]) & mask] * SCALE12;		t2 = ToLinearF[(cb += wp[2]) & mask] * SCALE12;		t3 = ToLinearF[(ca += wp[3]) & mask] * SCALE12;		op[0] = CLAMP12(t0);		op[1] = CLAMP12(t1);		op[2] = CLAMP12(t2);		op[3] = CLAMP12(t3);	    }	} else {	    REPEAT(stride, t0 = ToLinearF[*wp&mask] * SCALE12;                           *op = CLAMP12(t0); wp++; op++)	    n -= stride;	    while (n > 0) {		REPEAT(stride,		    wp[stride] += *wp; t0 = ToLinearF[wp[stride]&mask]*SCALE12;		    *op = CLAMP12(t0);  wp++; op++)		n -= stride;	    }	}    }}static voidhorizontalAccumulate16(uint16 *wp, int n, int stride, uint16 *op,	uint16 *ToLinear16){    register unsigned int  cr, cg, cb, ca, mask;    if (n >= stride) {	mask = CODE_MASK;	if (stride == 3) {	    op[0] = ToLinear16[cr = wp[0]];	    op[1] = ToLinear16[cg = wp[1]];	    op[2] = ToLinear16[cb = wp[2]];	    n -= 3;	    while (n > 0) {		wp += 3;		op += 3;		n -= 3;		op[0] = ToLinear16[(cr += wp[0]) & mask];		op[1] = ToLinear16[(cg += wp[1]) & mask];		op[2] = ToLinear16[(cb += wp[2]) & mask];	    }	} else if (stride == 4) {	    op[0] = ToLinear16[cr = wp[0]];	    op[1] = ToLinear16[cg = wp[1]];	    op[2] = ToLinear16[cb = wp[2]];	    op[3] = ToLinear16[ca = wp[3]];	    n -= 4;	    while (n > 0) {		wp += 4;		op += 4;		n -= 4;		op[0] = ToLinear16[(cr += wp[0]) & mask];		op[1] = ToLinear16[(cg += wp[1]) & mask];		op[2] = ToLinear16[(cb += wp[2]) & mask];		op[3] = ToLinear16[(ca += wp[3]) & mask];	    }	} else {	    REPEAT(stride, *op = ToLinear16[*wp&mask]; wp++; op++)	    n -= stride;	    while (n > 0) {		REPEAT(stride,		    wp[stride] += *wp; *op = ToLinear16[*wp&mask]; wp++; op++)		n -= stride;	    }	}    }}/*  * Returns the log encoded 11-bit values with the horizontal * differencing undone. */static voidhorizontalAccumulate11(uint16 *wp, int n, int stride, uint16 *op){    register unsigned int  cr, cg, cb, ca, mask;    if (n >= stride) {	mask = CODE_MASK;	if (stride == 3) {	    op[0] = cr = wp[0];  op[1] = cg = wp[1];  op[2] = cb = wp[2];	    n -= 3;	    while (n > 0) {		wp += 3;		op += 3;		n -= 3;		op[0] = (cr += wp[0]) & mask;		op[1] = (cg += wp[1]) & mask;		op[2] = (cb += wp[2]) & mask;	    }	} else if (stride == 4) {	    op[0] = cr = wp[0];  op[1] = cg = wp[1];	    op[2] = cb = wp[2];  op[3] = ca = wp[3];	    n -= 4;	    while (n > 0) {		wp += 4;		op += 4;		n -= 4;		op[0] = (cr += wp[0]) & mask;		op[1] = (cg += wp[1]) & mask;		op[2] = (cb += wp[2]) & mask;		op[3] = (ca += wp[3]) & mask;	    } 	} else {	    REPEAT(stride, *op = *wp&mask; wp++; op++)	    n -= stride;	    while (n > 0) {		REPEAT(stride,		    wp[stride] += *wp; *op = *wp&mask; wp++; op++)	    	n -= stride;	    }	}    }}static voidhorizontalAccumulate8(uint16 *wp, int n, int stride, unsigned char *op,	unsigned char *ToLinear8){    register unsigned int  cr, cg, cb, ca, mask;    if (n >= stride) {	mask = CODE_MASK;	if (stride == 3) {	    op[0] = ToLinear8[cr = wp[0]];	    op[1] = ToLinear8[cg = wp[1]];	    op[2] = ToLinear8[cb = wp[2]];	    n -= 3;	    while (n > 0) {		n -= 3;		wp += 3;		op += 3;		op[0] = ToLinear8[(cr += wp[0]) & mask];		op[1] = ToLinear8[(cg += wp[1]) & mask];		op[2] = ToLinear8[(cb += wp[2]) & mask];	    }	} else if (stride == 4) {	    op[0] = ToLinear8[cr = wp[0]];	    op[1] = ToLinear8[cg = wp[1]];	    op[2] = ToLinear8[cb = wp[2]];	    op[3] = ToLinear8[ca = wp[3]];	    n -= 4;	    while (n > 0) {		n -= 4;		wp += 4;		op += 4;		op[0] = ToLinear8[(cr += wp[0]) & mask];		op[1] = ToLinear8[(cg += wp[1]) & mask];		op[2] = ToLinear8[(cb += wp[2]) & mask];		op[3] = ToLinear8[(ca += wp[3]) & mask];	    }	} else {	    REPEAT(stride, *op = ToLinear8[*wp&mask]; wp++; op++)	    n -= stride;	    while (n > 0) {		REPEAT(stride,		    wp[stride] += *wp; *op = ToLinear8[*wp&mask]; wp++; op++)		n -= stride;	    }	}    }}static voidhorizontalAccumulate8abgr(uint16 *wp, int n, int stride, unsigned char *op,	unsigned char *ToLinear8){    register unsigned int  cr, cg, cb, ca, mask;    register unsigned char  t0, t1, t2, t3;    if (n >= stride) {	mask = CODE_MASK;	if (stride == 3) {	    op[0] = 0;	    t1 = ToLinear8[cb = wp[2]];	    t2 = ToLinear8[cg = wp[1]];	    t3 = ToLinear8[cr = wp[0]];	    op[1] = t1;	    op[2] = t2;	    op[3] = t3;	    n -= 3;	    while (n > 0) {		n -= 3;		wp += 3;		op += 4;		op[0] = 0;		t1 = ToLinear8[(cb += wp[2]) & mask];		t2 = ToLinear8[(cg += wp[1]) & mask];		t3 = ToLinear8[(cr += wp[0]) & mask];		op[1] = t1;		op[2] = t2;		op[3] = t3;	    }	} else if (stride == 4) {	    t0 = ToLinear8[ca = wp[3]];	    t1 = ToLinear8[cb = wp[2]];	    t2 = ToLinear8[cg = wp[1]];	    t3 = ToLinear8[cr = wp[0]];	    op[0] = t0;	    op[1] = t1;	    op[2] = t2;	    op[3] = t3;	    n -= 4;	    while (n > 0) {		n -= 4;		wp += 4;		op += 4;		t0 = ToLinear8[(ca += wp[3]) & mask];		t1 = ToLinear8[(cb += wp[2]) & mask];		t2 = ToLinear8[(cg += wp[1]) & mask];		t3 = ToLinear8[(cr += wp[0]) & mask];		op[0] = t0;		op[1] = t1;		op[2] = t2;		op[3] = t3;	    }

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -