How do I extract the width and height of a PNG from looking at the header in objective c?

倾然丶 夕夏残阳落幕 提交于 2019-12-03 11:59:50

Rationale

According to the PNG specification:

The first eight bytes of a PNG file always contain the following (decimal) values: 137 80 78 71 13 10 26 10

So you have to read those to make sure you really have a PNG file.

Then,

The IHDR chunk must appear FIRST. It contains:

Width: 4 bytes

Height: 4 bytes

etc...

So according to the structure of chunks, you first have to read the four bytes representing the length of the chunk's data field, then the four bytes representing the chunk's name, then the two 32-bit integers representing width and height, eight bytes in total.

So, the exact minimal number of bytes you must read in order to determine width and height is 8 + 4 + 4 + 8 = 24 bytes.

Objective-C code

Once you have your NSData object, you simply have to access the bytes that it contains:

unsigned char buffer[24];
[data getBytes:buffer length:24];

Optionally, but I recommend it strongly, check that you indeed have a PNG file:

unsigned char png_header[] = {137, 80, 78, 71, 13, 10, 26, 10};
if (memcmp(buffer, png_header, 8)) {
     // this is not a PNG !
}

Make sure you have an IHDR:

unsigned char ihdr_name[] = "IHDR";
if (memcmp(buffer+8+4, ihdr_name, 4)) {
    // not an IHDR chunk, invalid PNG file
}

Width and height can be accessed as big-endian encoded unsigned ints at offset 24 minus 8 and minus 4 bytes respectively:

unsigned int width = OSReadBigInt32(buffer + 24 - 8);
unsigned int height = OSReadBigInt32(buffer + 24 - 4);

Edit: Fixed buffer reading code: PNG actually stores integers in big-endian.

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!