Procházet zdrojové kódy

1. 补充异常设备上报功能

bjb před 1 měsícem
rodič
revize
c3657cc8f5

+ 169 - 0
app/src/main/java/com/iscs/bozzys/ui/dialog/ExceptReportDialog.kt

@@ -0,0 +1,169 @@
+package com.iscs.bozzys.ui.dialog
+
+import android.view.WindowManager
+import androidx.compose.foundation.background
+import androidx.compose.foundation.clickable
+import androidx.compose.foundation.interaction.MutableInteractionSource
+import androidx.compose.foundation.layout.Box
+import androidx.compose.foundation.layout.Column
+import androidx.compose.foundation.layout.Row
+import androidx.compose.foundation.layout.Spacer
+import androidx.compose.foundation.layout.fillMaxSize
+import androidx.compose.foundation.layout.fillMaxWidth
+import androidx.compose.foundation.layout.height
+import androidx.compose.foundation.layout.padding
+import androidx.compose.foundation.shape.RoundedCornerShape
+import androidx.compose.material3.MaterialTheme
+import androidx.compose.material3.Text
+import androidx.compose.runtime.Composable
+import androidx.compose.runtime.LaunchedEffect
+import androidx.compose.runtime.SideEffect
+import androidx.compose.runtime.remember
+import androidx.compose.ui.Alignment
+import androidx.compose.ui.Modifier
+import androidx.compose.ui.draw.clip
+import androidx.compose.ui.graphics.Color
+import androidx.compose.ui.platform.LocalContext
+import androidx.compose.ui.text.font.FontWeight
+import androidx.compose.ui.text.style.TextAlign
+import androidx.compose.ui.unit.dp
+import androidx.compose.ui.unit.sp
+import androidx.compose.ui.window.Dialog
+import androidx.compose.ui.window.DialogProperties
+import com.iscs.bozzys.ui.common.PageBase
+import com.iscs.bozzys.ui.pages.compose.CardBox
+import com.iscs.bozzys.ui.pages.compose.FormBox
+import com.iscs.bozzys.ui.pages.compose.getFormListByJsonList
+import com.iscs.bozzys.ui.theme.Text
+
+/**
+ * 异常上报Dialog
+ *
+ * @param show          是否显示异常上报Dialog
+ * @param onConfirm     确认上报
+ * @param onCancel      取消上报
+ */
+@Composable
+fun ExceptReportDialog(show: Boolean, mac: String, onConfirm: () -> Unit = {}, onCancel: () -> Unit = {}) {
+    val ctx = LocalContext.current
+    if (!show || ctx !is PageBase) return
+
+    // 表单基准数据
+    val json = "[{\"id\":\"device_mac\",\"label\":\"异常设备\",\"value\":[\"$mac\"],\"type\":\"input\",\"placeholder\":[\"请输入异常的设备Mac\"],\"required\":true,\"enabled\":false},{\"id\":\"execpt_type\",\"label\":\"异常类别\",\"value\":[\"0\"],\"type\":\"select\",\"placeholder\":[\"请选择异常类别\"],\"required\":true,\"options\":[{\"label\":\"硬件故障\",\"value\":\"0\"},{\"label\":\"硬件丢失\",\"value\":\"1\"},{\"label\":\"作业取消\",\"value\":\"2\"},{\"label\":\"作业异常\",\"value\":\"3\"},{\"label\":\"其他异常\",\"value\":\"4\"}]},{\"id\":\"report_status\",\"label\":\"上报状态\",\"value\":[\"1\"],\"type\":\"radio\",\"placeholder\":[\"\"],\"required\":true,\"options\":[{\"label\":\"已上报\",\"value\":\"0\"},{\"label\":\"未上报\",\"value\":\"1\"}]},{\"id\":\"device_return\",\"label\":\"设备是否归还\",\"value\":[\"1\"],\"type\":\"radio\",\"placeholder\":[\"\"],\"required\":true,\"options\":[{\"label\":\"已归还\",\"value\":\"0\"},{\"label\":\"未归还\",\"value\":\"1\"}]},{\"id\":\"job_finish\",\"label\":\"作业任务是否完成\",\"value\":[\"1\"],\"type\":\"radio\",\"placeholder\":[\"\"],\"required\":true,\"options\":[{\"label\":\"已完成\",\"value\":\"0\"},{\"label\":\"未完成\",\"value\":\"1\"}]}]"
+    val forms = json.getFormListByJsonList(null)
+
+    LaunchedEffect(Unit) {
+        ctx.setNavigationLight(false)
+    }
+
+    Dialog(
+        onDismissRequest = onCancel,
+        properties = DialogProperties(decorFitsSystemWindows = false)
+    ) {
+        val activityWindow = ctx.window
+        val dialogWindow = ctx.getDialogWindow()
+        SideEffect {
+            if (activityWindow != null && dialogWindow != null) {
+                val attributes = WindowManager.LayoutParams()
+                // 复制Activity窗口属性
+                attributes.copyFrom(activityWindow.attributes)
+                // 这个一定要设置
+                attributes.type = dialogWindow.attributes.type
+                // 更新窗口属性
+                dialogWindow.attributes = attributes
+                // 设置窗口的宽度和高度,这段代码Dialog源码中就有哦,可以自己去查看
+                dialogWindow.setLayout(
+                    activityWindow.decorView.width,
+                    activityWindow.decorView.height
+                )
+            }
+        }
+        Box(
+            modifier = Modifier
+                .fillMaxSize()
+                .background(Color.Black.copy(alpha = 0.4f))
+                .clickable(
+                    indication = null,
+                    interactionSource = remember { MutableInteractionSource() },
+                    onClick = {}),
+            contentAlignment = Alignment.Center
+        ) {
+            CardBox(
+                topRadius = 16.dp,
+                bottomRadius = 16.dp,
+                modifier = Modifier
+                    .fillMaxWidth(0.85f)
+                    // 防止点击穿透
+                    .clickable(
+                        indication = null,
+                        interactionSource = remember { MutableInteractionSource() },
+                        onClick = {})
+                    .background(Color.White, RoundedCornerShape(16.dp))
+            ) {
+                Column(Modifier.fillMaxWidth()) {
+                    Row(
+                        Modifier
+                            .fillMaxWidth()
+                            .padding(horizontal = 16.dp),
+                        verticalAlignment = Alignment.CenterVertically
+                    ) {
+                        Text(
+                            "异常上报",
+                            fontSize = 18.sp,
+                            lineHeight = 48.sp,
+                            fontWeight = FontWeight.Bold,
+                            color = Text,
+                            modifier = Modifier.weight(1f),
+                            textAlign = TextAlign.Center
+                        )
+                    }
+                    Spacer(
+                        Modifier
+                            .fillMaxWidth()
+                            .height(0.5.dp)
+                            .background(Color.Black.copy(alpha = 0.05f))
+                    )
+                    FormBox(
+                        forms, {}, modifier = Modifier
+                            .padding(horizontal = 16.dp)
+                            .padding(bottom = 6.dp)
+                    )
+                    Spacer(
+                        Modifier
+                            .fillMaxWidth()
+                            .height(0.5.dp)
+                            .background(Color.Black.copy(alpha = 0.05f))
+                    )
+                    Row(Modifier.padding(horizontal = 5.dp, vertical = 10.dp)) {
+                        Text(
+                            "取消", color = Color.White, modifier = Modifier
+                                .padding(horizontal = 5.dp)
+                                .weight(1f)
+                                .clip(RoundedCornerShape(6.dp))
+                                .background(Color.Gray.copy(alpha = 0.6f))
+                                .clickable(onClick = { onCancel() })
+                                .padding(vertical = 8.dp),
+                            textAlign = TextAlign.Center,
+                            fontSize = 16.sp,
+                            fontWeight = FontWeight.Bold
+                        )
+                        Text(
+                            "确定",
+                            color = Color.White,
+                            modifier = Modifier
+                                .padding(horizontal = 5.dp)
+                                .weight(1f)
+                                .clip(RoundedCornerShape(6.dp))
+                                .background(MaterialTheme.colorScheme.primary)
+                                .clickable(onClick = { onConfirm() })
+                                .padding(vertical = 8.dp),
+                            textAlign = TextAlign.Center,
+                            fontSize = 16.sp,
+                            fontWeight = FontWeight.Bold
+                        )
+                    }
+                }
+            }
+        }
+    }
+}

