百度人脸识别开发套件4.HelloWorld!
goJhou 发布于2018-12 浏览:14798 回复:14
0
收藏

之前分析了百度人脸识别开发套件的硬件与萤火虫人脸识别Demo,今天起就开始动工写代码啦。本来还想下载一下萤火虫关于百度人脸识别套件产品规格书最后一页的源码

结果链接点进去后台似乎工作不正常。
同时通过这个偶然的机会,也可以基本判断出萤火虫网站是用Angular或者Vue写的。
可看了一下他们主页或是分页,都没有框架的引用。
可能是后来发现大多数页面都没用到就删除了?
可是 v-for这个attribute可是Vue的亚~
有兴趣的同学可以去翻翻萤火虫的官网代码,以上全是猜测~

 

具体原因就不得而知了,反正目前是没源码下载了。 

 

那没了源码,只得自己研究咯,就按我自己研究东西的习惯跑吧。文档刷一遍~

真正上手一套SDK前,我们要了解这SDK可以做到哪些功能。官方所发布的离线SDK安卓版可以直接编译成app进行体验,这就很适合拿来测试接口。

那SDK包含功能如下:

离线SDK有几大优势:

网络:无网、局域网等情况,无法连接公网。如政府单位、金融保险、教育机构等。
安全:行业特点所带来的人脸数据敏感性,即使可以连接公网也不可请求。
速度:由于各地网络线路、机房部署等诸多原因,网络请求速度存在不可控因素。
稳定:需要尽可能避免网络抖动、机房故障等影响,进一步控制可用性影响因素。

这意味着离线SDK哪怕在核心机房瘫痪的情况下依旧可以继续使用,这可以广泛应用在停电事故较少但对门禁要求极高的场景
例如金融保险,银行,核电站等无法进行公网对接的极度敏感场景。

按12月4日截取到的官方文档,一些参数如下所示:

包大小:~ 100M
最小人脸检测大小:50px 50px
可识别人脸角度:yaw ≤ ±30°, pitch ≤ ±30°
检测速度:100ms 720p
追踪速度:30ms 720p*
人脸检测耗时:< 100ms
RGB图片特征抽取耗时:< 300ms
RGB活体检测耗时:< 200ms
近红外活体检测耗时:< 50ms
3D结构光活体检测耗时:< 50ms
1万本地人脸库检索速度:< 400ms

以上摘取自官方文档,数值只是参考,软件性能跟硬件有着比较密切的关系

 

可以看到,追踪速度是极快的,检测在其次,活体与特征在之后,脸库检索在最后

这也可以大概推测我们整个系统的性能瓶颈会出现在哪里

我们的调用频率应该满足以下条件:

追踪>检测>活体>脸库检索

同时这里如果使用RGB活体会耗时很多,如果使用双目(近红外)的话可以达到跟追踪近乎的速度。所以使用单目为了性能可能会舍弃掉活体功能。毕竟如果对活体有所要求的话,甲方也不会吝啬这点设备成本了。直接上双目或者结构光吧。
当然简单的活体需求单目还是可以满足的

720p画质下达到30ms的追踪速度,也就是100/3 一秒钟有33次的更新次数,肉眼只要在25次/秒以上就无法区分出区别来,所以只要达到20次以上基本上都是可接受的。

安卓SDK也给出了兼容性要求在Android4.4以上,不过目前的设备应该都在这之上了。

授权是离线SDK特有的离在线可选授权,授权码以阶梯收费

有附赠测试码进行测试的,可以先用测试码进行调试

 

功能介绍:

1.2.1 人脸检测与追踪
可在设备端,离线实时检测视频流中的人脸。同时支持处理静态图片或者视频流,并对当前检测到的人脸持续跟踪,动态定位人脸轮廓,稳定贴合人脸。

1.2.2 质量控制
在人脸检测及追踪过程中,实时校验人脸的姿态角度、遮挡、清晰度、光照条件,符合质量条件的人脸图片才会被采集。

1.2.3 人脸采集
针对视频流实时完成人脸图片采集,并输出满足质量过滤条件的人脸图片,可自定义采集人脸大小,采集频率,采集质量等设置。

1.2.4 离线RGB可见光活体检测
针对视频流/图片,通过采集人像的破绽(摩尔纹、成像畸形等)来判断目标对象是否为活体,可有效防止屏幕二次翻拍等作弊攻击,可使用单张或多张判断逻辑。

1.2.5 离线NIR近红外活体检测
针对视频流/图片,利用近红外成像原理,实现夜间或无自然光条件下的活体判断。其成像特点(如屏幕无法成像,不同材质反射率不同等)可以实现高鲁棒性的活体判断。

