Сохранение прозрачности с помощью GIF-файлов в режиме палитры в Pillow

Я пытаюсь взять GIF с палитрой, содержащей один индекс прозрачности, и использовать Pillow для создания обрезанных фрагментов изображения. Однако при использовании метода crop () результаты перестают быть прозрачными.

original = Image.open("filename.gif")
print(original.mode) # prints "P", as it should
transparent = original.info["transparency"]
print(transparent) # prints the correct index of the transparent color
cropped = original.crop((0, 0, 10, 10))
print(cropped.info) # transparency no longer present
cropped.info["transparency"] = 255
print(cropped.info) # key is entered, but not transparent in a drawn image

Как сохранить или восстановить прозрачный индекс с помощью манипуляций в Pillow? Как показано выше, даже если я «грубой силой» добавлю индекс прозрачности обратно в «информационный» словарь, это, очевидно, не то место, где Python ищет индекс для указания. В документации также упоминается, что некоторые методы, такие как crop (), ленивы и не передают всю информацию об изображении, поэтому есть ли способ повторно добавить такую ​​информацию в объект Image? В документации говорится, что я могу сделать это, сохранив новый файл GIF, но мне не понадобятся дополнительные изображения после того, как программа завершит работу и отобразит их.

отредактирован, чтобы добавить дополнительную информацию ниже:

исходное изображение Исходное изображение, созданное в GIMP (красный кружок, отмечен как прозрачный с помощью IrfanView)

code output Результат моего кода, в котором круг становится видимым красным

Вся моя программа здесь:

from tkinter import *
from tkinter import ttk
from PIL import Image
from PIL import ImageTk

class Main:
    def __init__(self):
        self.root = Tk()
        self.background = Canvas(self.root)
        self.background.grid(column=0,row=0)
        self.Draw()

    def Draw(self):
        original = Image.open("Transparency_test.gif")
        print(original.mode) # prints "P", as it should
        transparent = original.info["transparency"]
        print(transparent) # prints the correct index of the transparent color
        cropped = original.crop((0, 0, 50, 50))
        print(cropped.info) # transparency no longer present

        test_uncropped = ImageTk.PhotoImage(image=original)
        test_cropped = ImageTk.PhotoImage(image=cropped)

        self.background.create_image((0,0), image=test_uncropped, anchor=NW)
        self.background.create_image((100,0), image=test_cropped, anchor=NW)

        self.root.mainloop()

instance = Main()

person Taugosz    schedule 01.10.2015    source источник
comment
Можете ли вы опубликовать конкретный файл GIF, который вы используете?   -  person Michiel Overtoom    schedule 01.10.2015
comment
Привет, Мишель. Я добавил изображение и свой код с его выводом. Изображение выполнено с использованием стандартной веб-палитры из 216 цветов, в частности, предоставленной GIMP.   -  person Taugosz    schedule 01.10.2015


Ответы (1)


Я не уверен, что это наиболее эффективное решение, но я заставил его работать, сделав копию изображения с измененным размером, а затем вставив поверх нее пиксели исходного изображения. Думаю, результат такой, какой вы ожидаете.

    cropped = original.crop((0, 0, 50, 50))
    cropped.load()
    print(cropped.info) # transparency no longer present

    copied = original.resize((50,50))
    copied.paste(original, (0, 0))
    print(copied.info) # transparency present

    test_uncropped = ImageTk.PhotoImage(image=original)
    test_cropped = ImageTk.PhotoImage(image=cropped)
    test_copied = ImageTk.PhotoImage(image=copied)

    self.background.create_image((0,0), image=test_uncropped, anchor=NW)
    self.background.create_image((100,0), image=test_cropped, anchor=NW)
    self.background.create_image((200,0), image=test_copied, anchor=NW)
person Michiel Overtoom    schedule 02.10.2015
comment
Спасибо, Мишель! Это действительно работает. Это, вероятно, не самое эффективное решение, но оно остается в рамках ограничений, связанных с сохранением палитры повсюду, отлично работает для моих нужд и прекрасно обходит недостатки метода crop (). - person Taugosz; 02.10.2015