Implements basic navigation

This commit is contained in:
Dennis Schoepf 2025-04-07 00:13:23 +02:00
parent d6c93f262b
commit c45d852aa0
10 changed files with 237 additions and 39 deletions

View file

@ -0,0 +1,50 @@
<component name="InspectionProjectProfileManager">
<profile version="1.0">
<option name="myName" value="Project Default" />
<inspection_tool class="ComposePreviewDimensionRespectsLimit" enabled="true" level="WARNING" enabled_by_default="true">
<option name="composableFile" value="true" />
</inspection_tool>
<inspection_tool class="ComposePreviewMustBeTopLevelFunction" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
</inspection_tool>
<inspection_tool class="ComposePreviewNeedsComposableAnnotation" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
</inspection_tool>
<inspection_tool class="ComposePreviewNotSupportedInUnitTestFiles" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
</inspection_tool>
<inspection_tool class="GlancePreviewDimensionRespectsLimit" enabled="true" level="WARNING" enabled_by_default="true">
<option name="composableFile" value="true" />
</inspection_tool>
<inspection_tool class="GlancePreviewMustBeTopLevelFunction" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
</inspection_tool>
<inspection_tool class="GlancePreviewNeedsComposableAnnotation" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
</inspection_tool>
<inspection_tool class="GlancePreviewNotSupportedInUnitTestFiles" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
</inspection_tool>
<inspection_tool class="PreviewAnnotationInFunctionWithParameters" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
</inspection_tool>
<inspection_tool class="PreviewApiLevelMustBeValid" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
</inspection_tool>
<inspection_tool class="PreviewDeviceShouldUseNewSpec" enabled="true" level="WEAK WARNING" enabled_by_default="true">
<option name="composableFile" value="true" />
</inspection_tool>
<inspection_tool class="PreviewFontScaleMustBeGreaterThanZero" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
</inspection_tool>
<inspection_tool class="PreviewMultipleParameterProviders" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
</inspection_tool>
<inspection_tool class="PreviewParameterProviderOnFirstParameter" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
</inspection_tool>
<inspection_tool class="PreviewPickerAnnotation" enabled="true" level="ERROR" enabled_by_default="true">
<option name="composableFile" value="true" />
</inspection_tool>
</profile>
</component>

View file

@ -1,24 +1,44 @@
package com.dnsc.plaindo package com.dnsc.plaindo
import android.util.Log
import androidx.compose.material.icons.Icons
import androidx.compose.material.icons.outlined.DateRange
import androidx.compose.material.icons.outlined.Home
import androidx.compose.material3.Scaffold
import androidx.compose.runtime.Composable import androidx.compose.runtime.Composable
import androidx.navigation.compose.NavHost import androidx.navigation.compose.NavHost
import androidx.navigation.compose.composable import androidx.navigation.compose.composable
import androidx.navigation.compose.rememberNavController import androidx.navigation.compose.rememberNavController
import com.dnsc.plaindo.ui.overview.PlaindoOverview import com.dnsc.plaindo.ui.agenda.PlaindoAgendaScreen
import com.dnsc.plaindo.ui.components.BottomNavigation
import com.dnsc.plaindo.ui.components.TopBar
import com.dnsc.plaindo.ui.overview.PlaindoOverviewScreen import com.dnsc.plaindo.ui.overview.PlaindoOverviewScreen
import com.dnsc.plaindo.ui.settings.PlaindoSettings
import com.dnsc.plaindo.ui.settings.PlaindoSettingsScreen import com.dnsc.plaindo.ui.settings.PlaindoSettingsScreen
@Composable @Composable
fun PlaindoApp() { fun PlaindoApp() {
val topLevelRoutes = listOf(
TopLevelRoute("Home", "overview", Icons.Outlined.Home),
TopLevelRoute("Agenda", "agenda", Icons.Outlined.DateRange),
)
val navController = rememberNavController() val navController = rememberNavController()
NavHost(navController, startDestination = PlaindoOverview) { Scaffold(
composable<PlaindoOverview> { topBar = {
PlaindoOverviewScreen() TopBar("Plaindo", navController)
} },
composable<PlaindoSettings> { bottomBar = { BottomNavigation(navController, topLevelRoutes) }
PlaindoSettingsScreen() ) { innerPadding ->
NavHost(navController, startDestination = "overview") {
composable("overview") {
PlaindoOverviewScreen(navController, innerPadding)
}
composable("agenda") {
PlaindoAgendaScreen(innerPadding)
}
composable("settings") {
PlaindoSettingsScreen(innerPadding)
}
} }
} }
} }

