初始代码提交

This commit is contained in:
2026-01-14 10:36:27 +08:00
parent 600aa4dbb0
commit 196cacfe5a
268 changed files with 22545 additions and 2 deletions
@@ -0,0 +1,44 @@
package com.sw.inbound.ext
import androidx.compose.ui.Modifier
import androidx.compose.ui.composed
import androidx.compose.ui.draw.drawWithCache
import androidx.compose.ui.geometry.CornerRadius
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.graphics.PathEffect
import androidx.compose.ui.graphics.drawscope.Stroke
import androidx.compose.ui.platform.LocalDensity
import androidx.compose.ui.unit.Dp
import androidx.compose.ui.unit.dp
/**
* 虚线边框
*/
fun Modifier.dashedBorder(
strokeWidth: Dp = 2.dp,
color: Color = Color(0xFFDCDCF0),
cornerRadiusDp: Dp = 10.dp
) = composed(
factory = {
val density = LocalDensity.current
val strokeWidthPx = density.run { strokeWidth.toPx() }
val cornerRadiusPx = density.run { cornerRadiusDp.toPx() }
this.then(
Modifier.drawWithCache {
onDrawBehind {
val stroke = Stroke(
width = strokeWidthPx,
pathEffect = PathEffect.dashPathEffect(floatArrayOf(10f, 10f), 0f)
)
drawRoundRect(
color = color,
style = stroke,
cornerRadius = CornerRadius(cornerRadiusPx)
)
}
}
)
}
)
@@ -0,0 +1,105 @@
package com.sw.inbound.ext
import java.math.BigDecimal
import java.math.RoundingMode
import kotlin.math.pow
import kotlin.math.round
fun Float.toFormattedString(decimalPlaces: Int = 2): String {
return when (this) {
0f -> ""
else -> "%.${decimalPlaces}f".format(this) // 先格式化为固定位数
// .replace(Regex("\\.?0+$"), "") // 移除末尾的0
}
}
fun Double.toFormattedString(decimalPlaces: Int = 2): String {
return when (this) {
0.0 -> ""
else -> "%.${decimalPlaces}f".format(this)
// .replace(Regex("\\.?0+$"), "")
}
}
fun Double.toSafeBigDecimal(): BigDecimal {
return when (this) {
0.0 -> BigDecimal(0)
else -> toBigDecimal()
}
}
/**
* 保留指定小数位数
*/
private fun Double.roundToDouble(decimalPlaces: Int): Double {
val factor = 10.0.pow(decimalPlaces)
return round(this * factor) / factor
}
private fun Float.roundToDouble(decimalPlaces: Int): Double {
val factor = 10.0.pow(decimalPlaces)
return round(this * factor) / factor
}
fun Float?.toSafeString(unitName: String?): String {
if (this == null || this == 0f) return ""
val decimalPlaces = getDecimalPlaces(unitName)
return "%.${decimalPlaces}f".format(this)
}
fun Double?.toSafeString(unitName: String?): String {
if (this == null || this == 0.0) return ""
val decimalPlaces = getDecimalPlaces(unitName)
return "%.${decimalPlaces}f".format(this)
}
fun Double?.toSafeDouble(unitName: String?): Double {
if (this == null || this == 0.0) return 0.0
val decimalPlaces = getDecimalPlaces(unitName)
return roundToDouble(decimalPlaces)
}
fun Double?.toSafeDouble(decimalPlaces: Int = 2): Double {
if (this == null || this == 0.0) return 0.0
return roundToDouble(decimalPlaces)
}
fun Double?.toSafeFloat(unitName: String?): Float {
if (this == null || this == 0.0) return 0f
val decimalPlaces = getDecimalPlaces(unitName)
return roundToDouble(decimalPlaces).toFloat()
}
fun Double?.toSafeFloat(decimalPlaces: Int = 2): Float {
if (this == null || this == 0.0) return 0f
return roundToDouble(decimalPlaces).toFloat()
}
fun Float?.toSafeFloat(decimalPlaces: Int = 2): Float {
if (this == null || this == 0f) return 0f
return roundToDouble(decimalPlaces).toFloat()
}
/**
* 通过单位判断小数
*/
private fun getDecimalPlaces(unitName: String?): Int {
val decimalPlaces = when (unitName) {
"", "公斤", "", "千克" -> 2
else -> 0
}
return decimalPlaces
}
fun BigDecimal.toFormattedString(): String {
return this.setScale(2, RoundingMode.HALF_UP).toString()
}
fun Int.toFormattedString(): String {
return this.toString()
}
@@ -0,0 +1,104 @@
package com.sw.inbound.ext
import java.math.BigDecimal
import java.math.RoundingMode
fun String.isValidAmount(): Boolean {
// 空字符串允许(用于删除所有字符)
if (this.isEmpty()) return true
// 检查是否只包含数字和小数点
if (!matches(Regex("^\\d*\\.?\\d*$"))) return false
// 检查小数点数量(最多一个)
if (count { it == '.' } > 1) return false
// 检查小数点后位数(最多2位)
if (contains('.')) {
val decimalPart = substringAfter('.')
if (decimalPart.length > 2) return false
}
// 检查不以小数点开头
if (startsWith('.')) return false
return true
}
fun String.isNumeric(): Boolean {
return this.matches("-?\\d+(\\.\\d+)?".toRegex())
}
fun String?.toFormattedString(decimalPlaces: Int = 2): String {
return when (this) {
null -> ""
else -> "%.${decimalPlaces}s".format(this)
}
}
fun String.toSafeBigDecimal(
scale: Int = 2,
roundingMode: RoundingMode = RoundingMode.HALF_UP
): BigDecimal {
return when {
this.isBlank() -> BigDecimal.ZERO.setScale(scale, roundingMode)
this == "." -> BigDecimal.ZERO.setScale(scale, roundingMode)
else -> try {
BigDecimal(this.trim())
.setScale(scale, roundingMode)
} catch (e: Exception) {
BigDecimal.ZERO.setScale(scale, roundingMode)
}
}
}
fun String.isValidNumber(): Boolean {
return matches(Regex("^\\d*$"))
}
fun String.toSafeInt(): Int {
return if (this.isEmpty()) {
0
} else {
this.toInt()
}
}
fun String.toSafeDouble(): Double {
return if (this.isEmpty()) {
0.0
} else {
this.toDouble()
}
}
fun String.isValidFloat(maxFractionDigits: Int = 2): Boolean {
if (isEmpty()) return false
if (startsWith(".")) return false
// 处理前导零的情况
if (length > 1 && startsWith("0")) {
// 允许 "0" 和 "0.x" 但不允许 "00", "01", "00.1" 等
if (!startsWith("0.")) {
return false
}
}
// 构建动态正则表达式
val decimalRegex = when {
maxFractionDigits <= 0 -> Regex("^\\d+$") // 不允许小数
else -> Regex("^\\d+\\.?\\d{0,${maxFractionDigits}}$")
}
return matches(decimalRegex)
}
fun String.toSafeFloat(maxDecimalDigits: Int = 2): Float {
return if (this.isEmpty()) {
0f
} else if (isValidFloat()) {
toFloat()
} else {
0f
}
}
@@ -0,0 +1,33 @@
package com.sw.inbound.ext
import androidx.annotation.ColorRes
import androidx.compose.runtime.Composable
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.res.colorResource
import androidx.compose.ui.text.TextStyle
import androidx.compose.ui.text.font.FontWeight
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.unit.TextUnit
import androidx.compose.ui.unit.sp
// 快速修改颜色
fun TextStyle.withColor(color: Color): TextStyle = this.copy(color = color)
@Composable
fun TextStyle.withColorRes(@ColorRes colorRes: Int): TextStyle {
return this.copy(color = colorResource(id = colorRes))
}
// 快速修改字体大小
fun TextStyle.withSize(size: TextUnit): TextStyle = this.copy(fontSize = size)
fun TextStyle.withSizeSp(sp: Float): TextStyle = this.copy(fontSize = sp.sp)
// 快速修改字体粗细
fun TextStyle.withWeight(weight: FontWeight): TextStyle = this.copy(fontWeight = weight)
fun TextStyle.bold(): TextStyle = this.copy(fontWeight = FontWeight.Bold)
fun TextStyle.medium(): TextStyle = this.copy(fontWeight = FontWeight.Medium)
fun TextStyle.light(): TextStyle = this.copy(fontWeight = FontWeight.Light)
fun TextStyle.textAlign(textAlign: TextAlign): TextStyle = this.copy(textAlign = textAlign)