CV2 не отображает цвета при конвертации в uint8 - PullRequest
0 голосов
/ 17 ноября 2018

У меня есть список Python, который содержит данные RGBA изображения PNG, представленного как int32, который был отправлен с сервера сокетов Java.

Пример вывода этих данных в виде пустого массива без каких-либо преобразований:

[[-12763847 -12763847 -12763847 ...  -5590160 -12039396 -12434915]
 [-12763847 -12763847 -12763847 ...  -6643102 -12828909 -12830184]
 [-12763847 -12763847 -12763847 ...  -8419763 -13487094 -12435167]]

CV2, конечно, принимает uint8 в качестве типа данных (при отображении в виде int32 отображается черный экран), поэтому я преобразую свой список в массив numpy с помощью dtype = np.uint8 со следующим:

image_data = np.array(data_list, dtype = np.uint8)

Пример вывода этого:

[[ 57  57  57 ... 112  28  29]
 [ 57  57  57 ...  98  19  24]
 [ 57  57  57 ...  77  10  33]]

Однако, когда я отображаю изображение, используя

cv2.imshow("Image", image_data)

Я получаю окно с изображением, но в оттенках серого; ему не хватает цвета.

Как я могу предотвратить игнорирование цветов?

Ответы [ 2 ]

0 голосов
/ 17 ноября 2018

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

im=np.array([-12763847,-12763847,-12763847,-5590160,-12039396,-12434915],dtype=np.int32)

R = ((im & 0xff).astype(np.uint8)
# array([ 57,  57,  57, 112,  28,  29], dtype=uint8)

G = ((im>>8) & 0xff).astype(np.uint8)
# array([ 61,  61,  61, 179,  75,  66], dtype=uint8)

B = ((im>>16) & 0xff).astype(np.uint8)
# array([ 61,  61,  61, 170,  72,  66], dtype=uint8)

Если эти значения выглядят правильно, вы сможете объединить их в цветное изображение с:

img = cv2.merge((B,G,R))

с учетом того, что OpenCV использует BGR упорядочение каналов, а не более обычный RGB.


Порядок следования байтов в вашем 32-битном числе может отличаться от того, что я предполагаю выше. Самый простой способ проверить это - поставить перед камерой красную карточку и посмотреть, что из этого выйдет, затем зеленую, а затем синюю. Четыре канала (R, G, B, A) должны быть заданы следующим образом, но это может быть вопросом эксперимента:

(im    ) & 0xff
(im>>8 ) & 0xff
(im>>16) & 0xff
(im>>24) & 0xff
0 голосов
/ 17 ноября 2018

Для вывода цветного изображения с помощью cv2 необходимо, чтобы изображение имело форму (x,y,3), последняя ось - цвета.

Поскольку ваши данные являются представлением RGBA в int32, я предполагаю, что каждое число на самом деле содержит 4 разных числа, где первые 2 байта - это uint8 красного, второй зеленый, третий синий и последний альфа: (0000 0001, 0000 0010, 0000 0100,0000 1000) в этом примере r равно 1, g равно 2, b равно 4 и альфа равно 8.
Вам нужно будет извлечь эти 8 байтов в отдельные цвета.

Кроме того, имейте в виду, что цветовое пространство cv2 равно BGR, а не RGB, поэтому вам придется переключать каналы после преобразования.

...