Skip to content

Commit a22862c

Browse files
committed
update formatter
1 parent 7548cc2 commit a22862c

File tree

20 files changed

+275
-259
lines changed

20 files changed

+275
-259
lines changed

compose-ui/build.gradle.kts

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -81,7 +81,6 @@ kotlin {
8181
implementation(libs.fluent.ui)
8282
implementation(libs.koin.compose)
8383
implementation(libs.androidx.collection)
84-
implementation(libs.prettytime)
8584
}
8685
}
8786
val iosMain by getting {

compose-ui/src/androidMain/kotlin/dev/dimension/flare/ui/component/DateTimeText.android.kt

Lines changed: 0 additions & 75 deletions
This file was deleted.

compose-ui/src/commonMain/kotlin/dev/dimension/flare/ui/component/DateTimeText.kt

Lines changed: 6 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,6 @@ package dev.dimension.flare.ui.component
22

33
import androidx.compose.foundation.text.InlineTextContent
44
import androidx.compose.runtime.Composable
5-
import androidx.compose.runtime.saveable.SaverScope
65
import androidx.compose.ui.Modifier
76
import androidx.compose.ui.graphics.Color
87
import androidx.compose.ui.text.TextLayoutResult
@@ -17,14 +16,6 @@ import androidx.compose.ui.unit.TextUnit
1716
import dev.dimension.flare.ui.component.platform.PlatformText
1817
import dev.dimension.flare.ui.component.platform.PlatformTextStyle
1918
import dev.dimension.flare.ui.render.UiDateTime
20-
import dev.dimension.flare.ui.render.toUi
21-
import kotlin.time.Instant
22-
23-
@Composable
24-
internal expect fun rememberFormattedDateTime(
25-
data: UiDateTime,
26-
fullTime: Boolean = false,
27-
): String
2819

2920
@Composable
3021
public fun DateTimeText(
@@ -48,10 +39,13 @@ public fun DateTimeText(
4839
style: TextStyle = PlatformTextStyle.current,
4940
fullTime: Boolean = false,
5041
) {
51-
val text = rememberFormattedDateTime(data, fullTime)
52-
5342
PlatformText(
54-
text = text,
43+
text =
44+
if (fullTime) {
45+
data.full
46+
} else {
47+
data.relative
48+
},
5549
modifier = modifier,
5650
color = color,
5751
fontSize = fontSize,
@@ -71,9 +65,3 @@ public fun DateTimeText(
7165
style = style,
7266
)
7367
}
74-
75-
internal data object UiDateTimeSaver : androidx.compose.runtime.saveable.Saver<UiDateTime, Long> {
76-
override fun restore(value: Long): UiDateTime? = Instant.fromEpochMilliseconds(value).toUi()
77-
78-
override fun SaverScope.save(value: UiDateTime): Long = value.value.toEpochMilliseconds()
79-
}

compose-ui/src/commonMain/kotlin/dev/dimension/flare/ui/component/status/CommonStatusComponent.kt

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -124,7 +124,6 @@ import dev.dimension.flare.ui.component.platform.PlatformText
124124
import dev.dimension.flare.ui.component.platform.PlatformTextButton
125125
import dev.dimension.flare.ui.component.platform.PlatformTextStyle
126126
import dev.dimension.flare.ui.component.platform.placeholder
127-
import dev.dimension.flare.ui.component.rememberFormattedDateTime
128127
import dev.dimension.flare.ui.model.ClickContext
129128
import dev.dimension.flare.ui.model.Digit
130129
import dev.dimension.flare.ui.model.UiCard
@@ -1138,13 +1137,11 @@ private fun StatusPollComponent(
11381137
)
11391138
} else {
11401139
poll.expiredAt?.let { expiredAt ->
1141-
val localizedExpiredTimeline =
1142-
rememberFormattedDateTime(expiredAt, fullTime = true)
11431140
PlatformText(
11441141
text =
11451142
stringResource(
11461143
resource = Res.string.poll_expired_at,
1147-
localizedExpiredTimeline,
1144+
expiredAt.full,
11481145
),
11491146
modifier =
11501147
Modifier

compose-ui/src/iosMain/kotlin/dev/dimension/flare/ui/controllers/ComposeUIHelper.kt

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ import dev.dimension.flare.common.InAppNotification
88
import dev.dimension.flare.common.Message
99
import dev.dimension.flare.data.network.ktorClient
1010
import dev.dimension.flare.di.KoinHelper
11+
import dev.dimension.flare.ui.humanizer.SwiftFormatter
1112
import kotlinx.coroutines.CoroutineScope
1213
import kotlinx.coroutines.Dispatchers
1314
import kotlinx.coroutines.launch
@@ -17,14 +18,20 @@ import org.koin.dsl.binds
1718
import org.koin.dsl.module
1819

1920
public object ComposeUIHelper {
20-
public fun initialize(inAppNotification: InAppNotification) {
21+
public fun initialize(
22+
inAppNotification: InAppNotification,
23+
swiftFormatter: SwiftFormatter,
24+
) {
2125
startKoin {
2226
modules(KoinHelper.modules())
2327
modules(
2428
module {
2529
single {
2630
ProxyInAppNotification(inAppNotification, get())
2731
} binds arrayOf(InAppNotification::class)
32+
single {
33+
swiftFormatter
34+
}
2835
},
2936
)
3037
modules(dev.dimension.flare.di.composeUiModule)

compose-ui/src/jvmMain/kotlin/dev/dimension/flare/ui/component/DateTimeText.jvm.kt

Lines changed: 0 additions & 58 deletions
This file was deleted.

desktopApp/src/main/kotlin/dev/dimension/flare/ui/theme/FlareTheme.kt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,7 @@ import dev.dimension.flare.data.model.Theme
3636
import dev.dimension.flare.data.repository.SettingsRepository
3737
import dev.dimension.flare.ui.component.ComponentAppearance
3838
import dev.dimension.flare.ui.component.LocalComponentAppearance
39-
import dev.dimension.flare.ui.component.updateTimeFormatterLocale
39+
import dev.dimension.flare.ui.humanizer.updateTimeFormatterLocale
4040
import dev.dimension.flare.ui.model.collectAsUiState
4141
import dev.dimension.flare.ui.model.onSuccess
4242
import io.github.composefluent.ExperimentalFluentApi

shared/build.gradle.kts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -106,6 +106,7 @@ kotlin {
106106
val jvmMain by getting {
107107
dependencies {
108108
implementation(libs.commons.lang3)
109+
implementation(libs.prettytime)
109110
}
110111
}
111112
val appleMain by getting {

shared/src/androidMain/kotlin/dev/dimension/flare/di/PlatformModule.android.kt

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,8 +4,11 @@ import dev.dimension.flare.data.database.DriverFactory
44
import dev.dimension.flare.data.datastore.AppDataStore
55
import dev.dimension.flare.data.io.PlatformPathProducer
66
import dev.dimension.flare.data.network.rss.NativeWebScraper
7+
import dev.dimension.flare.ui.humanizer.AndroidFormatter
8+
import dev.dimension.flare.ui.humanizer.PlatformFormatter
79
import org.koin.core.module.Module
810
import org.koin.core.module.dsl.singleOf
11+
import org.koin.dsl.bind
912
import org.koin.dsl.module
1013

1114
internal actual val platformModule: Module =
@@ -14,4 +17,5 @@ internal actual val platformModule: Module =
1417
singleOf(::DriverFactory)
1518
singleOf(::NativeWebScraper)
1619
singleOf(::PlatformPathProducer)
20+
singleOf(::AndroidFormatter) bind PlatformFormatter::class
1721
}
Lines changed: 98 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,98 @@
1+
package dev.dimension.flare.ui.humanizer
2+
3+
import android.content.Context
4+
import android.icu.text.CompactDecimalFormat
5+
import android.text.format.DateUtils
6+
import kotlinx.datetime.TimeZone
7+
import kotlinx.datetime.toLocalDateTime
8+
import java.math.RoundingMode
9+
import java.util.Locale
10+
import kotlin.time.Clock
11+
import kotlin.time.Instant
12+
13+
internal class AndroidFormatter(
14+
private val context: Context,
15+
) : PlatformFormatter {
16+
override fun formatNumber(number: Long): String {
17+
val cdf =
18+
CompactDecimalFormat.getInstance(
19+
Locale.getDefault(),
20+
CompactDecimalFormat.CompactStyle.SHORT,
21+
)
22+
cdf.maximumFractionDigits = 2
23+
cdf.minimumFractionDigits = 0
24+
cdf.roundingMode = RoundingMode.DOWN.ordinal
25+
cdf.isGroupingUsed = false
26+
return cdf.format(number)
27+
}
28+
29+
override fun formatRelativeInstant(instant: Instant): String {
30+
val compareTo = Clock.System.now()
31+
val timeZone = TimeZone.currentSystemDefault()
32+
val time = instant.toLocalDateTime(timeZone)
33+
val diff = compareTo - instant
34+
return when {
35+
diff.inWholeDays >= 7 -> {
36+
DateUtils.formatDateTime(
37+
context,
38+
instant.toEpochMilliseconds(),
39+
DateUtils.FORMAT_SHOW_DATE or DateUtils.FORMAT_ABBREV_MONTH,
40+
)
41+
}
42+
diff.inWholeDays >= 1 -> {
43+
DateUtils
44+
.getRelativeTimeSpanString(
45+
instant.toEpochMilliseconds(),
46+
System.currentTimeMillis(),
47+
DateUtils.DAY_IN_MILLIS,
48+
DateUtils.FORMAT_ABBREV_RELATIVE,
49+
).toString()
50+
}
51+
diff.inWholeHours >= 1 -> {
52+
DateUtils
53+
.getRelativeTimeSpanString(
54+
instant.toEpochMilliseconds(),
55+
System.currentTimeMillis(),
56+
DateUtils.HOUR_IN_MILLIS,
57+
DateUtils.FORMAT_ABBREV_RELATIVE,
58+
).toString()
59+
}
60+
diff.inWholeMinutes < 1 -> {
61+
DateUtils
62+
.getRelativeTimeSpanString(
63+
instant.toEpochMilliseconds(),
64+
System.currentTimeMillis(),
65+
DateUtils.SECOND_IN_MILLIS,
66+
DateUtils.FORMAT_ABBREV_RELATIVE,
67+
).toString()
68+
}
69+
compareTo.toLocalDateTime(timeZone).year != time.year -> {
70+
DateUtils.formatDateTime(
71+
context,
72+
instant.toEpochMilliseconds(),
73+
DateUtils.FORMAT_SHOW_DATE or DateUtils.FORMAT_ABBREV_MONTH or DateUtils.FORMAT_NUMERIC_DATE,
74+
)
75+
}
76+
else -> {
77+
DateUtils
78+
.getRelativeTimeSpanString(
79+
instant.toEpochMilliseconds(),
80+
System.currentTimeMillis(),
81+
DateUtils.MINUTE_IN_MILLIS,
82+
DateUtils.FORMAT_ABBREV_RELATIVE,
83+
).toString()
84+
}
85+
}
86+
}
87+
88+
override fun formatFullInstant(instant: Instant): String =
89+
DateUtils.formatDateTime(
90+
context,
91+
instant.toEpochMilliseconds(),
92+
DateUtils.FORMAT_SHOW_DATE or
93+
DateUtils.FORMAT_SHOW_TIME or
94+
DateUtils.FORMAT_ABBREV_MONTH or
95+
DateUtils.FORMAT_NUMERIC_DATE or
96+
DateUtils.FORMAT_SHOW_YEAR,
97+
)
98+
}

0 commit comments

Comments
 (0)