Отримайте піксельний RGB за допомогою PIL


93

Чи можна отримати колір RGB пікселя за допомогою PIL? Я використовую цей код:

im = Image.open("image.gif")
pix = im.load()
print(pix[1,1])

Однак він виводить лише число (наприклад, 0або 1), а не три числа (наприклад, 60,60,60для R, G, B). Я думаю, я щось не розумію щодо функції. Я хотів би пояснити.

Дуже дякую.

Відповіді:


147

Так, таким чином:

im = Image.open('image.gif')
rgb_im = im.convert('RGB')
r, g, b = rgb_im.getpixel((1, 1))

print(r, g, b)
(65, 100, 137)

Причиною того, що раніше ви отримували одне значення, pix[1, 1]є те, що пікселі GIF посилаються на одне з 256 значень у палітрі кольорів GIF.

Дивіться також цю публікацію SO: Значення пікселів Python та PIL різні для GIF та JPEG, і ця довідкова сторінка PIL містить додаткову інформацію про convert()функцію.

До речі, ваш код добре працював би для .jpgзображень.


1
Чи можна це зробити для екрана комп'ютера, а не лише для файлу зображення?
Musixauce3000

1
Image.getpixel () на базі 0 або на базі 1? Я маю на увазі, самий верхній лівий піксель дорівнює (0,0) або це (1, 1)?

2
@NimaBavari Він базується на 0.
Нолан

3

GIF-файли зберігають кольори як один із x можливих кольорів у палітрі. Прочитайте про кольорову палітру gif . Отже, PIL надає вам індекс палітри, а не інформацію про колір цього кольору палітри.

Редагувати: Вилучено посилання на рішення публікації в блозі, яке мало друкарську помилку. Інші відповіді роблять те саме без помилки.


2

Альтернативою перетворенню зображення є створення індексу RGB з палітри.

from PIL import Image

def chunk(seq, size, groupByList=True):
    """Returns list of lists/tuples broken up by size input"""
    func = tuple
    if groupByList:
        func = list
    return [func(seq[i:i + size]) for i in range(0, len(seq), size)]


def getPaletteInRgb(img):
    """
    Returns list of RGB tuples found in the image palette
    :type img: Image.Image
    :rtype: list[tuple]
    """
    assert img.mode == 'P', "image should be palette mode"
    pal = img.getpalette()
    colors = chunk(pal, 3, False)
    return colors

# Usage
im = Image.open("image.gif")
pal = getPalletteInRgb(im)

2

Не PIL, але imageio.imreadвсе одно може бути цікавим:

import imageio
im = scipy.misc.imread('um_000000.png', flatten=False, mode='RGB')
im = imageio.imread('Figure_1.png', pilmode='RGB')
print(im.shape)

дає

(480, 640, 3)

так воно і є (висота, ширина, канали). Отже, піксель у позиції (x, y)є

color = tuple(im[y][x])
r, g, b = color

Застарілий

scipy.misc.imreadє застарілим в SciPy 1.0.0 (спасибі за нагадування, fbahr !)


PSA: scipy.misc.imreadзастарілий! imreadзастаріло в SciPy 1.0.0 і буде видалено в 1.2.0. Використовуйте imageio.imreadзамість цього.
fbahr

1
Дякуємо за нагадування, fbahr! (Я насправді брав участь у припиненні цього - github.com/scipy/scipy/issues/6242 🙈)
Мартін Тома,

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.