今天學習的目標依舊是研究影像的合成,重點還是在 ROI 與掩膜相關知識
本文的最終目標,把下面這個章扣在任意圖片上,當然你可以把這個章更換成任意的,例如發票章,

PNG 圖片相關通道說明
讀取圖片比較簡單,直接進行操作即可,重點注意 imread 中第三個引數即可,
# 讀取圖片
def read_img(path):
img = cv.imread(path,-1)
print(img.shape)
dst = cv.resize(img,(130,124))
cv.imshow("img", dst)
if __name__ == "__main__":
# png 透明圖片路徑
path = r"./18_png.png"
read_img(path)
cv.waitKey()
cv.destroyAllWindows()
下面的步驟是將 PNG 圖片,透明部分修改為黑色,
def alpha2black_opencv2(img):
width,height,channels = img.shape
for yh in range(height):
for xw in range(width):
color_d = img[xw, yh]
# 找到alpha通道為 0 的像素
if(color_d[3] == 0):
# 改變像素顏色為黑色
img[xw, yh] = [0, 0, 0, 0]
# 回傳一個不透明的BGR圖片
return cv.cvtColor(img, cv.COLOR_BGRA2BGR)
回圈每一個像素點,當發現 alpha 通道為 0 的時候,就修改該點像素為 [0,0,0,0],
這里要注意的是 png 圖片每個像素點的顏色為 [ 76 112 71 0] 格式,其中最后一個值表示 alpha 通道值,
該通道透明部分都為 0,所以修改該值即可,
運行效果截圖:

如果你還有疑問,可以這樣進行測驗,
獲取任意透明部分的像素顏色值,或者獲取任意有顏色部分像素值,
透明部分的值為:[ 76 112 71 0]
非透明部分的值為:[ 0 0 255 255]
那 alpha 部分有其他值嗎?肯定存在呀,這個是透明度,可以做如下嘗試,就拿本案例提供的圖片來說
當 alpha 通道為 255 的時候,我們將其調整為 100,看一下對比效果,
def alpha2black_opencv2(img):
width, height, channels = img.shape
print(img[50, 30])
print(img[50, 30][0])
for yh in range(height):
for xw in range(width):
color_d = img[xw, yh]
if(color_d[3] == 255):
img[xw, yh, 3] = 100
print(img[62, 62])
print(img[62, 62][0])
# 回傳一個不透明的BGR圖片
print(img.shape)
cv.imwrite("./1.png", img)
return img
# return cv.cvtColor(img, cv.COLOR_BGRA2BGR)
注意上述代碼在運行之后,不要通過 cv.imshow() 展示,要通過 cv.imwrite() 寫入到檔案中,才可查看效果,

加載待蓋章圖片
加載背景圖,并且在背景圖上找到 ROI 區域,
先整理邏輯,一會在查看代碼:
第一步:找到目標 ROI 區域,這個區域要和印章圖片大小一致,不一致無法進行圖片相加操作
第二步:在目標區域中把印章紅色區域摳出來,采用任何方式都可以,但是要把印章紅色區域全部置為黑色
第三步:將印章圖片與第二步合成的圖片進行二次相加操作,因為在第二步已經將印章區域像素值設定為 0,所以在于印章合并的時候,黑色區域會顯示成印章
第四步:將合成好的圖片還原回去,
最終完整呈現的代碼如下:
import cv2 as cv
def alpha2black_opencv2(img):
width, height, channels = img.shape
for yh in range(height):
for xw in range(width):
color_d = img[xw, yh]
if(color_d[3] == 0):
img[xw, yh] = [0, 0, 0, 0]
return cv.cvtColor(img, cv.COLOR_BGRA2BGR)
# 讀取圖片
def read_img(path):
img = cv.imread(path, -1)
print(img.shape)
dst = cv.resize(img, (130, 124))
# cv.imshow("img", dst)
# 接下來將 png 透明部分處理成黑色
ret = alpha2black_opencv2(dst)
# cv.imshow("ret", ret)
# 加載背景圖
bg = cv.imread("./bg.jpeg")
# 獲取目標 roi
roi = bg[300:424, 400:530]
# cv.imshow("roi",roi)
# 將印章與roi進行疊加
mask = cv.cvtColor(ret, cv.COLOR_BGR2GRAY)
# 想要得到紅色印章和背景融合的圖
# 獲取印章的二值化影像,紅色印章為純白色
thresh, new_mask = cv.threshold(mask, 10, 255, cv.THRESH_BINARY)
# 獲取反向圖
mask_inv = cv.bitwise_not(new_mask)
# cv.imshow("mask_inv",mask_inv)
# 第一步:在原圖中摳出印章區域,即印章區域為黑色
new_img = cv.add(roi, 1, mask = mask_inv)
# cv.imshow("new_img", new_img)
# 第二步,將摳出印章區域得到的圖片與印章相加,獲取到合成圖
replace_img = cv.add(new_img,ret)
print(replace_img.shape)
# cv.imshow("bg", bg)
# 第三步,將合成好的圖片,送回到原圖
bg[300:424, 400:530] = replace_img
cv.imshow("bg",bg)
if __name__ == "__main__":
# png 透明圖片路徑
path = r"./18_png.png"
read_img(path)
cv.waitKey()
cv.destroyAllWindows()
兩張單獨的圖片如下:

合成之后的效果圖如下,整體效果滿意,但是還是存在黑邊,接下來我們還是繼續研究這個東東,下篇博客見,

OpenCV 尾聲
1 個小時又過去了,對 Python OpenCV 相關的知識點,你掌握了嗎?
空閑之余,可以訂閱橡皮擦的爬蟲百例課程學習爬蟲知識,
想學 Python 爬蟲,可以訂閱橡皮擦專欄哦~ 🈲🈲🈲🈲 點擊發現驚喜 🈲🈲🈲🈲
今天是持續寫作的第 57 / 100 天,
如果你有想要交流的想法、技術,歡迎在評論區留言,
如果你想跟博主建立親密關系,可以關注博主,或者關注博主公眾號 “
非本科程式員”,了解一個非本科程式員是如何成長的,
博主 ID:夢想橡皮擦,希望大家點贊、評論、收藏
CSDN認證博客專家
高級產品經理
互聯網從業者
業余編程愛好者
轉載請註明出處,本文鏈接:https://www.uj5u.com/houduan/250693.html
標籤:python
上一篇:了解js逆向的第一天
下一篇:通過爬蟲實作CSDN自動點贊
