Permalink
Browse files

start adding xmp/icc/exif/etc. for IM

needs to work for im6, im7 and gm, and it's not quite there yet :(
  • Loading branch information...
jcupitt committed Feb 6, 2019
1 parent 10b3000 commit 90fef08ee0d5548caa461b844bfe5022aadab07e
@@ -762,6 +762,16 @@ if test x"$magick6" = x"yes"; then
LIBS="$save_LIBS"
fi

if test x"$magick6" = x"yes"; then
# IM uses SetImageProfile() with StringInfo
save_LIBS="$LIBS"
LIBS="$LIBS $MAGICK_LIBS"
AC_CHECK_FUNCS(BlobToStringInfo,
AC_DEFINE(HAVE_BLOBTOSTRINGINFO,1,
[define if your magick has BlobToStringInfo().]))
LIBS="$save_LIBS"
fi

if test x"$magick6" = x"yes"; then
# GM is missing InheritException
save_LIBS="$LIBS"
@@ -92,6 +92,21 @@ magick_set_property( Image *image, const char *property, const char *value,
(void) SetImageProperty( image, property, value, exception );
}

int
magick_set_profile( Image *image,
const char *name, const void *data, size_t length,
ExceptionInfo *exception )
{
StringInfo *string;
MagickBooleanType result;

string = BlobToStringInfo( data, length );
result = SetImageProfile( image, name, string, exception );
DestroyStringInfo( string );

return( result );
}

