Попытка извлечь значения пикселей из заданного изображения PNG

Попытка понять формат PNG.

Рассмотрим это изображение PNG:

enter image description here

Изображение взято из здесь

В Hex Editor это выглядит так:

89 50 4E 47 0D 0A 1A 0A 00 00 00 0D 49 48 44 52 00 00 00 80 00 00 00 44 08 02 00 00 00 
C6 25 AA 3E 00 00 00 C2 49 44 41 54 78 5E ED D4 81 06 C3 30 14 40 D1 B7 34 DD FF FF 6F 
B3 74 56 EA 89 12 6C 28 73 E2 AA 34 49 03 87 D6 FE D8 7B 89 BB 52 8D 3B 87 FE 01 00 80 
00 00 10 00 00 02 00 40 00 00 08 00 00 01 00 20 00 00 04 00 80 00 00 10 00 00 02 00 40 
00 00 08 00 00 01 00 20 00 00 00 D4 5E 6A 64 4B 94 F5 98 7C D1 F4 92 5C 5C 3E CF 9C 3F 
73 71 58 5F AF 8B 79 5B EE 96 B6 47 EB F1 EA D1 CE B6 E3 75 3B E6 B9 95 8D C7 CE 03 39 
C9 AF C6 33 93 7B 66 37 CF AB BF F9 C9 2F 08 80 00 00 10 00 00 02 00 40 00 00 08 00 00 
01 00 20 00 00 04 00 80 00 00 10 00 00 02 00 40 00 00 08 00 00 01 00 20 00 00 8C 37 DB 
68 03 20 FB ED 96 65 00 00 00 00 49 45 4E 44 AE 42 60 82

Эквивалентные символы:

‰PNG........IHDR...€...D.....Æ%ª>...ÂIDATx^íÔ..Ã[email protected]Ñ·4Ýÿÿo³tVê‰.l(sâª4I.‡ÖþØ{‰
»R.;‡þ..€[email protected] ....€[email protected] ...Ô^jdK"õ˜|Ñô’\\>Ïœ?sqX_¯
‹y[î–¶GëñêÑζãu;湕.ÇÎ.9ɯÆ3"{f7Ï«¿ùÉ/.€[email protected] ....€[email protected] ..Œ7Ûh. 
ûí–e....IEND®B`‚

То же самое показано на следующем снимке экрана редактора HEX:

enter image description here

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

Кусок IHDR должен появиться FIRST. Он содержит:

Width:              4 bytes
Height:             4 bytes
Bit depth:          1 byte
Color type:         1 byte
Compression method: 1 byte
Filter method:      1 byte
Interlace method:   1 byte

Ниже я начинаю читать данные HEX последовательно:

1- Первые 8-байтовые: это 8-байтовая подпись

 89 50 4E 47 0D 0A 1A 0A

Эквивалентно это:% PNG, как видно из редактора HEX

Правильное изображение PNG должно содержать кусок IHDR, один или несколько фрагментов IDAT и кусок IEND.

2- Chunk: Length

 00 00 00 0D

3-Chunk: Тип фрагмента

 49 48 44 52

Что такое IHDR.

http://www.w3.org/TR/PNG-Chunks.html

4 Chunk: Ширина изображения (в десятичном разряде 128)

00 00 00 80

5 Chunk: Высота изображения (в десятичном разряде 68)

00 00 00 44

6- Chunk: BIT DEPTH (1 байт)

08

7- Chunk: Тип цвета

02

8- Метод сжатия

00

9- Метод фильтра:

00

10- Метод чередования:

00

11- Какие следующие данные?

C6 25 AA 3E 00 00 00 C2

12 - IDAT

49 44 41 54

13. Что это за данные (после IDAT):

78 5E ED D4 81 06 C3 30 14 40 D1 B7 34 DD FF FF 6F B3 74 56 EA 89 12 6C 28 73 E2 AA 34 49 03 87 D6 FE D8 7B 89 BB 52 8D 3B 87 FE 01 00 80 00 00 10 00 00 02 00 40 00 00 08 00 00 01 00 20 00 00 04 00 80 00 00 10 00 00 02 00 40 00 00 08 00 00 01 00 20 00 00 00 D4 5E 6A 64 4B 94 F5 98 7C D1 F4 92 5C 5C 3E CF 9C 3F 73 71 58 5F AF 8B 79 5B EE 96 B6 47 EB F1 EA D1 CE B6 E3 75 3B E6 B9 95 8D C7 CE 03 39 C9 AF C6 33 93 7B 66 37 CF AB BF F9 C9 2F 08 80 00 00 10 00 00 02 00 40 00 00 08 00 00 01 00 20 00 00 04 00 80 00 00 10 00 00 02 00 40 00 00 08 00 00 01 00 20 00 00 8C 37 DB 68 03 20 FB ED 96 65 00 00 00 00

14-IEND:

49 45 4E 44

15- Последние 4 байта

 AE 42 60 82

Что это такое?

Может ли кто-нибудь помочь мне понять, пункты 11, 13 и 15 выше? И где значения Pixel? Изображение имеет (128 x 68 пикселей)

Цель знать эти детали:

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

ОБНОВЛЕНИЕ

Теперь я понимаю, что из-за сжатия я не смог бы найти значения пикселей.

У меня появилась идея, что я могу написать файл в OpenCV и сохранить его как png. Ну, теперь мой прямой вопрос: у меня есть двоичный файл с 16-разрядными значениями в сером шкале. Могу ли я написать это в OpenCV как 16-битный PNG?

Ответ 1

Хотя может быть интересно узнать, что на самом деле есть PNG-изображения, и как изображение фактически представлено в файле, вам не нужно знать это, чтобы сгенерировать PNG файл.

Обратите внимание, что PNG использует сжатие без потерь, что означает, что вы не получите два байта на пиксель.

Вы можете сгенерировать свое изображение в программе и вывести его в формате PNG, используя многие из библиотек, которые там есть. Например, вы можете сделать свое изображение в OpenCV, а затем вывести его с помощью imWrite. Один из параметров может выводить его на PNG.


Если у вас есть 16-разрядные пиксельные значения серого цвета, вы можете поместить их в Mat.

Затем преобразуем это в IplImage: Преобразование cv:: Mat в IplImage *

Затем вы можете вывести его в файл.

Ответ 2

Просто для полноты (eboix ответ прямо на месте)

11- Каковы следующие данные?

C6 25 AA 3E 00 00 00 C2

Каждый фрагмент заканчивается CRC (4 байта) и начинается с 4 байтов, которые указывают его длину. Таким образом, C6 25 AA 3E - это CRC предыдущего фрагмента (IHDR) и 00 00 00 C2 (194) - это длина следующего (IDAT) фрагмента.

Таким же образом, последние 4 байта - это CRC блока IEND.

Ответ 3

Я не выглядел слишком осторожно, но смотрел на структуру...

Q11. C6 25 AA 3E = CRC32 00 00 00 C2 = Размер следующего фрагмента

Q13. проверьте спецификацию png, о которой вы говорили ранее, которая похожа на фрагмент IDAT, который вы уже знаете, применяемое к нему сжатие!

Q15. AE 42 60 82 = CRC32