Изменить цвет всех пикселей другим цветом - PullRequest
10 голосов
/ 26 июня 2011

Я бы хотел изменить один цвет с помощью Python.

Если существует быстрое решение с PIL, я бы предпочел это решение.

В данный момент я использую

convert -background black -opaque '#939393' MyImage.png MyImage.png

Ответы [ 4 ]

18 голосов
/ 28 июня 2011

Если на вашем компьютере доступно numpy, попробуйте сделать что-то вроде:

import numpy as np
from PIL import Image

im = Image.open('fig1.png')
data = np.array(im)

r1, g1, b1 = 0, 0, 0 # Original value
r2, g2, b2 = 255, 255, 255 # Value that we want to replace it with

red, green, blue = data[:,:,0], data[:,:,1], data[:,:,2]
mask = (red == r1) & (green == g1) & (blue == b1)
data[:,:,:3][mask] = [r2, g2, b2]

im = Image.fromarray(data)
im.save('fig1_modified.png')

Он будет использовать (в 3 раза) больше памяти, но он должен быть значительно (~ 5х, но больше для больших изображений) быстрее.

Также обратите внимание, что приведенный выше код немного сложнее, чем нужно, если у вас есть только изображения RGB (а не RGBA). Однако этот пример оставит альфа-полосу в покое, тогда как более простая версия не будет иметь этого.

4 голосов
/ 26 июня 2011

Я только что придумал это решение:

import Image
im = Image.open("MyImage.png")
width, height = im.size
colortuples = im.getcolors()
mycolor1 = min(colortuples)[1]
mycolor2 = max(colortuples)[1]
pix = im.load()
for x in range(0, width):
    for y in range(0, height):
        if pix[x,y] == mycolor1:
            im.putpixel((x, y), mycolor2)
im.save('MyImage.png')

Хотя putpixel не быстрый, он мне кажется достаточно быстрым.

3 голосов
/ 26 июня 2013

Это модификация ответа Джо Кингтона выше.Ниже описано, как это сделать, если ваше изображение также содержит альфа-канал.

import numpy as np
import Image

im = Image.open('fig1.png')
im = im.convert('RGBA')
data = np.array(im)

r1, g1, b1 = 0, 0, 0 # Original value
r2, g2, b2, a2 = 255, 255, 255, 255 # Value that we want to replace it with

red, green, blue, alpha = data[:,:,0], data[:,:,1], data[:,:,2], data[:,:,3]
mask = (red == r1) & (green == g1) & (blue == b1)
data[:,:,:4][mask] = [r2, g2, b2, a2]

im = Image.fromarray(data)
im.save('fig1_modified.png')

Мне понадобилось много времени, чтобы понять, как заставить его работать.Я надеюсь, что это поможет кому-то еще.

0 голосов
/ 29 ноября 2015

Это решение использует glob для редактирования всех png-файлов в папке, удаления цвета и замены его другим, но использует RGBA.

import glob
from PIL import Image

old_color = 255, 0, 255, 255
new_color = 0, 0, 0, 0

for path in glob.glob("*.png"):
    if "__out" in path:
        print "skipping on", path
        continue

    print "working on", path

    im = Image.open(path)
    im = im.convert("RGBA")
    width, height = im.size
    colortuples = im.getcolors()

    pix = im.load()
    for x in xrange(0, width):
        for y in xrange(0, height):
            if pix[x,y] == old_color:
                im.putpixel((x, y), new_color)

    im.save(path+"__out.png")

Это модификация https://stackoverflow.com/a/6483549/541208

...