diff --git a/app/src/main/java/com/rehome/dywoa/bean/FaceRecognitionResult.java b/app/src/main/java/com/rehome/dywoa/bean/FaceRecognitionResult.java new file mode 100644 index 0000000..abb2a61 --- /dev/null +++ b/app/src/main/java/com/rehome/dywoa/bean/FaceRecognitionResult.java @@ -0,0 +1,88 @@ +package com.rehome.dywoa.bean; + +public class FaceRecognitionResult { + private int state; + private String msg; + private Data data; + + public int getState() { + return state; + } + + public void setState(int state) { + this.state = state; + } + + public String getMsg() { + return msg; + } + + public void setMsg(String msg) { + this.msg = msg; + } + + public Data getData() { + return data; + } + + public void setData(Data data) { + this.data = data; + } + + public static class Data { + private String name; + private String id_card; + private String gh; + private String phone; + private String sex; + private String faceType; + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } + + public String getGh() { + return gh; + } + + public void setGh(String gh) { + this.gh = gh; + } + + public String getId_card() { + return id_card; + } + + public void setId_card(String id_card) { + this.id_card = id_card; + } + + public String getPhone() { + return phone; + } + + public void setPhone(String phone) { + this.phone = phone; + } + + public String getSex() { + return sex; + } + + public void setSex(String sex) { + this.sex = sex; + } + + public String getFaceType() { + return faceType; + } + + public void setFaceType(String faceType) { + this.faceType = faceType; + } + } +} diff --git a/app/src/main/java/com/rehome/dywoa/ui/activity/FaceRecognitionAppActivity.java b/app/src/main/java/com/rehome/dywoa/ui/activity/FaceRecognitionAppActivity.java index 503612a..e69e357 100644 --- a/app/src/main/java/com/rehome/dywoa/ui/activity/FaceRecognitionAppActivity.java +++ b/app/src/main/java/com/rehome/dywoa/ui/activity/FaceRecognitionAppActivity.java @@ -6,6 +6,7 @@ import android.Manifest; import android.content.Context; import android.content.Intent; import android.content.pm.PackageManager; +import android.content.res.Resources; import android.graphics.Bitmap; import android.graphics.BitmapFactory; import android.graphics.Canvas; @@ -17,6 +18,8 @@ import android.graphics.Rect; //import android.hardware.Camera; import android.graphics.RectF; import android.graphics.SurfaceTexture; +import android.graphics.drawable.BitmapDrawable; +import android.graphics.drawable.Drawable; import android.hardware.Camera; import android.hardware.camera2.CameraAccessException; import android.hardware.camera2.CameraCaptureSession; @@ -28,6 +31,7 @@ import android.hardware.camera2.CaptureRequest; import android.media.Image; import android.media.ImageReader; import android.os.Bundle; +import android.os.Environment; import android.os.Handler; import android.os.HandlerThread; import android.text.TextUtils; @@ -66,8 +70,11 @@ import java.util.ArrayList; import java.util.Collections; import java.util.Comparator; import java.util.List; +import java.util.Objects; import java.util.Timer; import java.util.TimerTask; +import java.util.UUID; + import com.rehome.dywoa.base.BaseActivity; import com.rehome.dywoa.utils.BitmapUtil; import com.rehome.dywoa.utils.BitmapUtils; @@ -93,6 +100,8 @@ public class FaceRecognitionAppActivity extends BaseActivity { private ImageView imgView; + private String path = Environment.getExternalStorageDirectory().getAbsolutePath() + File.separator + "com.rehome.dywoa/images"; + private Timer timer; private int faceRecognTricker = 1; @@ -125,7 +134,17 @@ public class FaceRecognitionAppActivity extends BaseActivity { } }); + //android 10 以上 + if (context.getExternalFilesDir(null) != null) { + path = Objects.requireNonNull(context.getExternalFilesDir(null)).getPath() + "/images"; + } else { + path = context.getFilesDir().getPath() + "/images"; + } + File fileDir = new File(path); + if(!fileDir.exists()){ + fileDir.mkdir(); + } } @Override @@ -251,22 +270,36 @@ public class FaceRecognitionAppActivity extends BaseActivity { showLog(String.valueOf(rectBitmap.getWidth())); showLog(String.valueOf(rectBitmap.getHeight())); //Bitmap bitmapResize = BitmapUtils.resizeBitmap(rectBitmap, rectBitmap.getWidth()/4, rectBitmap.getHeight()/4); - Bitmap bitmapResize = BitmapUtils.resizeBitmap(rectBitmap, 480, 640); - byte[] bitmapResizeByte = BitmapUtils.bitmapToByte(bitmapResize); - showLog(String.valueOf(bitmapResize.getWidth())); - showLog(String.valueOf(bitmapResize.getHeight())); - showLog(String.valueOf(bitmapResizeByte.length)); +// Bitmap bitmapResize = BitmapUtils.resizeBitmap(rectBitmap, 480, 640); +// byte[] bitmapResizeByte = BitmapUtils.bitmapToByte(bitmapResize); +// showLog(String.valueOf(bitmapResize.getWidth())); +// showLog(String.valueOf(bitmapResize.getHeight())); +// showLog(String.valueOf(bitmapResizeByte.length)); //imgView.setImageBitmap(bitmapResize); - imgView.setImageBitmap(drawWithRectangle(faces, bitmapResize)); +// imgView.setImageBitmap(drawWithRectangle(faces, bitmapResize)); + //imgView.setImageDrawable(new BitmapDrawable(rectBitmap)); + Drawable drawable = bitmapToDrawable(FaceRecognitionAppActivity.this,rectBitmap); + imgView.setImageDrawable(drawable); + imgView.setVisibility(View.VISIBLE); //BitmapUtils.resizeBitmap(rectBitmap,rectBitmap.getWidth()/3, rectBitmap.getHeight()/3); mTextureView.setVisibility(View.GONE); - //stopCamera(); + stopCamera(); + + String fileName = UUID.randomUUID().toString()+".jpeg"; + String faceTempPath = path + File.separator + fileName; + showLog(faceTempPath); - Intent resultIntent = new Intent(); - resultIntent.putExtra("FaceRecognition", bitmapResizeByte); - setResult(RESULT_OK, resultIntent); - finish(); + BitmapUtil.saveBitmap(faceTempPath,rectBitmap); + File faceFile = new File(faceTempPath); + showLog(String.valueOf(faceFile.length())); + + if(faceFile!=null){ + Intent resultIntent = new Intent(); + resultIntent.putExtra("FaceRecognitionPicPath", faceTempPath); + setResult(RESULT_OK, resultIntent); + finish(); + } } else { startFaceRecognition = true; } @@ -281,6 +314,17 @@ public class FaceRecognitionAppActivity extends BaseActivity { }); } + public static Drawable bitmapToDrawable(Context context, Bitmap bitmap) { + Resources resources = context.getResources(); + float scale = resources.getDisplayMetrics().density; + int width = Math.round(bitmap.getWidth() / scale); + int height = Math.round(bitmap.getHeight() / scale); + + BitmapDrawable drawable = new BitmapDrawable(resources, bitmap); + drawable.setBounds(0, 0, width, height); + return drawable; + } + //Bitmap保存成文件 private void saveBitmapToFile(Bitmap bitmap) { diff --git a/app/src/main/java/com/rehome/dywoa/ui/activity/LoginActivity.kt b/app/src/main/java/com/rehome/dywoa/ui/activity/LoginActivity.kt index eb90a0f..ec3f945 100644 --- a/app/src/main/java/com/rehome/dywoa/ui/activity/LoginActivity.kt +++ b/app/src/main/java/com/rehome/dywoa/ui/activity/LoginActivity.kt @@ -211,13 +211,13 @@ class LoginActivity : BaseActivityOaToolbarViewBinding() { // binding.etPassword.setText("A000000a.") //ceshi1 - binding.etUsername.setText("ceshi1") - binding.etPassword.setText("A000000a.") +// binding.etUsername.setText("ceshi1") +// binding.etPassword.setText("A000000a.") //瑞洪 RH00002/王总 RH00002/chao工 RH00003/范红波 -// binding.etUsername.setText("RH00002") -// binding.etPassword.setText("A000000a.") + binding.etUsername.setText("RH00002") + binding.etPassword.setText("A000000a.") // binding.etUsername.setText("RH00002") // binding.etPassword.setText("A000000a.") diff --git a/app/src/main/java/com/rehome/dywoa/ui/fragment/HomeFragment.java b/app/src/main/java/com/rehome/dywoa/ui/fragment/HomeFragment.java index bf600ea..54783c5 100644 --- a/app/src/main/java/com/rehome/dywoa/ui/fragment/HomeFragment.java +++ b/app/src/main/java/com/rehome/dywoa/ui/fragment/HomeFragment.java @@ -32,6 +32,7 @@ import com.rehome.dywoa.R; import com.rehome.dywoa.adapter.GridViewAdapter; import com.rehome.dywoa.base.BaseFragment; import com.rehome.dywoa.base.MipcaActivityCapture; +import com.rehome.dywoa.bean.FaceRecognitionResult; import com.rehome.dywoa.bean.FwSingleLoginResult; import com.rehome.dywoa.bean.GridItem; import com.rehome.dywoa.bean.WaitForBean; @@ -59,6 +60,8 @@ import com.rehome.dywoa.utils.NohttpUtils; import com.rehome.dywoa.utils.RSAUtils; import com.rehome.dywoa.utils.UiUtlis; import com.rehome.dywoa.weiget.AutoGridView; +import com.rehome.dywoa.weiget.ConfirmDialog; +import com.rehome.dywoa.weiget.ConfirmFaceDialog; import com.yolanda.nohttp.NoHttp; import com.yolanda.nohttp.RequestMethod; import com.yolanda.nohttp.rest.Request; @@ -74,6 +77,7 @@ import java.util.Calendar; import java.util.Date; import java.util.HashMap; import java.util.List; +import java.util.Map; import java.util.Objects; import java.util.UUID; @@ -234,39 +238,33 @@ public class HomeFragment extends BaseFragment { int resultCode = result.getResultCode(); if (resultCode == RESULT_OK) { Intent resultIntent = result.getData(); - byte[] faceByte = resultIntent.getByteArrayExtra("FaceRecognition"); - - String fileName = UUID.randomUUID().toString()+".png"; - File fileDir = new File(path); - if(!fileDir.exists()){ - fileDir.mkdir(); - } - - String fileTempName = path + File.separator + fileName; - showLog(fileTempName); + //byte[] faceByte = resultIntent.getByteArrayExtra("FaceRecognition"); + String faceTempPath = resultIntent.getStringExtra("FaceRecognitionPicPath"); + File faceFile = new File(faceTempPath); + showLog(String.valueOf(faceFile.length())); + +// String fileName = UUID.randomUUID().toString()+".png"; +// File fileDir = new File(path); +// if(!fileDir.exists()){ +// fileDir.mkdir(); +// } +// +// String fileTempName = path + File.separator + fileName; +// showLog(fileTempName); try { - FileOutputStream fileOutputStream = new FileOutputStream(fileTempName); - IoUtil.write(fileOutputStream,true,faceByte); +// FileOutputStream fileOutputStream = new FileOutputStream(fileTempName); +// IoUtil.write(fileOutputStream,true,faceByte); - File fileFaceUpToServer = new File(fileTempName); - showLog(String.valueOf(fileFaceUpToServer.length())); + //File fileFaceUpToServer = new File(fileTempName); + //showLog(String.valueOf(fileFaceUpToServer.length())); - String url = "http://10.25.188.110:8088/"+Contans.FACE_RECOGNITION_APP_URL; + //String url = "http://192.168.2.115:8601/"+Contans.FACE_RECOGNITION_APP_URL; + String url = Contans.IP+Contans.FACE_RECOGNITION_APP_URL; Request request = NoHttp.createStringRequest(url, RequestMethod.POST); // showLog(json); // request.setDefineRequestBodyForJson(json); - request.add("face", fileFaceUpToServer); - - if(DataPassUtils.checkCanDj()){ - if(App.getInstance().getUserInfo()!=null&&App.getInstance().getUserInfo().getToken()!=null){ - String token = App.getInstance().getUserInfo().getToken(); - String credential = "Bearer " + token; - request.addHeader("Authorization", credential); - request.addHeader("token", token); - showLog(request.url()); - } - } + request.add("face", faceFile); NohttpUtils.getInstance().add(mActivity,30,request,new HttpListener(){ @Override @@ -275,8 +273,51 @@ public class HomeFragment extends BaseFragment { String jsonResult = response.get(); showLog("-----face------"); showLog(jsonResult); - - + FaceRecognitionResult faceRecognitionResult = GsonUtils.GsonToBean(jsonResult,FaceRecognitionResult.class); + if(faceRecognitionResult!=null){ + if(faceRecognitionResult.getState()==1){ + if(faceRecognitionResult.getData()!=null){ + FaceRecognitionResult.Data data = faceRecognitionResult.getData(); + String name = data.getName(); + String gh = data.getGh(); + String faceType = data.getFaceType(); + String msg = faceRecognitionResult.getMsg(); + ConfirmFaceDialog confirmDialog = new ConfirmFaceDialog(context, "人脸识别成功",msg,name,gh,faceType,faceTempPath,new ConfirmFaceDialog.ConfirmDialogFaceListener() { + @Override + public void confirm() { + + } + }); + confirmDialog.setTvTitle("人脸识别成功"); + confirmDialog.setCancelable(false); + confirmDialog.show(); + } + }else if(faceRecognitionResult.getState()==0){ + String msg = faceRecognitionResult.getMsg(); + if(TextUtils.isEmpty(msg)){ + msg="超脑连接异常"; + }else if("身份证号码为空".equals(msg)){ + msg="人脸库没有检索到当前人脸信息,人脸对比结果失败"; + } + ConfirmFaceDialog confirmDialog = new ConfirmFaceDialog(context, "人脸识别失败",msg,null,null,null,null, new ConfirmFaceDialog.ConfirmDialogFaceListener() { + @Override + public void confirm() { + + } + }); + confirmDialog.setTvTitle("人脸识别失败"); + confirmDialog.setCancelable(false); + confirmDialog.show(); + +// if(TextUtils.isEmpty(faceRecognitionResult.getMsg())){ +// showToast("人脸识别失败"); +// }else{ +// showToast(faceRecognitionResult.getMsg()); +// } + } + }else { + showToast("数据异常"); + } } @Override @@ -288,29 +329,6 @@ public class HomeFragment extends BaseFragment { } catch (Exception e) { e.printStackTrace(); } - - - - // 将字节数组转换为Base64编码的字符串 -// String base64String = ""; -// try { -// base64String = RSAUtils.encryptBASE64(faceByte); -// } catch (Exception e) { -// throw new RuntimeException(e); -// } -// showLog(base64String); -// showLog(String.valueOf(base64String.length())); -// -// showLog("----------"); -// String headBase64String = "data:image/png;base64," + base64String; -// //showLog(headBase64String); -// showLog(String.valueOf(headBase64String.length())); - -// HashMap param = new HashMap<>(); -// param.put("face",base64String); -// String json = new Gson().toJson(param); - - } } }); @@ -479,13 +497,8 @@ public class HomeFragment extends BaseFragment { startActivity(intentHightRisk); break; case 10: - if (ContextCompat.checkSelfPermission(mActivity, Manifest.permission.CAMERA) == PackageManager.PERMISSION_GRANTED) { - Intent intentFaceRecognition = new Intent(mActivity, FaceRecognitionAppActivity.class); - intentFaceRecognition.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_SINGLE_TOP); - launcherResultFaceRecognition.launch(intentFaceRecognition); - } else { - ActivityCompat.requestPermissions(mActivity, permission, CAMERA_REQUEST_CODE); - } + //人脸识别,先检测网络能否连接到服务器,能连接到服务器后申请权限打开摄像头 + checkFaceServerConnectStatus(); break; case 11: Intent intentYhTake = new Intent(mActivity, HightRiskActivity.class); @@ -529,6 +542,26 @@ public class HomeFragment extends BaseFragment { } } + //人脸识别请求权限 + private ActivityResultLauncher requestPermissionLauncher = registerForActivityResult( + new ActivityResultContracts.RequestPermission(), + new ActivityResultCallback() { + @Override + public void onActivityResult(Boolean result) { + if (result) { + // PERMISSION GRANTED + Intent intent = new Intent(mActivity, FaceRecognitionAppActivity.class); + intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_SINGLE_TOP); + launcherResultFaceRecognition.launch(intent); + } else { + // PERMISSION NOT GRANTED + //权限拒绝 + showToast("权限拒绝,无法打开摄像头,请手动设置开启APP访问摄像头权限"); + } + } + } + ); + private void initLists() { items = new ArrayList<>(); // String[] titles = {"两票系统", "会议管理", "用餐管理", "车辆管理", "办公领用", "工作任务", "日程查看", "考勤", "来访管理", "培训", "党建", "安防"}; @@ -616,6 +649,50 @@ public class HomeFragment extends BaseFragment { } }); } + + //检查服务器连接状态 + private void checkFaceServerConnectStatus() { + Map param = new HashMap<>(); + param.put("login","dywoa"); + String json = GsonUtils.GsonString(param); + String url = Contans.IP + Contans.check_server_connect; + showLog(url); + showLog(json); + Request request = NoHttp.createStringRequest( + url, + RequestMethod.POST + ); + request.setDefineRequestBodyForJson(json); + NoProgresshttpUtils.getInstance().add(requireActivity(), 0, request, new HttpListener() { + + @Override + public void onSucceed(int what, Response response) { + String result = response.get(); + showLog("-----onSucceed----"); + showLog(result); + if(result.equals("1")){ + showLog("connect server success"); + //可以连接到服务器,请求数据 + requestPermissionLauncher.launch(Manifest.permission.CAMERA); + +// if (ContextCompat.checkSelfPermission(mActivity, Manifest.permission.CAMERA) == PackageManager.PERMISSION_GRANTED) { +// Intent intentFaceRecognition = new Intent(mActivity, FaceRecognitionAppActivity.class); +// intentFaceRecognition.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_SINGLE_TOP); +// launcherResultFaceRecognition.launch(intentFaceRecognition); +// } else { +// ActivityCompat.requestPermissions(mActivity, permission, CAMERA_REQUEST_CODE); +// } + } + } + + @Override + public void onFailed(int what, Response response) { + showLog("connect server onFailed"); + showToast("人脸识别需要访问服务器,当前无法连接到服务器,请检查网络环境。"); + } + }); + } + //更新待办 public void updateWaitForToDo() { getWaitForToDo(); diff --git a/app/src/main/java/com/rehome/dywoa/utils/BitmapUtil.java b/app/src/main/java/com/rehome/dywoa/utils/BitmapUtil.java index 33a39ff..2003b52 100644 --- a/app/src/main/java/com/rehome/dywoa/utils/BitmapUtil.java +++ b/app/src/main/java/com/rehome/dywoa/utils/BitmapUtil.java @@ -155,4 +155,14 @@ public class BitmapUtil { return bitmap; } + public static Bitmap readBitmapFromFile(String filePath) { + File imgFile = new File(filePath); + if (imgFile.exists()) { + // 从文件解码为 Bitmap + Bitmap bitmap = BitmapFactory.decodeFile(imgFile.getAbsolutePath()); + return bitmap; + } + return null; + } + } \ No newline at end of file diff --git a/app/src/main/java/com/rehome/dywoa/weiget/ConfirmFaceDialog.java b/app/src/main/java/com/rehome/dywoa/weiget/ConfirmFaceDialog.java new file mode 100644 index 0000000..24d5538 --- /dev/null +++ b/app/src/main/java/com/rehome/dywoa/weiget/ConfirmFaceDialog.java @@ -0,0 +1,153 @@ +package com.rehome.dywoa.weiget; + + +import android.app.Dialog; +import android.content.Context; +import android.content.res.Resources; +import android.graphics.Bitmap; +import android.graphics.drawable.BitmapDrawable; +import android.graphics.drawable.Drawable; +import android.os.Build; +import android.os.Bundle; +import android.text.TextUtils; +import android.view.Display; +import android.view.Gravity; +import android.view.View; +import android.view.Window; +import android.view.WindowManager; + +import androidx.annotation.NonNull; + +import com.rehome.dywoa.databinding.DialogConfirmFaceBinding; +import com.rehome.dywoa.ui.activity.FaceRecognitionAppActivity; +import com.rehome.dywoa.utils.BitmapUtil; + +/** + * Create By HuangWenFei + * 创建日期:2023-01-12 11:55 + * 描述: + */ + +public class ConfirmFaceDialog extends Dialog { + + protected Context context; + protected View mView; + protected DialogConfirmFaceBinding binding; + protected ConfirmDialogFaceListener listener; + protected String msg; + protected String titleName; + + @Override + protected void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + setContentView(mView); + Window window = getWindow(); + WindowManager.LayoutParams lp = window.getAttributes(); + lp.width = (getScreenWidth(context)) * 2 / 3; + window.setGravity(Gravity.CENTER); + setTvMsg(msg); + binding.bottomBtnView.dialogCommit.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View v) { + dismiss(); + if (listener != null) { + listener.confirm(); + } + } + }); + + } + + public ConfirmFaceDialog(@NonNull Context context, String titleName, String msg, String name, String gh, String faceType, String facePath,ConfirmDialogFaceListener listener) { + super(context); + this.context=context; + this.listener = listener; + this.msg=msg; + this.titleName=titleName; + binding = DialogConfirmFaceBinding.inflate(getLayoutInflater()); + mView = binding.getRoot(); + requestWindowFeature(Window.FEATURE_NO_TITLE); + getWindow().setBackgroundDrawableResource(android.R.color.transparent); + + if (!TextUtils.isEmpty(titleName)) { + if("人脸识别成功".equals(titleName)){ + binding.tvMsg.setVisibility(View.GONE); + Bitmap rectBitmap = BitmapUtil.readBitmapFromFile(facePath); + Drawable drawable = bitmapToDrawable(context,rectBitmap); + binding.ivPhoto.setImageDrawable(drawable); + binding.ivPhoto.setVisibility(View.VISIBLE); + binding.tvName.setVisibility(View.VISIBLE); + binding.tvGh.setVisibility(View.VISIBLE); + binding.tvFaceType.setVisibility(View.VISIBLE); + if(!TextUtils.isEmpty(name)){ + binding.tvName.setText("姓名:"+name); + }else{ + binding.tvName.setText("姓名:"); + } + if(!TextUtils.isEmpty(gh)){ + binding.tvGh.setText("工号:"+gh); + }else{ + binding.tvGh.setText("工号:"); + } + if(!TextUtils.isEmpty(faceType)){ + binding.tvFaceType.setText("人员类型:"+faceType); + }else{ + binding.tvFaceType.setText("人员类型:"); + } + }else{ + binding.ivPhoto.setVisibility(View.GONE); + binding.tvName.setVisibility(View.GONE); + binding.tvGh.setVisibility(View.GONE); + binding.tvFaceType.setVisibility(View.GONE); + binding.tvMsg.setVisibility(View.VISIBLE); + binding.tvMsg.setText("错误提示:"+msg); + } + } + } + + public void setTvMsg(String msg) { + if (!TextUtils.isEmpty(msg)) { + binding.tvMsg.setText(msg); + } + } + + public static Drawable bitmapToDrawable(Context context, Bitmap bitmap) { + Resources resources = context.getResources(); + float scale = resources.getDisplayMetrics().density; + int width = Math.round(bitmap.getWidth() / scale); + int height = Math.round(bitmap.getHeight() / scale); + + BitmapDrawable drawable = new BitmapDrawable(resources, bitmap); + drawable.setBounds(0, 0, width, height); + return drawable; + } + + + public void setTvTitle(String title) { + if (!TextUtils.isEmpty(title)) { + this.titleName = title; + binding.tvTitle.setText(title); + } + } + + public void hideBottomClick() { + binding.bottomBtnView.bottomClick.setVisibility(View.GONE); + } + + + //获取屏幕宽度 + public static int getScreenWidth(Context context) { + WindowManager manager = (WindowManager) context + .getSystemService(Context.WINDOW_SERVICE); + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) { + return manager.getCurrentWindowMetrics().getBounds().width(); + }else{ + Display display = manager.getDefaultDisplay(); + return display.getWidth(); + } + } + + public interface ConfirmDialogFaceListener { + void confirm(); + } +} \ No newline at end of file diff --git a/app/src/main/res/layout/dialog_confirm_face.xml b/app/src/main/res/layout/dialog_confirm_face.xml new file mode 100644 index 0000000..3f0107e --- /dev/null +++ b/app/src/main/res/layout/dialog_confirm_face.xml @@ -0,0 +1,80 @@ + + + + + + + + + + + + + +