多種條件限制之下,如何完成真人實景遊戲場景下的人臉識別開鎖功能?雲加社區邀請到騰訊科技產品經理—高樹磊,分享他是如何用200行代碼,從系統架構、硬件選型、到系統搭建,一步步地實現此精緻小巧的人臉識別開鎖應用的,但願能和你們一道交流。
幫朋友實現了一我的臉識別進行開鎖的功能,用在他的真人實景遊戲業務中。幾個月來運行穩定,體驗良好,藉着這次宅家的時間,整理一下這個應用的實現過程。 html
總的來講需求描述簡單,但因爲約束比較多,在架構與選型上仍是花了些心思。python
因爲該遊戲還在線上服務中,此處就不放出具體操做的視頻了。部署效果以下圖所示:git
需求提出時比較明確,核心邏輯不復雜。github
畢竟是生意,因此在商言商,對實用性和成本要求很高,關鍵是不要影響遊戲過程,同時保證玩家體驗。算法
可能的架構方案有多種(不一樣方案間的比較,在文末進行),下面展開說明一下最終上線的方案。json
流程與效果,請參考前文「玩家體驗」 部份內容。網絡
a. 騰訊雲密鑰對架構
修改配置文件,用於適配騰訊雲帳號切換功能(測試帳號/正式帳號)。框架
b. 人員庫IDdom
修改配置文件,用於指定不一樣人員庫(測試庫/正式庫)。
c. 水印提示
更換對應圖片,實現更換水印。使用圖片管理,而不是文字配置的緣由,是因爲圖片配置模式無需字庫支持,無需配置顯示大小,易於圖案嵌入。因爲所見即所得,對維護人員要求低。
d. 關機選項
可配置任務完成後,是否自動關機。用於遊戲環境復位準備,減小復位工做量。
a. 系統運營管理
場景啓動時,統一上電。認證經過後,自動關機,完成復位。
b. 故障處理
軟硬件故障:沒法開機、可開機無顯示、可開機顯示系統異常,可開機未知異常等等,更換樹莓派或其它硬件。
網絡故障:正常運行,沒法認證,可查網絡+查雲日誌,解決網絡問題;
雲產品異常:運行4個月,未發生過,能夠忽略,如發生則聯繫雲售後;
硬件成本:500~600元。
備件成本:按1:1備件,500~600元。
運行成本:雲端0元,使用免費額度;電費網費,忽略不計。
樹莓派:終端主控
攝像頭:視頻輸入
傳感器:超聲波測距
顯示屏:視頻輸出
繼電器:控制電磁鎖
電磁鎖:控制保險箱門
圖片識別:使用圖片識別,而非視頻流,減小對網絡帶寬要求。
識別要求低:欠曝光照片也有高識別率。
觸發識別:玩家在場景內活動時間長,觸發模式避免了高頻認證、誤開鎖狀況,同時下降認證成本。
測距選型:超聲波傳感器技術成熟,成本低(3元);激光傳感器成本高(30元)
多進程:視頻處理與監測鑑權由兩個進程實現,避免了阻塞等狀況,同時使用進程間通訊,實現可靠交互。
a. 註冊帳號
按文檔指引,獲取API密鑰
b. 配置人臉識別
訪問官網控制檯,經過「新建人員庫->建立人員->上傳照片」,創建認證基礎。
其中所使用的「人員庫ID」是關鍵信息,用於後續API調用識別時,指定認證動做匹配的人員庫。
注:因爲此案例只識別一我的員,無需對人員ID進行匹配,故不用指定人員ID。
a. 安裝系統
訪問 www.raspberrypi.org 獲取鏡像,並進行安裝。注意必須安裝桌面版,不然須要單獨管理HDMI輸出。
b. 配置網絡
進入命令行,執行 "raspi-config",選擇"Network Options",配置WiFi接入點。爲了固定IP,編輯 /etc/dhcpcd.conf 文件,添加配置信息。
`
# 具體內容請參考你的本地網絡規劃 interface wlan0 static ip\_address\=192.168.0.xx/24 static routers\=192.168.0.1 static domain\_name\_servers\=192.168.0.1 192.168.0.2`
c. 安裝騰訊雲SDK
參考指引文檔,安裝調用騰訊雲API的依賴庫。
sudo apt\-get install python\-pip \-y pip install tencentcloud\-sdk\-python
d. 安裝圖像處理庫
系統默認安裝python2.7,但沒有 opencv 庫,須要安裝。(下載包體積較大,默認源爲國外站,比較慢。樹莓派改國內源方法,請自行百度,並挑選離本身近的源站)
sudo apt\-get install libopencv\-dev \-y sudo apt\-get install python\-opencv \-y
e. 部署代碼
訪問github獲取源碼,將src文件夾內容,複製到 /home/pi/faceid 下。
更改 /home/pi/faceid/config.json 中的配置信息,必須改成你的 雲API密鑰(sid/skey)、人員庫ID(facegroupid),其它配置按需調整。
f. 配置自啓動
須要配置圖形界面自啓動,保證視頻輸出由HDMI接口輸出至顯示屏,編輯 /home/pi/.config/autostart/faceid.desktop 寫入以下內容
Type\=Application Exec\=python /home/pi/faceid/main.py
樹莓派GPIO圖示:
a. 攝像頭
camera+rpi.png
b. 超聲波傳感器
c. 繼電器
4引腳側 接 樹莓派GPIO引腳
3端口側 接 電磁鎖
完成上述工做後,接電啓動系統,本地反饋查看顯示屏,雲端識別結果可查看系統日誌。
# 監測鑑權進程\-主進程 獲取應用配置(API ID/Key 等) 初始化GPIO引腳(準備控制 傳感器、繼電器) 啓動視頻管理進程(輔進程) 循環開始: if not 測距達到觸發標準: continue 與輔進程通訊(捕獲當前幀,並存入指定路徑,並添加「認證中」水印) 調用雲API,使用該幀圖片人臉識別 if 識別成功: 與輔進程通訊(變動水印爲「認證成功」) 等待5秒 關機 或 繼續運行(由config.json中 su2halt 字段指定) else: 與輔進程通訊(變動水印爲「認證失敗」) 等待2秒 與輔進程通訊(清除水印) # 視頻管理進程\-輔進程 初始化攝像頭 循環開始: 取幀 取進程間共享隊列 按消息進行不一樣操做(幀圖像保存/加不一樣水印/不處理) 輸出幀
a. 實時視頻
如上文僞代碼所示,經過逐幀處理,並連續輸出,顯示實時視頻。
b. 觸發識別
測距傳感器確認物體靠近,且0.3秒內距離變化小於2cm,確認爲待認證狀態。再延時0.3秒,進行圖像幀捕獲。再次延時的緣由是物體中止時,會有扭轉、微調等動做,若直接取幀,會因爲採光不足(上文提到的約束)出現模糊狀況,因此再次延時,確保捕獲穩定圖像。
c. 人臉識別
請參考文檔介紹
a. 水印原理
opencv中,提供了多種圖像處理函數,如:圖文處理(圖加字)、圖圖處理(圖間加/減/乘/除/位運算)等等。經過不一樣的處理方式,能夠實現 底圖加字、底圖加圖、掩膜處理等等多種效果。本案例中使用的是基於位運算的掩膜處理方式。
b. 水印圖片
爲了便於維護和更新,本案例中使用圖片作爲水印來源,避免字庫約束,也增大了靈活性,易於在水印中增長圖形,並以分辨率直接定義水印大小,所見即所得。
默認水印圖片爲白底黑字。
c. 水印處理邏輯
爲突出水印的浮動效果,將水印圖片中的黑色區域透明化後,疊加到原始圖片中。因爲字體透明效果,水印字體顏色隨基礎視頻變化,效果比較明顯。
源碼說明
# img1爲當前視頻幀(底圖),img2爲已讀取水印圖
def addpic(img1,img2):
# 關注區域ROI\-取底圖中將被水印圖編輯的圖像 rows, cols \= img2.shape\[:2\] roi \= img1\[:rows, :cols\] # 圖片灰化\-避免水印圖非純黑純白狀況 img2gray \= cv2.cvtColor(img2, cv2.COLOR\_BGR2GRAY) # 生成掩膜\-過濾淺色,位運算取非 ret, mask \= cv2.threshold(img2gray, 220, 255, 3) #cv2.THRESH\_BINARY mask\_inv \= cv2.bitwise\_not(mask) # 生成水印區圖像\-底圖裁出字體部分,生成水印區最終圖像,替換原圖水印區 img1\_bg \= cv2.bitwise\_and(roi, roi, mask\=mask\_inv) dst \= cv2.add(img1\_bg, img2) img1\[:rows, :cols\] \= dst return img1
水印效果示意圖(示意圖擴大了水印區,用於突出效果,實際應用方案中水印區較小)
示意圖.jpg
a. 超聲波測距
超聲波傳感器(4引腳:VCC、Trig、Echo、GND),Trig端輸出一個大於10μs的高電平,激活發出超聲波,並在收到反射波後,Echo端會輸出一個持續高電平,持續時間就是「發波至收波」的時間。
即:測距結果(米)=Echo端高電平時長*340米/2
b. 繼電器
使用的5V繼電器模塊有雙側接線,一側爲供電與信號(4引腳,兼容3.3V信號),一側爲通路開閉管理(3端口)。
繼電器在「通路管理側」實現了一個「單刀雙開關」的模式,經過「供電與信號」側「CH1引腳」的高低電平,控制單刀的方向。
在安裝過程當中,電磁鎖供電默認接繼電器常閉端,對繼電器給出信號後,繼電器切換到常開端,則電磁鎖斷電開鎖.
c. GPIO
GPIO(General-purpose input/output 通用輸入輸出),以引腳方式提供硬件間的聯繫能力。樹莓派 3B+,有40個GPIO引腳(請參考上文硬件接線 中的參考圖示),樹莓派官方操做系統 Raspbian 下,可使用系統默認安裝的 python 中 RPi.GPIO 庫,進行操做。
設計的核心在於人臉鑑權模塊,這裏直接影響成本和穩定性,最後選擇了上文方案(平衡成本、維護性及可靠性)。曾經的其它幾種備選人臉識別方案:
使用ESP-EYE芯片,均由芯片完成,依賴ESP-IDF、ESP—WHO,使用C進行開發。
低硬件成本(模塊成本189*2),高開發維護成本(C開發)。
問題:難於更新配置與故障分析處理。適用於大量部署場景。
使用樹莓派直接進行人臉識別,方案成熟,開源代碼豐富。
中硬件成本,低開發成本,高維護成本。
問題:樹莓派負載高,即便用間隔幀算法,也僅維持在20fps如下,卡頓明顯。如進一步調優,受限於我的經驗問題,恐難以保持長期穩定運行。
使用 BM1880邊緣計算開發板 或其它圖像處理板,社區口碑不錯,有框架支持。
問題:高硬件成本(模塊成本1000*2),高開發維護成本(C開發)。若是使用算力棒,須要X86_64作基礎平臺,成本下降有限,複雜度不變。適用於擴展能力場景。
使用騰訊雲的視頻智能分析產品,簡化終端架構,使用樹莓派zero推流上雲(後續放出實現方案),便可獲取識別結果,且支持高頻屢次檢索等特性。
部署成本低(終端視頻相關模塊150元),運營成本低(當前0.28元/分鐘,按該場景下單次運行20分鐘計算,單次遊戲成本5.6元)
問題:對網絡穩定性依賴大,斷流等狀況影響體驗。在本案例的網絡約束下,影響使用效果,更適於網絡條件較好、高頻檢索的應用場景。