[Image-SIG] patch for more TIFF tags when saving TIFF images
Greg Couch
gregc@cgl.ucsf.EDU
Fri, 11 May 2001 17:42:30 -0700 (PDT)
Then enclosed patch adds support for more TIFF tags, namely the
Artist, Copyright, DateTime, ResolutionUnit, Software, XResolution
and YResolution tags. The trickiest part was adding support for
TIFF rational numbers. Hope this makes it into the next release,
Greg Couch
UCSF Computer Graphics Lab
gregc@cgl.ucsf.edu
===================================================================
RCS file: RCS/TiffImagePlugin.py,v
retrieving revision 1.1
diff -c -r1.1 TiffImagePlugin.py
*** TiffImagePlugin.py 2001/05/11 23:37:24 1.1
--- TiffImagePlugin.py 2001/05/12 00:26:56
***************
*** 66,77 ****
--- 66,84 ----
SAMPLESPERPIXEL = 277
ROWSPERSTRIP = 278
STRIPBYTECOUNTS = 279
+ X_RESOLUTION = 282
+ Y_RESOLUTION = 283
PLANAR_CONFIGURATION = 284
+ RESOLUTION_UNIT = 296
+ SOFTWARE = 305
+ DATE_TIME = 306
+ ARTIST = 315
PREDICTOR = 317
COLORMAP = 320
EXTRASAMPLES = 338
SAMPLEFORMAT = 339
JPEGTABLES = 347
+ COPYRIGHT = 33432
IPTC_NAA_CHUNK = 33723 # newsphoto properties
PHOTOSHOP_CHUNK = 34377 # photoshop properties
***************
*** 313,318 ****
--- 320,328 ----
if tag == STRIPOFFSETS:
stripoffsets = len(directory)
typ = 4 # to avoid catch-22
+ elif tag in (X_RESOLUTION, Y_RESOLUTION):
+ # identify rational data fields
+ typ = 5
else:
typ = 3
for v in value:
***************
*** 329,335 ****
elif len(data) < 4:
append((tag, typ, len(value), data + (4-len(data))*"\0", ""))
else:
! append((tag, typ, len(value), o32(offset), data))
offset = offset + len(data)
if offset & 1:
offset = offset + 1 # word padding
--- 339,348 ----
elif len(data) < 4:
append((tag, typ, len(value), data + (4-len(data))*"\0", ""))
else:
! count = len(value)
! if typ == 5:
! count = count / 2 # adjust for rational data field
! append((tag, typ, count, o32(offset), data))
offset = offset + len(data)
if offset & 1:
offset = offset + 1 # word padding
***************
*** 551,556 ****
--- 564,579 ----
"LAB": ("LAB", 8, 1, (8,8,8), None),
}
+ def _cvt_res(value):
+ # convert value to TIFF rational number -- (numerator, denominator)
+ if type(value) in (type([]), type(())):
+ assert(len(value) % 2 == 0)
+ return value
+ if type(value) == type(1):
+ return (value, 1)
+ value = float(value)
+ return (int(value * 65536), 65536)
+
def _save(im, fp, filename):
try:
***************
*** 566,573 ****
--- 589,626 ----
ifd[IMAGEWIDTH] = im.size[0]
ifd[IMAGELENGTH] = im.size[1]
+ # additions written by Greg Couch, gregc@cgl.ucsf.edu
+ # inspired by image-sig posting from Kevin Cazabon, kcazabon@home.com
+ if hasattr(im, 'tag'):
+ # preserve tags from original TIFF image file
+ for key in (RESOLUTION_UNIT, X_RESOLUTION, Y_RESOLUTION):
+ if im.tag.tagdata.has_key(key):
+ ifd[key] = im.tag.tagdata.get(key)
if im.encoderinfo.has_key("description"):
ifd[IMAGEDESCRIPTION] = im.encoderinfo["description"]
+ if im.encoderinfo.has_key("resolution"):
+ ifd[X_RESOLUTION] = ifd[Y_RESOLUTION] \
+ = _cvt_res(im.encoderinfo["resolution"])
+ if im.encoderinfo.has_key("x resolution"):
+ ifd[X_RESOLUTION] = _cvt_res(im.encoderinfo["x resolution"])
+ if im.encoderinfo.has_key("y resolution"):
+ ifd[Y_RESOLUTION] = _cvt_res(im.encoderinfo["y resolution"])
+ if im.encoderinfo.has_key("resolution unit"):
+ unit = im.encoderinfo["resolution unit"]
+ if unit == "inch":
+ ifd[RESOLUTION_UNIT] = 2
+ elif unit == "cm" or unit == "centimeter":
+ ifd[RESOLUTION_UNIT] = 3
+ else:
+ ifd[RESOLUTION_UNIT] = 1
+ if im.encoderinfo.has_key("software"):
+ ifd[SOFTWARE] = im.encoderinfo["software"]
+ if im.encoderinfo.has_key("date time"):
+ ifd[DATE_TIME] = im.encoderinfo["date time"]
+ if im.encoderinfo.has_key("artist"):
+ ifd[ARTIST] = im.encoderinfo["artist"]
+ if im.encoderinfo.has_key("copyright"):
+ ifd[COPYRIGHT] = im.encoderinfo["copyright"]
if bits != (1,):
ifd[BITSPERSAMPLE] = bits