使用Boost.GIL将图像转换为“原始”字节 [英] Using Boost.GIL to convert an image into "raw" bytes
问题描述
我试图转向Boost GIL来替换一些类似的功能,我已经实现了它的可维护性生命的结束。
I'm trying to move towards Boost GIL to replace some similar functionality I've implemented that is reaching the end of its maintainable life.
我有现有的代码,使用 uint8_t *
可以使用24 BPP,8位RGB图像。我不能改变它,因为相同的接口用于暴露不同地方的图像(例如OpenGL缓冲区),并且已经有很多代码。
I have existing code that works with 24 BPP, 8bit RGB images using uint8_t*
. I can't change that as the same interface is used to expose images from different places (e.g. OpenGL buffers) and there's already quite a lot of code.
尝试以小步骤使用GIL,首先读取一个文件,并将字节逐个字节复制到 std :: vector
中,我可以使用它来管理存储,但仍然通过使用& vector [0]
获得 uint8_t *
。
Therefore I'm trying to use GIL in small steps, starting by reading a file and copying the pixels byte by byte into a std::vector<uint8_t>
which I can use to manage the storage, but still get a uint8_t*
by using &vector[0]
.
这可以在现有接口的后面透明地删除,直到重构有意义。
This can be dropped in transparently behind the existing interfaces until it's at a point where refactoring makes sense.
我认为这应该是使用 copy_pixels()
。
I thought this should be a simple case of using copy_pixels()
with two appropriately constructed views.
我整理了一个简单完整的例子,说明了我通过查看文档和尝试操作来实现的总和:
I've put together a minimal, complete example that illustrates the sum of what I've manage to achieve by looking over the documents and trying things out:
#include <boost/gil/rgb.hpp>
#include <boost/gil/extension/io/png_dynamic_io.hpp>
#include <stdint.h>
#include <vector>
int main() {
std::vector<uint8_t> storage;
{
using namespace boost::gil;
rgb8_image_t img;
png_read_image("test.png", img);
// what should replace 3 here to be more "generic"?
storage.resize(img.width()*img.height()*3);
// doesn't work, the type of the images aren't compatible.
copy_pixels(const_view(img),
interleaved_view(img.width(), img.height(), &storage[0], 3*img.width()));
}
}
我被困在哪里
这不编译:
Where I'm stuck
This doesn't compile:
error: cannot convert ‘const boost::gil::pixel<unsigned char, boost::gil::layout<boost::mpl::vector3<boost::gil::red_t, boost::gil::green_t, boost::gil::blue_t> > >’ to ‘unsigned char’ in assignment
这是相当不言自明的 - 不能自动转换为单个 unsigned char
。我以为我会尝试使用 copy_and_convert_pixels()
来解决这个问题,但是我看不到3:1的方法(即我有3 unsigned char
s在输出为源图像中的每个像素)这些转换的问题。转换似乎更多针对颜色空间转换(例如RGB-> HSV)或换行。
Which is fairly self-explanatory - an RGB pixel can't be converted to a single unsigned char
automatically. I thought I'd try using copy_and_convert_pixels()
to fix this, but I can't see a way around the 3:1 (i.e. I have 3 unsigned char
s in the output for every pixel in the source image) problem with these conversions. Conversion seems to be more aimed at colourspace conversions (e.g. RGB->HSV) or packing changes.
推荐答案
个别的颜色rgb8_pixel_t:
I would just push_back each color of the rgb8_pixel_t individually:
struct PixelInserter{
std::vector<uint8_t>* storage;
PixelInserter(std::vector<uint8_t>* s) : storage(s) {}
void operator()(boost::gil::rgb8_pixel_t p) const {
storage->push_back(boost::gil::at_c<0>(p));
storage->push_back(boost::gil::at_c<1>(p));
storage->push_back(boost::gil::at_c<2>(p));
}
};
int main() {
std::vector<uint8_t> storage;
{
using namespace boost::gil;
rgb8_image_t img;
png_read_image("test.png", img);
storage.reserve(img.width() * img.height() * num_channels<rgb8_image_t>());
for_each_pixel(const_view(img), PixelInserter(&storage));
}
...
}
...我不是GIL的专家。
...but I'm not an expert on GIL either.
这篇关于使用Boost.GIL将图像转换为“原始”字节的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!