Skip to content

Commit 5f9cb99

Browse files
committed
v0.3.1
1 parent df1bb3f commit 5f9cb99

File tree

8 files changed

+949
-332
lines changed

8 files changed

+949
-332
lines changed

CHANGELOG.md

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,22 @@
22

33
All notable changes to this project will be documented in this file.
44

5+
## [0.3.1 - 2022-06-17]
6+
7+
### Added
8+
9+
- (Heif) - `HeifFile` gets `images: List[HeifImage]` and alternative method of changing order of images by editing it.
10+
- (HeifImagePlugin) - `info` image dictionary can be now edited in place and it will be saved for image sequences.
11+
12+
### Changed
13+
14+
- Updated docs.
15+
16+
### Fixed
17+
18+
- (HeifImagePlugin) Again fixing image order, for Pillow plugin it was not fixed fully in 0.3.0.
19+
- Optimizing code.
20+
521
## [0.3.0 - 2022-06-11]
622

723
### Added

docs/cooking-heif-file.rst

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -75,7 +75,8 @@ Starting from version `0.3.1` all images are in public list, and you can swap th
7575
Saving images
7676
-------------
7777

78-
Refer to :py:meth:`~pillow_heif.HeifFile.save` to see what additional parameters is supported.
78+
Refer to :py:meth:`~pillow_heif.HeifFile.save` to see what additional parameters is supported
79+
and to :ref:`encoding` for some explanations.
7980

8081
.. code-block:: python
8182

docs/encoding.rst

Lines changed: 25 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
.. _encoding:
2+
13
Encoding of images
24
==================
35

