開箱:得捷越做越好,現(xiàn)在從購買到收貨速度越來越快啦!短短一周就收到貨了。
UNITV M12板子非常小巧,正面是使用陽極氧化鋁切割出來的外殼,背面是塑料殼。有顆大大的攝像頭,攝像頭背面,可以插入SD卡。底部有兩個接口,一個是Type-C電源數(shù)據(jù)口,另外一個是2.0mm的4P的GLOVE接口,對應(yīng)管腳G34、G35,可以做串口或I2C口使用。側(cè)面各有一個按鍵,按鍵對應(yīng)管腳G19、G18。
因?yàn)橐龅墓苣_有限,在編程開發(fā)時,從Grove接口用杜邦線接了個串口轉(zhuǎn)Usb模塊,將G34、G35作為串口使用,輸出數(shù)據(jù),方便調(diào)試。
需求:大樓電機(jī)房需要定時巡檢。電機(jī)房位置比較偏僻,巡檢工作內(nèi)容簡單,但是要求巡檢到位。為了保證值班人員巡檢到位,通過AI攝像頭,進(jìn)行工作質(zhì)量檢查。
設(shè)計(jì):通過攝像頭進(jìn)行人臉識別,當(dāng)識別到人臉,就拍照記錄到SD卡上。定期收集SD卡的文件,核驗(yàn)工作情況。
實(shí)現(xiàn):首先附上代碼。
import sensor
import image
import lcd
import time
import utime
from machine import UART
import KPU as kpu
from Maix import GPIO
from fpioa_manager import *
fm.register(34,fm.fpioa.UART1_TX)
fm.register(35,fm.fpioa.UART1_RX)
uart_out = UART(UART.UART1, 115200, 8, None, 1, timeout=1000, read_buf_len=4096)
lastsnaptime=""
sensor.reset()
sensor.set_pixformat(sensor.RGB565)
sensor.set_framesize(sensor.QVGA)
sensor.run(1)
while False:
uart_out.write('TEST\n')
utime.sleep_ms(100)
def getStrTime():
nowtime=time.localtime()
return "{:0>4d}{:0>2d}{:0>2d}{:0>2d}{:0>2d}{:0>2d}".format(nowtime[0],nowtime[1],nowtime[2],nowtime[3],nowtime[4],nowtime[5])
#task = kpu.load(0x300000) # 你需要把模型(face.kfpkg)在閃存地址0x300000
task = kpu.load("/sd/face.kmodel")#將模型放在 SD 卡中。
#模型描參數(shù)
anchor = (1.889, 2.5245, 2.9465, 3.94056, 3.99987, 5.3658, 5.155437, 6.92275, 6.718375, 9.01025)
#初始化 yolo2 網(wǎng)絡(luò)
a = kpu.init_yolo2(task, 0.8, 0.3, 5, anchor)
while(True):
img = sensor.snapshot()
code = kpu.run_yolo2(task, img)#運(yùn)行 yolo2 網(wǎng)絡(luò)
if code:
for i in code:
uart_out.write(getStrTime()+" "+str(i)+"\n")
if lastsnaptime!=getStrTime():
lastsnaptime=getStrTime()
img.save("/sd/img/"+lastsnaptime+".jpg?x-oss-process=image/watermark,g_center,image_YXJ0aWNsZS9wdWJsaWMvd2F0ZXJtYXJrLnBuZz94LW9zcy1wcm9jZXNzPWltYWdlL3Jlc2l6ZSxQXzQwCg,t_20")
#sensor.snapshot().save("/sd/img/"+str(time.ticks_ms())+".jpg?x-oss-process=image/watermark,g_center,image_YXJ0aWNsZS9wdWJsaWMvd2F0ZXJtYXJrLnBuZz94LW9zcy1wcm9jZXNzPWltYWdlL3Jlc2l6ZSxQXzQwCg,t_20")
a = img.draw_rectangle(i.rect())
a = lcd.display(img)
a = kpu.deinit(task)#反初始化
這里使用了maixpy作為編程工具,使用了官網(wǎng)提供的KPU人臉識別算法。從官網(wǎng)下載人臉識別算法模型文件(既可以保存在flash里,也可以保存在SD卡上)。在代碼中使用kpu.load()方法加載模型文件。
#初始化 yolo2 網(wǎng)絡(luò)
a = kpu.init_yolo2(task, 0.8, 0.3, 5, anchor)
為yolo2網(wǎng)絡(luò)模型傳入初始化參數(shù), 留意第二個參數(shù),是概率閾值, 只有是這個物體的概率大于這個值才會輸出結(jié)果, 取值范圍:[0, 1],我這里取了0.8的閾值,實(shí)測基本不會誤記錄了。當(dāng)kpu模型檢測到人臉時,就將獲得到的圖片保存到SD卡。最后將代碼保持到boot.py就能夠上電運(yùn)行了。
問題:整個項(xiàng)目過程中遇到兩個大問題。
問題1:原本計(jì)劃著搞好人臉檢測,再加上人臉識別的。Maixpy的人臉識別也提供了模型,但是模型是加了密的。 密碼使用的是機(jī)器碼。機(jī)器碼是一機(jī)一碼的一種加密方式,用于模型文件的加密。如果使用別的機(jī)器碼去加密或者下載以 smodel 為文件后綴的模型文件,開發(fā)板是無法使用該模型文件的。通過官方的說明,下載了key_gen.bin這個固件,燒寫后上電應(yīng)該就能通過串口獲得到機(jī)器碼了。但是UNITV M12這個板子,沒有復(fù)位鍵!沒有復(fù)位鍵!沒有復(fù)位鍵!燒寫完固件后,只能通過插拔USB線,復(fù)位,但是插上USB線后,電腦要好一會才能認(rèn)到這個USB串口,讀不到機(jī)器碼!最終放棄了這個思路。
問題2:這個模塊的RTC感覺很奇怪,使用 time.localtime()去讀取時間,按文檔說明,應(yīng)該讀取到的是一個 年、月、日、時、分、秒……的元組。有時能讀到正常的時間,有時讀取到的數(shù)據(jù)又是亂的,找不到規(guī)律,還不清楚是什么引起的。
所以,這個UNITV M12很適合做一個圖像的傳感器,配合其它主控一起工作。