View file

@ -0,0 +1,6 @@
package com.dnsc.plaindo
import androidx.compose.ui.graphics.vector.ImageVector
data class TopLevelRoute(val name: String, val route: String, val icon: ImageVector)

View file

@ -0,0 +1,6 @@
package com.dnsc.plaindo.ui.agenda
import kotlinx.serialization.Serializable
@Serializable
object PlaindoAgenda

View file

@ -0,0 +1,15 @@
package com.dnsc.plaindo.ui.agenda
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.PaddingValues
import androidx.compose.foundation.layout.padding
import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier
@Composable
fun PlaindoAgendaScreen(innerPadding: PaddingValues) {
Column(modifier = Modifier.padding(innerPadding)) {
Text(text = "Agenda")
}
}

View file

@ -0,0 +1,42 @@
package com.dnsc.plaindo.ui.components
import android.util.Log
import androidx.compose.material.icons.Icons
import androidx.compose.material.icons.outlined.DateRange
import androidx.compose.material.icons.outlined.Home
import androidx.compose.material.icons.outlined.List
import androidx.compose.material3.Icon
import androidx.compose.material3.NavigationBar
import androidx.compose.material3.NavigationBarItem
import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.navigation.NavDestination.Companion.hierarchy
import androidx.navigation.NavGraph.Companion.findStartDestination
import androidx.navigation.NavHostController
import androidx.navigation.compose.currentBackStackEntryAsState
import com.dnsc.plaindo.TopLevelRoute
@Composable
fun BottomNavigation(navController: NavHostController, topLevelRoutes: List<TopLevelRoute>) {
NavigationBar {
val navBackStackEntry = navController.currentBackStackEntryAsState().value
val currentDestination = navBackStackEntry?.destination
topLevelRoutes.forEach { topLevelRoute ->
NavigationBarItem(
icon = { Icon(topLevelRoute.icon, contentDescription = topLevelRoute.name) },
label = { Text(topLevelRoute.name) },
selected = currentDestination?.hierarchy?.any { it.route == topLevelRoute.route } == true,
onClick = {
navController.navigate(topLevelRoute.route) {
popUpTo(navController.graph.findStartDestination().id) {
saveState = true
}
launchSingleTop = true
restoreState = true
}
}
)
}
}
}

View file

@ -1,23 +1,30 @@
package com.dnsc.plaindo.ui.shared package com.dnsc.plaindo.ui.components
import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.padding
import androidx.compose.material3.ExperimentalMaterial3Api import androidx.compose.material3.ExperimentalMaterial3Api
import androidx.compose.material3.Text import androidx.compose.material3.Text
import androidx.compose.material3.TopAppBar import androidx.compose.material3.TopAppBar
import androidx.compose.runtime.Composable import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier import androidx.compose.ui.Modifier
import androidx.compose.ui.text.style.TextAlign import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.unit.dp
import androidx.navigation.NavController
import androidx.navigation.NavHostController
@OptIn(ExperimentalMaterial3Api::class) @OptIn(ExperimentalMaterial3Api::class)
@Composable @Composable
fun TopBar(title: String) { fun TopBar(title: String, navController: NavHostController) {
TopAppBar( TopAppBar(
title = { title = {
Text( Text(
text = title, text = title,
modifier = Modifier.fillMaxWidth(), modifier = Modifier.fillMaxWidth().padding(start = 12.dp),
textAlign = TextAlign.Left textAlign = TextAlign.Left
) )
},
actions = {
TopBarMenu(navController)
} }
) )
} }

View file

