degal/thumbnail.py
author Tero Marttila <terom@fixme.fi>
Sun, 14 Jun 2009 23:43:40 +0300
changeset 120 55cb7fc9c8fb
parent 116 2d3721b9ffd0
child 122 292aaba6d6ec
permissions -rw-r--r--
add new exif.py to abstract between different exif libraries, and add partially working support for pyexiv2 and EXIFpy
85
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
     1
"""
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
     2
    State for thumbnails; derivates of Images
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
     3
"""
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
     4
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
     5
import filesystem
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
     6
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
     7
import PIL.Image
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
     8
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
     9
class Thumbnail (filesystem.File) :
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    10
    """
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    11
        A Thumbnail is a derivate of an Image, usually resized to some other size.
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    12
    """
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    13
115
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    14
    def __init__ (self, image, subdir, target_size) :
85
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    15
        """
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    16
            Initialize to link against the given `image`.
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    17
            
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    18
            `subdir` specifies the directory to store this thumbnail in.
115
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    19
            `target_size` determines the target resolution of the output thumbnail.
85
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    20
        """
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    21
95
3b00bd676fc9 fix Thumbnail.stale/File.older_than behaviour
Tero Marttila <terom@fixme.fi>
parents: 85
diff changeset
    22
        # our file path, image name inside of the given subdir
3b00bd676fc9 fix Thumbnail.stale/File.older_than behaviour
Tero Marttila <terom@fixme.fi>
parents: 85
diff changeset
    23
        super(Thumbnail, self).__init__(subdir, image.fsname)
85
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    24
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    25
        # store
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    26
        self.image = image
115
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    27
        self.target_size = target_size
85
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    28
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    29
    def stale (self) :
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    30
        """
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    31
            Tests if this thumbnail is stale
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    32
        """
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    33
        
95
3b00bd676fc9 fix Thumbnail.stale/File.older_than behaviour
Tero Marttila <terom@fixme.fi>
parents: 85
diff changeset
    34
        if self.image.older_than(self) :
3b00bd676fc9 fix Thumbnail.stale/File.older_than behaviour
Tero Marttila <terom@fixme.fi>
parents: 85
diff changeset
    35
            # both exist and this is newer
3b00bd676fc9 fix Thumbnail.stale/File.older_than behaviour
Tero Marttila <terom@fixme.fi>
parents: 85
diff changeset
    36
            return False
3b00bd676fc9 fix Thumbnail.stale/File.older_than behaviour
Tero Marttila <terom@fixme.fi>
parents: 85
diff changeset
    37
        
3b00bd676fc9 fix Thumbnail.stale/File.older_than behaviour
Tero Marttila <terom@fixme.fi>
parents: 85
diff changeset
    38
        else :
3b00bd676fc9 fix Thumbnail.stale/File.older_than behaviour
Tero Marttila <terom@fixme.fi>
parents: 85
diff changeset
    39
            # this thumb doesn't exist or is older
3b00bd676fc9 fix Thumbnail.stale/File.older_than behaviour
Tero Marttila <terom@fixme.fi>
parents: 85
diff changeset
    40
            return True
115
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    41
    
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    42
    @property
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    43
    def size (self) :
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    44
        """
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    45
            Compute the *real* size of this thumbnail, from the image's actual size and our target size.
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    46
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    47
            Preserves the aspect ratio etc.
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    48
        """
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    49
        
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    50
        # real image size
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    51
        img_width, img_height = self.image.img_size
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    52
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    53
        # target size
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    54
        thumb_width, thumb_height = self.target_size
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    55
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    56
        # calc new size, preserving aspect ratio
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    57
        if img_width > thumb_width : 
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    58
            height = max(img_height * thumb_width / img_width, 1)
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    59
            width = thumb_width
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    60
        
116
2d3721b9ffd0 fix Thumbnail.size logic, s/if/elif/
Tero Marttila <terom@fixme.fi>
parents: 115
diff changeset
    61
        elif img_height > thumb_height :
115
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    62
            width = max(img_width * thumb_height / img_height, 1)
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    63
            height = thumb_height
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    64
        
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    65
        return width, height 
85
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    66
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    67
    def update (self) :
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    68
        """
115
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    69
            Render new output thumbnail.
85
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    70
        """
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    71
115
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    72
        # create resized copy of main image, using our size
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    73
        thumb = self.image.img.resize(self.size, resample=PIL.Image.ANTIALIAS)
85
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    74
115
d5aa320697df rename Image.pil_image -> Image.img, and shave off ~30ms per image by using Image.resize instead of Image.copy/Image.thumbnail
Tero Marttila <terom@fixme.fi>
parents: 95
diff changeset
    75
        # write it out
85
7da934333469 move thumbnail rendering from render.py to thumbnail.py, and implement staleness checking for Images, plus index_images for Folder
Tero Marttila <terom@fixme.fi>
parents:
diff changeset
    76
        thumb.save(self.path)
95
3b00bd676fc9 fix Thumbnail.stale/File.older_than behaviour
Tero Marttila <terom@fixme.fi>
parents: 85
diff changeset
    77