随着人脸识别应用越来越广泛,用它来做智能锁也是再适合不过。
硬件连接
在这个项目中,我们计划拍照并识别其中的人脸,然后在屏幕上显示识别结果。如果是已认证面孔,打开门,并通过短信将开门的人发送到指定的电话号码。
因此,您需要将摄像头连接到 Raspberry Pi 的摄像头接口,并将天线和 Grove - Relay 安装到 LTE Pi HAT,然后将 HAT 插入您的 Pi。屏幕可以通过 HDMI 电缆连接到 Raspberry Pi,不要忘记将电源连接到屏幕和 Pi。
软件编程
人脸识别
以下步骤将向您展示如何在 Pi 上设置人脸识别。
步骤 1. 使用 raspi-config 配置相机和 GPU 内存。
sudo raspi-config
选择Interface Options -- Camera启用 picamera,然后选择Advanced Options -- Memory Split设置 GPU 内存,它应该更改为 64。完成后,重新启动您的 Raspberry Pi。
步骤 2. 安装所需的库。
sudo apt-get update
sudo apt-get upgrade
sudo apt-get install build-essential
cmake
gfortran
git
wget
curl
graphicsmagick
libgraphicsmagick1-dev
libatlas-dev
libavcodec-dev
libavformat-dev
libboost-all-dev
libgtk2.0-dev
libjpeg-dev
liblapack-dev
libswscale-dev
pkg-config
python3-dev
python3-numpy
python3-picamera
python3-pip
zip
sudo apt-get clean
步骤 3. 使 picamerea 支持数组。
sudo pip3 install --upgrade picamera[array]
步骤 4. 安装dlib和人脸识别。
sudo pip3 install dlib
sudo pip3 install face_recognition
步骤 5. 下载并运行人脸识别示例
git clone --single-branch https://github.com/ageitgey/face_recognition.git
cd ./face_recognition/examples
python3 facerec_on_raspberry_pi.py
注意:如果您收到 ImportError: libatlas.so.3: cannot open shared object file: No such file or directory,请运行以下命令进行修复。
sudo apt-get install libatlas3-base
中继
当人脸识别准备好后,我们可以继续添加额外的功能。我们将 Grove - Relay 连接到 LTE Cat 1 Pi HAT,但它使用数字端口而不是 I2C 端口。
这是 Raspberry Pi 3B 的引脚,我们可以看到 SDA 引脚和 SCL 引脚位于板的引脚 3 和引脚 5。
所以我们可以通过输出数字信号到pin 5来控制继电器。在你的Raspberry Pi上运行下面的python程序,如果没有任何问题,你会听到来自继电器的Ti-Ta。
import RPi.GPIO as GPIO
RELAY_PIN = 5
GPIO.setmode(GPIO.BOARD)
GPIO.setup(RELAY_PIN, GPIO.OUT)
GPIO.output(RELAY_PIN, GPIO.HIGH)
所以这里的想法是,我们从文件夹中加载已知的人脸,识别 picamera 捕获的人脸,如果人脸在文件夹中,控制继电器解锁门。我们可以将它们打包成一个类,这里是load_known_faces()方法和unlock()方法,完成的程序可以在文末下载。
def load_known_faces(self):
known_faces = os.listdir(self.__known_faces_path)
for known_face in known_faces:
self.__known_faces_name.append(known_face[0 : len(known_face) - len('.jpg')])
known_face_image = face_recognition.load_image_file(self.__known_faces_path + known_face)
self.__known_faces_encoding.append(face_recognition.face_encodings(known_face_image)[0])
return len(self.__known_faces_encoding)
def unlock(self):
if self.__matched.count(True) > 0:
GPIO.output(self.__relay_pin, GPIO.HIGH)
print('Door opened')
time.sleep(5)
GPIO.output(self.__relay_pin, GPIO.LOW)
self.__reset_recognise_params()
return True
self.__retry_count += 1
print('Please try again...{}'.format(self.__retry_count))
return False
超然思考,我们可以显示识别的图片,库 PIL 和 matplotlib 会有所帮助,其中 matplotlib 需要手动安装,在您的树莓派终端中运行此命令。
sudo pip3 install matplotlib
将它们导入您的代码中,并在 unlock() 方法中更改 if 块,如下所示:
img = Image.open('{}/{}.jpg'.format(self.__known_faces_path, self.__known_faces_name[0]))
plt.imshow(img)
plt.ion()
GPIO.output(self.__relay_pin, GPIO.HIGH)
print('Door opened')
plt.pause(3)
plt.close()
GPIO.output(self.__relay_pin, GPIO.LOW)
self.__reset_recognise_params()
return True
现在,如果识别出人脸,文件夹中的图片将显示在屏幕上。
短信
有时我们想知道谁在我们的房间里,现在有一个地方可以放置 LTE Cat 1 Pi HAT。将 SIM 卡插入其中,然后按照步骤测试它是否可以正常工作。
步骤 1. 在 Raspberry Pi 中启用 UART0
使用 nano 编辑 /boot 中的 config.txt
sudo nano /boot/config.txt
将 dtoverlay=pi3-disable-bt 添加到它的底部,并禁用 hciuart 服务
sudo systemctl disable hciuart
然后在 /boot 的 cmdline.txt 中删除 console=serial0, 115200
sudo nano /boot/cmdline.txt
一切完成后,你应该重启你的树莓派。
步骤 2. 下载示例并运行它。
在 Raspberry Pi 上打开一个终端,逐行输入这些命令。
cd ~
git clone https://github.com/Seeed-Studio/ublox_lara_r2_pi_hat.git
cd ublox_lara_r2_pi_hat
sudo python setup.py install
cd test
sudo python test01.py
如果您在终端中看到这些输出,则 LTE Cat 1 Pi HAT 运行良好。
40-pin GPIO header detected
Enabling CTS0 and RTS0 on GPIOs 16 and 17
rts cts on
waking up...
module name: LARA-R211
RSSI: 3
现在我们知道了 HAT 很好用,如何使用它来发送短信?您需要知道的第一件事是,Raspberry Pi 通过 UART 发送 AT 命令与 HAT 通信。您可以通过在 python 中运行此代码将 AT 命令发送到 LTE HAT
from ublox_lara_r2 import *
u = Ublox_lara_r2()
u.initialize()
u.reset_power()
# Close debug massage
u.debug = False
u.sendAT('')
发送短信的AT指令如下
AT+CMGF=1
AT+CMGS=
所以这里是 __send_sms() 方法:
def __send_sms(self):
if self.__phonenum == None:
return False
for unlocker in self.__recognise_face_names():
if self.__ublox.sendAT('AT+CMGF=1rn'):
print(self.__ublox.response)
if self.__ublox.sendAT('AT+CMGS="{}"rn'.format(self.__phonenum)):
print(self.__ublox.response)
if self.__ublox.sendAT('{} enter the room.x1a'.format(unlocker)):
print(self.__ublox.response)