@ -0,0 +1,68 @@
package com.dnsc.plaindo.ui.components
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.padding
import androidx.compose.material.icons.Icons
import androidx.compose.material.icons.filled.MoreVert
import androidx.compose.material.icons.outlined.Menu
import androidx.compose.material.icons.outlined.Search
import androidx.compose.material.icons.outlined.Settings
import androidx.compose.material3.DropdownMenu
import androidx.compose.material3.DropdownMenuItem
import androidx.compose.material3.Icon
import androidx.compose.material3.IconButton
import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
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 androidx.compose.ui.unit.sp
import androidx.navigation.NavController
import androidx.navigation.NavGraph.Companion.findStartDestination
import androidx.navigation.NavHostController
@Composable
fun TopBarMenu(navController: NavHostController) {
var expanded by remember { mutableStateOf(false) }
Box(
modifier = Modifier
.padding(16.dp)
) {
IconButton(onClick = { expanded = !expanded }) {
Icon(Icons.Default.MoreVert, contentDescription = "More options")
}
DropdownMenu(
expanded = expanded,
onDismissRequest = { expanded = false }
) {
DropdownMenuItem(
leadingIcon = { Icon(Icons.Outlined.Menu, contentDescription = "Filter", modifier = Modifier.padding(start = 12.dp)) },
text = { Text("Filter", fontSize = 16.sp, modifier = Modifier.padding(end = 16.dp)) },
onClick = { /* Do something... */ }
)
DropdownMenuItem(
leadingIcon = { Icon(Icons.Outlined.Search, contentDescription = "Search", modifier = Modifier.padding(start = 12.dp)) },
text = { Text("Search", fontSize = 16.sp, modifier = Modifier.padding(end = 16.dp)) },
onClick = { /* Do something... */ }
)
DropdownMenuItem(
leadingIcon = { Icon(Icons.Outlined.Settings, contentDescription = "Settings", modifier = Modifier.padding(start = 12.dp)) },
text = { Text("Settings", fontSize = 16.sp, modifier = Modifier.padding(end = 16.dp)) },
onClick = {
navController.navigate("settings") {
popUpTo(navController.graph.findStartDestination().id) {
saveState = true
}
launchSingleTop = true
restoreState = true
}
expanded = false
}
)
}
}
}

View file

@ -1,24 +1,17 @@
package com.dnsc.plaindo.ui.overview package com.dnsc.plaindo.ui.overview
import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.PaddingValues
import androidx.compose.foundation.layout.padding import androidx.compose.foundation.layout.padding
import androidx.compose.material3.Scaffold
import androidx.compose.material3.Text import androidx.compose.material3.Text
import androidx.compose.runtime.Composable import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier import androidx.compose.ui.Modifier
import com.dnsc.plaindo.ui.shared.TopBar import androidx.navigation.NavHostController
import com.dnsc.plaindo.ui.components.TopBar
@Composable @Composable
fun PlaindoOverviewScreen() { fun PlaindoOverviewScreen(navController: NavHostController, innerPadding: PaddingValues) {
Scaffold( Column(modifier = Modifier.padding(innerPadding)) {
topBar = { Text(text = "Overview")
TopBar(title = "Overview")
}
) { innerPadding ->
Column(
modifier = Modifier.padding(innerPadding)
) {
Text(text = "Overview")
}
} }
} }

View file

@ -1,24 +1,15 @@
package com.dnsc.plaindo.ui.settings package com.dnsc.plaindo.ui.settings
import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.PaddingValues
import androidx.compose.foundation.layout.padding import androidx.compose.foundation.layout.padding
import androidx.compose.material3.Scaffold
import androidx.compose.material3.Text import androidx.compose.material3.Text
import androidx.compose.runtime.Composable import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier import androidx.compose.ui.Modifier
import com.dnsc.plaindo.ui.shared.TopBar
@Composable @Composable
fun PlaindoSettingsScreen() { fun PlaindoSettingsScreen(innerPadding: PaddingValues) {
Scaffold( Column(modifier = Modifier.padding(innerPadding)) {
topBar = { Text(text = "Settings")
TopBar(title = "Settings")
}
) { innerPadding ->
Column(
modifier = Modifier.padding(innerPadding)
) {
Text(text = "Settings")
}
} }
} }