J'ai une image où les couleurs sont BGR. Comment puis-je transformer mon image PIL pour échanger efficacement les éléments B et R de chaque pixel?
En supposant qu'il n'y ait pas de bande alpha, n'est-ce pas aussi simple que cela?
b, g, r = im.split()
im = Image.merge("RGB", (r, g, b))
Modifier:
Hmm ... Il semble que PIL présente quelques bugs à ce sujet ... im.split()
ne semble pas fonctionner avec les versions récentes de PIL (1.1.7). Cela peut (?) Fonctionner avec 1.1.6, bien que ...
Alternativement, si vous avez numpy disponible, vous pouvez l'utiliser pour ceci: (Encore une fois, je suppose une image RVB ici, non une image RVBA!):
data = np.asarray(im)
im = Image.fromarray(np.roll(data, 1, axis=-1))
Si im.split()
fonctionne, c’est certainement une option plus simple et plus lisible!
Juste pour ajouter une réponse plus à jour:
Avec la nouvelle interface cv2, les images chargées sont désormais automatiquement des tableaux numpy.
Mais openCV cv2.imread () charge les images au format BGR alors que numpy.imread () les charge au format RGB.
Le moyen le plus simple de convertir consiste à utiliser openCV cvtColor.
import cv2
srcBGR = cv2.imread("sample.png")
destRGB = cv2.cvtColor(srcBGR, cv2.COLOR_BGR2RGB)
Je sais que c'est une vieille question, mais j'avais le même problème et l'ai résolu avec:
img = img[:,:,::-1]
C'était ma meilleure réponse. Soit dit en passant, cela fonctionne aussi avec Alpha.
from PIL import Image
import numpy as np
import sys
sub = Image.open(sys.argv[1])
sub = sub.convert("RGBA")
data = np.array(sub)
red, green, blue, alpha = data.T
data = np.array([blue, green, red, alpha])
data = data.transpose()
sub = Image.fromarray(data)
import cv2
srcBGR = cv2.imread("sample.png")
destRGB = cv2.cvtColor(srcBGR,cv2.COLOR_BGR2RGB)
Juste pour clarifier la solution de Martin Beckets, car je suis incapable de commenter. Vous avez besoin de cv2. devant la constante de couleur.
En utilisant les idées expliquées précédemment ... en utilisant numpy, vous pourriez.
bgr_image_array = numpy.asarray(bgr_image)
B, G, R = bgr_image_array.T
rgb_image_array = np.array((R, G, B)).T
rgb_image = Image.fromarray(rgb_image_array, mode='RGB')
De plus, il peut supprimer le canal Alpha.
assert bgra_image_array.shape == (image_height, image_width, 4)
B, G, R, _ = bgra_image_array.T
rgb_image_array = np.array((R, G, B)).T
Vous devriez pouvoir le faire avec le module ImageMath
.
La solution de Joe est encore meilleure, j'y pensais trop. :)
im = Image.frombuffer('RGB', (width, height), bgr_buf, 'raw', 'BGR', 0, 0)