1.2.6 离线Depth深度图像(3D结构光)活体检测
通过3D建模判断目标对象是否为活体,基于3D结构光成像原理,可强效防御图片、视频、屏幕、模具等攻击。

1.2.7 离线1:1对比
提供本地化的1:1人脸对比功能,高鲁棒性算法,可对应各种姿态、肤色、光照等场景,可有效应用于人证比对、身份核验等场景。

示例工程中包含:

图片与图片的比对:两张人脸图片的1:1对比,并返回相似度分值。
图片与视频流比对:一张预设的人脸图片,和摄像头实时采集的符合条件的人脸图片进行对比。
1.2.8 离线1:N搜索
本地数据库中保留所有人脸特征值(如需要保留原图,可根据业务需要自行修改工程)。

视频流采集的人脸在人脸库中搜索:视频流中实时采集人脸,并与人脸库中预设的人脸库进行一一对比,返回相似度最高的user及对应分值。
1.2.9 离线人脸库管理
人脸数量不做上限,可根据业务需要适当调整,支持人脸库、人脸组、用户、Face几个维度的增删改查设置。

 

 

同时文档也给出了业务流程概述

 

活体检测原理:

RGB可见光活体:主要基于图片破绽,判断目标对象是否为活体。例如图像中的屏幕反光、成像畸形等,最主要的应用情形为屏幕的二次翻拍等攻击防御。此种活体对于待检测图片的要求,主要需要满足画面中除了人脸以外,要尽可能保留一些背景内容,用于查找破绽,通常建议人脸与屏幕的长宽比为1:3。为控制达到此比例,建议通过调整最小检测人脸参数,控制采集的人脸不可过大,避免人脸面积占比过高,而导致图片中没有多少背景信息。同时RGB活体受光线影响较大,所以在强光、暗光等场景,容易数值波动较大,主要影响的是「通过率」,产品策略上需要通过适当的补光、使用宽动态镜头抵消逆光等方式缓解。
NIR近红外活体:主要基于近红外光线反射成像原理,通过人脸呈现来判断是否为活体。即使是夜间或者没有自然光的情况下,依然可以判断活体。因为其成像特点,对于屏幕、图片等攻击形式,基本可以达到近似于100%的活体防御。同时近红外设备的成本,相对性价比更高。
Depth深度活体(3D结构光):结构光原理是通过主动光发射,在物体上形成光栅,并接受此信息进行活体分析。同样可以不需要自然光。3D结构光的成像更为稳定,抗攻击能力更强,对图像噪声的抗干扰能力也更强,是相对更加安全和稳定的方案,但相应的硬件设备造价也较高,需要根据实际业务成本预算,进行综合考虑。

如果开启了活体识别,那将有多个活体分,单目为1个,请以2个都通过活体阈值才批准进入下一步业务,否则视为非法攻击而抛弃。

 

 

离线SDK适合

网络条件不稳定
无网络
数据安全性高,不允许联网
人脸库较小,且变更不频繁,如1w人以下
单台设备、单人脸检测与识别

 

典型场景及设备类型

人脸门禁
人脸闸机
人证核验机
自助柜机
人脸考勤机
会场签到

 

好了,其实我想说这几个经典案例都是很好的人脸识别的例子,我们可以沉下心来一个一个做过去。

我将百度安卓SDK的包已经download,并已经铺设好android开发环境,相关部署工作请各位自行百度啦。

 

 

这里声明一下,本人是C#开发者,android及java语言都是本篇开始从0入门的,如果有相关错误或谬论,也请希望各位能明确指出我的问题~

 

 

那百度的SDK目录结构如下

lib目录是动态库so和jar包
assets目录是模型文件
java目录为用户组管理、人脸SDK操作、视频流、图片等操作辅助类
所以我们只需要着眼在java目录里就行

在android studio中,目录结构有些许不同

 

java内是用户组管理、人脸SDK操作、视频流、图片等操作辅助类

