iT邦幫忙

2024 iThome 鐵人賽

DAY 5
0
AI/ ML & Data

AI 影像處理 30天系列 第 5

[AI 影像處理 30天] [Day 05] 前後景分離 (上) : 以 OpenCV 實作圖像二值化

  • 分享至 

  • xImage
  •  

昨天我們利用 stable-diffusion-webui-depthmap-script 套件取得了場景照的深度圖,但距離分離前後景還差得遠,所以今天我們進一步來用二值化的技術試著把前後景分離看看吧!

depthmap


圖像二值化

二值化是一種影像處理技術,用來將灰階圖像轉換為只有兩個值的圖像,通常是黑色(0)和白色(255)。這種轉換通過應用一個閾值(threshold)來完成:大於或等於閾值的像素被設為白色,小於閾值的像素被設為黑色。二值化在模式識別、物件偵測以及文件處理(如文字辨識)等領域中非常常見,因為它可以簡化圖像數據並強調主要結構。

記得先 import 昨天那篇文所 import 的套件~

def binarized(image: Image, threshold=38) -> Image:
    if not image.mode.startswith('I'):
        raise Exception(f"{image.mode = }, but it must be 'I'!")
    image_array = np.array(image) // 256
    image_array = image_array.astype(np.uint8)
    _, bin_image = cv2.threshold(image_array, int(threshold*2.55), 255, cv2.THRESH_BINARY)
    return (binarized_image := Image.fromarray(bin_image))

上述函式是圖像二值化的 Python 實作程式碼,步驟說明如下:

  1. 檢查輸入圖像的模式是否以 'I' 開頭,這表示圖像是32位整數模式。如果圖像不符合這個要求,則拋出異常。
  2. 將圖像轉換為 NumPy 陣列後,每個像素值都被縮小 256 倍,這是為了將原本可能非常大的整數範圍縮小至 8 位無符號整數的範圍(0-255)。
  3. 將圖像陣列的資料型態轉換為 np.uint8,即 8 位無符號整數,這是 OpenCV 處理圖像所需的格式。
  4. 使用 OpenCV 的 threshold 函式進行二值化。閾值被設定為 threshold*2.55,這是將 0-100 的範圍轉換為 0-255 範圍的標準化操作。大於或等於該閾值的像素被設為 255(白色),否則設為 0(黑色)。
  5. 最後,將二值化後的 NumPy 陣列轉換回 PIL 圖像,並返回該圖像。
    這個函式的核心是將符合特定條件的像素轉換為白色,其他則轉換為黑色,從而達到二值化的效果。

至於那個閾值要設多少嘛 —— 筆者建議可用迴圈把多個閾值遍歷一次並根據依使用情境建立的判斷標準 (e.g. 黑色像素占比) break 出來。

輸出結果如下:
binarized

其實這樣並沒有完全取得背景的範圍,但已經比單純的深度圖明確地分離許多了,明天我們再用另一個工具將背景完全框出來!


撰文者: PikasXYZ


上一篇
[AI 影像處理 30天] [Day 04] 深究深度圖生成套件 stable-diffusion-webui-depthmap-script 的用途
下一篇
[AI 影像處理 30天] [Day 06] 前後景分離 (下) : 以 Segment Anything Model 搭配二值化圖像取出前景
系列文
AI 影像處理 30天30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言