Compare commits
1 Commits
2.3.1
...
feature/#3
| Author | SHA1 | Date | |
|---|---|---|---|
| d1b4ab1e8c |
@@ -37,7 +37,7 @@ import me.zobrist.tichucounter.ui.settings.SettingsViewModel
|
||||
import javax.inject.Inject
|
||||
|
||||
@AndroidEntryPoint
|
||||
class MainActivity : AppCompatActivity(), ISettingsChangeListener {
|
||||
class MainActivity : AppCompatActivity(), ISystemSettingsChangeListener {
|
||||
|
||||
@Inject
|
||||
lateinit var settingsAdapter: SettingsAdapter
|
||||
|
||||
@@ -16,17 +16,26 @@ enum class Language(val value: LocaleListCompat) {
|
||||
|
||||
enum class KeepScreenOn(val value: Boolean) { ON(true), OFF(false) }
|
||||
|
||||
interface ISettingsChangeListener {
|
||||
enum class CounterListView { BY_ROUND, CONTINUOUS }
|
||||
|
||||
|
||||
interface ISystemSettingsChangeListener {
|
||||
fun onLanguageChanged(language: Language)
|
||||
fun onThemeChanged(theme: Theme)
|
||||
fun onScreenOnChanged(keepOn: KeepScreenOn)
|
||||
}
|
||||
|
||||
interface IDisplaySettingsChangeListener {
|
||||
fun onCounterListViewChanged(listView: CounterListView)
|
||||
}
|
||||
|
||||
@Singleton
|
||||
class SettingsAdapter @Inject constructor(@ApplicationContext private val context: Context) {
|
||||
|
||||
private val sharedPreferences = PreferenceManager.getDefaultSharedPreferences(context)
|
||||
private var listenerList = mutableListOf<ISettingsChangeListener>()
|
||||
private var systemListenerList = mutableListOf<ISystemSettingsChangeListener>()
|
||||
private var displayListenerList = mutableListOf<IDisplaySettingsChangeListener>()
|
||||
|
||||
|
||||
var language: Language
|
||||
private set
|
||||
@@ -37,6 +46,9 @@ class SettingsAdapter @Inject constructor(@ApplicationContext private val contex
|
||||
var keepScreenOn: KeepScreenOn
|
||||
private set
|
||||
|
||||
var counterListView: CounterListView
|
||||
private set
|
||||
|
||||
init {
|
||||
language = try {
|
||||
enumValueOf(sharedPreferences.getString(Language::class.simpleName, null)!!)
|
||||
@@ -55,19 +67,37 @@ class SettingsAdapter @Inject constructor(@ApplicationContext private val contex
|
||||
} catch (_: java.lang.Exception) {
|
||||
KeepScreenOn.OFF
|
||||
}
|
||||
|
||||
counterListView = try {
|
||||
enumValueOf(sharedPreferences.getString(CounterListView::class.simpleName, null)!!)
|
||||
} catch (_: java.lang.Exception) {
|
||||
CounterListView.BY_ROUND
|
||||
}
|
||||
}
|
||||
|
||||
fun registerOnChangeListener(listener: ISettingsChangeListener) {
|
||||
listenerList.add(listener)
|
||||
fun registerOnChangeListener(listener: ISystemSettingsChangeListener) {
|
||||
systemListenerList.add(listener)
|
||||
|
||||
listener.onThemeChanged(theme)
|
||||
listener.onLanguageChanged(language)
|
||||
listener.onScreenOnChanged(keepScreenOn)
|
||||
}
|
||||
|
||||
fun unregisterOnChangeListener(listener: ISettingsChangeListener?) {
|
||||
fun registerOnChangeListener(listener: IDisplaySettingsChangeListener) {
|
||||
displayListenerList.add(listener)
|
||||
|
||||
listener.onCounterListViewChanged(counterListView)
|
||||
}
|
||||
|
||||
fun unregisterOnChangeListener(listener: ISystemSettingsChangeListener?) {
|
||||
if (listener != null) {
|
||||
listenerList.remove(listener)
|
||||
systemListenerList.remove(listener)
|
||||
}
|
||||
}
|
||||
|
||||
fun unregisterOnChangeListener(listener: IDisplaySettingsChangeListener?) {
|
||||
if (listener != null) {
|
||||
displayListenerList.remove(listener)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -89,6 +119,12 @@ class SettingsAdapter @Inject constructor(@ApplicationContext private val contex
|
||||
notifyListeners(setting)
|
||||
}
|
||||
|
||||
fun setCounterViewList(setting: CounterListView) {
|
||||
this.counterListView = setting
|
||||
updatePreference(CounterListView::class.simpleName, setting.name)
|
||||
notifyListeners(setting)
|
||||
}
|
||||
|
||||
private fun updatePreference(name: String?, value: String) {
|
||||
val editor = sharedPreferences.edit()
|
||||
editor.putString(name, value)
|
||||
@@ -96,21 +132,27 @@ class SettingsAdapter @Inject constructor(@ApplicationContext private val contex
|
||||
}
|
||||
|
||||
private fun notifyListeners(language: Language) {
|
||||
listenerList.forEach {
|
||||
systemListenerList.forEach {
|
||||
it.onLanguageChanged(language)
|
||||
}
|
||||
}
|
||||
|
||||
private fun notifyListeners(theme: Theme) {
|
||||
listenerList.forEach {
|
||||
systemListenerList.forEach {
|
||||
it.onThemeChanged(theme)
|
||||
}
|
||||
}
|
||||
|
||||
private fun notifyListeners(keepScreenOn: KeepScreenOn) {
|
||||
listenerList.forEach {
|
||||
systemListenerList.forEach {
|
||||
it.onScreenOnChanged(keepScreenOn)
|
||||
}
|
||||
}
|
||||
|
||||
private fun notifyListeners(counterListView: CounterListView) {
|
||||
displayListenerList.forEach {
|
||||
it.onCounterListViewChanged(counterListView)
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -52,6 +52,7 @@ fun Landscape(viewModel: ICounterViewModel) {
|
||||
|
||||
RoundListView(
|
||||
viewModel.roundScoreList,
|
||||
viewModel.sumUpScores,
|
||||
Modifier.weight(1f)
|
||||
)
|
||||
}
|
||||
@@ -83,6 +84,7 @@ fun Portrait(viewModel: ICounterViewModel) {
|
||||
|
||||
RoundListView(
|
||||
viewModel.roundScoreList,
|
||||
viewModel.sumUpScores,
|
||||
Modifier.weight(1f)
|
||||
)
|
||||
|
||||
@@ -109,6 +111,7 @@ internal class PreviewViewModel : ICounterViewModel {
|
||||
override var totalScoreB: Int = 750
|
||||
override var teamNameA: String = "Team A"
|
||||
override var teamNameB: String = "Team B"
|
||||
override val sumUpScores: Boolean = false
|
||||
override var currentScoreA: String = ""
|
||||
override var currentScoreB: String = "45"
|
||||
override var isValidRound: Boolean = false
|
||||
|
||||
@@ -11,9 +11,7 @@ import kotlinx.coroutines.Job
|
||||
import kotlinx.coroutines.delay
|
||||
import kotlinx.coroutines.launch
|
||||
import me.zobrist.tichucounter.data.entity.Round
|
||||
import me.zobrist.tichucounter.domain.Tichu
|
||||
import me.zobrist.tichucounter.domain.digitCount
|
||||
import me.zobrist.tichucounter.domain.getTotalPoints
|
||||
import me.zobrist.tichucounter.domain.*
|
||||
import me.zobrist.tichucounter.repository.GameRepository
|
||||
import javax.inject.Inject
|
||||
|
||||
@@ -53,6 +51,7 @@ interface ICounterViewModel : IKeyBoardViewModel {
|
||||
val roundScoreList: List<Round>
|
||||
val totalScoreA: Int
|
||||
val totalScoreB: Int
|
||||
val sumUpScores: Boolean
|
||||
val teamNameA: String
|
||||
val teamNameB: String
|
||||
val teamNameSuggestionsA: List<String>
|
||||
@@ -64,9 +63,10 @@ interface ICounterViewModel : IKeyBoardViewModel {
|
||||
|
||||
@HiltViewModel
|
||||
class CounterViewModel @Inject constructor(
|
||||
private val gameRepository: GameRepository
|
||||
private val gameRepository: GameRepository,
|
||||
private val settingsAdapter: SettingsAdapter
|
||||
) :
|
||||
ViewModel(), ICounterViewModel {
|
||||
ViewModel(), ICounterViewModel, IDisplaySettingsChangeListener {
|
||||
|
||||
override var roundScoreList by mutableStateOf(emptyList<Round>())
|
||||
private set
|
||||
@@ -80,6 +80,9 @@ class CounterViewModel @Inject constructor(
|
||||
override var teamNameA by mutableStateOf("")
|
||||
private set
|
||||
|
||||
override var sumUpScores by mutableStateOf(false)
|
||||
private set
|
||||
|
||||
override var teamNameB by mutableStateOf("")
|
||||
private set
|
||||
|
||||
@@ -181,6 +184,12 @@ class CounterViewModel @Inject constructor(
|
||||
buildTeamNameSuggestions()
|
||||
}
|
||||
}
|
||||
|
||||
settingsAdapter.registerOnChangeListener(this)
|
||||
}
|
||||
|
||||
override fun onCleared() {
|
||||
settingsAdapter.unregisterOnChangeListener(this)
|
||||
}
|
||||
|
||||
override fun focusLastInput() {
|
||||
@@ -362,4 +371,8 @@ class CounterViewModel @Inject constructor(
|
||||
|
||||
return filtered.sorted().sortedBy { it.length }.take(10)
|
||||
}
|
||||
|
||||
override fun onCounterListViewChanged(listView: CounterListView) {
|
||||
sumUpScores = listView == CounterListView.CONTINUOUS
|
||||
}
|
||||
}
|
||||
@@ -21,13 +21,22 @@ import me.zobrist.tichucounter.data.entity.Round
|
||||
import me.zobrist.tichucounter.ui.AppTheme
|
||||
|
||||
@Composable
|
||||
fun RoundListView(rounds: List<Round>, modifier: Modifier) {
|
||||
fun RoundListView(rounds: List<Round>, sumUpRounds: Boolean = false, modifier: Modifier) {
|
||||
val lazyListState = rememberLazyListState()
|
||||
val scope = rememberCoroutineScope()
|
||||
var sumA = 0
|
||||
var sumB = 0
|
||||
|
||||
LazyColumn(state = lazyListState, modifier = modifier) {
|
||||
itemsIndexed(rounds) { index, item ->
|
||||
RoundListItem(item, index)
|
||||
if (sumUpRounds) {
|
||||
sumA += item.scoreA
|
||||
sumB += item.scoreB
|
||||
RoundListItem(sumA, sumB, index)
|
||||
|
||||
} else {
|
||||
RoundListItem(item.scoreA, item.scoreB, index)
|
||||
}
|
||||
}
|
||||
|
||||
scope.launch {
|
||||
@@ -37,14 +46,14 @@ fun RoundListView(rounds: List<Round>, modifier: Modifier) {
|
||||
}
|
||||
|
||||
@Composable
|
||||
private fun RoundListItem(round: Round, index: Int) {
|
||||
private fun RoundListItem(scoreA: Int, scoreB: Int, index: Int) {
|
||||
Row(
|
||||
modifier = Modifier
|
||||
.fillMaxWidth()
|
||||
.padding(all = 4.dp)
|
||||
) {
|
||||
Text(
|
||||
text = round.scoreA.toString(),
|
||||
text = scoreA.toString(),
|
||||
style = MaterialTheme.typography.bodyMedium,
|
||||
modifier = Modifier.weight(5f),
|
||||
textAlign = TextAlign.Center
|
||||
@@ -56,7 +65,7 @@ private fun RoundListItem(round: Round, index: Int) {
|
||||
textAlign = TextAlign.Center
|
||||
)
|
||||
Text(
|
||||
text = round.scoreB.toString(),
|
||||
text = scoreB.toString(),
|
||||
style = MaterialTheme.typography.bodyMedium,
|
||||
modifier = Modifier.weight(5f),
|
||||
textAlign = TextAlign.Center
|
||||
@@ -78,7 +87,7 @@ fun RoundListViewPreview() {
|
||||
|
||||
AppTheme {
|
||||
Surface {
|
||||
RoundListView(rounds, Modifier)
|
||||
RoundListView(rounds, true, Modifier)
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -25,6 +25,7 @@ import androidx.compose.ui.text.style.TextOverflow
|
||||
import androidx.compose.ui.tooling.preview.Preview
|
||||
import androidx.compose.ui.unit.dp
|
||||
import me.zobrist.tichucounter.R
|
||||
import me.zobrist.tichucounter.domain.CounterListView
|
||||
import me.zobrist.tichucounter.domain.KeepScreenOn
|
||||
import me.zobrist.tichucounter.domain.Language
|
||||
import me.zobrist.tichucounter.domain.Theme
|
||||
@@ -44,6 +45,11 @@ val themeMap = mapOf(
|
||||
Theme.LIGHT to R.string.light
|
||||
)
|
||||
|
||||
val counterListViewMap = mapOf(
|
||||
CounterListView.BY_ROUND to R.string.by_round,
|
||||
CounterListView.CONTINUOUS to R.string.continuous,
|
||||
)
|
||||
|
||||
|
||||
@Composable
|
||||
fun SettingsView(viewModel: SettingsViewModel) {
|
||||
@@ -51,9 +57,11 @@ fun SettingsView(viewModel: SettingsViewModel) {
|
||||
viewModel.screenOn.value,
|
||||
viewModel.language,
|
||||
viewModel.theme,
|
||||
viewModel.counterListView,
|
||||
{ viewModel.updateScreenOn(it) },
|
||||
{ viewModel.updateLanguage(it) },
|
||||
{ viewModel.updateTheme(it) })
|
||||
{ viewModel.updateTheme(it) },
|
||||
{ viewModel.updateCounterListView(it) })
|
||||
}
|
||||
|
||||
@Composable
|
||||
@@ -61,9 +69,11 @@ fun SettingsView(
|
||||
valueScreenOn: Boolean = true,
|
||||
valueLanguage: Language = Language.ENGLISH,
|
||||
valueTheme: Theme = Theme.DARK,
|
||||
valueCounterListView: CounterListView = CounterListView.BY_ROUND,
|
||||
updateScreenOn: (KeepScreenOn) -> Unit = {},
|
||||
updateLanguage: (Language) -> Unit = {},
|
||||
updateTheme: (Theme) -> Unit = {}
|
||||
updateTheme: (Theme) -> Unit = {},
|
||||
updateCounterListView: (CounterListView) -> Unit = {}
|
||||
) {
|
||||
Column {
|
||||
BooleanSetting(
|
||||
@@ -82,6 +92,14 @@ fun SettingsView(
|
||||
themeMap,
|
||||
valueTheme,
|
||||
) { updateTheme(it) }
|
||||
|
||||
StringSetting(
|
||||
stringResource(R.string.counter_mode),
|
||||
counterListViewMap,
|
||||
valueCounterListView,
|
||||
) { updateCounterListView(it) }
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -5,10 +5,7 @@ import androidx.compose.runtime.mutableStateOf
|
||||
import androidx.compose.runtime.setValue
|
||||
import androidx.lifecycle.ViewModel
|
||||
import dagger.hilt.android.lifecycle.HiltViewModel
|
||||
import me.zobrist.tichucounter.domain.KeepScreenOn
|
||||
import me.zobrist.tichucounter.domain.Language
|
||||
import me.zobrist.tichucounter.domain.SettingsAdapter
|
||||
import me.zobrist.tichucounter.domain.Theme
|
||||
import me.zobrist.tichucounter.domain.*
|
||||
import javax.inject.Inject
|
||||
|
||||
@HiltViewModel
|
||||
@@ -24,6 +21,9 @@ class SettingsViewModel @Inject constructor(private val settings: SettingsAdapte
|
||||
var screenOn by mutableStateOf(settings.keepScreenOn)
|
||||
private set
|
||||
|
||||
var counterListView by mutableStateOf(settings.counterListView)
|
||||
private set
|
||||
|
||||
fun updateLanguage(language: Language) {
|
||||
settings.setLanguage(language)
|
||||
this.language = settings.language
|
||||
@@ -39,4 +39,9 @@ class SettingsViewModel @Inject constructor(private val settings: SettingsAdapte
|
||||
screenOn = settings.keepScreenOn
|
||||
}
|
||||
|
||||
fun updateCounterListView(value: CounterListView) {
|
||||
settings.setCounterViewList(value)
|
||||
counterListView = settings.counterListView
|
||||
}
|
||||
|
||||
}
|
||||
@@ -26,6 +26,9 @@
|
||||
<string name="inactive">Old Games</string>
|
||||
<string name="menu_counter">Counter</string>
|
||||
<string name="menu_about">About</string>
|
||||
<string name="by_round">Display Single Round</string>
|
||||
<string name="continuous">Sum up rounds</string>
|
||||
<string name="counter_mode">Counter Mode</string>
|
||||
<string name="contact_us">Contact us</string>
|
||||
<string name="play_store" translatable="false">Play Store</string>
|
||||
</resources>
|
||||
Reference in New Issue
Block a user