我想将RGB图像转换为索引颜色类型。
这是我的C++代码。它可以将图像转换为灰度图像。
我应该怎么做?
Mat black_background = imread("image_path", IMREAD_COLOR);
Mat output;
cvtColor(black_background, output, cv::COLOR_RGB2GRAY);
imwrite("save_path", output);
magick input.png PNG8:result.png
convert input.png PNG8:result.png
PNG8:
前缀会强制生成调色板颜色的PNG格式图片。
如果你不想事后手动转换文件,可以使用OpenCV的imwrite()
将它们作为PNG文件写入文件系统,然后使用C++的system()
调用ImageMagick进行转换:
#include <stdlib.h>
...
imwrite('result.png', image);
// Delegate conversion to palette image to ImageMagick
system("magick result.png PNG8:result.png');
对于更加焦虑/敏锐的读者:
是的,与其他Unix工具不同,使用相同的文件作为ImageMagick的输入和输出是可以的,并且不会出现损坏的情况,因为在处理之前文件会被完整地读取,然后再写出。
是的,ImageMagick将隐式处理量化,以将图像中的颜色减少为调色板版本。
是的,您可以强制使用其他类型的PNG
文件,例如使用其他前缀的RGB24:result.png
将导致RGB888输出,RGB32:result.png
将导致RGBA8888输出,RGB48:result.png
将导致16位红色、16位绿色和16位蓝色输出等。
我为索引色图像编写了自己的编码器/解码器,通过手动对BMP和PNG格式进行编码/解码。它在我的生产环境中运行良好。
代码思路:手动查看BMP/PNG内部的块(例如png中的PLTE块)。示例代码如下,您也可以编写/修改您自己的代码。
代码的用法:
// sample usage
int main() {
Mat image_index = ...;
Mat palette = ...;
vector<uchar> encoded_bytes = imencode_palette_bmp(image_index, palette);
}
imwrite
来保存这样的图像。 - Dan Mašek