如何将 32bpp 图像转换为索引格式?
以下是详细信息(顺便说一句,我使用的是 C#):
我从服务器收到一个 32bpp 图像(JPEG 压缩)。 在某些时候,我想使用位图的 Palette 属性将过饱和的像素(亮度 > 240)着色为红色。 为此,我需要将图像转换为索引格式。
我尝试过将图像转换为 GIF,但质量有所损失。 我尝试通过这些方法创建索引格式的新位图:
// causes a "Parameter not valid" error
Bitmap indexed = new Bitmap(orig.Width, orig.Height, PixelFormat.Indexed)
// no error, but the resulting image is black due to information loss I assume
Bitmap indexed = new Bitmap(orig.Width, orig.Height, PixelFormat.Format8bppIndexed)
我现在不知所措。 该图像中的数据会被用户不断更改,因此我不想手动设置亮度 > 的像素。 240 如果我能避免的话。 如果我可以在创建图像时设置调色板一次,我的工作就完成了。 如果我一开始就以错误的方式处理这个问题,请告诉我。
编辑:谢谢大家,这里有一些关于我试图完成的事情的更多细节。
我们正在以高分辨率扫描组织切片(病理学应用)。 我编写了实际扫描仪的接口。 我们使用线扫描相机。 为了测试相机的线速率,用户扫描非常小的部分并查看图像。
图像显示在轨迹栏旁边。 当用户移动轨迹栏(调整线速率)时,我会更改图像的整体强度,尝试对新线速率下的图像进行建模。 我当前使用 ImageAttributes 和 ColorMatrix 对象来执行此操作。
当用户调整轨迹栏时,我调整矩阵。 这不会给我每个像素的信息,但性能非常好。 我可以在这里使用LockBits和一些不安全的代码,但如果可能的话我宁愿不重写它。 创建新图像时,我希望所有像素的亮度值 > 240 被染成红色。 我认为预先为位图定义调色板将是一种干净的方法。
So here are the details (I am using C# BTW):
I receive a 32bpp image (JPEG compressed) from a server. At some point, I would like to use the Palette property of a bitmap to color over-saturated pixels (brightness > 240) red. To do so, I need to get the image into an indexed format.
I have tried converting the image to a GIF, but I get quality loss. I have tried creating a new bitmap in an index format by these methods:
// causes a "Parameter not valid" error
Bitmap indexed = new Bitmap(orig.Width, orig.Height, PixelFormat.Indexed)
// no error, but the resulting image is black due to information loss I assume
Bitmap indexed = new Bitmap(orig.Width, orig.Height, PixelFormat.Format8bppIndexed)
I am at a loss now. The data in this image is changed constantly by the user, so I don't want to manually set pixels that have a brightness > 240 if I can avoid it. If I can set the palette once when the image is created, my work is done. If I am going about this the wrong way to begin with please let me know.
EDIT: Thanks guys, here is some more detail on what I am attempting to accomplish.
We are scanning a tissue slide at high resolution (pathology application). I write the interface to the actual scanner. We use a line-scan camera. To test the line rate of the camera, the user scans a very small portion and looks at the image.
The image is displayed next to a track bar. When the user moves the track bar (adjusting line rate), I change the overall intensity of the image in an attempt to model what it would look like at the new line rate. I do this using an ImageAttributes and ColorMatrix object currently.
When the user adjusts the track bar, I adjust the matrix. This does not give me per pixel information, but the performance is very nice. I could use LockBits and some unsafe code here, but I would rather not rewrite it if possible. When the new image is created, I would like for all pixels with a brightness value of > 240 to be colored red. I was thinking that defining a palette for the bitmap up front would be a clean way of doing this.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
从 32bpp 到 8bpp 索引几乎总是会导致质量损失,除非原始图像的颜色总数少于 256 色。
您可以创建另一个图像,该图像是受影响的红色像素的叠加层,然后显示这两个图像吗?
既然你追求的是亮度> 240,您可以先将叠加层转换为灰度,然后进行索引以获得过亮的像素。
一旦你标记了罪犯,你就不会指定你要做什么,所以我不知道这是否有效。
Going from 32bpp to 8bpp indexed will almost always result in quality loss, unless the original image has less than 256 colors total.
Can you create another image that is a overlay with the affected pixels red, then show both of those?
Since you are going for brightness > 240, you can convert the overlay to grayscale first, then to indexed to get the overbright pixels.
You don't specify what you are doing with it once you have tagged the offenders, so I don't know if that will work.
听起来像是可以使用像素着色器轻松完成的事情。 即使是非常早期的着色器模型也会支持这样简单的东西。
然而问题是:
您能否在您的应用程序中包含着色器支持而不会太匆忙?
你了解着色器编程吗?
编辑:
你可能没有 3D 上下文,你可以做这样的事情 =/
我主要只是表达我的想法。
用单个 CPU 实时逐像素操作图片应该是可行的,不是吗?
如果没有,请研究 GPGPU 编程和 Open CL。
再次编辑:
如果您提供有关该应用程序实际功能的更多详细信息,我们可能会提供更多帮助? 例如,如果您正在制作一个网络应用程序,那么我的建议就没有意义。
Sounds like something you could do easily with a pixel shader. Even very early shader models would support something as easy as this.
The question is however:
Can you include shader support in your application without too much hastle?
Do you know shader programming?
EDIT:
You probably don't have a 3D context where you can do stuff like this =/
I was mostly just airing my thoughts.
Manipulating the picture pixel by pixel should be doable in real-time with a single CPU shouldn't it?
If not, look into GPGPU programming and Open CL.
EDIT AGAIN:
If you gave some more details about what the app actually does we might help a bit more? For example, if you're making a web-app none of my tips would make sense.
感谢大家的帮助。 似乎可以使用 ImageAttributes 类并简单地设置颜色重映射表来解决这个问题。
再次感谢您的帮助,至少我学到了一些东西。
Thanks for the help everyone. It seems that this can be solved using the ImageAttributes class and simply setting a color remap table.
Thanks for the help again, at least I learned something.