diff options
author | Brecht Van Lommel <brechtvanlommel@pandora.be> | 2011-08-16 20:15:34 +0400 |
---|---|---|
committer | Brecht Van Lommel <brechtvanlommel@pandora.be> | 2011-08-16 20:15:34 +0400 |
commit | 360fcd73fe2868ba32c65697e21ed1bbab8b649a (patch) | |
tree | 29c77024343a26c0358b814e581efaf388a3030a /source/blender/imbuf | |
parent | 18387f3e3fc4e3fbb9f2cd27d49d12e56975e87c (diff) |
Cycles:
* add some (disabled) test code for using OpenImageIO in imbuf
* link cycles, openimageio and boost into blender instead of a shared library
* some cmakefile changes to simplify the code and follow conventions better
* this may solve running cycles problems on windows XP, or give a different
and hopefully more useful error message
Diffstat (limited to 'source/blender/imbuf')
-rw-r--r-- | source/blender/imbuf/CMakeLists.txt | 8 | ||||
-rw-r--r-- | source/blender/imbuf/IMB_imbuf_types.h | 12 | ||||
-rw-r--r-- | source/blender/imbuf/intern/IMB_filetype.h | 18 | ||||
-rw-r--r-- | source/blender/imbuf/intern/filetype.c | 36 | ||||
-rw-r--r-- | source/blender/imbuf/intern/openimageio.cpp | 237 | ||||
-rw-r--r-- | source/blender/imbuf/intern/readimage.c | 37 | ||||
-rw-r--r-- | source/blender/imbuf/intern/util.c | 6 | ||||
-rw-r--r-- | source/blender/imbuf/intern/writeimage.c | 2 |
8 files changed, 318 insertions, 38 deletions
diff --git a/source/blender/imbuf/CMakeLists.txt b/source/blender/imbuf/CMakeLists.txt index 18b5eff5c73..de9fb323451 100644 --- a/source/blender/imbuf/CMakeLists.txt +++ b/source/blender/imbuf/CMakeLists.txt @@ -61,6 +61,7 @@ set(SRC intern/md5.c intern/metadata.c intern/module.c + intern/openimageio.cpp intern/png.c intern/radiance_hdr.c intern/readimage.c @@ -165,4 +166,11 @@ if(WITH_IMAGE_HDR) add_definitions(-DWITH_HDR) endif() +if(WITH_OPENIMAGEIO) + list(APPEND INC_SYS + ${OPENIMAGEIO_INCLUDES} + ) + # disabled for now add_definitions(-DWITH_OPENIMAGEIO ${OPENIMAGEIO_DEFINITIONS}) +endif() + blender_add_lib(bf_imbuf "${SRC}" "${INC}" "${INC_SYS}") diff --git a/source/blender/imbuf/IMB_imbuf_types.h b/source/blender/imbuf/IMB_imbuf_types.h index f5e2bf71468..c4872f370e5 100644 --- a/source/blender/imbuf/IMB_imbuf_types.h +++ b/source/blender/imbuf/IMB_imbuf_types.h @@ -169,39 +169,27 @@ typedef struct ImBuf { #define JPG (1 << 27) #define BMP (1 << 26) -#ifdef WITH_QUICKTIME #define QUICKTIME (1 << 25) -#endif -#ifdef WITH_HDR #define RADHDR (1 << 24) -#endif -#ifdef WITH_TIFF #define TIF (1 << 23) #define TIF_16BIT (1 << 8 ) -#endif #define OPENEXR (1 << 22) #define OPENEXR_HALF (1 << 8 ) #define OPENEXR_COMPRESS (7) -#ifdef WITH_CINEON #define CINEON (1 << 21) #define DPX (1 << 20) -#endif -#ifdef WITH_DDS #define DDS (1 << 19) -#endif -#ifdef WITH_OPENJPEG #define JP2 (1 << 18) #define JP2_12BIT (1 << 17) #define JP2_16BIT (1 << 16) #define JP2_YCC (1 << 15) #define JP2_CINE (1 << 14) #define JP2_CINE_48FPS (1 << 13) -#endif #define RAWTGA (TGA | 1) diff --git a/source/blender/imbuf/intern/IMB_filetype.h b/source/blender/imbuf/intern/IMB_filetype.h index cf0d0990d33..3a7725ae706 100644 --- a/source/blender/imbuf/intern/IMB_filetype.h +++ b/source/blender/imbuf/intern/IMB_filetype.h @@ -46,6 +46,9 @@ typedef struct ImFileType { int (*save)(struct ImBuf *ibuf, const char *name, int flags); void (*load_tile)(struct ImBuf *ibuf, unsigned char *mem, size_t size, int tx, int ty, unsigned int *rect); + int (*is_a_filepath)(const char *filepath); + struct ImBuf *(*load_filepath)(const char *filepath, int flags); + int flag; int filetype; } ImFileType; @@ -121,5 +124,20 @@ void imb_loadtiletiff(struct ImBuf *ibuf, unsigned char *mem, size_t size, int imb_savetiff(struct ImBuf *ibuf, const char *name, int flags); void *libtiff_findsymbol(char *name); +/* openimageio */ +#ifdef __cplusplus +extern "C" { +#endif + +int imb_is_a_openimageio(unsigned char *buf); +int imb_is_a_filepath_openimageio(const char *filepath); +int imb_ftype_openimageio(struct ImFileType *type, struct ImBuf *ibuf); +struct ImBuf *imb_load_openimageio(const char *filepath, int flags); +int imb_save_openimageio(struct ImBuf *ibuf, const char *filepath, int flags); + +#ifdef __cplusplus +} +#endif + #endif /* IMB_FILETYPE_H */ diff --git a/source/blender/imbuf/intern/filetype.c b/source/blender/imbuf/intern/filetype.c index c5121189952..47be6f609c8 100644 --- a/source/blender/imbuf/intern/filetype.c +++ b/source/blender/imbuf/intern/filetype.c @@ -51,9 +51,6 @@ static int imb_ftype_default(ImFileType *type, ImBuf *ibuf) { return (ibuf->ftyp static int imb_ftype_cocoa(ImFileType *type, ImBuf *ibuf) { return (ibuf->ftype & TIF); } #endif static int imb_ftype_iris(ImFileType *type, ImBuf *ibuf) { (void)type; return (ibuf->ftype == IMAGIC); } -#ifdef WITH_QUICKTIME -static int imb_ftype_quicktime(ImFileType *type, ImBuf *ibuf) { return 0; } // XXX -#endif #ifdef WITH_QUICKTIME void quicktime_init(void); @@ -61,36 +58,39 @@ void quicktime_exit(void); #endif ImFileType IMB_FILE_TYPES[]= { - {NULL, NULL, imb_is_a_jpeg, imb_ftype_default, imb_load_jpeg, imb_savejpeg, NULL, 0, JPG}, - {NULL, NULL, imb_is_a_png, imb_ftype_default, imb_loadpng, imb_savepng, NULL, 0, PNG}, - {NULL, NULL, imb_is_a_bmp, imb_ftype_default, imb_bmp_decode, imb_savebmp, NULL, 0, BMP}, - {NULL, NULL, imb_is_a_targa, imb_ftype_default, imb_loadtarga, imb_savetarga, NULL, 0, TGA}, - {NULL, NULL, imb_is_a_iris, imb_ftype_iris, imb_loadiris, imb_saveiris, NULL, 0, IMAGIC}, +#ifdef WITH_OPENIMAGEIO + {NULL, NULL, imb_is_a_openimageio, imb_ftype_openimageio, NULL, imb_save_openimageio, NULL, imb_is_a_filepath_openimageio, imb_load_openimageio, 0, 0}, +#endif + {NULL, NULL, imb_is_a_jpeg, imb_ftype_default, imb_load_jpeg, imb_savejpeg, NULL, NULL, NULL, 0, JPG}, + {NULL, NULL, imb_is_a_png, imb_ftype_default, imb_loadpng, imb_savepng, NULL, NULL, NULL, 0, PNG}, + {NULL, NULL, imb_is_a_bmp, imb_ftype_default, imb_bmp_decode, imb_savebmp, NULL, NULL, NULL, 0, BMP}, + {NULL, NULL, imb_is_a_targa, imb_ftype_default, imb_loadtarga, imb_savetarga, NULL, NULL, NULL, 0, TGA}, + {NULL, NULL, imb_is_a_iris, imb_ftype_iris, imb_loadiris, imb_saveiris, NULL, NULL, NULL, 0, IMAGIC}, #ifdef WITH_CINEON - {NULL, NULL, imb_is_dpx, imb_ftype_default, imb_loaddpx, imb_save_dpx, NULL, IM_FTYPE_FLOAT, DPX}, - {NULL, NULL, imb_is_cineon, imb_ftype_default, imb_loadcineon, imb_savecineon, NULL, IM_FTYPE_FLOAT, CINEON}, + {NULL, NULL, imb_is_dpx, imb_ftype_default, imb_loaddpx, imb_save_dpx, NULL, NULL, NULL, IM_FTYPE_FLOAT, DPX}, + {NULL, NULL, imb_is_cineon, imb_ftype_default, imb_loadcineon, imb_savecineon, NULL, NULL, NULL, IM_FTYPE_FLOAT, CINEON}, #endif #ifdef WITH_TIFF - {imb_inittiff, NULL, imb_is_a_tiff, imb_ftype_default, imb_loadtiff, imb_savetiff, imb_loadtiletiff, 0, TIF}, + {imb_inittiff, NULL, imb_is_a_tiff, imb_ftype_default, imb_loadtiff, imb_savetiff, imb_loadtiletiff, NULL, NULL, 0, TIF}, #elif defined(__APPLE__) && defined(IMBUF_COCOA) - {NULL, NULL, imb_is_a_cocoa, imb_ftype_cocoa, imb_imb_cocoaLoadImage, imb_savecocoa, NULL, 0, TIF}, + {NULL, NULL, imb_is_a_cocoa, imb_ftype_cocoa, imb_imb_cocoaLoadImage, imb_savecocoa, NULL, NULL, NULL, 0, TIF}, #endif #ifdef WITH_HDR - {NULL, NULL, imb_is_a_hdr, imb_ftype_default, imb_loadhdr, imb_savehdr, NULL, IM_FTYPE_FLOAT, RADHDR}, + {NULL, NULL, imb_is_a_hdr, imb_ftype_default, imb_loadhdr, imb_savehdr, NULL, NULL, NULL, IM_FTYPE_FLOAT, RADHDR}, #endif #ifdef WITH_OPENEXR - {NULL, NULL, imb_is_a_openexr, imb_ftype_default, imb_load_openexr, imb_save_openexr, NULL, IM_FTYPE_FLOAT, OPENEXR}, + {NULL, NULL, imb_is_a_openexr, imb_ftype_default, imb_load_openexr, imb_save_openexr, NULL, NULL, NULL, IM_FTYPE_FLOAT, OPENEXR}, #endif #ifdef WITH_OPENJPEG - {NULL, NULL, imb_is_a_jp2, imb_ftype_default, imb_jp2_decode, imb_savejp2, NULL, IM_FTYPE_FLOAT, JP2}, + {NULL, NULL, imb_is_a_jp2, imb_ftype_default, imb_jp2_decode, imb_savejp2, NULL, NULL, NULL, IM_FTYPE_FLOAT, JP2}, #endif #ifdef WITH_DDS - {NULL, NULL, imb_is_a_dds, imb_ftype_default, imb_load_dds, NULL, NULL, 0, DDS}, + {NULL, NULL, imb_is_a_dds, imb_ftype_default, imb_load_dds, NULL, NULL, NULL, NULL, 0, DDS}, #endif #ifdef WITH_QUICKTIME - {quicktime_init, quicktime_exit, imb_is_a_quicktime, imb_ftype_quicktime, imb_quicktime_decode, NULL, NULL, 0, QUICKTIME}, + {quicktime_init, quicktime_exit, imb_is_a_quicktime, NULL, imb_quicktime_decode, NULL, NULL, NULL, 0, QUICKTIME}, #endif - {NULL, NULL, NULL, NULL, NULL, NULL, NULL, 0}}; + {NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, 0}}; void imb_filetypes_init(void) { diff --git a/source/blender/imbuf/intern/openimageio.cpp b/source/blender/imbuf/intern/openimageio.cpp new file mode 100644 index 00000000000..2e5dd5b6613 --- /dev/null +++ b/source/blender/imbuf/intern/openimageio.cpp @@ -0,0 +1,237 @@ +/* + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program 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 General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + * $Id: png.c 36777 2011-05-19 11:54:03Z blendix $ + */ + +/** \file blender/imbuf/intern/png.c + * \ingroup imbuf + */ + +#ifdef WITH_OPENIMAGEIO + +#include "MEM_sys_types.h" + +#include "imbuf.h" + +extern "C" { + +#include "IMB_imbuf_types.h" +#include "IMB_imbuf.h" + +#include "IMB_allocimbuf.h" +#include "IMB_metadata.h" +#include "IMB_filetype.h" + +} + +#include <OpenImageIO/imageio.h> + +OIIO_NAMESPACE_USING + +int imb_is_a_openimageio(unsigned char *buf) +{ + return 0; +} + +int imb_is_a_filepath_openimageio(const char *filepath) +{ + ImageInput *in = ImageInput::create(filepath); + ImageSpec spec; + int recognized = in->open(filepath, spec); + in->close(); + + return recognized; +} + +template<typename T> static void pack_pixels(T *pixels, int width, int height, int components, T alpha) +{ + if(components == 3) { + for(int i = width*height-1; i >= 0; i--) { + pixels[i*4+3] = alpha; + pixels[i*4+2] = pixels[i*3+2]; + pixels[i*4+1] = pixels[i*3+1]; + pixels[i*4+0] = pixels[i*3+0]; + } + } + else if(components == 1) { + for(int i = width*height-1; i >= 0; i--) { + pixels[i*4+3] = alpha; + pixels[i*4+2] = pixels[i]; + pixels[i*4+1] = pixels[i]; + pixels[i*4+0] = pixels[i]; + } + } +} + +int imb_ftype_openimageio(ImFileType *type, ImBuf *ibuf) +{ + return ibuf->ftype & (PNG|TGA|JPG|BMP|RADHDR|TIF|OPENEXR|CINEON|DPX|DDS|JP2); +} + +static int format_name_to_ftype(const char *format_name) +{ + if(strcmp(format_name, "png") == 0) + return PNG; + else if(strcmp(format_name, "targa") == 0) + return TGA; /* RAWTGA */ + else if(strcmp(format_name, "jpeg") == 0) + return JPG; + else if(strcmp(format_name, "bmp") == 0) + return BMP; + else if(strcmp(format_name, "hdr") == 0) + return RADHDR; + else if(strcmp(format_name, "tiff") == 0) + return TIF; /* TIF_16BIT */ + else if(strcmp(format_name, "openexr") == 0) + return OPENEXR; /* OPENEXR_HALF, OPENEXR_COMPRESS */ + else if(strcmp(format_name, "cineon") == 0) + return CINEON; + else if(strcmp(format_name, "dpx") == 0) + return DPX; + else if(strcmp(format_name, "dds") == 0) + return DDS; + else if(strcmp(format_name, "jpeg2000") == 0) + return JP2; /* JP2_12BIT, JP2_16BIT, JP2_YCC , JP2_CINE , JP2_CINE_48FPS */ + + /* not handled: "field3d", "fits", "ico", "iff", "pnm", "ptex", "sgi", "zfile" */ + + return 0; +} + +ImBuf *imb_load_openimageio(const char *filepath, int flags) +{ + ImageInput *in = ImageInput::create(filepath); + ImageSpec spec; + bool success; + + if(!in->open(filepath, spec)) { + delete in; + return NULL; + } + + /* we only handle certain number of components */ + int width = spec.width; + int height = spec.height; + int components = spec.nchannels; + + if(!(components == 1 || components == 3 || components == 4)) { + delete in; + return NULL; + } + + ImBuf *ibuf = IMB_allocImBuf(width, height, 32, 0); + ibuf->ftype = format_name_to_ftype(in->format_name()); + + /* TODO: handle oiio:ColorSpace, oiio:Gamma, metadata, multilayer, size_t_safe */ + + /* read RGBA pixels */ + if(spec.format == TypeDesc::UINT8 || spec.format == TypeDesc::INT8) { + //if(in->get_string_attribute("oiio:ColorSpace") == "sRGB") + ibuf->profile = IB_PROFILE_SRGB; + + imb_addrectImBuf(ibuf); + + uint8_t *pixels = (uint8_t*)ibuf->rect; + int scanlinesize = width*components; + + success = in->read_image(TypeDesc::UINT8, + pixels + (height-1)*scanlinesize, + AutoStride, + -scanlinesize*sizeof(uint8_t), + AutoStride); + + pack_pixels<uint8_t>(pixels, width, height, components, 255); + } + else { + ibuf->profile = IB_PROFILE_LINEAR_RGB; /* XXX assumption */ + + imb_addrectfloatImBuf(ibuf); + + float *pixels = ibuf->rect_float; + int scanlinesize = width*components; + + success = in->read_image(TypeDesc::FLOAT, + pixels + (height-1)*scanlinesize, + AutoStride, + -scanlinesize*sizeof(float), + AutoStride); + + pack_pixels<float>(pixels, width, height, components, 1.0f); + } + + if(!success) + fprintf(stderr, "OpenImageIO: error loading image: %s\n", in->geterror().c_str()); + + in->close(); + delete in; + + return ibuf; +} + +int imb_save_openimageio(struct ImBuf *ibuf, const char *filepath, int flags) +{ + ImageOutput *out = ImageOutput::create(filepath); + + if(ibuf->rect_float) { + /* XXX profile */ + + /* save as float image XXX works? */ + ImageSpec spec(ibuf->x, ibuf->y, 4, TypeDesc::FLOAT); + int scanlinesize = ibuf->x*4; + + out->open(filepath, spec); + + /* conversion for different top/bottom convention */ + out->write_image(TypeDesc::FLOAT, + ibuf->rect_float + (ibuf->y-1)*scanlinesize, + AutoStride, + -scanlinesize*sizeof(float), + AutoStride); + } + else { + /* save as 8bit image */ + ImageSpec spec(ibuf->x, ibuf->y, 4, TypeDesc::UINT8); + int scanlinesize = ibuf->x*4; + + out->open(filepath, spec); + + /* conversion for different top/bottom convention */ + out->write_image(TypeDesc::UINT8, + (uint8_t*)ibuf->rect + (ibuf->y-1)*scanlinesize, + AutoStride, + -scanlinesize*sizeof(uint8_t), + AutoStride); + } + + out->close(); + delete out; + + return 1; +} + +#endif /* WITH_OPENIMAGEIO */ + diff --git a/source/blender/imbuf/intern/readimage.c b/source/blender/imbuf/intern/readimage.c index 849b3ff0ce2..dac7e91fec6 100644 --- a/source/blender/imbuf/intern/readimage.c +++ b/source/blender/imbuf/intern/readimage.c @@ -51,6 +51,28 @@ #include "IMB_imbuf.h" #include "IMB_filetype.h" +static ImBuf *imb_ibImageFromFile(const char *filepath, int flags) +{ + ImBuf *ibuf; + ImFileType *type; + + for(type=IMB_FILE_TYPES; type->is_a; type++) { + if(type->load_filepath) { + ibuf= type->load_filepath(filepath, flags); + if(ibuf) { + if(flags & IB_premul) { + IMB_premultiply_alpha(ibuf); + ibuf->flags |= IB_premul; + } + + return ibuf; + } + } + } + + return NULL; +} + ImBuf *IMB_ibImageFromMemory(unsigned char *mem, size_t size, int flags) { ImBuf *ibuf; @@ -127,10 +149,15 @@ ImBuf *IMB_loadiffname(const char *name, int flags) imb_cache_filename(filename, name, flags); - file = open(filename, O_BINARY|O_RDONLY); - if(file < 0) return NULL; + ibuf= imb_ibImageFromFile(name, flags); + + if(!ibuf) { + file = open(filename, O_BINARY|O_RDONLY); + if(file < 0) return NULL; - ibuf= IMB_loadifffile(file, flags); + ibuf= IMB_loadifffile(file, flags); + close(file); + } if(ibuf) { BLI_strncpy(ibuf->name, name, sizeof(ibuf->name)); @@ -140,8 +167,6 @@ ImBuf *IMB_loadiffname(const char *name, int flags) if(flags & IB_fields) IMB_de_interlace(ibuf); } - close(file); - return ibuf; } @@ -184,7 +209,7 @@ static void imb_loadtilefile(ImBuf *ibuf, int file, int tx, int ty, unsigned int } for(type=IMB_FILE_TYPES; type->is_a; type++) - if(type->load_tile && type->ftype(type, ibuf)) + if(type->load_tile && type->ftype && type->ftype(type, ibuf)) type->load_tile(ibuf, mem, size, tx, ty, rect); if(munmap(mem, size)) diff --git a/source/blender/imbuf/intern/util.c b/source/blender/imbuf/intern/util.c index 6db8dcc06cf..f548d8eda92 100644 --- a/source/blender/imbuf/intern/util.c +++ b/source/blender/imbuf/intern/util.c @@ -155,6 +155,10 @@ static int IMB_ispic_name(const char *name) int fp, buf[10]; if(UTIL_DEBUG) printf("IMB_ispic_name: loading %s\n", name); + + /*for(type=IMB_FILE_TYPES; type->is_a; type++) + if(type->is_a_filepath && type->is_a_filepath(name)) + return type->filetype;*/ if(stat(name,&st) == -1) return FALSE; @@ -176,7 +180,7 @@ static int IMB_ispic_name(const char *name) return JPG; for(type=IMB_FILE_TYPES; type->is_a; type++) - if(type->is_a((uchar*)buf)) + if(type->is_a && type->is_a((uchar*)buf)) return type->filetype; return FALSE; diff --git a/source/blender/imbuf/intern/writeimage.c b/source/blender/imbuf/intern/writeimage.c index cd660e11f26..96e6df6d758 100644 --- a/source/blender/imbuf/intern/writeimage.c +++ b/source/blender/imbuf/intern/writeimage.c @@ -50,7 +50,7 @@ short IMB_saveiff(struct ImBuf *ibuf, const char *name, int flags) ibuf->flags = flags; for(type=IMB_FILE_TYPES; type->is_a; type++) { - if(type->save && type->ftype(type, ibuf)) { + if(type->save && type->ftype && type->ftype(type, ibuf)) { if(!(type->flag & IM_FTYPE_FLOAT)) { if(ibuf->rect==NULL && ibuf->rect_float) IMB_rect_from_float(ibuf); |