From ff6a0c3a33eb699ee83a29a746c534b32ec3b0f1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=BE=90=E5=8B=A4=E6=B0=91?= Date: Tue, 14 Apr 2026 22:51:57 +0800 Subject: [PATCH] =?UTF-8?q?feat(spraying):=20=E6=B7=BB=E5=8A=A0=E5=96=B7?= =?UTF-8?q?=E6=B4=92=E5=AE=8C=E6=88=90=E9=A1=B5=E9=9D=A2=E5=92=8C=E7=A6=BB?= =?UTF-8?q?=E7=BA=BF=E8=AF=AD=E9=9F=B3=E5=91=BD=E4=BB=A4=E4=BC=98=E5=8C=96?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - 实现了 SprayingFinishActivity 页面用于显示拍摄结果 - 添加了 SprayingPhotoManager 管理器用于管理喷洒照片 - 创建了 SprayingFinishVM 视图模型处理页面数据 - 设计了 activity_spraying_finish.xml 布局文件 - 优化了 OfflineCmdServiceHelper 的初始化逻辑,添加线程安全和单次初始化控制 - 实现了语音命令支持补充照片、确认提交和返回功能 - 添加了照片预览和统计功能,显示实际拍摄数量 --- .../glass/helper/OfflineCmdServiceHelper.kt | 42 ++++++--- .../glass/helper/SprayingPhotoManager.kt | 23 +++++ .../brain/glass/ui/SprayingFinishActivity.kt | 86 +++++++++++++++++ .../brain/glass/viewmodel/SprayingFinishVM.kt | 19 ++++ .../res/layout/activity_spraying_finish.xml | 93 +++++++++++++++++++ 5 files changed, 251 insertions(+), 12 deletions(-) create mode 100644 app/src/main/java/com/nova/brain/glass/helper/SprayingPhotoManager.kt create mode 100644 app/src/main/java/com/nova/brain/glass/ui/SprayingFinishActivity.kt create mode 100644 app/src/main/java/com/nova/brain/glass/viewmodel/SprayingFinishVM.kt create mode 100644 app/src/main/res/layout/activity_spraying_finish.xml diff --git a/app/src/main/java/com/nova/brain/glass/helper/OfflineCmdServiceHelper.kt b/app/src/main/java/com/nova/brain/glass/helper/OfflineCmdServiceHelper.kt index c3fb793..7bf91c0 100644 --- a/app/src/main/java/com/nova/brain/glass/helper/OfflineCmdServiceHelper.kt +++ b/app/src/main/java/com/nova/brain/glass/helper/OfflineCmdServiceHelper.kt @@ -4,11 +4,17 @@ import com.rokid.security.glass3.open.sdk.GlassSdk import com.rokid.security.glass3.sdk.base.data.offlineCmd.bean.VoiceAction import com.rokid.security.glass3.sdk.base.data.offlineCmd.listener.IVoiceCallback import com.xuqm.base.common.LogHelper +import java.util.concurrent.Executors data class OfflineCmdBean(val text: String, val pinyin: String) object OfflineCmdServiceHelper { private var listenerList = mutableListOf() + private val initExecutor = Executors.newSingleThreadExecutor() + @Volatile + private var initialized = false + @Volatile + private var initializing = false private val list = mutableListOf().apply { // 首页 @@ -169,22 +175,34 @@ object OfflineCmdServiceHelper { add(OfflineCmdBean("确认", "que ren")) // } + @Synchronized fun init(){ - val service = GlassSdk.getGlassOfflineCmdService() - if (service == null){ - LogHelper.e("OfflineCmdServiceHelper","service is null") + if (initialized || initializing) { return } - LogHelper.e("OfflineCmdServiceHelper","service 存在") - for (bean in list) { - service.add(VoiceAction(bean.text, bean.pinyin, object : IVoiceCallback.Stub() { - override fun onVoiceTriggered() { - LogHelper.d("onOfflineCmd: ${bean.text}") - for (l in listenerList) { - l.onOfflineCmd(bean.text) - } + initializing = true + initExecutor.execute { + try { + val service = GlassSdk.getGlassOfflineCmdService() + if (service == null){ + LogHelper.e("OfflineCmdServiceHelper","service is null") + return@execute } - })) + LogHelper.e("OfflineCmdServiceHelper","service 存在") + for (bean in list) { + service.add(VoiceAction(bean.text, bean.pinyin, object : IVoiceCallback.Stub() { + override fun onVoiceTriggered() { + LogHelper.d("onOfflineCmd: ${bean.text}") + for (l in listenerList) { + l.onOfflineCmd(bean.text) + } + } + })) + } + initialized = true + } finally { + initializing = false + } } } fun addOnLineListener(listener: OfflineCmdListener){ diff --git a/app/src/main/java/com/nova/brain/glass/helper/SprayingPhotoManager.kt b/app/src/main/java/com/nova/brain/glass/helper/SprayingPhotoManager.kt new file mode 100644 index 0000000..ac81927 --- /dev/null +++ b/app/src/main/java/com/nova/brain/glass/helper/SprayingPhotoManager.kt @@ -0,0 +1,23 @@ +package com.nova.brain.glass.helper + +object SprayingPhotoManager { + private val photoPaths = mutableListOf() + + @Synchronized + fun addPhoto(path: String) { + photoPaths.add(path) + } + + @Synchronized + fun getPhotoCount(): Int = photoPaths.size + + @Synchronized + fun getLastPhotos(limit: Int = 3): List { + return photoPaths.takeLast(limit) + } + + @Synchronized + fun clear() { + photoPaths.clear() + } +} diff --git a/app/src/main/java/com/nova/brain/glass/ui/SprayingFinishActivity.kt b/app/src/main/java/com/nova/brain/glass/ui/SprayingFinishActivity.kt new file mode 100644 index 0000000..fc2b6ed --- /dev/null +++ b/app/src/main/java/com/nova/brain/glass/ui/SprayingFinishActivity.kt @@ -0,0 +1,86 @@ +package com.nova.brain.glass.ui + +import android.app.Activity +import android.content.Intent +import android.graphics.BitmapFactory +import androidx.recyclerview.widget.RecyclerView +import com.nova.brain.glass.R +import com.nova.brain.glass.databinding.ActivitySprayingFinishBinding +import com.nova.brain.glass.helper.OfflineCmdListener +import com.nova.brain.glass.helper.OfflineCmdServiceHelper +import com.nova.brain.glass.helper.SprayingPhotoManager +import com.nova.brain.glass.model.ItemItem +import com.nova.brain.glass.viewmodel.SprayingFinishVM +import com.xuqm.base.adapter.BasePagedAdapter +import com.xuqm.base.adapter.CommonPagedAdapter +import com.xuqm.base.adapter.ViewHolder +import com.xuqm.base.ui.BaseListFormLayoutNormalActivity + +class SprayingFinishActivity : + BaseListFormLayoutNormalActivity() { + override fun getLayoutId(): Int = R.layout.activity_spraying_finish + override fun fullscreen(): Boolean = true + + override fun getRecyclerOrientation(): Int = RecyclerView.VERTICAL + + private val listener = object : OfflineCmdListener { + override fun onOfflineCmd(cmd: String) { + runOnUiThread { + when (cmd) { + "补充照片", "继续拍摄", "继续拍照" -> finishWithAction(ACTION_SUPPLEMENT) + "确认提交", "提交", "确认" -> finishWithAction(ACTION_SUBMIT) + "取消", "返回", "退回", "退出" -> finish() + } + } + } + } + + override fun initData() { + super.initData() + OfflineCmdServiceHelper.addOnLineListener(listener) + renderPhotos() + } + + override fun onDestroy() { + super.onDestroy() + OfflineCmdServiceHelper.removeOnLineListener(listener) + } + + private fun renderPhotos() { + val photos = SprayingPhotoManager.getLastPhotos() + binding.title.text = "本次任务应拍摄3张,实际拍摄${SprayingPhotoManager.getPhotoCount()}张" + val imageViews = listOf(binding.photo1, binding.photo2, binding.photo3) + imageViews.forEach { it.setImageDrawable(null) } + photos.forEachIndexed { index, path -> + imageViews.getOrNull(index)?.setImageBitmap(BitmapFactory.decodeFile(path)) + } + } + + private val adapter = object : CommonPagedAdapter(R.layout.item_manual_result_action) { + override fun convert(holder: ViewHolder, item: ItemItem, position: Int) { + holder + .setText(R.id.text, item.text) + .setClickListener(R.id.actionRoot) { + when (item.text) { + "补充照片" -> finishWithAction(ACTION_SUPPLEMENT) + "确认提交" -> finishWithAction(ACTION_SUBMIT) + } + } + } + } + + override fun adapter(): BasePagedAdapter = adapter + + private fun finishWithAction(action: String) { + setResult(Activity.RESULT_OK, Intent().apply { + putExtra(EXTRA_FINISH_ACTION, action) + }) + finish() + } + + companion object { + const val EXTRA_FINISH_ACTION = "extra_finish_action" + const val ACTION_SUPPLEMENT = "supplement" + const val ACTION_SUBMIT = "submit" + } +} diff --git a/app/src/main/java/com/nova/brain/glass/viewmodel/SprayingFinishVM.kt b/app/src/main/java/com/nova/brain/glass/viewmodel/SprayingFinishVM.kt new file mode 100644 index 0000000..51ca1bf --- /dev/null +++ b/app/src/main/java/com/nova/brain/glass/viewmodel/SprayingFinishVM.kt @@ -0,0 +1,19 @@ +package com.nova.brain.glass.viewmodel + +import com.nova.brain.glass.model.ItemItem +import com.xuqm.base.viewmodel.BaseListViewModel +import com.xuqm.base.viewmodel.callback.Response + +class SprayingFinishVM : BaseListViewModel() { + override fun loadData( + page: Int, + onResponse: Response + ) { + onResponse.onResponse( + arrayListOf().apply { + add(ItemItem("补充照片")) + add(ItemItem("确认提交")) + } + ) + } +} diff --git a/app/src/main/res/layout/activity_spraying_finish.xml b/app/src/main/res/layout/activity_spraying_finish.xml new file mode 100644 index 0000000..2c14571 --- /dev/null +++ b/app/src/main/res/layout/activity_spraying_finish.xml @@ -0,0 +1,93 @@ + + + + + + + + + + + + + + + + + + + + + + +