refactor: 注释移除 Compose 相关代码,统一入口替换为 HomeActivity

- 注释掉全部 Compose UI 代码(ui/、theme/、NavController、MainActivity、InitActivity 等)
- BorderExt、TextExt、ToastUtils、LoadingState 中的 Compose 逻辑全部注释
- LoadingState 保留 show()/hide() 空方法避免编译报错
- 注释 SensorScaleUtils、BaseViewModel、DeviceViewModel 中的 ToastUtils 调用
- BootReceiver、CrashHandler 中 MainActivity 替换为 HomeActivity
- UserViewModel、PurchaseOrderActivity 删除残余 Compose import
- build.gradle.kts 替换为非 Compose 的 activity-ktx 和 coil 依赖

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
2026-03-06 09:28:55 +08:00
co-authored by Claude Sonnet 4.6
parent b6c7570efd
commit 2c3ebd86f9
34 changed files with 2691 additions and 2692 deletions
@@ -2,9 +2,9 @@ package com.sw.inbound.utils
import android.content.Context
import android.view.View
import androidx.compose.runtime.Composable
import androidx.compose.ui.platform.LocalContext
import androidx.compose.ui.platform.LocalView
//import androidx.compose.runtime.Composable
//import androidx.compose.ui.platform.LocalContext
//import androidx.compose.ui.platform.LocalView
/**
* Context 工具类
@@ -17,18 +17,18 @@ object ContextUtils {
* 获取当前 Composable 的 Activity Context
* 只能在 @Composable 函数中调用
*/
@Composable
fun getActivityContext(): Context {
return LocalContext.current
}
// @Composable
// fun getActivityContext(): Context {
// return LocalContext.current
// }
/**
* 获取当前 Composable 的 View
*/
@Composable
fun getLocalView(): View {
return LocalView.current
}
// @Composable
// fun getLocalView(): View {
// return LocalView.current
// }
// ========== 非 Composable 环境获取 ==========
@@ -47,4 +47,4 @@ object ContextUtils {
"Application context not initialized. Call initAppContext() first."
)
}
}
}
@@ -9,7 +9,7 @@ import android.os.Build
import android.os.Handler
import android.os.Looper
import android.os.Process
import com.sw.inbound.MainActivity
import com.sw.inbound.activity.HomeActivity
import timber.log.Timber
import java.io.File
import java.io.FileOutputStream
@@ -86,7 +86,7 @@ class CrashHandler private constructor(private val context: Context) :
private fun restartApp() {
// 延迟1秒后重启应用
Handler(Looper.getMainLooper()).postDelayed({
val intent = Intent(context, MainActivity::class.java).apply {
val intent = Intent(context, HomeActivity::class.java).apply {
addFlags(Intent.FLAG_ACTIVITY_NEW_TASK)
}
@@ -1,223 +1,223 @@
package com.sw.inbound.utils
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableIntStateOf
import androidx.compose.runtime.mutableLongStateOf
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.rememberCoroutineScope
import androidx.compose.runtime.setValue
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Job
import kotlinx.coroutines.delay
import kotlinx.coroutines.launch
/**
* Jetpack Compose 交互工具集
* 包含快速点击过滤、防抖、节流、双击检测、长按检测等功能
*/
object InteractionUtils {
// ======================== 点击过滤 ========================
/**
* 快速点击过滤器
* @param minInterval 最小点击间隔时间(毫秒),默认500ms
*/
class ClickFilter(private val minInterval: Long = 500L) {
private var lastClickTime: Long = 0
/**
* 处理点击事件
* @return Boolean 是否允许此次点击(true=允许,false=拦截)
*/
fun processClick(): Boolean {
val currentTime = System.currentTimeMillis()
return if (currentTime - lastClickTime > minInterval) {
lastClickTime = currentTime
true
} else {
false
}
}
/**
* 处理点击事件(带回调)
*/
fun processClick(block: () -> Unit) {
if (processClick()) {
block()
}
}
}
/**
* 记住点击过滤器
*/
@Composable
fun rememberClickFilter(minInterval: Long = 500L): ClickFilter {
return remember { ClickFilter(minInterval) }
}
// ======================== 防抖处理 ========================
/**
* 防抖工具类
* @param delayMillis 防抖延迟时间(毫秒)
*/
class Debouncer(private val delayMillis: Long) {
private var lastActionTime = 0L
/**
* 执行防抖操作
* @param block 要执行的代码块
* @return Boolean 是否实际执行了操作
*/
fun debounce(block: () -> Unit): Boolean {
val currentTime = System.currentTimeMillis()
if (currentTime - lastActionTime >= delayMillis) {
lastActionTime = currentTime
block()
return true
}
return false
}
}
// ======================== 双击检测 ========================
/**
* 双击检测器
*/
class DoubleClickDetector(
private val timeout: Long = 500L,
private val onSingleClick: () -> Unit = {},
private val onDoubleClick: () -> Unit
) {
private var clickCount by mutableIntStateOf(0)
private var lastClickTime by mutableLongStateOf(0L)
/**
* 处理点击事件
*/
fun processClick(coroutineScope: CoroutineScope) {
val currentTime = System.currentTimeMillis()
if (currentTime - lastClickTime < timeout) {
clickCount++
if (clickCount == 2) {
onDoubleClick()
clickCount = 0
}
} else {
clickCount = 1
coroutineScope.launch {
delay(timeout)
if (clickCount == 1) {
onSingleClick()
}
clickCount = 0
}
}
lastClickTime = currentTime
}
}
/**
* 记住双击检测器
*/
@Composable
fun rememberDoubleClickDetector(
timeout: Long = 300L,
onSingleClick: () -> Unit = {},
onDoubleClick: () -> Unit
): () -> Unit {
val detector = remember { DoubleClickDetector(timeout, onSingleClick, onDoubleClick) }
val scope = rememberCoroutineScope()
return {
detector.processClick(scope)
}
}
// ======================== 长按检测 ========================
/**
* 长按检测器
*/
class LongPressDetector(
private val delay: Long = 1000L,
private val onLongPress: () -> Unit,
private val onClick: () -> Unit = {}
) {
private var pressJob: Job? = null
/**
* 处理按压事件
*/
fun handlePress(coroutineScope: CoroutineScope) {
pressJob = coroutineScope.launch {
delay(delay)
onLongPress()
}
}
/**
* 处理释放事件
*/
fun handleRelease() {
pressJob?.cancel()
pressJob = null
onClick()
}
}
/**
* 记住长按检测器
*/
@Composable
fun rememberLongPressDetector(
delay: Long = 1000L,
onLongPress: () -> Unit,
onClick: () -> Unit = {}
): Pair<() -> Unit, () -> Unit> {
val detector = remember { LongPressDetector(delay, onLongPress, onClick) }
val scope = rememberCoroutineScope()
return Pair(
first = { detector.handlePress(scope) },
second = { detector.handleRelease() }
)
}
// ======================== 组合工具 ========================
/**
* 带状态的按钮控制器
*/
class StatefulButtonController {
var isLoading by mutableStateOf(false)
private val clickFilter = ClickFilter()
/**
* 处理按钮点击
*/
suspend fun handleClick(block: suspend () -> Unit) {
if (clickFilter.processClick()) {
isLoading = true
try {
block()
} finally {
isLoading = false
}
}
}
}
/**
* 记住带状态的按钮控制器
*/
@Composable
fun rememberStatefulButtonController(): StatefulButtonController {
return remember { StatefulButtonController() }
}
}
//package com.sw.inbound.utils
//
//import androidx.compose.runtime.Composable
//import androidx.compose.runtime.getValue
//import androidx.compose.runtime.mutableIntStateOf
//import androidx.compose.runtime.mutableLongStateOf
//import androidx.compose.runtime.mutableStateOf
//import androidx.compose.runtime.remember
//import androidx.compose.runtime.rememberCoroutineScope
//import androidx.compose.runtime.setValue
//import kotlinx.coroutines.CoroutineScope
//import kotlinx.coroutines.Job
//import kotlinx.coroutines.delay
//import kotlinx.coroutines.launch
//
///**
// * Jetpack Compose 交互工具集
// * 包含快速点击过滤、防抖、节流、双击检测、长按检测等功能
// */
//object InteractionUtils {
//
// // ======================== 点击过滤 ========================
//
// /**
// * 快速点击过滤器
// * @param minInterval 最小点击间隔时间(毫秒),默认500ms
// */
// class ClickFilter(private val minInterval: Long = 500L) {
// private var lastClickTime: Long = 0
//
// /**
// * 处理点击事件
// * @return Boolean 是否允许此次点击(true=允许,false=拦截)
// */
// fun processClick(): Boolean {
// val currentTime = System.currentTimeMillis()
// return if (currentTime - lastClickTime > minInterval) {
// lastClickTime = currentTime
// true
// } else {
// false
// }
// }
//
// /**
// * 处理点击事件(带回调)
// */
// fun processClick(block: () -> Unit) {
// if (processClick()) {
// block()
// }
// }
// }
//
// /**
// * 记住点击过滤器
// */
// @Composable
// fun rememberClickFilter(minInterval: Long = 500L): ClickFilter {
// return remember { ClickFilter(minInterval) }
// }
//
// // ======================== 防抖处理 ========================
//
// /**
// * 防抖工具类
// * @param delayMillis 防抖延迟时间(毫秒)
// */
// class Debouncer(private val delayMillis: Long) {
// private var lastActionTime = 0L
//
// /**
// * 执行防抖操作
// * @param block 要执行的代码块
// * @return Boolean 是否实际执行了操作
// */
// fun debounce(block: () -> Unit): Boolean {
// val currentTime = System.currentTimeMillis()
// if (currentTime - lastActionTime >= delayMillis) {
// lastActionTime = currentTime
// block()
// return true
// }
// return false
// }
// }
// // ======================== 双击检测 ========================
//
// /**
// * 双击检测器
// */
// class DoubleClickDetector(
// private val timeout: Long = 500L,
// private val onSingleClick: () -> Unit = {},
// private val onDoubleClick: () -> Unit
// ) {
// private var clickCount by mutableIntStateOf(0)
// private var lastClickTime by mutableLongStateOf(0L)
//
// /**
// * 处理点击事件
// */
// fun processClick(coroutineScope: CoroutineScope) {
// val currentTime = System.currentTimeMillis()
// if (currentTime - lastClickTime < timeout) {
// clickCount++
// if (clickCount == 2) {
// onDoubleClick()
// clickCount = 0
// }
// } else {
// clickCount = 1
// coroutineScope.launch {
// delay(timeout)
// if (clickCount == 1) {
// onSingleClick()
// }
// clickCount = 0
// }
// }
// lastClickTime = currentTime
// }
// }
//
// /**
// * 记住双击检测器
// */
// @Composable
// fun rememberDoubleClickDetector(
// timeout: Long = 300L,
// onSingleClick: () -> Unit = {},
// onDoubleClick: () -> Unit
// ): () -> Unit {
// val detector = remember { DoubleClickDetector(timeout, onSingleClick, onDoubleClick) }
// val scope = rememberCoroutineScope()
//
// return {
// detector.processClick(scope)
// }
// }
//
// // ======================== 长按检测 ========================
//
// /**
// * 长按检测器
// */
// class LongPressDetector(
// private val delay: Long = 1000L,
// private val onLongPress: () -> Unit,
// private val onClick: () -> Unit = {}
// ) {
// private var pressJob: Job? = null
//
// /**
// * 处理按压事件
// */
// fun handlePress(coroutineScope: CoroutineScope) {
// pressJob = coroutineScope.launch {
// delay(delay)
// onLongPress()
// }
// }
//
// /**
// * 处理释放事件
// */
// fun handleRelease() {
// pressJob?.cancel()
// pressJob = null
// onClick()
// }
// }
//
// /**
// * 记住长按检测器
// */
// @Composable
// fun rememberLongPressDetector(
// delay: Long = 1000L,
// onLongPress: () -> Unit,
// onClick: () -> Unit = {}
// ): Pair<() -> Unit, () -> Unit> {
// val detector = remember { LongPressDetector(delay, onLongPress, onClick) }
// val scope = rememberCoroutineScope()
//
// return Pair(
// first = { detector.handlePress(scope) },
// second = { detector.handleRelease() }
// )
// }
//
// // ======================== 组合工具 ========================
//
// /**
// * 带状态的按钮控制器
// */
// class StatefulButtonController {
// var isLoading by mutableStateOf(false)
// private val clickFilter = ClickFilter()
//
// /**
// * 处理按钮点击
// */
// suspend fun handleClick(block: suspend () -> Unit) {
// if (clickFilter.processClick()) {
// isLoading = true
// try {
// block()
// } finally {
// isLoading = false
// }
// }
// }
// }
//
// /**
// * 记住带状态的按钮控制器
// */
// @Composable
// fun rememberStatefulButtonController(): StatefulButtonController {
// return remember { StatefulButtonController() }
// }
//}
@@ -5,9 +5,9 @@ import android.net.Uri
import androidx.camera.core.ImageCapture
import androidx.camera.core.ImageCaptureException
import androidx.camera.view.CameraController
import androidx.compose.runtime.Composable
import androidx.compose.runtime.remember
import androidx.compose.ui.platform.LocalContext
//import androidx.compose.runtime.Composable
//import androidx.compose.runtime.remember
//import androidx.compose.ui.platform.LocalContext
import androidx.core.content.ContextCompat
import timber.log.Timber
import java.io.File
@@ -101,21 +101,21 @@ class PhotoCaptureHelper(
* @param onError (String) -> Unit 拍照失败回调
* @return Pair<PhotoCaptureHelper, () -> Unit> 返回工具类实例和拍照函数
*/
@Composable
fun rememberPhotoCapture(
cameraController: CameraController,
onSuccess: (Uri) -> Unit = {},
onError: (String) -> Unit = {}
): Pair<PhotoCaptureHelper, () -> Unit> {
val context = LocalContext.current
val photoCaptureHelper = remember {
PhotoCaptureHelper(
context = context,
cameraController = cameraController,
onSuccess = onSuccess,
onError = onError
)
}
return Pair(photoCaptureHelper) { photoCaptureHelper.takePhoto() }
}
//@Composable
//fun rememberPhotoCapture(
// cameraController: CameraController,
// onSuccess: (Uri) -> Unit = {},
// onError: (String) -> Unit = {}
//): Pair<PhotoCaptureHelper, () -> Unit> {
// val context = LocalContext.current
// val photoCaptureHelper = remember {
// PhotoCaptureHelper(
// context = context,
// cameraController = cameraController,
// onSuccess = onSuccess,
// onError = onError
// )
// }
//
// return Pair(photoCaptureHelper) { photoCaptureHelper.takePhoto() }
//}
@@ -1,56 +1,56 @@
package com.sw.inbound.utils
import androidx.compose.foundation.background
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.runtime.LaunchedEffect
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.setValue
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.unit.dp
import androidx.compose.ui.unit.sp
import kotlinx.coroutines.delay
object ToastUtils {
private var show by mutableStateOf(false)
private var message by mutableStateOf("")
fun showToast(msg: String) {
message = msg
show = true
// Toast.makeText(ContextUtils.getAppContext(), msg, Toast.LENGTH_LONG).show()
}
@Composable
fun ToastComposable() {
if (show) {
LaunchedEffect(Unit) {
delay(2000) // 自动2秒后消失
show = false
}
Box(
modifier = Modifier
// .fillMaxWidth()
.fillMaxSize()
.padding(bottom = 156.dp),
contentAlignment = Alignment.BottomCenter
) {
Text(
text = message,
modifier = Modifier
.background(Color.Black.copy(alpha = 0.7f), RoundedCornerShape(8.dp))
.padding(horizontal = 24.dp, vertical = 12.dp),
color = Color.White,
fontSize = 24.sp
)
}
}
}
}
//package com.sw.inbound.utils
//
//import androidx.compose.foundation.background
//import androidx.compose.foundation.layout.Box
//import androidx.compose.foundation.layout.fillMaxSize
//import androidx.compose.foundation.layout.padding
//import androidx.compose.foundation.shape.RoundedCornerShape
//import androidx.compose.material3.Text
//import androidx.compose.runtime.Composable
//import androidx.compose.runtime.LaunchedEffect
//import androidx.compose.runtime.getValue
//import androidx.compose.runtime.mutableStateOf
//import androidx.compose.runtime.setValue
//import androidx.compose.ui.Alignment
//import androidx.compose.ui.Modifier
//import androidx.compose.ui.graphics.Color
//import androidx.compose.ui.unit.dp
//import androidx.compose.ui.unit.sp
//import kotlinx.coroutines.delay
//
//object ToastUtils {
// private var show by mutableStateOf(false)
// private var message by mutableStateOf("")
//
// fun showToast(msg: String) {
// message = msg
// show = true
//// Toast.makeText(ContextUtils.getAppContext(), msg, Toast.LENGTH_LONG).show()
// }
//
// @Composable
// fun ToastComposable() {
// if (show) {
// LaunchedEffect(Unit) {
// delay(2000) // 自动2秒后消失
// show = false
// }
// Box(
// modifier = Modifier
//// .fillMaxWidth()
// .fillMaxSize()
// .padding(bottom = 156.dp),
// contentAlignment = Alignment.BottomCenter
// ) {
// Text(
// text = message,
// modifier = Modifier
// .background(Color.Black.copy(alpha = 0.7f), RoundedCornerShape(8.dp))
// .padding(horizontal = 24.dp, vertical = 12.dp),
// color = Color.White,
// fontSize = 24.sp
// )
// }
// }
// }
//}