仅使用位操作是否可以有效地完成图像遮罩?
Can image masking be done efficiently using only bit operations?
我有一张位图,在将多个图层合成到一个目标位图中时需要将其用作图像遮罩。图像掩码是黑白图像,其中黑色指定应 不 绘制的像素,白色从源位图中绘制像素。
像素均为32位ARGB格式。
如上所述,掩码中的像素为黑色 (0xFF000000) 或白色 (0xFFFFFFFF)。
我正在尝试想出一种快速有效的方法来仅使用位操作将掩码像素与要绘制的位图中的像素组合起来。如果用于剪切的黑色像素的 alpha 值为 0,那将是微不足道的——那么我可以只对蒙版像素和位图像素执行与操作。
是否有某种位饱和指令,或类似的指令?我在想一些事情:
uint mask = maskPixel & 0x00FFFFFF;
saturate(mask);
// If the maskPixel was black, mask will be all 0s, so the result of saturation is still all 0s.
// If the maskPixel was white, mask will be 0x00FFFFFF, so the saturation will result in 0xFFFFFFFF
有什么想法吗?
下面的get_mask
函数将低位扩展为一个完整的unsigned int值。如果只有黑色或白色像素,这应该足够了。
#include <iostream>
#include <iomanip>
unsigned int get_mask(unsigned int pixel) {
return ~((pixel & 1)-1);
}
int main() {
const unsigned int white = 0x00ffffff;
const unsigned int black = 0x00000000;
std::cout << std::hex << std::setfill('0');
std::cout << std::setw(8) << white << " => " << std::setw(8) << get_mask(white) << "\n";
std::cout << std::setw(8) << black << " => " << std::setw(8) << get_mask(black) << "\n";
}
我有一张位图,在将多个图层合成到一个目标位图中时需要将其用作图像遮罩。图像掩码是黑白图像,其中黑色指定应 不 绘制的像素,白色从源位图中绘制像素。
像素均为32位ARGB格式。
如上所述,掩码中的像素为黑色 (0xFF000000) 或白色 (0xFFFFFFFF)。
我正在尝试想出一种快速有效的方法来仅使用位操作将掩码像素与要绘制的位图中的像素组合起来。如果用于剪切的黑色像素的 alpha 值为 0,那将是微不足道的——那么我可以只对蒙版像素和位图像素执行与操作。
是否有某种位饱和指令,或类似的指令?我在想一些事情:
uint mask = maskPixel & 0x00FFFFFF;
saturate(mask);
// If the maskPixel was black, mask will be all 0s, so the result of saturation is still all 0s.
// If the maskPixel was white, mask will be 0x00FFFFFF, so the saturation will result in 0xFFFFFFFF
有什么想法吗?
下面的get_mask
函数将低位扩展为一个完整的unsigned int值。如果只有黑色或白色像素,这应该足够了。
#include <iostream>
#include <iomanip>
unsigned int get_mask(unsigned int pixel) {
return ~((pixel & 1)-1);
}
int main() {
const unsigned int white = 0x00ffffff;
const unsigned int black = 0x00000000;
std::cout << std::hex << std::setfill('0');
std::cout << std::setw(8) << white << " => " << std::setw(8) << get_mask(white) << "\n";
std::cout << std::setw(8) << black << " => " << std::setw(8) << get_mask(black) << "\n";
}