<s> import ctypes <EOL> import numpy <EOL> import sys <EOL> import os <EOL> import os . path <EOL> from numpy . compat import asbytes , asstr <EOL> def _generate_candidate_libs ( ) : <EOL> lib_dirs = [ os . path . dirname ( __file__ ) , <EOL> '<STR_LIT>' , <EOL> '<STR_LIT>' , <EOL> '<STR_LIT>' , <EOL> '<STR_LIT>' , <EOL> os . path . join ( sys . prefix , '<STR_LIT>' ) , <EOL> os . path . join ( sys . prefix , '<STR_LIT>' ) <EOL> ] <EOL> if '<STR_LIT>' in os . environ : <EOL> lib_dirs . append ( os . path . join ( os . environ [ '<STR_LIT>' ] , '<STR_LIT>' ) ) <EOL> lib_dirs = [ ld for ld in lib_dirs if os . path . exists ( ld ) ] <EOL> lib_names = [ '<STR_LIT>' , '<STR_LIT>' ] <EOL> lib_paths = [ ] <EOL> for lib_dir in lib_dirs : <EOL> for lib_name in lib_names : <EOL> files = os . listdir ( lib_dir ) <EOL> lib_paths += [ os . path . join ( lib_dir , lib ) for lib in files <EOL> if lib . lower ( ) . startswith ( lib_name ) and not <EOL> os . path . splitext ( lib ) [ <NUM_LIT:1> ] in ( '<STR_LIT>' , '<STR_LIT>' , '<STR_LIT>' ) ] <EOL> lib_paths = [ lp for lp in lib_paths if os . path . exists ( lp ) ] <EOL> return lib_dirs , lib_paths <EOL> if sys . platform == '<STR_LIT:win32>' : <EOL> LOADER = ctypes . windll <EOL> FUNCTYPE = ctypes . WINFUNCTYPE <EOL> else : <EOL> LOADER = ctypes . cdll <EOL> FUNCTYPE = ctypes . CFUNCTYPE <EOL> def handle_errors ( ) : <EOL> global FT_ERROR_STR <EOL> if FT_ERROR_STR : <EOL> tmp = FT_ERROR_STR <EOL> FT_ERROR_STR = None <EOL> raise RuntimeError ( tmp ) <EOL> FT_ERROR_STR = None <EOL> @ FUNCTYPE ( None , ctypes . c_int , ctypes . c_char_p ) <EOL> def c_error_handler ( fif , message ) : <EOL> global FT_ERROR_STR <EOL> FT_ERROR_STR = '<STR_LIT>' % message <EOL> def load_freeimage ( ) : <EOL> freeimage = None <EOL> errors = [ ] <EOL> bare_libs = [ '<STR_LIT>' , '<STR_LIT>' , '<STR_LIT>' , <EOL> '<STR_LIT>' ] <EOL> lib_dirs , lib_paths = _generate_candidate_libs ( ) <EOL> lib_paths = bare_libs + lib_paths <EOL> for lib in lib_paths : <EOL> try : <EOL> freeimage = LOADER . LoadLibrary ( lib ) <EOL> break <EOL> except Exception : <EOL> if lib not in bare_libs : <EOL> e_type , e_value , e_tb = sys . exc_info ( ) <EOL> del e_tb <EOL> errors . append ( ( lib , e_value ) ) <EOL> if freeimage is None : <EOL> if errors : <EOL> err_txt = [ '<STR_LIT>' % ( l , str ( e ) ) for l , e in errors ] <EOL> raise RuntimeError ( '<STR_LIT>' <EOL> '<STR_LIT>' <EOL> '<STR_LIT>' . join ( err_txt ) ) <EOL> else : <EOL> raise RuntimeError ( '<STR_LIT>' <EOL> '<STR_LIT>' . join ( lib_dirs ) ) <EOL> freeimage . FreeImage_SetOutputMessage ( c_error_handler ) <EOL> return freeimage <EOL> _FI = load_freeimage ( ) <EOL> API = { <EOL> '<STR_LIT>' : ( ctypes . c_void_p , None ) , <EOL> '<STR_LIT>' : ( ctypes . c_void_p , None ) , <EOL> '<STR_LIT>' : ( ctypes . c_void_p , None ) , <EOL> '<STR_LIT>' : ( ctypes . c_void_p , None ) , <EOL> '<STR_LIT>' : ( ctypes . c_char_p , None ) , <EOL> '<STR_LIT>' : ( ctypes . c_void_p , None ) , <EOL> '<STR_LIT>' : ( ctypes . c_void_p , None ) , <EOL> '<STR_LIT>' : ( ctypes . c_void_p , None ) , <EOL> '<STR_LIT>' : ( ctypes . c_void_p , None ) <EOL> } <EOL> def register_api ( lib , api ) : <EOL> for f , ( restype , argtypes ) in api . items ( ) : <EOL> func = getattr ( lib , f ) <EOL> func . restype = restype <EOL> func . argtypes = argtypes <EOL> register_api ( _FI , API ) <EOL> class FiTypes ( object ) : <EOL> FIT_UNKNOWN = <NUM_LIT:0> <EOL> FIT_BITMAP = <NUM_LIT:1> <EOL> FIT_UINT16 = <NUM_LIT:2> <EOL> FIT_INT16 = <NUM_LIT:3> <EOL> FIT_UINT32 = <NUM_LIT:4> <EOL> FIT_INT32 = <NUM_LIT:5> <EOL> FIT_FLOAT = <NUM_LIT:6> <EOL> FIT_DOUBLE = <NUM_LIT:7> <EOL> FIT_COMPLEX = <NUM_LIT:8> <EOL> FIT_RGB16 = <NUM_LIT:9> <EOL> FIT_RGBA16 = <NUM_LIT:10> <EOL> FIT_RGBF = <NUM_LIT:11> <EOL> FIT_RGBAF = <NUM_LIT:12> <EOL> dtypes = { FIT_BITMAP : numpy . uint8 , <EOL> FIT_UINT16 : numpy . uint16 , <EOL> FIT_INT16 : numpy . int16 , <EOL> FIT_UINT32 : numpy . uint32 , <EOL> FIT_INT32 : numpy . int32 , <EOL> FIT_FLOAT : numpy . float32 , <EOL> FIT_DOUBLE : numpy . float64 , <EOL> FIT_COMPLEX : numpy . complex128 , <EOL> FIT_RGB16 : numpy . uint16 , <EOL> FIT_RGBA16 : numpy . uint16 , <EOL> FIT_RGBF : numpy . float32 , <EOL> FIT_RGBAF : numpy . float32 , <EOL> } <EOL> fi_types = { ( numpy . dtype ( '<STR_LIT>' ) , <NUM_LIT:1> ) : FIT_BITMAP , <EOL> ( numpy . dtype ( '<STR_LIT>' ) , <NUM_LIT:3> ) : FIT_BITMAP , <EOL> ( numpy . dtype ( '<STR_LIT>' ) , <NUM_LIT:4> ) : FIT_BITMAP , <EOL> ( numpy . dtype ( '<STR_LIT>' ) , <NUM_LIT:1> ) : FIT_UINT16 , <EOL> ( numpy . dtype ( '<STR_LIT>' ) , <NUM_LIT:1> ) : FIT_INT16 , <EOL> ( numpy . dtype ( '<STR_LIT>' ) , <NUM_LIT:1> ) : FIT_UINT32 , <EOL> ( numpy . dtype ( '<STR_LIT>' ) , <NUM_LIT:1> ) : FIT_INT32 , <EOL> ( numpy . dtype ( '<STR_LIT>' ) , <NUM_LIT:1> ) : FIT_FLOAT , <EOL> ( numpy . dtype ( '<STR_LIT>' ) , <NUM_LIT:1> ) : FIT_DOUBLE , <EOL> ( numpy . dtype ( '<STR_LIT>' ) , <NUM_LIT:1> ) : FIT_COMPLEX , <EOL> ( numpy . dtype ( '<STR_LIT>' ) , <NUM_LIT:3> ) : FIT_RGB16 , <EOL> ( numpy . dtype ( '<STR_LIT>' ) , <NUM_LIT:4> ) : FIT_RGBA16 , <EOL> ( numpy . dtype ( '<STR_LIT>' ) , <NUM_LIT:3> ) : FIT_RGBF , <EOL> ( numpy . dtype ( '<STR_LIT>' ) , <NUM_LIT:4> ) : FIT_RGBAF , <EOL> } <EOL> extra_dims = { FIT_UINT16 : [ ] , <EOL> FIT_INT16 : [ ] , <EOL> FIT_UINT32 : [ ] , <EOL> FIT_INT32 : [ ] , <EOL> FIT_FLOAT : [ ] , <EOL> FIT_DOUBLE : [ ] , <EOL> FIT_COMPLEX : [ ] , <EOL> FIT_RGB16 : [ <NUM_LIT:3> ] , <EOL> FIT_RGBA16 : [ <NUM_LIT:4> ] , <EOL> FIT_RGBF : [ <NUM_LIT:3> ] , <EOL> FIT_RGBAF : [ <NUM_LIT:4> ] , <EOL> } <EOL> @ classmethod <EOL> def get_type_and_shape ( cls , bitmap ) : <EOL> w = _FI . FreeImage_GetWidth ( bitmap ) <EOL> handle_errors ( ) <EOL> h = _FI . FreeImage_GetHeight ( bitmap ) <EOL> handle_errors ( ) <EOL> fi_type = _FI . FreeImage_GetImageType ( bitmap ) <EOL> handle_errors ( ) <EOL> if not fi_type : <EOL> raise ValueError ( '<STR_LIT>' ) <EOL> dtype = cls . dtypes [ fi_type ] <EOL> if fi_type == cls . FIT_BITMAP : <EOL> bpp = _FI . FreeImage_GetBPP ( bitmap ) <EOL> handle_errors ( ) <EOL> if bpp == <NUM_LIT:8> : <EOL> extra_dims = [ ] <EOL> elif bpp == <NUM_LIT> : <EOL> extra_dims = [ <NUM_LIT:3> ] <EOL> elif bpp == <NUM_LIT:32> : <EOL> extra_dims = [ <NUM_LIT:4> ] <EOL> else : <EOL> raise ValueError ( '<STR_LIT>' % bpp ) <EOL> else : <EOL> extra_dims = cls . extra_dims [ fi_type ] <EOL> return numpy . dtype ( dtype ) , extra_dims + [ w , h ] <EOL> class IoFlags ( object ) : <EOL> FIF_LOAD_NOPIXELS = <NUM_LIT> <EOL> BMP_DEFAULT = <NUM_LIT:0> <EOL> BMP_SAVE_RLE = <NUM_LIT:1> <EOL> CUT_DEFAULT = <NUM_LIT:0> <EOL> DDS_DEFAULT = <NUM_LIT:0> <EOL> EXR_DEFAULT = <NUM_LIT:0> <EOL> EXR_FLOAT = <NUM_LIT> <EOL> EXR_NONE = <NUM_LIT> <EOL> EXR_ZIP = <NUM_LIT> <EOL> EXR_PIZ = <NUM_LIT> <EOL> EXR_PXR24 = <NUM_LIT> <EOL> EXR_B44 = <NUM_LIT> <EOL> EXR_LC = <NUM_LIT> <EOL> FAXG3_DEFAULT = <NUM_LIT:0> <EOL> GIF_DEFAULT = <NUM_LIT:0> <EOL> GIF_LOAD256 = <NUM_LIT:1> <EOL> GIF_PLAYBACK = <NUM_LIT:2> <EOL> HDR_DEFAULT = <NUM_LIT:0> <EOL> ICO_DEFAULT = <NUM_LIT:0> <EOL> ICO_MAKEALPHA = <NUM_LIT:1> <EOL> IFF_DEFAULT = <NUM_LIT:0> <EOL> J2K_DEFAULT = <NUM_LIT:0> <EOL> JP2_DEFAULT = <NUM_LIT:0> <EOL> JPEG_DEFAULT = <NUM_LIT:0> <EOL> JPEG_FAST = <NUM_LIT> <EOL> JPEG_ACCURATE = <NUM_LIT> <EOL> JPEG_CMYK = <NUM_LIT> <EOL> JPEG_EXIFROTATE = <NUM_LIT> <EOL> JPEG_QUALITYSUPERB = <NUM_LIT> <EOL> JPEG_QUALITYGOOD = <NUM_LIT> <EOL> JPEG_QUALITYNORMAL = <NUM_LIT> <EOL> JPEG_QUALITYAVERAGE = <NUM_LIT> <EOL> JPEG_QUALITYBAD = <NUM_LIT> <EOL> JPEG_PROGRESSIVE = <NUM_LIT> <EOL> JPEG_SUBSAMPLING_411 = <NUM_LIT> <EOL> JPEG_SUBSAMPLING_420 = <NUM_LIT> <EOL> JPEG_SUBSAMPLING_422 = <NUM_LIT> <EOL> JPEG_SUBSAMPLING_444 = <NUM_LIT> <EOL> JPEG_OPTIMIZE = <NUM_LIT> <EOL> JPEG_BASELINE = <NUM_LIT> <EOL> KOALA_DEFAULT = <NUM_LIT:0> <EOL> LBM_DEFAULT = <NUM_LIT:0> <EOL> MNG_DEFAULT = <NUM_LIT:0> <EOL> PCD_DEFAULT = <NUM_LIT:0> <EOL> PCD_BASE = <NUM_LIT:1> <EOL> PCD_BASEDIV4 = <NUM_LIT:2> <EOL> PCD_BASEDIV16 = <NUM_LIT:3> <EOL> PCX_DEFAULT = <NUM_LIT:0> <EOL> PFM_DEFAULT = <NUM_LIT:0> <EOL> PICT_DEFAULT = <NUM_LIT:0> <EOL> PNG_DEFAULT = <NUM_LIT:0> <EOL> PNG_IGNOREGAMMA = <NUM_LIT:1> <EOL> PNG_Z_BEST_SPEED = <NUM_LIT> <EOL> PNG_Z_DEFAULT_COMPRESSION = <NUM_LIT> <EOL> PNG_Z_BEST_COMPRESSION = <NUM_LIT> <EOL> PNG_Z_NO_COMPRESSION = <NUM_LIT> <EOL> PNG_INTERLACED = <NUM_LIT> <EOL> PNM_DEFAULT = <NUM_LIT:0> <EOL> PNM_SAVE_RAW = <NUM_LIT:0> <EOL> PNM_SAVE_ASCII = <NUM_LIT:1> <EOL> PSD_DEFAULT = <NUM_LIT:0> <EOL> PSD_CMYK = <NUM_LIT:1> <EOL> PSD_LAB = <NUM_LIT:2> <EOL> RAS_DEFAULT = <NUM_LIT:0> <EOL> RAW_DEFAULT = <NUM_LIT:0> <EOL> RAW_PREVIEW = <NUM_LIT:1> <EOL> RAW_DISPLAY = <NUM_LIT:2> <EOL> SGI_DEFAULT = <NUM_LIT:0> <EOL> TARGA_DEFAULT = <NUM_LIT:0> <EOL> TARGA_LOAD_RGB888 = <NUM_LIT:1> <EOL> TARGA_SAVE_RLE = <NUM_LIT:2> <EOL> TIFF_DEFAULT = <NUM_LIT:0> <EOL> TIFF_CMYK = <NUM_LIT> <EOL> TIFF_PACKBITS = <NUM_LIT> <EOL> TIFF_DEFLATE = <NUM_LIT> <EOL> TIFF_ADOBE_DEFLATE = <NUM_LIT> <EOL> TIFF_NONE = <NUM_LIT> <EOL> TIFF_CCITTFAX3 = <NUM_LIT> <EOL> TIFF_CCITTFAX4 = <NUM_LIT> <EOL> TIFF_LZW = <NUM_LIT> <EOL> TIFF_JPEG = <NUM_LIT> <EOL> TIFF_LOGLUV = <NUM_LIT> <EOL> WBMP_DEFAULT = <NUM_LIT:0> <EOL> XBM_DEFAULT = <NUM_LIT:0> <EOL> XPM_DEFAULT = <NUM_LIT:0> <EOL> class MetadataModels ( object ) : <EOL> FIMD_COMMENTS = <NUM_LIT:0> <EOL> FIMD_EXIF_MAIN = <NUM_LIT:1> <EOL> FIMD_EXIF_EXIF = <NUM_LIT:2> <EOL> FIMD_EXIF_GPS = <NUM_LIT:3> <EOL> FIMD_EXIF_MAKERNOTE = <NUM_LIT:4> <EOL> FIMD_EXIF_INTEROP = <NUM_LIT:5> <EOL> FIMD_IPTC = <NUM_LIT:6> <EOL> FIMD_XMP = <NUM_LIT:7> <EOL> FIMD_GEOTIFF = <NUM_LIT:8> <EOL> FIMD_ANIMATION = <NUM_LIT:9> <EOL> class MetadataDatatype ( object ) : <EOL> FIDT_BYTE = <NUM_LIT:1> <EOL> FIDT_ASCII = <NUM_LIT:2> <EOL> FIDT_SHORT = <NUM_LIT:3> <EOL> FIDT_LONG = <NUM_LIT:4> <EOL> FIDT_RATIONAL = <NUM_LIT:5> <EOL> FIDT_SBYTE = <NUM_LIT:6> <EOL> FIDT_UNDEFINED = <NUM_LIT:7> <EOL> FIDT_SSHORT = <NUM_LIT:8> <EOL> FIDT_SLONG = <NUM_LIT:9> <EOL> FIDT_SRATIONAL = <NUM_LIT:10> <EOL> FIDT_FLOAT = <NUM_LIT:11> <EOL> FIDT_DOUBLE = <NUM_LIT:12> <EOL> FIDT_IFD = <NUM_LIT> <EOL> FIDT_PALETTE = <NUM_LIT> <EOL> FIDT_LONG8 = <NUM_LIT:16> <EOL> FIDT_SLONG8 = <NUM_LIT> <EOL> FIDT_IFD8 = <NUM_LIT> <EOL> dtypes = { FIDT_BYTE : numpy . uint8 , <EOL> FIDT_SHORT : numpy . uint16 , <EOL> FIDT_LONG : numpy . uint32 , <EOL> FIDT_RATIONAL : [ ( '<STR_LIT>' , numpy . uint32 ) , <EOL> ( '<STR_LIT>' , numpy . uint32 ) ] , <EOL> FIDT_SBYTE : numpy . int8 , <EOL> FIDT_UNDEFINED : numpy . uint8 , <EOL> FIDT_SSHORT : numpy . int16 , <EOL> FIDT_SLONG : numpy . int32 , <EOL> FIDT_SRATIONAL : [ ( '<STR_LIT>' , numpy . int32 ) , <EOL> ( '<STR_LIT>' , numpy . int32 ) ] , <EOL> FIDT_FLOAT : numpy . float32 , <EOL> FIDT_DOUBLE : numpy . float64 , <EOL> FIDT_IFD : numpy . uint32 , <EOL> FIDT_PALETTE : [ ( '<STR_LIT:R>' , numpy . uint8 ) , ( '<STR_LIT>' , numpy . uint8 ) , <EOL> ( '<STR_LIT:B>' , numpy . uint8 ) , ( '<STR_LIT:A>' , numpy . uint8 ) ] , <EOL> FIDT_LONG8 : numpy . uint64 , <EOL> FIDT_SLONG8 : numpy . int64 , <EOL> FIDT_IFD8 : numpy . uint64 , <EOL> } <EOL> def _process_bitmap ( filename , flags , process_func ) : <EOL> filename = asbytes ( filename ) <EOL> ftype = _FI . FreeImage_GetFileType ( filename , <NUM_LIT:0> ) <EOL> handle_errors ( ) <EOL> if ftype == - <NUM_LIT:1> : <EOL> raise ValueError ( '<STR_LIT>' % filename ) <EOL> bitmap = _FI . FreeImage_Load ( ftype , filename , flags ) <EOL> handle_errors ( ) <EOL> bitmap = ctypes . c_void_p ( bitmap ) <EOL> if not bitmap : <EOL> raise ValueError ( '<STR_LIT>' % filename ) <EOL> try : <EOL> return process_func ( bitmap ) <EOL> finally : <EOL> _FI . FreeImage_Unload ( bitmap ) <EOL> handle_errors ( ) <EOL> def read ( filename , flags = <NUM_LIT:0> ) : <EOL> """<STR_LIT>""" <EOL> return _process_bitmap ( filename , flags , _array_from_bitmap ) <EOL> def read_metadata ( filename ) : <EOL> """<STR_LIT>""" <EOL> flags = IoFlags . FIF_LOAD_NOPIXELS <EOL> return _process_bitmap ( filename , flags , _read_metadata ) <EOL> def _process_multipage ( filename , flags , process_func ) : <EOL> filename = asbytes ( filename ) <EOL> ftype = _FI . FreeImage_GetFileType ( filename , <NUM_LIT:0> ) <EOL> handle_errors ( ) <EOL> if ftype == - <NUM_LIT:1> : <EOL> raise ValueError ( '<STR_LIT>' % filename ) <EOL> create_new = False <EOL> read_only = True <EOL> keep_cache_in_memory = True <EOL> multibitmap = _FI . FreeImage_OpenMultiBitmap ( <EOL> ftype , filename , create_new , read_only , keep_cache_in_memory , flags ) <EOL> handle_errors ( ) <EOL> multibitmap = ctypes . c_void_p ( multibitmap ) <EOL> if not multibitmap : <EOL> raise ValueError ( '<STR_LIT>' % filename ) <EOL> try : <EOL> pages = _FI . FreeImage_GetPageCount ( multibitmap ) <EOL> handle_errors ( ) <EOL> out = [ ] <EOL> for i in range ( pages ) : <EOL> bitmap = _FI . FreeImage_LockPage ( multibitmap , i ) <EOL> handle_errors ( ) <EOL> bitmap = ctypes . c_void_p ( bitmap ) <EOL> if not bitmap : <EOL> raise ValueError ( '<STR_LIT>' <EOL> % filename ) <EOL> try : <EOL> out . append ( process_func ( bitmap ) ) <EOL> finally : <EOL> _FI . FreeImage_UnlockPage ( multibitmap , bitmap , False ) <EOL> handle_errors ( ) <EOL> return out <EOL> finally : <EOL> _FI . FreeImage_CloseMultiBitmap ( multibitmap , <NUM_LIT:0> ) <EOL> handle_errors ( ) <EOL> def read_multipage ( filename , flags = <NUM_LIT:0> ) : <EOL> """<STR_LIT>""" <EOL> return _process_multipage ( filename , flags , _array_from_bitmap ) <EOL> def read_multipage_metadata ( filename ) : <EOL> """<STR_LIT>""" <EOL> flags = IoFlags . FIF_LOAD_NOPIXELS <EOL> return _process_multipage ( filename , flags , _read_metadata ) <EOL> def _wrap_bitmap_bits_in_array ( bitmap , shape , dtype ) : <EOL> """<STR_LIT>""" <EOL> pitch = _FI . FreeImage_GetPitch ( bitmap ) <EOL> handle_errors ( ) <EOL> height = shape [ - <NUM_LIT:1> ] <EOL> byte_size = height * pitch <EOL> itemsize = dtype . itemsize <EOL> if len ( shape ) == <NUM_LIT:3> : <EOL> strides = ( itemsize , shape [ <NUM_LIT:0> ] * itemsize , pitch ) <EOL> else : <EOL> strides = ( itemsize , pitch ) <EOL> bits = _FI . FreeImage_GetBits ( bitmap ) <EOL> handle_errors ( ) <EOL> array = numpy . ndarray ( <EOL> shape , dtype = dtype , <EOL> buffer = ( ctypes . c_char * byte_size ) . from_address ( bits ) , strides = strides ) <EOL> return array <EOL> def _array_from_bitmap ( bitmap ) : <EOL> """<STR_LIT>""" <EOL> dtype , shape = FiTypes . get_type_and_shape ( bitmap ) <EOL> array = _wrap_bitmap_bits_in_array ( bitmap , shape , dtype ) <EOL> def n ( arr ) : <EOL> return arr [ ... , : : - <NUM_LIT:1> ] . T <EOL> if len ( shape ) == <NUM_LIT:3> and _FI . FreeImage_IsLittleEndian ( ) and dtype . type == numpy . uint8 : <EOL> b = n ( array [ <NUM_LIT:0> ] ) <EOL> g = n ( array [ <NUM_LIT:1> ] ) <EOL> r = n ( array [ <NUM_LIT:2> ] ) <EOL> if shape [ <NUM_LIT:0> ] == <NUM_LIT:3> : <EOL> handle_errors ( ) <EOL> return numpy . dstack ( ( r , g , b ) ) <EOL> elif shape [ <NUM_LIT:0> ] == <NUM_LIT:4> : <EOL> a = n ( array [ <NUM_LIT:3> ] ) <EOL> return numpy . dstack ( ( r , g , b , a ) ) <EOL> else : <EOL> raise ValueError ( '<STR_LIT>' % shape ) <EOL> return n ( array ) . copy ( ) <EOL> def _read_metadata ( bitmap ) : <EOL> metadata = { } <EOL> models = [ ( name [ <NUM_LIT:5> : ] , number ) for name , number in <EOL> MetadataModels . __dict__ . items ( ) if name . startswith ( '<STR_LIT>' ) ] <EOL> tag = ctypes . c_void_p ( ) <EOL> for model_name , number in models : <EOL> mdhandle = _FI . FreeImage_FindFirstMetadata ( number , bitmap , <EOL> ctypes . byref ( tag ) ) <EOL> handle_errors ( ) <EOL> mdhandle = ctypes . c_void_p ( mdhandle ) <EOL> if mdhandle : <EOL> more = True <EOL> while more : <EOL> tag_name = asstr ( _FI . FreeImage_GetTagKey ( tag ) ) <EOL> tag_type = _FI . FreeImage_GetTagType ( tag ) <EOL> byte_size = _FI . FreeImage_GetTagLength ( tag ) <EOL> handle_errors ( ) <EOL> char_ptr = ctypes . c_char * byte_size <EOL> tag_str = char_ptr . from_address ( _FI . FreeImage_GetTagValue ( tag ) ) <EOL> handle_errors ( ) <EOL> if tag_type == MetadataDatatype . FIDT_ASCII : <EOL> tag_val = asstr ( tag_str . value ) <EOL> else : <EOL> tag_val = numpy . fromstring ( <EOL> tag_str , dtype = MetadataDatatype . dtypes [ tag_type ] ) <EOL> if len ( tag_val ) == <NUM_LIT:1> : <EOL> tag_val = tag_val [ <NUM_LIT:0> ] <EOL> metadata [ ( model_name , tag_name ) ] = tag_val <EOL> more = _FI . FreeImage_FindNextMetadata ( mdhandle , <EOL> ctypes . byref ( tag ) ) <EOL> handle_errors ( ) <EOL> _FI . FreeImage_FindCloseMetadata ( mdhandle ) <EOL> handle_errors ( ) <EOL> return metadata <EOL> def write ( array , filename , flags = <NUM_LIT:0> ) : <EOL> """<STR_LIT>""" <EOL> array = numpy . asarray ( array ) <EOL> filename = asbytes ( filename ) <EOL> ftype = _FI . FreeImage_GetFIFFromFilename ( filename ) <EOL> handle_errors ( ) <EOL> if ftype == - <NUM_LIT:1> : <EOL> raise ValueError ( '<STR_LIT>' % filename ) <EOL> bitmap , fi_type = _array_to_bitmap ( array ) <EOL> try : <EOL> if fi_type == FiTypes . FIT_BITMAP : <EOL> can_write = _FI . FreeImage_FIFSupportsExportBPP ( <EOL> ftype , _FI . FreeImage_GetBPP ( bitmap ) ) <EOL> handle_errors ( ) <EOL> else : <EOL> can_write = _FI . FreeImage_FIFSupportsExportType ( ftype , fi_type ) <EOL> handle_errors ( ) <EOL> if not can_write : <EOL> raise TypeError ( '<STR_LIT>' <EOL> '<STR_LIT>' ) <EOL> res = _FI . FreeImage_Save ( ftype , bitmap , filename , flags ) <EOL> handle_errors ( ) <EOL> if not res : <EOL> raise RuntimeError ( '<STR_LIT>' ) <EOL> finally : <EOL> _FI . FreeImage_Unload ( bitmap ) <EOL> handle_errors ( ) <EOL> def write_multipage ( arrays , filename , flags = <NUM_LIT:0> ) : <EOL> """<STR_LIT>""" <EOL> filename = asbytes ( filename ) <EOL> ftype = _FI . FreeImage_GetFIFFromFilename ( filename ) <EOL> if ftype == - <NUM_LIT:1> : <EOL> raise ValueError ( '<STR_LIT>' % filename ) <EOL> create_new = True <EOL> read_only = False <EOL> keep_cache_in_memory = True <EOL> multibitmap = _FI . FreeImage_OpenMultiBitmap ( ftype , filename , <EOL> create_new , read_only , <EOL> keep_cache_in_memory , <NUM_LIT:0> ) <EOL> multibitmap = ctypes . c_void_p ( multibitmap ) <EOL> if not multibitmap : <EOL> raise ValueError ( '<STR_LIT>' % <EOL> filename ) <EOL> try : <EOL> for array in arrays : <EOL> array = numpy . asarray ( array ) <EOL> bitmap , fi_type = _array_to_bitmap ( array ) <EOL> _FI . FreeImage_AppendPage ( multibitmap , bitmap ) <EOL> finally : <EOL> _FI . FreeImage_CloseMultiBitmap ( multibitmap , flags ) <EOL> _GREY_PALETTE = numpy . arange ( <NUM_LIT:0> , <NUM_LIT> , <NUM_LIT> , dtype = numpy . uint32 ) <EOL> def _array_to_bitmap ( array ) : <EOL> """<STR_LIT>""" <EOL> shape = array . shape <EOL> dtype = array . dtype <EOL> r , c = shape [ : <NUM_LIT:2> ] <EOL> if len ( shape ) == <NUM_LIT:2> : <EOL> n_channels = <NUM_LIT:1> <EOL> w_shape = ( c , r ) <EOL> elif len ( shape ) == <NUM_LIT:3> : <EOL> n_channels = shape [ <NUM_LIT:2> ] <EOL> w_shape = ( n_channels , c , r ) <EOL> else : <EOL> n_channels = shape [ <NUM_LIT:0> ] <EOL> try : <EOL> fi_type = FiTypes . fi_types [ ( dtype , n_channels ) ] <EOL> except KeyError : <EOL> raise ValueError ( '<STR_LIT>' ) <EOL> itemsize = array . dtype . itemsize <EOL> bpp = <NUM_LIT:8> * itemsize * n_channels <EOL> bitmap = _FI . FreeImage_AllocateT ( fi_type , c , r , bpp , <NUM_LIT:0> , <NUM_LIT:0> , <NUM_LIT:0> ) <EOL> bitmap = ctypes . c_void_p ( bitmap ) <EOL> if not bitmap : <EOL> raise RuntimeError ( '<STR_LIT>' ) <EOL> try : <EOL> def n ( arr ) : <EOL> return arr . T [ ... , : : - <NUM_LIT:1> ] <EOL> wrapped_array = _wrap_bitmap_bits_in_array ( bitmap , w_shape , dtype ) <EOL> if len ( shape ) == <NUM_LIT:3> and _FI . FreeImage_IsLittleEndian ( ) : <EOL> r = array [ : , : , <NUM_LIT:0> ] <EOL> g = array [ : , : , <NUM_LIT:1> ] <EOL> b = array [ : , : , <NUM_LIT:2> ] <EOL> if dtype . type == numpy . uint8 : <EOL> wrapped_array [ <NUM_LIT:0> ] = n ( b ) <EOL> wrapped_array [ <NUM_LIT:1> ] = n ( g ) <EOL> wrapped_array [ <NUM_LIT:2> ] = n ( r ) <EOL> elif dtype . type == numpy . uint16 : <EOL> wrapped_array [ <NUM_LIT:0> ] = n ( r ) <EOL> wrapped_array [ <NUM_LIT:1> ] = n ( g ) <EOL> wrapped_array [ <NUM_LIT:2> ] = n ( b ) <EOL> if shape [ <NUM_LIT:2> ] == <NUM_LIT:4> : <EOL> a = array [ : , : , <NUM_LIT:3> ] <EOL> wrapped_array [ <NUM_LIT:3> ] = n ( a ) <EOL> else : <EOL> wrapped_array [ : ] = n ( array ) <EOL> if len ( shape ) == <NUM_LIT:2> and dtype . type == numpy . uint8 : <EOL> palette = _FI . FreeImage_GetPalette ( bitmap ) <EOL> palette = ctypes . c_void_p ( palette ) <EOL> if not palette : <EOL> raise RuntimeError ( '<STR_LIT>' ) <EOL> ctypes . memmove ( palette , _GREY_PALETTE . ctypes . data , <NUM_LIT> ) <EOL> return bitmap , fi_type <EOL> except : <EOL> _FI . FreeImage_Unload ( bitmap ) <EOL> raise <EOL> def imread ( filename ) : <EOL> """<STR_LIT>""" <EOL> img = read ( filename ) <EOL> return img <EOL> def imsave ( filename , img ) : <EOL> '''<STR_LIT>''' <EOL> write ( img , filename ) </s>
