111 lines
4.0 KiB
Kotlin
111 lines
4.0 KiB
Kotlin
package com.atridad.magiccounter.ui
|
|
|
|
import android.os.Build
|
|
import androidx.annotation.RequiresApi
|
|
import androidx.compose.foundation.layout.Arrangement
|
|
import androidx.compose.foundation.layout.Column
|
|
import androidx.compose.foundation.layout.Row
|
|
import androidx.compose.foundation.layout.fillMaxSize
|
|
import androidx.compose.foundation.layout.padding
|
|
import androidx.compose.material.icons.Icons
|
|
import androidx.compose.material.icons.filled.Settings
|
|
import androidx.compose.material.icons.filled.Refresh
|
|
import androidx.compose.material3.Icon
|
|
import androidx.compose.material3.IconButton
|
|
import androidx.compose.material3.MaterialTheme
|
|
import androidx.compose.material3.Scaffold
|
|
import androidx.compose.material3.Text
|
|
import androidx.compose.material3.TopAppBar
|
|
import androidx.compose.material3.ExperimentalMaterial3Api
|
|
import androidx.compose.runtime.Composable
|
|
import androidx.compose.runtime.collectAsState
|
|
import androidx.compose.runtime.getValue
|
|
import androidx.compose.runtime.mutableStateOf
|
|
import androidx.compose.runtime.remember
|
|
import androidx.compose.runtime.setValue
|
|
import androidx.compose.ui.Modifier
|
|
import androidx.compose.ui.unit.dp
|
|
import com.atridad.magiccounter.ui.screens.GameScreen
|
|
import com.atridad.magiccounter.ui.screens.SetupScreen
|
|
import com.atridad.magiccounter.ui.state.GameState
|
|
import androidx.lifecycle.viewmodel.compose.viewModel
|
|
import com.atridad.magiccounter.ui.settings.AppSettingsViewModel
|
|
import com.atridad.magiccounter.ui.settings.ThemeMode
|
|
import com.atridad.magiccounter.ui.theme.MagicCounterTheme
|
|
import androidx.compose.material3.ModalBottomSheet
|
|
import androidx.compose.material3.FilterChip
|
|
// no-op
|
|
|
|
@RequiresApi(Build.VERSION_CODES.VANILLA_ICE_CREAM)
|
|
@OptIn(ExperimentalMaterial3Api::class)
|
|
@Composable
|
|
fun MagicCounterApp() {
|
|
var gameState by remember { mutableStateOf<GameState?>(null) }
|
|
var showSettings by remember { mutableStateOf(false) }
|
|
val settingsVm: AppSettingsViewModel = viewModel()
|
|
val theme = settingsVm.themeMode.collectAsState()
|
|
|
|
MagicCounterTheme(themeMode = theme.value) {
|
|
Scaffold(
|
|
topBar = {
|
|
TopAppBar(
|
|
title = { Text("Magic Counter", style = MaterialTheme.typography.titleLarge) },
|
|
actions = {
|
|
if (gameState != null) {
|
|
IconButton(onClick = { gameState = null }) {
|
|
Icon(Icons.Default.Refresh, contentDescription = "New game")
|
|
}
|
|
}
|
|
IconButton(onClick = { showSettings = true }) {
|
|
Icon(Icons.Default.Settings, contentDescription = "App settings")
|
|
}
|
|
}
|
|
)
|
|
}
|
|
) { paddingValues ->
|
|
if (gameState == null) {
|
|
SetupScreen(
|
|
modifier = Modifier
|
|
.padding(paddingValues)
|
|
.fillMaxSize(),
|
|
onStart = { state -> gameState = state }
|
|
)
|
|
} else {
|
|
GameScreen(
|
|
modifier = Modifier
|
|
.padding(paddingValues)
|
|
.fillMaxSize(),
|
|
state = gameState!!,
|
|
onEnd = { gameState = null }
|
|
)
|
|
}
|
|
if (showSettings) {
|
|
ModalBottomSheet(onDismissRequest = { showSettings = false }) {
|
|
SettingsSheet(
|
|
current = theme.value,
|
|
onSelect = { settingsVm.setTheme(it) }
|
|
)
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
@Composable
|
|
private fun SettingsSheet(current: ThemeMode, onSelect: (ThemeMode) -> Unit) {
|
|
Column(modifier = Modifier.fillMaxSize().padding(16.dp), verticalArrangement = Arrangement.spacedBy(12.dp)) {
|
|
Text("Theme")
|
|
Row(horizontalArrangement = Arrangement.spacedBy(8.dp)) {
|
|
ThemeMode.values().forEach { mode ->
|
|
FilterChip(
|
|
selected = current == mode,
|
|
onClick = { onSelect(mode) },
|
|
label = { Text(mode.name) }
|
|
)
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
|