Skip to content

Commit 00593ff

Browse files
authored
Merge pull request #8780 from radarhere/save_all
Allow encoderconfig and encoderinfo to be set for appended TIFF images
2 parents 5f36c9a + 5c93145 commit 00593ff

File tree

4 files changed

+34
-13
lines changed

4 files changed

+34
-13
lines changed

Tests/test_file_tiff.py

+12
Original file line numberDiff line numberDiff line change
@@ -660,6 +660,18 @@ def test_rowsperstrip(self, tmp_path: Path) -> None:
660660
assert isinstance(im, TiffImagePlugin.TiffImageFile)
661661
assert im.tag_v2[278] == 256
662662

663+
im = hopper()
664+
im2 = Image.new("L", (128, 128))
665+
im2.encoderinfo = {"tiffinfo": {278: 256}}
666+
im.save(outfile, save_all=True, append_images=[im2])
667+
668+
with Image.open(outfile) as im:
669+
assert isinstance(im, TiffImagePlugin.TiffImageFile)
670+
assert im.tag_v2[278] == 128
671+
672+
im.seek(1)
673+
assert im.tag_v2[278] == 256
674+
663675
def test_strip_raw(self) -> None:
664676
infile = "Tests/images/tiff_strip_raw.tif"
665677
with Image.open(infile) as im:

docs/handbook/image-file-formats.rst

+1-3
Original file line numberDiff line numberDiff line change
@@ -1163,9 +1163,7 @@ The :py:meth:`~PIL.Image.Image.save` method can take the following keyword argum
11631163

11641164
**append_images**
11651165
A list of images to append as additional frames. Each of the
1166-
images in the list can be single or multiframe images. Note however, that for
1167-
correct results, all the appended images should have the same
1168-
``encoderinfo`` and ``encoderconfig`` properties.
1166+
images in the list can be single or multiframe images.
11691167

11701168
.. versionadded:: 4.2.0
11711169

src/PIL/Image.py

+15-1
Original file line numberDiff line numberDiff line change
@@ -2475,7 +2475,21 @@ def save(
24752475
format to use is determined from the filename extension.
24762476
If a file object was used instead of a filename, this
24772477
parameter should always be used.
2478-
:param params: Extra parameters to the image writer.
2478+
:param params: Extra parameters to the image writer. These can also be
2479+
set on the image itself through ``encoderinfo``. This is useful when
2480+
saving multiple images::
2481+
2482+
# Saving XMP data to a single image
2483+
from PIL import Image
2484+
red = Image.new("RGB", (1, 1), "#f00")
2485+
red.save("out.mpo", xmp=b"test")
2486+
2487+
# Saving XMP data to the second frame of an image
2488+
from PIL import Image
2489+
black = Image.new("RGB", (1, 1))
2490+
red = Image.new("RGB", (1, 1), "#f00")
2491+
red.encoderinfo = {"xmp": b"test"}
2492+
black.save("out.mpo", save_all=True, append_images=[red])
24792493
:returns: None
24802494
:exception ValueError: If the output format could not be determined
24812495
from the file name. Use the format option to solve this.

src/PIL/TiffImagePlugin.py

+6-9
Original file line numberDiff line numberDiff line change
@@ -2295,22 +2295,19 @@ def fixOffsets(
22952295

22962296

22972297
def _save_all(im: Image.Image, fp: IO[bytes], filename: str | bytes) -> None:
2298-
encoderinfo = im.encoderinfo.copy()
2299-
encoderconfig = im.encoderconfig
2300-
append_images = list(encoderinfo.get("append_images", []))
2298+
append_images = list(im.encoderinfo.get("append_images", []))
23012299
if not hasattr(im, "n_frames") and not append_images:
23022300
return _save(im, fp, filename)
23032301

23042302
cur_idx = im.tell()
23052303
try:
23062304
with AppendingTiffWriter(fp) as tf:
23072305
for ims in [im] + append_images:
2308-
ims.encoderinfo = encoderinfo
2309-
ims.encoderconfig = encoderconfig
2310-
if not hasattr(ims, "n_frames"):
2311-
nfr = 1
2312-
else:
2313-
nfr = ims.n_frames
2306+
if not hasattr(ims, "encoderinfo"):
2307+
ims.encoderinfo = {}
2308+
if not hasattr(ims, "encoderconfig"):
2309+
ims.encoderconfig = ()
2310+
nfr = getattr(ims, "n_frames", 1)
23142311

23152312
for idx in range(nfr):
23162313
ims.seek(idx)

0 commit comments

Comments
 (0)