Android人脸识别和证件识别 程帅
由于疫情原因,最近的大数据和人脸识别检测就进入了大家的视线。对于技术的爱好,我也试着做了一下人脸识别和证件识别。
人脸识别用的是虹软的人脸识别SDK,目前是免费的,下载地址https://ai.arcsoft.com.cn/product/arcface.html
![人脸识别界面](https://img-blog.csdnimg.cn/20210103201950350.jpg?x-oss-process=image/watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L0F1cm9yYV9XZW4=,size_16,color_FFFFFF,t_70#pic_center)
人脸识别需要摄像头和存储卡权限
/**
* 权限检查
*
* @param neededPermissions 需要的权限
* @return 是否全部被允许
*/
protected boolean checkPermissions(String[] neededPermissions) {
if (neededPermissions == null || neededPermissions.length == 0) {
return true;
}
boolean allGranted = true;
for (String neededPermission : neededPermissions) {
allGranted &= ContextCompat.checkSelfPermission(this, neededPermission) == PackageManager.PERMISSION_GRANTED;
}
return allGranted;
}
@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
boolean isAllGranted = true;
for (int grantResult : grantResults) {
isAllGranted &= (grantResult == PackageManager.PERMISSION_GRANTED);
}
afterRequestPermission(requestCode, isAllGranted);
}
/**
* 请求权限的回调
*
* @param requestCode 请求码
* @param isAllGranted 是否全部被同意
*/
abstract void afterRequestPermission(int requestCode, boolean isAllGranted);
private static final String ROOT_DIR = Environment.getExternalStorageDirectory().getAbsolutePath() + File.separator + "arcfacedemo";
private static final String ROOT_DIR = Constant.facePath;
private static final String REGISTER_DIR = ROOT_DIR + File.separator + "register";
private static final String REGISTER_FAILED_DIR = ROOT_DIR + File.separator + "failed";
private static final int ACTION_REQUEST_PERMISSIONS = 0x001;
private static String[] NEEDED_PERMISSIONS = new String[]{
Manifest.permission.READ_EXTERNAL_STORAGE,
Manifest.permission.WRITE_EXTERNAL_STORAGE
};
ActivityCompat.requestPermissions(this, NEEDED_PERMISSIONS, ACTION_REQUEST_PERMISSIONS);
人脸识别初始化和初始化引擎
//本地人脸库初始化
FaceServer.getInstance().init(RegisterAndRecognizeActivity.this);
if (!EventBus.getDefault().isRegistered(this)) {
EventBus.getDefault().register(this);
}
ftEngine = new FaceEngine();
ftInitCode = ftEngine.init(this, DetectMode.ASF_DETECT_MODE_VIDEO, ConfigUtil.getFtOrient(this),
16, MAX_DETECT_NUM, FaceEngine.ASF_FACE_DETECT);
frEngine = new FaceEngine();
frInitCode = frEngine.init(this, DetectMode.ASF_DETECT_MODE_IMAGE, DetectFaceOrientPriority.ASF_OP_0_ONLY,
16, MAX_DETECT_NUM, FaceEngine.ASF_FACE_RECOGNITION);
flEngine = new FaceEngine();
flInitCode = flEngine.init(this, DetectMode.ASF_DETECT_MODE_IMAGE, DetectFaceOrientPriority.ASF_OP_0_ONLY,
16, MAX_DETECT_NUM, FaceEngine.ASF_LIVENESS);
Log.i(TAG, "initEngine: init: " + ftInitCode);
if (ftInitCode != ErrorInfo.MOK) {
String error = getString(R.string.specific_engine_init_failed, "ftEngine", ftInitCode);
Log.i(TAG, "initEngine: " + error);
showToast(error);
}
if (frInitCode != ErrorInfo.MOK) {
String error = getString(R.string.specific_engine_init_failed, "frEngine", frInitCode);
Log.i(TAG, "initEngine: " + error);
showToast(error);
}
if (flInitCode != ErrorInfo.MOK) {
String error = getString(R.string.specific_engine_init_failed, "flEngine", flInitCode);
Log.i(TAG, "initEngine: " + error);
showToast(error);
}
在人脸识别之前需要录入人脸进行注册
File dir = new File(REGISTER_DIR);
if (!dir.exists()) {
showToast(getString(R.string.batch_process_path_is_not_exists, REGISTER_DIR));
return;
}
if (!dir.isDirectory()) {
showToast(getString(R.string.batch_process_path_is_not_dir, REGISTER_DIR));
return;
}
/* final File[] jpgFiles = dir.listFiles(new FilenameFilter() {
@Override
public boolean accept(File dir, String name) {
return name.endsWith(FaceServer.IMG_SUFFIX);
}
});*/
executorService.execute(new Runnable() {
@Override
public void run() {
final File[] jpgFiles = dir.listFiles();
final int totalCount = jpgFiles.length;
int successCount = 0;
runOnUiThread(new Runnable() {
@Override
public void run() {
progressDialog.setMaxProgress(totalCount);
progressDialog.show();
tvNotificationRegisterResult.setText("");
tvNotificationRegisterResult.append(getString(R.string.batch_process_processing_please_wait));
}
});
for (int i = 0; i < totalCount; i++) {
final