pyvips
pyvips copied to clipboard
Q: How to set XMP metadata
I need to inject some XMP metadata into an image to be written to disk as (big)TIFF.
Some related functionality seems to be documented in the libvips header documentation but I'm missing a clear path on how to insert a simple property in pyvips.
E.g. if I try to use img.set('xmp:copyright', copy_str)
I get an error that I need to define the gtype
for the property, but if I want to use set_type
I am not sure which value I shall use for my type (str).
I also see a VIPS-META-XMP-NAME constant is defined in libvips but It's not clear to me how to use it or how to access it in pyvips.
Any help is appreciated. s
Hi @scossu, XMP is stored as a binary blob, confusingly, rather than as a string. For example:
john@yingna ~/pics $ python3
Python 3.6.7 (default, Oct 22 2018, 11:32:17)
[GCC 8.2.0] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> import pyvips
>>> im = pyvips.Image.new_from_file("wtc.jpg")
>>> im.get_fields()
['width', 'height', 'bands', 'format', 'coding', 'interpretation', 'xoffset', 'yoffset', 'xres', 'yres', 'filename', 'vips-loader', 'jpeg-multiscan', 'jpeg-chroma-subsample', 'exif-data', 'resolution-unit', 'exif-ifd0-Orientation', 'exif-ifd0-XResolution', 'exif-ifd0-YResolution', 'exif-ifd0-ResolutionUnit', 'exif-ifd0-YCbCrPositioning', 'exif-ifd2-ExifVersion', 'exif-ifd2-ComponentsConfiguration', 'exif-ifd2-FlashPixVersion', 'exif-ifd2-ColorSpace', 'exif-ifd2-PixelXDimension', 'exif-ifd2-PixelYDimension', 'orientation', 'icc-profile-data']
So there's no xmp-data
field, we have to make one:
>>> im.set_type(pyvips.GValue.blob_type, "xmp-data", b"my great xmp string")
>>> im.write_to_file("x.tif")
Then read back to verify:
>>> x = pyvips.Image.new_from_file("x.tif")
>>> x.get_fields()
['width', 'height', 'bands', 'format', 'coding', 'interpretation', 'xoffset', 'yoffset', 'xres', 'yres', 'filename', 'vips-loader', 'n-pages', 'icc-profile-data', 'xmp-data', 'resolution-unit', 'orientation']
>>> x.get("xmp-data")
b'my great xmp string'
Makes sense. I realize that I have to compose the XMP blob manually or with some other tool.
Thanks for the pointers. I now see the pyvips.GValue
enums in the code, but the autodoc command doesn't seem to carry them over in the documentation.
I think we were unsure about what should be in the public API. Probably type_from_name
would be a better thing to export, so you'd do:
im.set_type(pyvips.type_from_name('VipsBlob'), 'xmp-data', b'my great xmp string')
IMHO enums have a more canonical form than strings, but you may have architectural reasons for using strings; either one should be fine as long as there is a list of the options documented.