opencv 隱藏浮水印
本文章舉例的是灰階的圖片。我們先來講解圖片的LSB與MSB。灰階的圖片的像素值是0~255。
一張圖片是由很多的0~255的數值所組成。就是所謂的像素。
8個 bit,可以表示值的範圍為 0~255。
因此,比方說 226的二進制就是 11100010。
其中,越靠近左邊的越重要。也就是所謂的MSB。然後靠近右邊的相對來說較為不重要,就是所謂的LSB。
像是二進制中 1000000 轉換成十進制是等於128。相當於255的一半。
當我們要做隱藏浮水印時,就可以將MSB轉換成LSB在加入另一張圖片中。
例如:
今天有個照片的其中一個像素是 11011011 ,而我們要在這個的照片中加入一個隱藏的圖片。
那我們可以將 11011011 的LSB去除。變成 11011010。
假如我們要加入的圖片是 11001011 我們可以將他的MSB保留,其他的bit去除。
變成 10000000 然後在右邊位移7個bit。變成 00000001。
然後再將兩個像素值相加。 11011010 + 00000001 = 11011011。
我們這邊以圖片來舉例。
下圖是原始圖片。
這是我們要加入的浮水印。
這是我們加入浮水印的結果。可以發現是完全看不出來有浮水印的。
當我們要顯示浮水印時。只需要將上面所舉的例子。
只要將 11011011 的數值,往左邊移7格。就會變成 1000000 。
我們就可以看到浮水印出現在圖片中了。
下方為完整的程式碼:
#include<opencv2/opencv.hpp>
#include<iostream>
using namespace cv;
using namespace std;
int main()
{
Mat src = imread("test1.png", 0);
Mat qrcode = imread("test_qrcode.png", 0);
for (int i = 0; i < qrcode.rows; i++) {
for (int j = 0; j < qrcode.cols; j++) {
src.at<uchar>(i, j) = (int)(src.at<uchar>(i, j) & 0b11111110) + \
((int)(qrcode.at<uchar>(i, j) & 0b10000000) >> 7);
}
}
imwrite("result_qrcode.png", src);
Mat result_qrcode = imread("result_qrcode.png", 0);
for (int i = 0; i < result_qrcode.rows; i++) {
for (int j = 0; j < result_qrcode.cols; j++) {
if ((result_qrcode.at<uchar>(i, j) & 0b00000001)) {
result_qrcode.at<uchar>(i, j) = 255;
}
else {
result_qrcode.at<uchar>(i, j) = 0;
}
}
}
imshow("src", src);
imshow("qrcode", qrcode);
imshow("result_qrcode", result_qrcode);
waitKey();
}
如需更多客製化服務:
另外有安裝或者其他使用上的問題,皆可參考下列篇章:
如有任何問題歡迎下方留言討論!!!
留言列表