+ 33 - 35
app/src/main/java/com/iscs/bozzys/ui/pages/return_device/PageReturnDevice.kt

@@ -23,7 +23,6 @@ import androidx.compose.material3.ExperimentalMaterial3Api
 import androidx.compose.material3.Icon
 import androidx.compose.material3.MaterialTheme
 import androidx.compose.material3.Text
-import androidx.compose.material3.pulltorefresh.PullToRefreshBox
 import androidx.compose.runtime.Composable
 import androidx.compose.runtime.LaunchedEffect
 import androidx.compose.runtime.collectAsState
@@ -44,10 +43,9 @@ import androidx.compose.ui.unit.sp
 import androidx.lifecycle.viewmodel.compose.viewModel
 import com.iscs.bozzys.R
 import com.iscs.bozzys.ui.common.PageBase
-import com.iscs.bozzys.ui.dialog.TipsDialog
+import com.iscs.bozzys.ui.dialog.ExceptReportDialog
 import com.iscs.bozzys.ui.pages.compose.CardBox
-import com.iscs.bozzys.ui.pages.vm.StatePageMessage
-import com.iscs.bozzys.ui.pages.vm.VMMessage
+import com.iscs.bozzys.ui.pages.vm.VMReturnDevice
 import com.iscs.bozzys.ui.theme.Text
 
 /**
@@ -63,7 +61,7 @@ fun Context.openPageReturnDevice() {
 class PageReturnDevice : PageBase() {
     @Composable
     override fun GetViews(pv: PaddingValues) {
-        val vm: VMMessage = viewModel()
+        val vm: VMReturnDevice = viewModel()
         val state by vm.state.collectAsState()
         LaunchedEffect(Unit) {
             vm.toast.initToast()
@@ -82,13 +80,13 @@ class PageReturnDevice : PageBase() {
                     .fillMaxSize()
             ) {
                 TopToolBar(pv, vm)
-                MessageList(vm)
+                DeviceList(vm)
             }
-            // 提示弹窗
-            TipsDialog(
-                show = state.tips.show, title = state.tips.title, content = state.tips.content,
-                onCancel = { vm.hideTips() },
-                onConfirm = { vm.onTipsConfirm() })
+            // 异常上报Dialog
+            ExceptReportDialog(state.showExceptDialog, state.exceptDeviceMac,{
+                vm.hideExceptDialog()
+                vm.reportExcept()
+            }, { vm.hideExceptDialog() })
         }
     }
 
@@ -97,7 +95,7 @@ class PageReturnDevice : PageBase() {
      * 顶部工具栏
      */
     @Composable
