From bdc53f6c4d499c918cc8d050ed163b8b9a178fe3 Mon Sep 17 00:00:00 2001 From: Andrew Murray Date: Wed, 28 Aug 2024 18:33:43 +1000 Subject: [PATCH] Expand C image to match GIF frame image size --- Tests/images/test_extents_transparency.gif | Bin 0 -> 415 bytes Tests/test_file_gif.py | 37 ++++++++++++++++----- src/PIL/GifImagePlugin.py | 18 ++++++++++ 3 files changed, 47 insertions(+), 8 deletions(-) create mode 100644 Tests/images/test_extents_transparency.gif diff --git a/Tests/images/test_extents_transparency.gif b/Tests/images/test_extents_transparency.gif new file mode 100644 index 0000000000000000000000000000000000000000..739c82ad47c73560495e23c4b44bab5e1a88184f GIT binary patch literal 415 zcmZ?wbhEHbOkqf2Xk=jc&wv1mKUo+V7#JCJKtdpS29AXcj2to^8x|aF<`CA3Ik92k z;dTLKuQ?tY7ai@EFwVMjV&mfD{R+-qGM<~3oSdu?yej78rlqH+8zi5aWIx*cTa6yeSLkx;VxP4 zZEJ3B&bYiP_Vl*3x3?EOJ~h{S`?|ZkD?Y!vdwTo&`}-T1x#fIzY None: im.load() -def test_extents() -> None: - with Image.open("Tests/images/test_extents.gif") as im: - assert im.size == (100, 100) +@pytest.mark.parametrize( + "test_file, loading_strategy", + ( + ("test_extents.gif", GifImagePlugin.LoadingStrategy.RGB_AFTER_FIRST), + ( + "test_extents.gif", + GifImagePlugin.LoadingStrategy.RGB_AFTER_DIFFERENT_PALETTE_ONLY, + ), + ( + "test_extents_transparency.gif", + GifImagePlugin.LoadingStrategy.RGB_AFTER_FIRST, + ), + ), +) +def test_extents(test_file, loading_strategy) -> None: + GifImagePlugin.LOADING_STRATEGY = loading_strategy + try: + with Image.open("Tests/images/" + test_file) as im: + assert im.size == (100, 100) - # Check that n_frames does not change the size - assert im.n_frames == 2 - assert im.size == (100, 100) + # Check that n_frames does not change the size + assert im.n_frames == 2 + assert im.size == (100, 100) - im.seek(1) - assert im.size == (150, 150) + im.seek(1) + assert im.size == (150, 150) + + im.load() + assert im.im.size == (150, 150) + finally: + GifImagePlugin.LOADING_STRATEGY = GifImagePlugin.LoadingStrategy.RGB_AFTER_FIRST def test_missing_background() -> None: diff --git a/src/PIL/GifImagePlugin.py b/src/PIL/GifImagePlugin.py index fa8137fb9..82f58905d 100644 --- a/src/PIL/GifImagePlugin.py +++ b/src/PIL/GifImagePlugin.py @@ -438,6 +438,13 @@ class GifImageFile(ImageFile.ImageFile): self.im.putpalette("RGB", *self._frame_palette.getdata()) else: self._im = None + if not self._prev_im and self._im is not None and self.size != self.im.size: + expanded_im = Image.core.fill(self.im.mode, self.size) + if self._frame_palette: + expanded_im.putpalette("RGB", *self._frame_palette.getdata()) + expanded_im.paste(self.im, (0, 0) + self.im.size) + + self.im = expanded_im self._mode = temp_mode self._frame_palette = None @@ -455,6 +462,17 @@ class GifImageFile(ImageFile.ImageFile): return if not self._prev_im: return + if self.size != self._prev_im.size: + if self._frame_transparency is not None: + expanded_im = Image.core.fill("RGBA", self.size) + else: + expanded_im = Image.core.fill("P", self.size) + expanded_im.putpalette("RGB", "RGB", self.im.getpalette()) + expanded_im = expanded_im.convert("RGB") + expanded_im.paste(self._prev_im, (0, 0) + self._prev_im.size) + + self._prev_im = expanded_im + assert self._prev_im is not None if self._frame_transparency is not None: self.im.putpalettealpha(self._frame_transparency, 0) frame_im = self.im.convert("RGBA")