From 1372ba62a040bf61e647e8394db6ec9f40de2463 Mon Sep 17 00:00:00 2001 From: maxinyu Date: Tue, 12 May 2026 14:25:13 +0800 Subject: [PATCH] =?UTF-8?q?=E4=B8=AA=E4=BA=BA=E8=B5=84=E6=96=99?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/src/main/AndroidManifest.xml | 33 ++- .../home/PersonalFragment.kt | 10 + .../liveVideo/LinkedUserActivity.kt | 8 +- .../liveVideo/UserDetailsActivity.kt | 87 ++++++++ .../personal/FaceManagementActivity.kt | 35 ++++ .../personal/LoginPasswordActivity.kt | 30 +++ .../personal/OperationPasswordActivity.kt | 80 ++++++++ .../personal/PasswordManagementActivity.kt | 75 +++++++ .../personal/RetrievePasswordActivity.kt | 126 ++++++++++++ .../view/PasswordInputDialog.kt | 127 ++++++++++++ .../main/res/drawable/btn_selector_cyan.xml | 15 ++ .../main/res/drawable/password_input_bg.xml | 9 + .../main/res/layout/dialog_password_input.xml | 169 ++++++++++++++++ .../res/layout/face_management_activity.xml | 61 ++++++ .../res/layout/login_password_activity.xml | 109 ++++++++++ .../layout/operation_password_activity.xml | 121 +++++++++++ .../layout/password_management_activity.xml | 104 ++++++++++ .../res/layout/retrieve_password_activity.xml | 139 +++++++++++++ .../main/res/layout/user_details_activity.xml | 188 ++++++++++++++++++ app/src/main/res/values-zh/strings.xml | 21 ++ app/src/main/res/values/colors.xml | 1 + app/src/main/res/values/strings.xml | 26 +++ 22 files changed, 1566 insertions(+), 8 deletions(-) create mode 100644 app/src/main/java/com/example/defenseapplication/liveVideo/UserDetailsActivity.kt create mode 100644 app/src/main/java/com/example/defenseapplication/personal/FaceManagementActivity.kt create mode 100644 app/src/main/java/com/example/defenseapplication/personal/LoginPasswordActivity.kt create mode 100644 app/src/main/java/com/example/defenseapplication/personal/OperationPasswordActivity.kt create mode 100644 app/src/main/java/com/example/defenseapplication/personal/PasswordManagementActivity.kt create mode 100644 app/src/main/java/com/example/defenseapplication/personal/RetrievePasswordActivity.kt create mode 100644 app/src/main/java/com/example/defenseapplication/view/PasswordInputDialog.kt create mode 100644 app/src/main/res/drawable/btn_selector_cyan.xml create mode 100644 app/src/main/res/drawable/password_input_bg.xml create mode 100644 app/src/main/res/layout/dialog_password_input.xml create mode 100644 app/src/main/res/layout/face_management_activity.xml create mode 100644 app/src/main/res/layout/login_password_activity.xml create mode 100644 app/src/main/res/layout/operation_password_activity.xml create mode 100644 app/src/main/res/layout/password_management_activity.xml create mode 100644 app/src/main/res/layout/retrieve_password_activity.xml create mode 100644 app/src/main/res/layout/user_details_activity.xml diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml index e5e7a63..98d8b11 100644 --- a/app/src/main/AndroidManifest.xml +++ b/app/src/main/AndroidManifest.xml @@ -25,6 +25,24 @@ android:roundIcon="@mipmap/ic_launcher_round" android:supportsRtl="true" android:theme="@style/Theme.DefenseApplication"> + + + + + + @@ -57,12 +75,7 @@ android:exported="false" /> - - - - - + android:exported="false" /> @@ -86,7 +99,13 @@ android:exported="false" /> + android:exported="true"> + + + + + + diff --git a/app/src/main/java/com/example/defenseapplication/home/PersonalFragment.kt b/app/src/main/java/com/example/defenseapplication/home/PersonalFragment.kt index 91cde94..a74256a 100644 --- a/app/src/main/java/com/example/defenseapplication/home/PersonalFragment.kt +++ b/app/src/main/java/com/example/defenseapplication/home/PersonalFragment.kt @@ -9,6 +9,8 @@ import android.view.ViewGroup import com.bumptech.glide.Glide import com.example.defenseapplication.R import com.example.defenseapplication.databinding.PersonalFragmentBinding +import com.example.defenseapplication.liveVideo.LinkedUserActivity +import com.example.defenseapplication.personal.PasswordManagementActivity import com.example.defenseapplication.personal.PersonalProfileActivity import com.example.defenseapplication.utils.LanguageUtil import com.example.defenseapplication.view.FamilySwitchDialog @@ -48,6 +50,14 @@ class PersonalFragment : Fragment() { binding.itemSwitchFamily.setOnClickListener { showFamilySwitchDialog() } + binding.itemUserManage.setOnClickListener { + val intent= Intent(requireContext(), LinkedUserActivity::class.java) + startActivity(intent) + } + binding.itemPwdManage.setOnClickListener { + val intent= Intent(requireContext(), PasswordManagementActivity::class.java) + startActivity(intent) + } return binding.root } diff --git a/app/src/main/java/com/example/defenseapplication/liveVideo/LinkedUserActivity.kt b/app/src/main/java/com/example/defenseapplication/liveVideo/LinkedUserActivity.kt index da1edc6..8d4387f 100644 --- a/app/src/main/java/com/example/defenseapplication/liveVideo/LinkedUserActivity.kt +++ b/app/src/main/java/com/example/defenseapplication/liveVideo/LinkedUserActivity.kt @@ -42,7 +42,13 @@ class LinkedUserActivity : AppCompatActivity() { private fun initView() { adapter = LinkedUserAdapter( onItemClick = { user, position -> - + val intent = Intent(this, UserDetailsActivity::class.java).apply { + putExtra("name", user.name) + putExtra("phone", user.phone) + putExtra("idCard", user.idCard) + putExtra("time", user.time) + } + startActivity(intent) }, onDeleteClick = { user, position -> showUnlinkDialog(user, position) diff --git a/app/src/main/java/com/example/defenseapplication/liveVideo/UserDetailsActivity.kt b/app/src/main/java/com/example/defenseapplication/liveVideo/UserDetailsActivity.kt new file mode 100644 index 0000000..0a47377 --- /dev/null +++ b/app/src/main/java/com/example/defenseapplication/liveVideo/UserDetailsActivity.kt @@ -0,0 +1,87 @@ +package com.example.defenseapplication.liveVideo + +import android.os.Bundle +import androidx.appcompat.app.AppCompatActivity +import com.example.defenseapplication.R +import com.example.defenseapplication.databinding.UserDetailsActivityBinding +import com.example.defenseapplication.view.CustomDialogFragmentText +import com.gyf.immersionbar.ImmersionBar + +//用户详情页面 +class UserDetailsActivity : AppCompatActivity() { + private lateinit var binding: UserDetailsActivityBinding + + private lateinit var userName: String + private lateinit var phone: String + private lateinit var idCard: String + private lateinit var time: String + + override fun onCreate(savedInstanceState: Bundle?) { + super.onCreate(savedInstanceState) + binding = UserDetailsActivityBinding.inflate(layoutInflater) + setContentView(binding.root) + + ImmersionBar.with(this) + .statusBarDarkFont(true) + .titleBar(binding.topBar) + .init() + + initData() + initView() + initListener() + } + + private fun initData() { + userName = intent.getStringExtra("name") ?: "" + phone = intent.getStringExtra("phone") ?: "" + idCard = intent.getStringExtra("idCard") ?: "" + time = intent.getStringExtra("time") ?: "" + } + + private fun initView() { + binding.tvContactName.text = userName + binding.tvPhone.text = phone + binding.tvIdCard.text = idCard + binding.tvMacAddress.text = "AA:BB:CC:DD:EE:FF" + } + + private fun initListener() { + binding.ivBack.setOnClickListener { + finish() + } + + binding.swUserStatus.setOnCheckedChangeListener { _, isChecked -> + when (isChecked) { + true -> { + // 打开开关业务逻辑 + } + false -> { + // 关闭开关业务逻辑 + } + } + } + + binding.btnDelete.setOnClickListener { + showDeleteDialog() + } + } + + + private fun showDeleteDialog() { + val dialog = CustomDialogFragmentText() + dialog.setTitle(getString(R.string.tip)) + dialog.setMessage(getString(R.string.confirm_delete_user)) + dialog.setShowInput(false) + dialog.setPositiveText(getString(R.string.confirm)) + dialog.setNegativeText(getString(R.string.cancel)) + dialog.setOnConfirmListener { + finish() + // if(){ + // ToastUtils.showSuccess(this, getString(R.string.wifi_connection_success) + // }else{ + // ToastUtils.showError(this, getString(R.string.wifi_connection_failed)) + // } + } + dialog.show(supportFragmentManager, "DeleteUserDialog") + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/defenseapplication/personal/FaceManagementActivity.kt b/app/src/main/java/com/example/defenseapplication/personal/FaceManagementActivity.kt new file mode 100644 index 0000000..dcf8533 --- /dev/null +++ b/app/src/main/java/com/example/defenseapplication/personal/FaceManagementActivity.kt @@ -0,0 +1,35 @@ +package com.example.defenseapplication.personal + +import android.content.Intent +import android.os.Bundle +import androidx.activity.enableEdgeToEdge +import androidx.appcompat.app.AppCompatActivity +import androidx.core.view.ViewCompat +import androidx.core.view.WindowInsetsCompat +import com.example.defenseapplication.R +import com.example.defenseapplication.databinding.FaceManagementActivityBinding +import com.example.defenseapplication.databinding.LoginPasswordActivityBinding +import com.example.defenseapplication.login.FaceVerificationActivity +import com.gyf.immersionbar.ImmersionBar + +//人脸管理页面 +class FaceManagementActivity : AppCompatActivity() { + private lateinit var binding: FaceManagementActivityBinding + override fun onCreate(savedInstanceState: Bundle?) { + super.onCreate(savedInstanceState) + binding = FaceManagementActivityBinding.inflate(layoutInflater) + setContentView(binding.root) + + ImmersionBar.with(this) + .statusBarDarkFont(true) + .titleBar(binding.topBar) + .init() + + binding.ivBack.setOnClickListener { + finish() + } + binding.faceManagement.setOnClickListener { + startActivity(Intent(this, FaceVerificationActivity::class.java)) + } + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/defenseapplication/personal/LoginPasswordActivity.kt b/app/src/main/java/com/example/defenseapplication/personal/LoginPasswordActivity.kt new file mode 100644 index 0000000..c3f7117 --- /dev/null +++ b/app/src/main/java/com/example/defenseapplication/personal/LoginPasswordActivity.kt @@ -0,0 +1,30 @@ +package com.example.defenseapplication.personal + +import android.os.Bundle +import androidx.activity.enableEdgeToEdge +import androidx.appcompat.app.AppCompatActivity +import androidx.core.view.ViewCompat +import androidx.core.view.WindowInsetsCompat +import com.example.defenseapplication.R +import com.example.defenseapplication.databinding.LoginPasswordActivityBinding +import com.example.defenseapplication.databinding.PasswordManagementActivityBinding +import com.gyf.immersionbar.ImmersionBar + +//登录密码 +class LoginPasswordActivity : AppCompatActivity() { + private lateinit var binding: LoginPasswordActivityBinding + override fun onCreate(savedInstanceState: Bundle?) { + super.onCreate(savedInstanceState) + binding = LoginPasswordActivityBinding.inflate(layoutInflater) + setContentView(binding.root) + + ImmersionBar.with(this) + .statusBarDarkFont(true) + .titleBar(binding.topBar) + .init() + + binding.ivBack.setOnClickListener { + finish() + } + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/defenseapplication/personal/OperationPasswordActivity.kt b/app/src/main/java/com/example/defenseapplication/personal/OperationPasswordActivity.kt new file mode 100644 index 0000000..4e11807 --- /dev/null +++ b/app/src/main/java/com/example/defenseapplication/personal/OperationPasswordActivity.kt @@ -0,0 +1,80 @@ +package com.example.defenseapplication.personal + +import android.os.Bundle +import android.widget.Toast +import androidx.appcompat.app.AppCompatActivity +import com.blankj.utilcode.util.SPUtils +import com.example.defenseapplication.R +import com.example.defenseapplication.databinding.OperationPasswordActivityBinding +import com.gyf.immersionbar.ImmersionBar + +//操作密码 +class OperationPasswordActivity : AppCompatActivity() { + + private lateinit var binding: OperationPasswordActivityBinding + + override fun onCreate(savedInstanceState: Bundle?) { + super.onCreate(savedInstanceState) + binding = OperationPasswordActivityBinding.inflate(layoutInflater) + setContentView(binding.root) + + ImmersionBar.with(this) + .statusBarDarkFont(true) + .titleBar(binding.topBar) + .init() + + initListener() + } + + private fun initListener() { + binding.ivBack.setOnClickListener { + finish() + } + + binding.swOperationPassword.setOnCheckedChangeListener { _, isChecked -> + when (isChecked) { + true -> { + binding.etPassword.isEnabled = true + binding.etConfirmPassword.isEnabled = true + binding.btnConfirmReset.isEnabled = true + Toast.makeText(this, getString(R.string.operation_password_enabled), Toast.LENGTH_SHORT).show() + } + false -> { + binding.etPassword.isEnabled = false + binding.etConfirmPassword.isEnabled = false + binding.btnConfirmReset.isEnabled = false + SPUtils.getInstance().remove("operation_password") + Toast.makeText(this, getString(R.string.operation_password_disabled), Toast.LENGTH_SHORT).show() + } + } + } + + binding.btnConfirmReset.setOnClickListener { + val password = binding.etPassword.text.toString() + val confirmPassword = binding.etConfirmPassword.text.toString() + + if (password.isEmpty()) { + Toast.makeText(this, getString(R.string.password_cannot_empty), Toast.LENGTH_SHORT).show() + return@setOnClickListener + } + + if (password.length != 6) { + Toast.makeText(this, getString(R.string.password_must_be_6_digits), Toast.LENGTH_SHORT).show() + return@setOnClickListener + } + + if (confirmPassword.isEmpty()) { + Toast.makeText(this, getString(R.string.please_confirm_password), Toast.LENGTH_SHORT).show() + return@setOnClickListener + } + + if (password != confirmPassword) { + Toast.makeText(this, getString(R.string.password_mismatch), Toast.LENGTH_SHORT).show() + return@setOnClickListener + } + + SPUtils.getInstance().put("operation_password", password) + Toast.makeText(this, getString(R.string.operation_success), Toast.LENGTH_SHORT).show() + } + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/defenseapplication/personal/PasswordManagementActivity.kt b/app/src/main/java/com/example/defenseapplication/personal/PasswordManagementActivity.kt new file mode 100644 index 0000000..a9ad9d2 --- /dev/null +++ b/app/src/main/java/com/example/defenseapplication/personal/PasswordManagementActivity.kt @@ -0,0 +1,75 @@ +package com.example.defenseapplication.personal + +import android.content.Intent +import android.os.Bundle +import android.widget.Toast +import androidx.appcompat.app.AppCompatActivity +import com.example.defenseapplication.R +import com.example.defenseapplication.databinding.PasswordManagementActivityBinding +import com.example.defenseapplication.view.PasswordInputDialog +import com.blankj.utilcode.util.SPUtils +import com.gyf.immersionbar.ImmersionBar +//密码管理 +class PasswordManagementActivity : AppCompatActivity() { + + private lateinit var binding: PasswordManagementActivityBinding + private lateinit var passwordDialog: PasswordInputDialog + + override fun onCreate(savedInstanceState: Bundle?) { + super.onCreate(savedInstanceState) + binding = PasswordManagementActivityBinding.inflate(layoutInflater) + setContentView(binding.root) + + ImmersionBar.with(this) + .statusBarDarkFont(true) + .titleBar(binding.topBar) + .init() + + binding.ivBack.setOnClickListener { + finish() + } + + binding.loginPassword.setOnClickListener { + startActivity(Intent(this, LoginPasswordActivity::class.java)) + } + + binding.retrievePassword.setOnClickListener { + startActivity(Intent(this, RetrievePasswordActivity::class.java)) + } + + binding.operationPassword.setOnClickListener { + showPasswordDialog() + } + } + + private fun showPasswordDialog() { + passwordDialog = PasswordInputDialog(this).apply { + setOnConfirmListener { inputPassword -> + val savedPassword = SPUtils.getInstance().getString("operation_password", "111111") + if (savedPassword.isEmpty()) { + Toast.makeText(this@PasswordManagementActivity, getString(R.string.operation_password_not_set), Toast.LENGTH_SHORT).show() + dismiss() + return@setOnConfirmListener + } + if (inputPassword == savedPassword) { + startActivity(Intent(this@PasswordManagementActivity, OperationPasswordActivity::class.java)) + dismiss() + } else { + showError(getString(R.string.password_error)) + clearPassword() + } + } + setOnDismissListener { + // Dialog dismissed + } + } + passwordDialog.show() + } + + override fun onDestroy() { + if (::passwordDialog.isInitialized) { + passwordDialog.dismiss() + } + super.onDestroy() + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/defenseapplication/personal/RetrievePasswordActivity.kt b/app/src/main/java/com/example/defenseapplication/personal/RetrievePasswordActivity.kt new file mode 100644 index 0000000..a1a7029 --- /dev/null +++ b/app/src/main/java/com/example/defenseapplication/personal/RetrievePasswordActivity.kt @@ -0,0 +1,126 @@ +package com.example.defenseapplication.personal + +import android.os.Bundle +import android.os.CountDownTimer +import android.widget.Toast +import androidx.appcompat.app.AppCompatActivity +import com.example.defenseapplication.R +import com.example.defenseapplication.databinding.RetrievePasswordActivityBinding +import com.gyf.immersionbar.ImmersionBar + +//找回密码页面 +class RetrievePasswordActivity : AppCompatActivity() { + + private lateinit var binding: RetrievePasswordActivityBinding + private var countDownTimer: CountDownTimer? = null + private var isCountingDown = false + + override fun onCreate(savedInstanceState: Bundle?) { + super.onCreate(savedInstanceState) + binding = RetrievePasswordActivityBinding.inflate(layoutInflater) + setContentView(binding.root) + + ImmersionBar.with(this) + .statusBarDarkFont(true) + .titleBar(binding.topBar) + .init() + + initListener() + } + + private fun initListener() { + binding.ivBack.setOnClickListener { + finish() + } + + binding.btnGetCode.setOnClickListener { + val phoneNumber = binding.etPhoneNumber.text.toString() + + if (phoneNumber.isEmpty()) { + Toast.makeText(this, getString(R.string.enter_phone_number), Toast.LENGTH_SHORT).show() + return@setOnClickListener + } + + if (phoneNumber.length != 11) { + Toast.makeText(this, getString(R.string.phone_format_invalid), Toast.LENGTH_SHORT).show() + return@setOnClickListener + } + + startCountdown() + Toast.makeText(this, String.format(getString(R.string.code_sent_to), phoneNumber), Toast.LENGTH_SHORT).show() + } + + binding.btnConfirmReset.setOnClickListener { + val phoneNumber = binding.etPhoneNumber.text.toString() + val verificationCode = binding.etVerificationCode.text.toString() + val newPassword = binding.etNewPassword.text.toString() + val confirmPassword = binding.etConfirmPassword.text.toString() + + if (phoneNumber.isEmpty()) { + Toast.makeText(this, getString(R.string.enter_phone_number), Toast.LENGTH_SHORT).show() + return@setOnClickListener + } + + if (phoneNumber.length != 11) { + Toast.makeText(this, getString(R.string.phone_format_invalid), Toast.LENGTH_SHORT).show() + return@setOnClickListener + } + + if (verificationCode.isEmpty()) { + Toast.makeText(this, getString(R.string.enter_verification_code_pls), Toast.LENGTH_SHORT).show() + return@setOnClickListener + } + + if (verificationCode.length != 6) { + Toast.makeText(this, getString(R.string.verification_code_error), Toast.LENGTH_SHORT).show() + return@setOnClickListener + } + + if (newPassword.isEmpty()) { + Toast.makeText(this, getString(R.string.password_cannot_empty), Toast.LENGTH_SHORT).show() + return@setOnClickListener + } + + if (newPassword.length < 6 || newPassword.length > 20) { + Toast.makeText(this, getString(R.string.password_requirement), Toast.LENGTH_SHORT).show() + return@setOnClickListener + } + + if (confirmPassword.isEmpty()) { + Toast.makeText(this, getString(R.string.enter_password_again), Toast.LENGTH_SHORT).show() + return@setOnClickListener + } + + if (newPassword != confirmPassword) { + Toast.makeText(this, getString(R.string.password_mismatch), Toast.LENGTH_SHORT).show() + return@setOnClickListener + } + + Toast.makeText(this, getString(R.string.reset_success), Toast.LENGTH_SHORT).show() + finish() + } + } + + private fun startCountdown() { + isCountingDown = true + binding.btnGetCode.isEnabled = false + + countDownTimer = object : CountDownTimer(60000, 1000) { + override fun onTick(millisUntilFinished: Long) { + val seconds = millisUntilFinished / 1000 + binding.btnGetCode.text = String.format(getString(R.string.countdown_retry), seconds) + } + + override fun onFinish() { + isCountingDown = false + binding.btnGetCode.isEnabled = true + binding.btnGetCode.text = getString(R.string.get_verification_code) + } + }.start() + } + + override fun onDestroy() { + super.onDestroy() + countDownTimer?.cancel() + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/defenseapplication/view/PasswordInputDialog.kt b/app/src/main/java/com/example/defenseapplication/view/PasswordInputDialog.kt new file mode 100644 index 0000000..c6e6d22 --- /dev/null +++ b/app/src/main/java/com/example/defenseapplication/view/PasswordInputDialog.kt @@ -0,0 +1,127 @@ +package com.example.defenseapplication.view + +import android.app.Dialog +import android.content.Context +import android.graphics.Color +import android.graphics.drawable.ColorDrawable +import android.view.Gravity +import android.view.LayoutInflater +import android.view.View +import android.view.WindowManager +import android.widget.EditText +import com.example.defenseapplication.R +import com.example.defenseapplication.databinding.DialogPasswordInputBinding + +class PasswordInputDialog(context: Context) : Dialog(context) { + + private lateinit var binding: DialogPasswordInputBinding + private var onConfirmListener: ((String) -> Unit)? = null + private var onDismissListener: (() -> Unit)? = null + + init { + initView() + } + + private fun initView() { + binding = DialogPasswordInputBinding.inflate(LayoutInflater.from(context)) + setContentView(binding.root) + + window?.apply { + setBackgroundDrawable(ColorDrawable(Color.TRANSPARENT)) + val params = attributes + params.gravity = Gravity.CENTER + params.width = WindowManager.LayoutParams.MATCH_PARENT + params.height = WindowManager.LayoutParams.WRAP_CONTENT + params.horizontalMargin = 40f + attributes = params + } + + setupPasswordInput() + + binding.btnCancel.setOnClickListener { + dismiss() + } + + binding.btnConfirm.setOnClickListener { + val password = getPassword() + if (password.length == 6) { + onConfirmListener?.invoke(password) + dismiss() + } + } + } + + private fun setupPasswordInput() { + val editTexts = listOf( + binding.etPassword1, + binding.etPassword2, + binding.etPassword3, + binding.etPassword4, + binding.etPassword5, + binding.etPassword6 + ) + + editTexts.forEachIndexed { index, editText -> + editText.setOnKeyListener { _, _, _ -> + if (editText.text.isNotEmpty()) { + if (index < editTexts.size - 1) { + editTexts[index + 1].requestFocus() + } else { + editText.clearFocus() + } + } + false + } + + editText.setOnFocusChangeListener { v, hasFocus -> + if (hasFocus) { + (v as EditText).setSelection((v.text?.length ?: 0)) + } + } + } + } + + private fun getPassword(): String { + return binding.etPassword1.text.toString() + + binding.etPassword2.text.toString() + + binding.etPassword3.text.toString() + + binding.etPassword4.text.toString() + + binding.etPassword5.text.toString() + + binding.etPassword6.text.toString() + } + + fun setOnConfirmListener(listener: (String) -> Unit): PasswordInputDialog { + this.onConfirmListener = listener + return this + } + + fun setOnDismissListener(listener: () -> Unit): PasswordInputDialog { + this.onDismissListener = listener + return this + } + + fun showError(message: String) { + binding.tvError.text = message + binding.tvError.visibility = View.VISIBLE + } + + fun clearError() { + binding.tvError.visibility = View.GONE + binding.tvError.text = "" + } + + fun clearPassword() { + binding.etPassword1.text?.clear() + binding.etPassword2.text?.clear() + binding.etPassword3.text?.clear() + binding.etPassword4.text?.clear() + binding.etPassword5.text?.clear() + binding.etPassword6.text?.clear() + binding.etPassword1.requestFocus() + } + + override fun dismiss() { + super.dismiss() + onDismissListener?.invoke() + } +} \ No newline at end of file diff --git a/app/src/main/res/drawable/btn_selector_cyan.xml b/app/src/main/res/drawable/btn_selector_cyan.xml new file mode 100644 index 0000000..dd34181 --- /dev/null +++ b/app/src/main/res/drawable/btn_selector_cyan.xml @@ -0,0 +1,15 @@ + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/app/src/main/res/drawable/password_input_bg.xml b/app/src/main/res/drawable/password_input_bg.xml new file mode 100644 index 0000000..ddae5b6 --- /dev/null +++ b/app/src/main/res/drawable/password_input_bg.xml @@ -0,0 +1,9 @@ + + + + + + \ No newline at end of file diff --git a/app/src/main/res/layout/dialog_password_input.xml b/app/src/main/res/layout/dialog_password_input.xml new file mode 100644 index 0000000..56ef5b7 --- /dev/null +++ b/app/src/main/res/layout/dialog_password_input.xml @@ -0,0 +1,169 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/app/src/main/res/layout/face_management_activity.xml b/app/src/main/res/layout/face_management_activity.xml new file mode 100644 index 0000000..8aeef78 --- /dev/null +++ b/app/src/main/res/layout/face_management_activity.xml @@ -0,0 +1,61 @@ + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/app/src/main/res/layout/login_password_activity.xml b/app/src/main/res/layout/login_password_activity.xml new file mode 100644 index 0000000..babe93a --- /dev/null +++ b/app/src/main/res/layout/login_password_activity.xml @@ -0,0 +1,109 @@ + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/app/src/main/res/layout/operation_password_activity.xml b/app/src/main/res/layout/operation_password_activity.xml new file mode 100644 index 0000000..22f5aa6 --- /dev/null +++ b/app/src/main/res/layout/operation_password_activity.xml @@ -0,0 +1,121 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/app/src/main/res/layout/password_management_activity.xml b/app/src/main/res/layout/password_management_activity.xml new file mode 100644 index 0000000..caf31bf --- /dev/null +++ b/app/src/main/res/layout/password_management_activity.xml @@ -0,0 +1,104 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/app/src/main/res/layout/retrieve_password_activity.xml b/app/src/main/res/layout/retrieve_password_activity.xml new file mode 100644 index 0000000..c55df2f --- /dev/null +++ b/app/src/main/res/layout/retrieve_password_activity.xml @@ -0,0 +1,139 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/app/src/main/res/layout/user_details_activity.xml b/app/src/main/res/layout/user_details_activity.xml new file mode 100644 index 0000000..18f15f3 --- /dev/null +++ b/app/src/main/res/layout/user_details_activity.xml @@ -0,0 +1,188 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/app/src/main/res/values-zh/strings.xml b/app/src/main/res/values-zh/strings.xml index bff8784..ce90154 100644 --- a/app/src/main/res/values-zh/strings.xml +++ b/app/src/main/res/values-zh/strings.xml @@ -174,6 +174,7 @@ 中文 English 关联用户 + 用户详情 搜索 搜索预设文案 添加关联用户 @@ -249,6 +250,7 @@ 操作失败 网络不可用 请检查网络连接 + 确定删除该用户吗? 识别模式 @@ -305,7 +307,9 @@ 人脸采集 请将人脸放入圆形区域内 采集人脸 + 登录密码 找回密码 + 操作密码 请输入手机号 请输入验证码 发送验证码 @@ -375,4 +379,21 @@ 修改手机号 手机号格式不正确 验证并绑定 + 操作密码开关 + 请输入6位数字密码 + 请确认密码 + 操作密码已开启 + 操作密码已关闭 + 密码必须为6位数字 + 请确认密码 + 确定重设密码 + 获取验证码 + 请输入手机号 + 请输入验证码 + 请输入新密码 + 请再次输入新密码 + 请输入旧密码 + 密码错误 + 未设置操作密码 + 确认重置 \ No newline at end of file diff --git a/app/src/main/res/values/colors.xml b/app/src/main/res/values/colors.xml index 7fcf1d7..c3b18d5 100644 --- a/app/src/main/res/values/colors.xml +++ b/app/src/main/res/values/colors.xml @@ -18,5 +18,6 @@ #F3F3F3 #111111 #E8F7F7 + #E5E5E5 \ No newline at end of file diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 3fee377..701ed3d 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -166,6 +166,7 @@ Chinese English Linked user + User Details search Search preset text Add linked user @@ -224,6 +225,7 @@ Operation failed Network unavailable Please check your network connection + Are you sure to delete this user? Recognition Mode @@ -242,6 +244,10 @@ Please scan the QR code on the device or manual + 用户状态 + 联系人姓名 + 身份证号 + MAC地址 Workshop Parents Home Smart Hanging Defense @@ -290,7 +296,12 @@ Face Collection Please align your face within the circular area Collect Face + Login Password + Enter old password + Confirm Reset Password Retrieve Password + Operation Password + Enter phone number Enter verification code Send Code @@ -380,4 +391,19 @@ Verification code sent to %s Login successful Login successful + Operation Password Switch + Please enter a 6-digit numeric password + Please confirm your password + Operation password enabled + Operation password disabled + Password must be 6 digits + Please confirm your password + Password error + Operation password not set + Get Verification Code + Please enter your phone number + Please enter verification code + Please enter new password + Please re-enter new password + Confirm Reset \ No newline at end of file