@@ -10,31 +12,34 @@ Current limitations of encoder
1012
Metadata encoding
1113
"""""""""""""""""
1214

13-
All known metadata information in ``image.info`` dictionary are saved to output image.
15+
All known metadata information in ``info`` dictionary are saved to output image(for both `Pillow` plugin and `HeifFile`).
1416
Those are:
1517
``exif``, ``xmp`` and ``metadata``
1618

17-
So this is valid code for removing EXIF information:
19+
So this is valid code for removing EXIF and XMP information:
1820

1921
.. code-block:: python
2022
2123
image = Image.open(Path("test.heic"))
2224
image.info["exif"] = None
25+
image.info["xmp"] = None
2326
image.save("output.heic")
2427
2528
And this code is valid too:
2629

2730
.. code-block:: python
2831
2932
image = Image.open(Path("test.heic"))
30-
image.save("output.heic", exif=None)
33+
image.save("output.heic", exif=None, xmp=None)
3134
3235
Limitations of second code variant is that when file has multiply images inside,
33-
setting ``exif`` during save affects only Primary(Main) image and not all images.
36+
setting ``exif`` or ``xmp`` during ``save`` affects only Primary(Main) image and not all images.
37+
38+
To edit metadata of all images in a file just iterate throw all images and change metadata in place.
3439

35-
To edit metadata of all images in a file just iterate throw all images and change metadata you want(do not work for Pillow plugin).
40+
Here are two ways for `Pillow`:
3641

37-
When you want edit metadata when using as Pillow plugin for all images you can do something like this(editing ``info["exif"]`` field of each image):
42+
For example edit ``info["exif"]`` field of each image copy:
3843

3944
.. code-block:: python
4045
@@ -47,11 +52,21 @@ When you want edit metadata when using as Pillow plugin for all images you can d
4752
empty_pillow = Image.new("P", (0, 0))
4853
empty_pillow.save("no_exif.heic", save_all=True, append_images=output_wo_exif)
4954
55+
Or editing ``info["exif"]`` in place(from version `0.3.1`):
56+
57+
.. code-block:: python
58+
59+
heic_pillow = Image.open(Path("test.heic"))
60+
for frame in ImageSequence.Iterator(heic_pillow):
61+
frame.info["exif"] = None
62+
heic_pillow.save("no_exif.heic", save_all=True)
63+
5064
.. _changing-order-of-images:
5165

5266
Changing order of images
5367
""""""""""""""""""""""""
5468

69+
There is no such easy way to change order as for `HeifFile` usage, but the standard Pillow way to do so looks fine.
5570
Let's create image where second image will be primary:
5671

5772
.. code-block:: python
@@ -68,6 +83,10 @@ Now as example lets change primary image in a HEIC file:
6883
img1 = Image.open(Path("1_2P_3.heic"))
6984
img1.save("1_2_3P.heic", save_all=True, primary_index=-1, quality=-1)
7085
86+
.. note::
87+
88+
As a ``primary`` field are in `info` dictionary, you can change it in a place like with metadata before.
89+
7190
And here is an example how we can change order of images in container:
7291

7392
.. code-block:: python

pillow_heif/_version.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,3 @@
11
""" Version of pillow_heif """
22

3-
__version__ = "0.3.0"
3+
__version__ = "0.3.1"

pillow_heif/as_opener.py

Lines changed: 12 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@
1010
from ._options import options
1111
from .constants import HeifErrorCode
1212
from .error import HeifError
13-
from .heif import HeifFile, HeifImage, is_supported, open_heif
13+
from .heif import HeifFile, is_supported, open_heif
1414
from .misc import getxmp, set_orientation
1515

1616

@@ -23,6 +23,7 @@ class HeifImageFile(ImageFile.ImageFile):
2323
_close_exclusive_fp_after_loading = False
2424

2525
def __init__(self, *args, **kwargs):
26+
self.__frame = 0
2627
self.heif_file = None
2728
super().__init__(*args, **kwargs)
2829

@@ -33,12 +34,12 @@ def _open(self):
3334
raise SyntaxError(str(exception)) from None
3435
self.custom_mimetype = heif_file.mimetype
3536
self.heif_file = heif_file
36-
self._init_from_heif_file(heif_file)
37+
self._init_from_heif_file(self.__frame)
3738
self.tile = []
3839

3940
def load(self):
4041
if self.heif_file:
41-
frame_heif = self._heif_image_by_index(self.tell())
42+
frame_heif = self.heif_file[self.tell()]
4243
self.load_prepare()
4344
truncated = False
4445
try:
@@ -69,16 +70,11 @@ def getxmp(self) -> dict:
6970
def seek(self, frame):
7071
if not self._seek_check(frame):
7172
return
72-
self._init_from_heif_file(self._heif_image_by_index(frame))
73+
self.__frame = frame
74+
self._init_from_heif_file(frame)
7375

7476
def tell(self):
75-
i = 0
76-
if self.heif_file:
77-
for heif in self.heif_file:
78-
if self.info["img_id"] == heif.info["img_id"]:
79-
break
80-
i += 1
81-
return i
77+
return self.__frame
8278

8379
def verify(self) -> None:
8480
for _ in self.info["thumbnails"]:
@@ -103,18 +99,11 @@ def _seek_check(self, frame):
10399
raise EOFError("attempt to seek outside sequence")
104100
return self.tell() != frame
105101

106-
def _heif_image_by_index(self, index) -> HeifImage:
107-
return self.heif_file[index]
108-
109-
def _init_from_heif_file(self, heif_image) -> None:
110-
self._size = heif_image.size
111-
self.mode = heif_image.mode
112-
for k in ("exif", "xmp", "metadata", "primary", "img_id"):
113-
self.info[k] = heif_image.info[k]
114-
for k in ("icc_profile", "icc_profile_type", "nclx_profile"):
115-
if k in heif_image.info:
116-
self.info[k] = heif_image.info[k]
117-
self.info["thumbnails"] = heif_image.thumbnails
102+
def _init_from_heif_file(self, img_index: int) -> None:
103+
self._size = self.heif_file[img_index].size
104+
self.mode = self.heif_file[img_index].mode
105+
self.info = self.heif_file[img_index].info
106+
self.info["thumbnails"] = self.heif_file[img_index].thumbnails
118107
self.info["original_orientation"] = set_orientation(self.info)
119108

120109

0 commit comments

Comments
 (0)