訂閱
糾錯
加入自媒體

?使用Mediapipe對圖像進行手部地標檢測

概述

在本文中,我們將以深度庫即 Mediapipe為基礎庫,以及其他計算機視覺預處理的CV2庫來制作手部地標檢測模型。市場上有很多關于這種問題的用例,例如商業(yè)相關的虛擬現實、游戲部分的實時體驗。

行業(yè)用例

1. 智能家居:這是計算機視覺的現代用例之一,人們使用智能家居來過上更舒適的生活,這就是為什么它不再是一個小眾領域,它也正在蔓延到普通家庭。

2. 智能電視:我們經?吹竭@種用例,你可以用手勢來改變音量、改變頻道等等。

3. 游戲:對于真正的體驗,這項技術越來越多地融入互動游戲。

讓我們建立我們的手部檢測模型

導入庫

在這里,我們將導入整個管道中需要的所有庫。

import cv2

import numpy as np

import mediapipe as mp

import matplotlib.pyplot as plt

使用 Mediapipe 初始化手的地標檢測模型

第一步是使用有效參數初始化模型,無論我們采用哪種檢測技術,它可以是Mediapipe 或Yolo,初始化模型很重要,遵循相同的原則,我們將遵循所有給定的步驟:

# First step is to initialize the Hands class an store it in a variable

mp_hands = mp.solutions.hands


# Now second step is to set the hands function which will hold the landmarks points

hands = mp_hands.Hands(static_image_mode=True, max_num_hands=2, min_detection_confidence=0.3)


# Last step is to set up the drawing function of hands landmarks on the image

mp_drawing = mp.solutions.drawing_utils

代碼分解:

1. 首先,使用mp.solutions.hands初始化變量 mp_hands。然后使用相同的變量通過mp.solutions.hands.Hands()為hands設置函數。

2. 到目前為止,我們了解了手模型初始化的結構,現在讓我們深入研究函數中使用的參數hands。

· static_image_mode: 該參數將布爾值作為其有效值,即它可以是True或False。當處理視頻流時,默認條件是 False ,這意味著它會降低處理延遲,即它會繼續(xù)專注于特定的手并定位相同的手,直到它追蹤的手消失,當我們必須檢測實時流或視頻中的手時,這可能是有益的,根據我們的要求,我們必須檢測圖像上的地標,因此我們將值設置為True。

· max_num_hands:此參數將指示模型將在一個實例中檢測到的最大手數。默認情況下,該值為 2,這也是有意義的,盡管我們可以更改它,但我們希望至少檢測到一雙手。

· min_detection_confidence:它提供了置信水平的閾值。最小檢測置信度的理想范圍是 [0.0,1.0],默認情況下,它保持為 0.5,這意味著如果置信度低于 50%,則在輸出圖像中根本不會檢測到手。

最后,我們將使用mp.solutions.drawing_utils,它將負責在輸出圖像上繪制所有手的地標,這些地標由我們的 Hands 函數檢測到。

讀取圖像

在這里,我們將首先使用cv2.imread()讀取要在其上執(zhí)行手部檢測的圖像,并使用matplotlib庫來顯示該特定輸入圖像。

# Reading the sample image on which we will perform the detection

sample_img = cv2.imread('media/sample.jpg')

# Here we are specifing the size of the figure i.e. 10 -h(huán)eight; 10- width.

plt.figure(figsize = [10, 10])

# Here we will display the sample image as the output.

plt.title("Sample Image");plt.axis('off');plt.imshow(sample_img[:,:,::-1]);plt.show()

輸出:

執(zhí)行手部地標檢測

因此,現在我們已經初始化了我們的手部檢測模型,下一步將是處理輸入圖像上的手部地標檢測,并使用上述初始化模型在該圖像上繪制所有 21 個地標,我們將通過以下步驟。

results = hands.process(cv2.cvtColor(sample_img, cv2.COLOR_BGR2RGB))

if results.multi_hand_landmarks:
   

  for hand_no, hand_landmarks in enumerate(results.multi_hand_landmarks):

       print(f'HAND NUMBER: {hand_no+1}')

       print('-----------------------')
       

       for i in range(2):

           print(f'{mp_hands.HandLandmark(i).name}:')

           print(f'{hand_landmarks.landmark[mp_hands.HandLandmark(i).value]}')