-    private fun TopToolBar(pv: PaddingValues, vm: VMMessage) {
+    private fun TopToolBar(pv: PaddingValues, vm: VMReturnDevice) {
         Column(
             modifier = Modifier
                 .fillMaxWidth()
@@ -157,7 +155,7 @@ class PageReturnDevice : PageBase() {
  */
 @OptIn(ExperimentalMaterial3Api::class)
 @Composable
-private fun MessageList(vm: VMMessage) {
+private fun DeviceList(vm: VMReturnDevice) {
     val state by vm.state.collectAsState()
     // 监听顶部Item
     val listState = rememberLazyListState()
@@ -177,25 +175,25 @@ private fun MessageList(vm: VMMessage) {
         }
     }
     // 处理加载更多数据
-    LaunchedEffect(shouldLoadMore) {
-        if (shouldLoadMore && state.messages.isNotEmpty() && !state.page.noMore) {
-            vm.getMessage(state.page.copy(page = state.page.page + 1, isRefresh = false))
-        }
-    }
-    PullToRefreshBox(state.page.isRefresh, onRefresh = {
-        vm.getMessage(StatePageMessage(isRefresh = true, page = 1))
-    }, modifier = Modifier.fillMaxSize()) {
-        Box(
-            modifier = Modifier
-                .padding(top = 5.dp)
-                .fillMaxSize()
+//    LaunchedEffect(shouldLoadMore) {
+//        if (shouldLoadMore && state.messages.isNotEmpty() && !state.page.noMore) {
+//            vm.getMessage(state.page.copy(page = state.page.page + 1, isRefresh = false))
+//        }
+//    }
+//    PullToRefreshBox(state.page.isRefresh, onRefresh = {
+//        vm.getMessage(StatePageMessage(isRefresh = true, page = 1))
+//    }, modifier = Modifier.fillMaxSize()) {
+    Box(
+        modifier = Modifier
+            .padding(top = 5.dp)
+            .fillMaxSize()
+    ) {
+        LazyColumn(
+            state = listState,
+            modifier = Modifier.fillMaxSize()
         ) {
-            LazyColumn(
-                state = listState,
-                modifier = Modifier.fillMaxSize()
-            ) {
-                items(3) { item -> DeviceItem(item) }
-                // 数据不为空才会显示加载中
+            items(3) { item -> DeviceItem(item, vm) }
+            // 数据不为空才会显示加载中
 //                if (state.messages.isNotEmpty()) item {
 //                    Text(
 //                        if (state.page.noMore) "没有更多数据" else "加载更多数据中...",
@@ -207,7 +205,7 @@ private fun MessageList(vm: VMMessage) {
 //                        color = Text.copy(alpha = 0.6f)
 //                    )
 //                }
-            }
+        }
 //            Empty(tips = "暂无待归还设备")
 //            // 悬浮在列表的顶部
 //            if (state.messages.isNotEmpty()) Box(
@@ -216,7 +214,7 @@ private fun MessageList(vm: VMMessage) {
 //            ) {
 //                MessageListItemTitle(state.messages[topIdx])
 //            }
-        }
+//        }
     }
 }
 
@@ -224,7 +222,7 @@ private fun MessageList(vm: VMMessage) {
  * 消息内容
  */
 @Composable
-private fun DeviceItem(item: Int) {
+private fun DeviceItem(item: Int, vm: VMReturnDevice) {
     CardBox(modifier = Modifier.padding(vertical = 8.dp, horizontal = 16.dp)) {
         Row(
             Modifier
@@ -273,7 +271,7 @@ private fun DeviceItem(item: Int) {
                 )
             }
             Button(
-                {},
+                { vm.showExceptDialog("32A9553$item") },
                 shape = RoundedCornerShape(6.dp),
                 contentPadding = PaddingValues(vertical = 0.dp, horizontal = 5.dp),
                 modifier = Modifier.height(28.dp)

+ 44 - 0
app/src/main/java/com/iscs/bozzys/ui/pages/vm/VMReturnDevice.kt

@@ -0,0 +1,44 @@
+package com.iscs.bozzys.ui.pages.vm
+
+import androidx.lifecycle.viewModelScope
+import com.iscs.bozzys.ui.common.VMBase
+import kotlinx.coroutines.delay
+import kotlinx.coroutines.flow.MutableStateFlow
+import kotlinx.coroutines.flow.asStateFlow
+import kotlinx.coroutines.launch
+
+class VMReturnDevice : VMBase() {
+
+    private val _state = MutableStateFlow(StateReturnDevice())
+
+    val state = _state.asStateFlow()
+
+    fun init() {
+
+    }
+
+    fun showExceptDialog(mac: String) {
+        _state.value = _state.value.copy(showExceptDialog = true, exceptDeviceMac = mac)
+    }
+
+    fun hideExceptDialog() {
+        _state.value = _state.value.copy(showExceptDialog = false)
+    }
+
+    fun reportExcept() {
+        viewModelScope.launch {
+            loading.emit(StateLoading(show = true, content = "异常上报中..."))
+            delay(2000)
+            loading.emit(StateLoading())
+            toast.emit("上报成功")
+        }
+    }
+
+}
+
+/**
+ * 当前页面状态
+ *
+ * @param showExceptDialog  是否显示异常上报Dialog
+ */
+data class StateReturnDevice(val showExceptDialog: Boolean = false, val exceptDeviceMac: String = "")