.java 用途
FeatureSettingActivity 特征抽取模型设置,分为生活照模型和证件照模型。生活照模型适用于生活照图片,手机拍摄图片,镜头实时采集的图片等;证件照模型适用于身份证芯片照,各类证件照(如工卡,学生证,会员卡照片等),带水纹小图等。一经选择一个模型,则所有业务流程的特征抽取处理,都会使用此模型,两个模型不可同时作用。如业务中设计证件照的特征抽取,请务必选择证件照模型。
LivenessSettingActivity 活体类型设置,分为无活体、RGB活体、RGB+NIR活体、RGB+Depth活体、RGB+NIR+Depth活体。默认为不使用活体。示例工程里面进行活体设置后,后续的人脸注册、人脸1:1,1:n等操作需选择相应Activity。无活体和rgb活体需要使用单目usb摄像头,rgb+ir活体需要使用rgb+ir双目摄像头(如迪威泰、视派尔双目摄像头,具体推荐型号详见上文设备选型介绍)。RGB+Depth需要使用奥比中光mini/mini-s/Pro-S、或华捷艾米摄像头,且目前只能使用RGB+Depth活体功能。RGB+NIR+Depth的活体硬件设备适配还在开发中。
AddGroupActivity 添加分组,1:n中的n为某个分组下的人脸特征
BatchImportActivity 提供批量注册人脸到人脸库
GroupListActvity group列表,正常情况一个分组即可,可以根据业务需求用多个分组管理
ImageMatchImageActivity 两张图片进行1:1比对
MainActivity 示例主界面入口
RegActivity 人脸检测、抽取特征进行注册
RgbDetectActivity 摄像头视频流人脸检测,提供给注册、图片1:1实时采集人脸图片用。使用uvc免驱USB摄像头
UserActivity 注册用户信息
UserGroupMangerActivity 用户组管理
UserListActivity 某个分组下用户列表
VideoIdentityActivity 视频流人脸实时检测,并和某个分组的人脸库进行1:N比对
RgbVideoAttributeTrackActivity 视频流人脸实时检测,输出人脸的属性信息
VideoMatchImageActivity 视频流人脸实时检测,并和指定的图片进行1:1比对
RgbIrLivenessActivity RGB+NIR活体检测,提供给人脸注册、图片1:1实时采集人脸图片用。需要使用RGB+NIR的双目摄像头。如迪威泰、视派尔双目摄像头
RgbIrVideoIdentifyActivity 带RGB+NIR活体,视频流人脸实时检测,并和某个分组的人脸库进行1:n比对。需要使用RGB+NIR的双目摄像头。如迪威泰、视派尔双目摄像头。
RgbIrVideoMathImageActivity 带RGB+NIR活体,视频流人脸实时检测,并和指定的图片进行1:1比对。需要使用RGB+NIR的双目摄像头。如迪威泰、视派尔双目摄像头。
OrbbecLivenessDetectActivity RGB+Depth活体检测,提供给人脸注册、图片1:1实时采集人脸图片用。需要使用RGB+Depth的双目摄像头。如奥比中光mini或mini-s双目摄像头
OrbbecVideoIdentifyActivity 带RGB+Depth活体,视频流人脸实时检测,并和某个分组的人脸库进行1:n比对。需要使用RGB+Depth的双目摄像头。如奥比中光mini或mini-s双目摄像头
RgbIrVideoMathImageActivity 带RGB+Depth活体,视频流人脸实时检测,并和指定的图片进行1:1比对。需要使用RGB+Depth的双目摄像头。如奥比中光mini或mini-s双目摄像头。
OrbbecProVideoIdentifyActivity 带RGB+Depth活体,视频流人脸实时检测,并和某个分组的人脸库进行1:n比对。需要使用RGB+Depth的双目摄像头。如奥比中光Pro双目摄像头。
IminectVideoIdentifyActivity 带RGB+Depth活体,视频流人脸实时检测,并和某个分组的人脸库进行1:n比对。需要使用RGB+Depth的双目摄像头。如华捷艾米双目摄像头。

 

开始尝试开发第一个应用,当然这应用肯定是练练手的,小试牛刀任务还是要做滴
我这边用的是android studio开发的,eclipse应该可以参照官方文档。

将library库拷到自己工程中,哇塞这库将近1.2个G

在settings.gradle中添加:library。(这里官方文档缺少提示要加orbbec库)
选中app目录按F4,或者右击app点Open Module Settings

在Dependencies依赖中添加module dependency 选择:library

在视图编译的时候提示了

Error:(39, 0) Project with path ':orbbec' could not be found in project ':library'.
Open File

 

那我们还需要把orbbec目录拷过来,是结构光摄像头奥比中光的驱动库(36M左右,驱动方面耦合度还是挺高的。不装不行)
再次添加依赖 :orbbec 后重新build,build成功。

 

 

接下去尝试在app Create的时候的时候来初始化sdk

这里可以看到SDK采用的是单例设计模式,全局调用getInstance()方法来获取当前的SDK实例,最大程度降低了开发者代码冗余所产生的内存占用。

toast是封装的方法,用于弹出气泡,Toast是android.widget包中的成员
Handler是android.os.Handler中的,用于处理系统消息处理。
Looper是android.os.Looper中的,用于轮训消息队列里面的消息
android.os.Looper;