輸出:

代碼分解:

1. 第一步,我們使用Mediapipe 庫中的process函數將手部地標檢測結果存儲在變量results中,同時我們將圖像從 BGR 格式轉換為 RGB 格式。

2. 在進入下一步時,我們將首先檢查一些驗證,是否檢測到點,即變量results應該存放了一些結果。

3. 如果是,那么我們將遍歷在圖像中檢測到的具有手部地標的所有點。

4. 現在在另一個循環(huán)中,我們可以看到只有 2 次迭代,因為我們只想顯示手的 2 個地標。

5. 最后,我們將根據要求打印出所有檢測到并過濾掉的地標。

從上面的處理中,我們發(fā)現所有檢測到的地標都被歸一化為通用尺度,但是現在對于用戶端,這些縮放點是不相關的,因此我們會將這些地標恢復到原始狀態(tài)。

image_height, image_width, _ = sample_img.shape

if results.multi_hand_landmarks:

   for hand_no, hand_landmarks in enumerate(results.multi_hand_landmarks):
       

       print(f'HAND NUMBER: {hand_no+1}')

       print('-----------------------')
       

       for i in range(2):    

           print(f'{mp_hands.HandLandmark(i).name}:') 

           print(f'x: {hand_landmarks.landmark[mp_hands.HandLandmark(i).value].x * image_width}')

           print(f'y: {hand_landmarks.landmark[mp_hands.HandLandmark(i).value].y * image_height}')

           print(f'z: {hand_landmarks.landmark[mp_hands.HandLandmark(i).value].z * image_width}n')

輸出:

代碼分解:

我們只需要在這里執(zhí)行一個額外的步驟,即我們將從我們定義的示例圖像中獲得圖像的原始寬度和高度,然后所有步驟將與我們之前所做的相同,唯一不同的將是現在地標點沒有專門縮放。

在圖像上繪制地標

由于我們已經從上述預處理中獲得了手部地標,現在是時候執(zhí)行我們的最后一步了,即在圖像上繪制點,以便我們可以直觀地看到我們的手部地標檢測模型是如何執(zhí)行的。

img_copy = sample_img.copy()

if results.multi_hand_landmarks:


   for hand_no, hand_landmarks in enumerate(results.multi_hand_landmarks):
       

       mp_drawing.draw_landmarks(image = img_copy, landmark_list = hand_landmarks,

                                 connections = mp_hands.HAND_CONNECTIONS)

   fig = plt.figure(figsize = [10, 10])

   plt.title("Resultant Image");plt.axis('off');plt.imshow(img_copy[:,:,::-1]);plt.show()

輸出:

代碼分解:

1. 首先,我們將創(chuàng)建原始圖像的副本,此步驟是出于安全目的,因為我們不想失去圖像的原創(chuàng)性。

2. 然后我們將處理之前所做的驗證工作。

3. 然后我們將遍歷手的每個地標。

4. 最后,借助mp_drawing.draw_landmarks函數,我們將在圖像上繪制地標。

5. 是時候使用 matplotlib 繪制圖像了,所以首先,我們將給出圖形大小(此處為 width-10 和 height-10),然后在最后繪制,imshow將 BGR 格式轉換為 RGB 格式后的圖像使用函數,因為對于 RGB 格式更有意義。

結論

在整個管道中,我們首先初始化模型,然后讀取圖像,查看輸入圖像,然后進行預處理。我們縮小了地標點,但這些點與用戶無關,因此我們將其恢復到原始狀態(tài),最后我們將在圖像上繪制地標。


       原文標題 : ?使用Mediapipe對圖像進行手部地標檢測

聲明: 本文由入駐維科號的作者撰寫,觀點僅代表作者本人,不代表OFweek立場。如有侵權或其他問題,請聯系舉報。

發(fā)表評論

0條評論,0人參與

請輸入評論內容...

請輸入評論/評論長度6~500個字

您提交的評論過于頻繁,請輸入驗證碼繼續(xù)

暫無評論

暫無評論

    掃碼關注公眾號
    OFweek人工智能網
    獲取更多精彩內容
    文章糾錯
    x
    *文字標題:
    *糾錯內容:
    聯系郵箱:
    *驗 證 碼:

    粵公網安備 44030502002758號