|
Blender
V2.59
|
00001 /* 00002 * 00003 * ***** BEGIN GPL LICENSE BLOCK ***** 00004 * 00005 * This program is free software; you can redistribute it and/or 00006 * modify it under the terms of the GNU General Public License 00007 * as published by the Free Software Foundation; either version 2 00008 * of the License, or (at your option) any later version. 00009 * 00010 * This program is distributed in the hope that it will be useful, 00011 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00012 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00013 * GNU General Public License for more details. 00014 * 00015 * You should have received a copy of the GNU General Public License 00016 * along with this program; if not, write to the Free Software Foundation, 00017 * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 00018 * 00019 * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. 00020 * All rights reserved. 00021 * 00022 * The Original Code is: all of this file. 00023 * 00024 * Contributor(s): none yet. 00025 * 00026 * ***** END GPL LICENSE BLOCK ***** 00027 * cineon.c 00028 * contributors: joeedh 00029 * I hearby donate this code and all rights to the Blender Foundation. 00030 * $Id: cineon_dpx.c 36594 2011-05-10 13:11:36Z campbellbarton $ 00031 */ 00032 00038 #include <stdio.h> 00039 #include <string.h> /*for memcpy*/ 00040 00041 #include "logImageLib.h" 00042 #include "cineonlib.h" 00043 #include "dpxlib.h" 00044 00045 #include "IMB_imbuf_types.h" 00046 #include "IMB_imbuf.h" 00047 #include "IMB_filetype.h" 00048 00049 #include "BKE_global.h" 00050 00051 #include "MEM_guardedalloc.h" 00052 00053 #if 0 00054 static void cineon_conversion_parameters(LogImageByteConversionParameters *params) 00055 { 00056 // params->blackPoint = scene?scene->r.cineonblack:95; 00057 // params->whitePoint = scene?scene->r.cineonwhite:685; 00058 // params->gamma = scene?scene->r.cineongamma:1.7f; 00059 // params->doLogarithm = scene?scene->r.subimtype & R_CINEON_LOG:0; 00060 00061 params->blackPoint = 95; 00062 params->whitePoint = 685; 00063 params->gamma = 1.0f; 00064 params->doLogarithm = 0; 00065 } 00066 #endif 00067 00068 static struct ImBuf *imb_load_dpx_cineon(unsigned char *mem, int use_cineon, int size, int flags) 00069 { 00070 ImBuf *ibuf; 00071 LogImageFile *image; 00072 int x, y; 00073 unsigned short *row, *upix; 00074 int width, height, depth; 00075 float *frow; 00076 00077 logImageSetVerbose((G.f & G_DEBUG) ? 1:0); 00078 00079 image = logImageOpenFromMem(mem, size, use_cineon); 00080 00081 if (!image) { 00082 printf("no image!\n"); 00083 return NULL; 00084 } 00085 00086 logImageGetSize(image, &width, &height, &depth); 00087 00088 if (depth != 3) { /*need to do greyscale loading eventually.*/ 00089 logImageClose(image); 00090 return NULL; 00091 } 00092 00093 if (width == 0 && height == 0) { 00094 logImageClose(image); 00095 return NULL; 00096 } 00097 00098 ibuf = IMB_allocImBuf(width, height, 32, IB_rectfloat | flags); 00099 00100 row = MEM_mallocN(sizeof(unsigned short)*width*depth, "row in cineon_dpx.c"); 00101 frow = ibuf->rect_float+width*height*4; 00102 00103 for (y = 0; y < height; y++) { 00104 logImageGetRowBytes(image, row, y); /* checks image->params.doLogarithm and convert */ 00105 upix = row; 00106 frow -= width*4; 00107 00108 for (x=0; x<width; x++) { 00109 *(frow++) = ((float)*(upix++)) / 65535.0f; 00110 *(frow++) = ((float)*(upix++)) / 65535.0f; 00111 *(frow++) = ((float)*(upix++)) / 65535.0f; 00112 *(frow++) = 1.0f; 00113 } 00114 frow -= width*4; 00115 } 00116 00117 MEM_freeN(row); 00118 logImageClose(image); 00119 00120 if (flags & IB_rect) { 00121 IMB_rect_from_float(ibuf); 00122 } 00123 return ibuf; 00124 } 00125 00126 static int imb_save_dpx_cineon(ImBuf *ibuf, const char *filename, int use_cineon, int flags) 00127 { 00128 LogImageByteConversionParameters conversion; 00129 const int width= ibuf->x; 00130 const int height= ibuf->y; 00131 const int depth= 3; 00132 LogImageFile* logImage; 00133 unsigned short* line, *pixel; 00134 int i, j; 00135 float *fline; 00136 float *fbuf; 00137 int is_alloc= 0; 00138 00139 (void)flags; /* unused */ 00140 00141 // cineon_conversion_parameters(&conversion); 00142 logImageGetByteConversionDefaults(&conversion); 00143 00144 /* 00145 * Get the drawable for the current image... 00146 */ 00147 00148 fbuf= IMB_float_profile_ensure(ibuf, conversion.doLogarithm ? IB_PROFILE_LINEAR_RGB : IB_PROFILE_NONE, &is_alloc); 00149 00150 if (fbuf == NULL) { /* in the unlikely event that converting to a float buffer fails */ 00151 return 0; 00152 } 00153 00154 logImageSetVerbose((G.f & G_DEBUG) ? 1:0); 00155 logImage = logImageCreate(filename, use_cineon, width, height, depth); 00156 00157 if (!logImage) return 0; 00158 00159 if(logImageSetByteConversion(logImage, &conversion)==0) { 00160 printf("error setting args\n"); 00161 } 00162 00163 line = MEM_mallocN(sizeof(unsigned short)*depth*width, "line"); 00164 00165 /*note that image is flipped when sent to logImageSetRowBytes (see last passed parameter).*/ 00166 for (j = 0; j < height; ++j) { 00167 fline = &fbuf[width*j*4]; 00168 for (i=0; i<width; i++) { 00169 float *fpix, fpix2[3]; 00170 /*we have to convert to cinepaint's 16-bit-per-channel here*/ 00171 pixel = &line[i*depth]; 00172 fpix = &fline[i*4]; 00173 memcpy(fpix2, fpix, sizeof(float)*3); 00174 00175 if (fpix2[0]>=1.0f) fpix2[0] = 1.0f; else if (fpix2[0]<0.0f) fpix2[0]= 0.0f; 00176 if (fpix2[1]>=1.0f) fpix2[1] = 1.0f; else if (fpix2[1]<0.0f) fpix2[1]= 0.0f; 00177 if (fpix2[2]>=1.0f) fpix2[2] = 1.0f; else if (fpix2[2]<0.0f) fpix2[2]= 0.0f; 00178 00179 pixel[0] = (unsigned short)(fpix2[0] * 65535.0f); /*float-float math is faster*/ 00180 pixel[1] = (unsigned short)(fpix2[1] * 65535.0f); 00181 pixel[2] = (unsigned short)(fpix2[2] * 65535.0f); 00182 } 00183 logImageSetRowBytes(logImage, (const unsigned short*)line, height-1-j); 00184 } 00185 logImageClose(logImage); 00186 00187 MEM_freeN(line); 00188 00189 if(is_alloc) { 00190 MEM_freeN(fbuf); 00191 } 00192 00193 return 1; 00194 } 00195 00196 int imb_savecineon(struct ImBuf *buf, const char *myfile, int flags) 00197 { 00198 return imb_save_dpx_cineon(buf, myfile, 1, flags); 00199 } 00200 00201 00202 int imb_is_cineon(unsigned char *buf) 00203 { 00204 return cineonIsMemFileCineon(buf); 00205 } 00206 00207 ImBuf *imb_loadcineon(unsigned char *mem, size_t size, int flags) 00208 { 00209 if(imb_is_cineon(mem)) 00210 return imb_load_dpx_cineon(mem, 1, size, flags); 00211 return NULL; 00212 } 00213 00214 int imb_save_dpx(struct ImBuf *buf, const char *myfile, int flags) 00215 { 00216 return imb_save_dpx_cineon(buf, myfile, 0, flags); 00217 } 00218 00219 int imb_is_dpx(unsigned char *buf) 00220 { 00221 return dpxIsMemFileCineon(buf); 00222 } 00223 00224 ImBuf *imb_loaddpx(unsigned char *mem, size_t size, int flags) 00225 { 00226 if(imb_is_dpx(mem)) 00227 return imb_load_dpx_cineon(mem, 0, size, flags); 00228 return NULL; 00229 }