private Handler handler = new Handler(Looper.getMainLooper());
private void toast(final String text) {
    handler.post(new Runnable() {
        @Override
        public void run() {
            Toast.makeText(MainActivity.this, text, Toast.LENGTH_LONG).show();
        }
    });
}

 

onCreate最后代码为:

@Override
protected void onCreate(Bundle savedInstanceState) {

    FaceSDKManager.getInstance().init(this);

    FaceSDKManager.getInstance().setSdkInitListener(new FaceSDKManager.SdkInitListener(){
        @Override
        public void initStart() {
            toast("sdk init start");
        }

        @Override
        public void initSuccess() {
            toast("sdk init success");
        }

        @Override
        public void initFail(int errorCode, String msg) {
            toast("sdk init fail:"+msg);
        }
    });

 

build一下放到真机上跑一下看看初始化是否可以成功

发现一直闪退。后来查了些资料发现是把hello world里头的2句onCreate句子给删了

这一句是为了调用父类的onCreate函数,来使Activity活跃
super.onCreate(savedInstanceState);
这一句是为了将View给渲染出来
setContentView(R.layout.activity_main);

最后MainActivity代码如下:

package hello.word.gojhou.myapplication;

import android.os.Handler;
import android.os.Looper;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.widget.Toast;


import com.baidu.aip.manager.FaceSDKManager;

public class MainActivity extends AppCompatActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        FaceSDKManager.getInstance().init(this);
        FaceSDKManager.getInstance().setSdkInitListener(new FaceSDKManager.SdkInitListener(){
            @Override
            public void initStart() {
                toast("sdk init start");
            }

            @Override
            public void initSuccess() {
                toast("sdk init success");
            }

            @Override
            public void initFail(int errorCode, String msg) {
                toast("sdk init fail:"+msg);
            }
        });
    }

    private Handler handler = new Handler(Looper.getMainLooper());
    private void toast(final String text) {
        handler.post(new Runnable() {
            @Override
            public void run() {
                Toast.makeText(MainActivity.this, text, Toast.LENGTH_LONG).show();
            }
        });
    }
}

随后再次build测试,成功载入授权界面
这里我用的是手机调试,所以适配有问题,官方目前适配的是萤火虫的10.1屏幕。没关系,不影响大体。只验证软件功能为先。

可以发现我们已经可以成功调用sdk的init函数了。并且SDK自动的验证了我设备的授权情况了,也算是达成了安卓离线SDK的Hello World了!

并且发现,一个激活码可以在该设备的所有离线sdk上激活。

 

这就意味着,你可以装一个萤火虫的demo,再装一个百度离线sdk的demo,然后再装一个你自己的app,全部用一个激活码激活,是完全没有问题的。那还怕啥?来啊,造作阿!

收藏
点赞
0
个赞
共14条回复 最后由用户已被禁言回复于2022-04
#15goJhou回复于2019-04
#14 尼基塔007不错回复
移植方便吗

会者不难 难者不会

0
#14尼基塔007不错回复于2019-04

移植方便吗

0
#13goJhou回复于2019-04
#12 尼基塔007不错回复
都需要通过咱们社区购买?

在ai平台进入即可

0
#12尼基塔007不错回复于2019-04
#11 goJhou回复
人脸识别展开右侧

都需要通过咱们社区购买?

0
#11goJhou回复于2019-04
#10 尼基塔007不错回复
硬件在哪里?

人脸识别展开右侧

0
#10尼基塔007不错回复于2019-04

硬件在哪里?

0
#9goJhou回复于2019-04
#8 Gramiii回复
请问激活码怎么申请  

SDK激活码需要购买喔,详情请至后台应用查看

0
#8Gramiii回复于2019-03

请问激活码怎么申请

 

0
#7goJhou回复于2018-12
#5 才能我浪费99回复
比如移动物体的识别。这个可以用在很多监控、物流、生产的场合

集成的是人脸识别离线SDK。物体识别可能还不支持。本身套件就叫人脸识别开发套件呢

0
#6才能我浪费99回复于2018-12

还有就是表面瑕疵的识别,标注。这些有么?

0
#5才能我浪费99回复于2018-12
#3 goJhou回复
厚积薄发 嘿嘿

比如移动物体的识别。这个可以用在很多监控、物流、生产的场合

0
#4才能我浪费99回复于2018-12
#3 goJhou回复
厚积薄发 嘿嘿

看了这个东西的软件层主要是人脸,还有别的么?

0
#3goJhou回复于2018-12
#2 笔墨哥回复
今天分享了好多内容啊 

厚积薄发 嘿嘿

0
#2笔墨哥回复于2018-12

今天分享了好多内容啊 

0
TOP
切换版块