1. 程式人生 > >Node+vue實現視訊中的人臉識別

Node+vue實現視訊中的人臉識別

做什麼事, 思路最重要

  • 視訊的人臉識別, 說白了也就是圖片的識別, 因為視訊的每一幀都是一張圖片, 我們只要把每一幀的圖片的人臉都識別出來, 那也就實現了視訊的人臉識別。總體思路是:擷取視訊中的圖片,然後傳到伺服器端做識別,把識別結果(座標和寬高)傳回前端,前端做標記。

現在開始

  • 第一步: 我們需要把圖片從視訊中截取出來, 那現在就出現了三個問題, 1.怎麼從視訊是截圖片;2.截圖的頻率是多少?3.怎麼把圖片轉到伺服器?

    • 回答第一個問題:使用Canvas的toDataURL方法,這個方法可以實時的把視訊的畫面,截成Base64圖片編碼,效率高,也方便。

    • 回答第二個問題:畫面之幀率高於每秒約10-12幀的時候,人眼就會認為是連貫的。所以我們先取一個低值,每100毫秒截一次圖

    • 回答第三個問題:用Ajax嗎?當然可以,但是不太合適。對於這種前後端頻繁傳輸資料的情況,用Websocket是最好的選擇。前後端我們選擇socket.io來實現,傳送門

  • 第二步:Node端識別圖片。在影象識別領域,opencv是一套標準的解決方案,但是opencv由是C++編寫,也有JavaPython的介面,但是沒有JS的介面,沒辦法了嗎?當然不是,已經有大神出口了Node版的,叫node-opencvnode-opencv不是重寫了opencv,只是在Node層呼叫C++層的cv,最終還是在C++裡面執行的。

    • 安裝opencvnode-opencv可以對照之前的文章,這個東西比較難安裝,我也是折騰好久才安裝上

    • 使用node-opencv識別圖片中的人臉,核心程式碼如下:

    // 引入opencv
    const cv = require('opencv')
    // fileName就是我們前端的Base64傳到後端生成真正圖片的地址
    // cv.FACE_CASCADE引數為訓練集,因為人臉只是cv的一個應用領域,他還可以識別車、動物、植物、大樓等物件,你傳什麼訓練集,他就識別什麼
    cv.readImage(fileName, function (err, im) {
        im.detectObject(cv.FACE_CASCADE, {}, function (err, faces) {
            // 為什麼是複數呢?因為一張圖中可能有多張臉,每一張臉都有四的值:x/y/width/height,這四的基本值
            console.log(faces)
        })
    })
    • 識別出座標和寬高,就可以把這些資訊通過websocket轉到前端,前端做展示

  • 具體的技術細節,請移步Github:人臉識別原始碼