ExceptionInfo *
magick_acquire_exception( void )
{
@@ -227,6 +242,26 @@ magick_set_property( Image *image, const char *property, const char *value,
#endif /*HAVE_SETIMAGEPROPERTY*/
}

int
magick_set_profile( Image *image,
const char *name, const void *data, size_t length,
ExceptionInfo *exception )
{
int result;

#ifdef HAVE_BLOBTOSTRINGINFO
StringInfo *string;

string = BlobToStringInfo( data, length );
result = SetImageProfile( image, name, string );
DestroyStringInfo( string );
#else /*HAVE_BLOBTOSTRINGINFO*/
result = SetImageProfile( image, name, data, length );
#endif /*HAVE_BLOBTOSTRINGINFO*/

return( result );
}

ExceptionInfo *
magick_acquire_exception( void )
{
@@ -53,7 +53,10 @@ int magick_import_pixels( Image *image, const ssize_t x, const ssize_t y,
const StorageType type,const void *pixels, ExceptionInfo *exception );
void *magick_images_to_blob( const ImageInfo *image_info, Image *images,
size_t *length, ExceptionInfo *exception );
void magick_set_property( Image *image, const char *property, const char *value,
void magick_set_property( Image *image,
const char *property, const char *value, ExceptionInfo *exception );
int magick_set_profile( Image *image,
const char *name, const void *data, size_t length,
ExceptionInfo *exception );
void magick_set_image_option( ImageInfo *image_info,
const char *name, const char *value );
@@ -444,6 +444,8 @@ parse_header( Read *read )
vips_buf_appendf( &name, VIPS_META_IPTC_NAME );
else if( strcmp( key, "icc" ) == 0 )
vips_buf_appendf( &name, VIPS_META_ICC_NAME );
else if( strcmp( key, "exif" ) == 0 )
vips_buf_appendf( &name, VIPS_META_EXIF_NAME );
else
vips_buf_appendf( &name, "magickprofile-%s", key );

@@ -452,6 +454,9 @@ parse_header( Read *read )
length = GetStringInfoLength( profile );
vips_image_set_blob_copy( im, vips_buf_all( &name ),
data, length );

if( strcmp( key, "exif" ) == 0 )
(void) vips__exif_parse( im );
}
}
#endif /*HAVE_RESETIMAGEPROFILEITERATOR*/
@@ -562,6 +562,8 @@ vips_foreign_load_magick7_parse( VipsForeignLoadMagick7 *magick7,
vips_buf_appendf( &name, VIPS_META_IPTC_NAME );
else if( strcmp( key, "icc" ) == 0 )
vips_buf_appendf( &name, VIPS_META_ICC_NAME );
else if( strcmp( key, "exif" ) == 0 )
vips_buf_appendf( &name, VIPS_META_EXIF_NAME );
else
vips_buf_appendf( &name, "magickprofile-%s", key );

@@ -570,6 +572,9 @@ vips_foreign_load_magick7_parse( VipsForeignLoadMagick7 *magick7,
length = GetStringInfoLength( profile );
vips_image_set_blob_copy( out, vips_buf_all( &name ),
data, length );

if( strcmp( key, "exif" ) == 0 )
(void) vips__exif_parse( im );
}

magick7->n_pages = GetImageListLength( GetFirstImageInList( image ) );
@@ -89,12 +89,59 @@ vips_foreign_save_magick_dispose( GObject *gobject )
dispose( gobject );
}

static void
typedef struct {
VipsForeignSaveMagick *magick;
Image *image;
} CopyProfileInfo;

static void *
vips_foreign_save_magick_copy_profile( VipsImage *im,
const char *name, GValue *value, CopyProfileInfo *info )
{
char txt[256];
VipsBuf buf = VIPS_BUF_STATIC( txt );
const void *data;
size_t length;
int result;

if( strcmp( name, VIPS_META_XMP_NAME ) == 0 )
vips_buf_appendf( &buf, "xmp" );
else if( strcmp( name, VIPS_META_IPTC_NAME ) == 0 )
vips_buf_appendf( &buf, "iptc" );
else if( strcmp( name, VIPS_META_ICC_NAME ) == 0 )
vips_buf_appendf( &buf, "icc" );
else if( strcmp( name, VIPS_META_EXIF_NAME ) == 0 )
vips_buf_appendf( &buf, "exif" );
else if( vips_isprefix( "magickprofile-", name ) )
vips_buf_appendf( &buf,
"%s", name + strlen( "magickprofile-" ) );

if( vips_buf_is_empty( &buf ) )
return( NULL );
if( !vips_image_get_typeof( im, name ) )
return( NULL );
if( vips_image_get_blob( im, name, &data, &length ) )
return( im );

result = magick_set_profile( info->image,
vips_buf_all( &buf ), data, length, info->magick->exception );
if( !result ) {
VipsObjectClass *class = VIPS_OBJECT_GET_CLASS( info->magick );

magick_vips_error( class->nickname, info->magick->exception );
return( im );
}

return( NULL );
}

static int
vips_foreign_save_magick_set_properties( VipsForeignSaveMagick *magick,
Image *image, VipsImage *im )
{
int number;
const char *str;
CopyProfileInfo info;

if( vips_image_get_typeof( im, "gif-delay" ) &&
!vips_image_get_int( im, "gif-delay", &number ) )
@@ -107,6 +154,15 @@ vips_foreign_save_magick_set_properties( VipsForeignSaveMagick *magick,
if( vips_image_get_typeof( im, "gif-comment" ) &&
!vips_image_get_string( im, "gif-comment", &str ) )
magick_set_property( image, "comment", str, magick->exception );

info.magick = magick;
info.image = image;
if( vips_image_map( im,
(VipsImageMapFn) vips_foreign_save_magick_copy_profile,
&info ) )
return( -1 );

return( 0 );
}

static int
@@ -155,7 +211,8 @@ vips_foreign_save_magick_create_one( VipsForeignSaveMagick *magick,
if( !magick_set_image_size( image, im->Xsize, im->Ysize,
magick->exception ) )
return( -1 );
vips_foreign_save_magick_set_properties( magick, image, im );
if( vips_foreign_save_magick_set_properties( magick, image, im ) )
return( -1 );

magick->current_image = image;
status = vips_sink_disc( im, magick_write_block, magick );

0 comments on commit 90fef08

Please sign in to comment.