nextNoteVault #23

Merged
sebastian merged 57 commits from nextNoteVault into master 2025-05-10 06:23:23 +00:00
4 changed files with 205 additions and 55 deletions
Showing only changes of commit c3029c062e - Show all commits

View File

@ -4,7 +4,7 @@
<selectionStates> <selectionStates>
<SelectionState runConfigName="app"> <SelectionState runConfigName="app">
<option name="selectionMode" value="DROPDOWN" /> <option name="selectionMode" value="DROPDOWN" />
<DropdownSelection timestamp="2025-05-03T07:36:08.121278195Z"> <DropdownSelection timestamp="2025-05-03T08:26:48.052108137Z">
<Target type="DEFAULT_BOOT"> <Target type="DEFAULT_BOOT">
<handle> <handle>
<DeviceId pluginId="LocalEmulator" identifier="path=/home/sebastian/.android/avd/Small_Phone_API_36.avd" /> <DeviceId pluginId="LocalEmulator" identifier="path=/home/sebastian/.android/avd/Small_Phone_API_36.avd" />

View File

@ -7,20 +7,44 @@ import androidx.activity.ComponentActivity
import androidx.activity.compose.rememberLauncherForActivityResult import androidx.activity.compose.rememberLauncherForActivityResult
import androidx.activity.compose.setContent import androidx.activity.compose.setContent
import androidx.activity.result.contract.ActivityResultContracts import androidx.activity.result.contract.ActivityResultContracts
import androidx.compose.foundation.layout.padding
import androidx.compose.material.icons.Icons
import androidx.compose.material.icons.filled.Menu
import androidx.compose.material3.DrawerValue
import androidx.compose.material3.ExperimentalMaterial3Api
import androidx.compose.material3.Icon
import androidx.compose.material3.IconButton
import androidx.compose.material3.MaterialTheme
import androidx.compose.material3.ModalDrawerSheet
import androidx.compose.material3.ModalNavigationDrawer
import androidx.compose.material3.NavigationDrawerItem
import androidx.compose.material3.NavigationDrawerItemDefaults
import androidx.compose.material3.Scaffold
import androidx.compose.material3.Text
import androidx.compose.material3.TopAppBar
import androidx.compose.material3.rememberDrawerState
import androidx.compose.runtime.* import androidx.compose.runtime.*
import androidx.compose.ui.Modifier
import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.platform.LocalContext
import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel import androidx.lifecycle.viewmodel.compose.viewModel
import androidx.navigation.compose.NavHost
import androidx.navigation.compose.composable
import androidx.navigation.compose.rememberNavController
import come.stormborntales.notevault.data.local.AppDatabase import come.stormborntales.notevault.data.local.AppDatabase
import come.stormborntales.notevault.data.local.entity.NoteEntity import come.stormborntales.notevault.data.local.entity.NoteEntity
import come.stormborntales.notevault.data.repository.NoteRepository import come.stormborntales.notevault.data.repository.NoteRepository
import come.stormborntales.notevault.ui.screens.AddNoteDialog import come.stormborntales.notevault.ui.screens.AddNoteDialog
import come.stormborntales.notevault.ui.screens.MainScreen import come.stormborntales.notevault.ui.screens.MainScreen
import come.stormborntales.notevault.ui.screens.SettingsScreen
import come.stormborntales.notevault.ui.theme.NoteVaultTheme import come.stormborntales.notevault.ui.theme.NoteVaultTheme
import come.stormborntales.notevault.ui.viewmodel.NoteViewModel import come.stormborntales.notevault.ui.viewmodel.NoteViewModel
import come.stormborntales.notevault.ui.viewmodel.NoteViewModelFactory import come.stormborntales.notevault.ui.viewmodel.NoteViewModelFactory
import kotlinx.coroutines.launch
class MainActivity : ComponentActivity() { class MainActivity : ComponentActivity() {
@OptIn(ExperimentalMaterial3Api::class)
override fun onCreate(savedInstanceState: Bundle?) { override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState) super.onCreate(savedInstanceState)
val applicationContext = applicationContext val applicationContext = applicationContext
@ -30,12 +54,15 @@ class MainActivity : ComponentActivity() {
setContent { setContent {
NoteVaultTheme { NoteVaultTheme {
val navController = rememberNavController()
val viewModel: NoteViewModel = viewModel(factory = viewModelFactory) val viewModel: NoteViewModel = viewModel(factory = viewModelFactory)
// Bildauswahl + Dialog-States
var selectedUris by remember { mutableStateOf<List<Uri>>(emptyList()) } var selectedUris by remember { mutableStateOf<List<Uri>>(emptyList()) }
var showDialog by remember { mutableStateOf(false) } var showDialog by remember { mutableStateOf(false) }
var noteToEdit by remember { mutableStateOf<NoteEntity?>(null) }
val drawerState = rememberDrawerState(DrawerValue.Closed)
val scope = rememberCoroutineScope()
// Launcher innerhalb von Compose
val imagePickerLauncher = rememberLauncherForActivityResult( val imagePickerLauncher = rememberLauncherForActivityResult(
contract = ActivityResultContracts.OpenMultipleDocuments(), contract = ActivityResultContracts.OpenMultipleDocuments(),
onResult = { uris -> onResult = { uris ->
@ -46,34 +73,79 @@ class MainActivity : ComponentActivity() {
} }
) )
var noteToEdit by remember { mutableStateOf<NoteEntity?>(null) }
// Dialog anzeigen
val openDialog: (NoteEntity?) -> Unit = { note -> val openDialog: (NoteEntity?) -> Unit = { note ->
Log.d("EditNote", "NoteEntity: " + note?.title) Log.d("EditNote", "NoteEntity: ${note?.title}")
noteToEdit = note noteToEdit = note
showDialog = true showDialog = true
} }
// UI anzeigen val navItems = listOf(
"Home" to "main",
"Einstellungen" to "settings"
)
ModalNavigationDrawer(
drawerState = drawerState,
drawerContent = {
ModalDrawerSheet {
Text("Navigation", modifier = Modifier.padding(16.dp), style = MaterialTheme.typography.titleMedium)
navItems.forEach { (label, route) ->
NavigationDrawerItem(
label = { Text(label) },
selected = false,
onClick = {
navController.navigate(route) {
popUpTo(navController.graph.startDestinationId) { saveState = true }
launchSingleTop = true
restoreState = true
}
scope.launch { drawerState.close() }
},
modifier = Modifier.padding(NavigationDrawerItemDefaults.ItemPadding)
)
}
}
}
) {
Scaffold(
topBar = {
TopAppBar(
title = { Text("NoteVault") },
navigationIcon = {
IconButton(onClick = {
scope.launch { drawerState.open() }
}) {
Icon(Icons.Default.Menu, contentDescription = "Menu")
}
}
)
}
) { innerPadding ->
NavHost(
navController = navController,
startDestination = "main",
modifier = Modifier.padding(innerPadding)
) {
composable("main") {
MainScreen( MainScreen(
viewModel = viewModel, viewModel = viewModel,
onAddNoteClicked = { onAddNoteClicked = {
imagePickerLauncher.launch( imagePickerLauncher.launch(arrayOf("image/*"))
arrayOf("image/*")
)
}, },
onEditNote = openDialog onEditNote = openDialog
) )
}
composable("settings") {
SettingsScreen()
}
}
// Dialog bei Bedarf
if (showDialog) { if (showDialog) {
val context = LocalContext.current; val context = LocalContext.current
val scope = rememberCoroutineScope();
AddNoteDialog( AddNoteDialog(
onDismiss = { showDialog = false }, onDismiss = { showDialog = false },
onSave = { title, composer, year, genre, description -> onSave = { title, composer, year, genre, description ->
if(noteToEdit == null) { if (noteToEdit == null) {
viewModel.addNote( viewModel.addNote(
context = context, context = context,
title = title, title = title,
@ -105,5 +177,9 @@ class MainActivity : ComponentActivity() {
} }
} }
} }
}
}
} }
} }

View File

@ -244,11 +244,6 @@ fun MainScreen(
) { ) {
val notes by viewModel.notes.observeAsState(emptyList()) val notes by viewModel.notes.observeAsState(emptyList())
Scaffold( Scaffold(
topBar = {
TopAppBar(
title = { Text("Meine Noten") }
)
},
floatingActionButton = { floatingActionButton = {
FloatingActionButton( FloatingActionButton(
onClick = onAddNoteClicked onClick = onAddNoteClicked

View File

@ -0,0 +1,79 @@
package come.stormborntales.notevault.ui.screens
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.Spacer
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.height
import androidx.compose.foundation.layout.padding
import androidx.compose.material3.Divider
import androidx.compose.material3.MaterialTheme
import androidx.compose.material3.OutlinedButton
import androidx.compose.material3.Switch
import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.unit.dp
@Composable
fun SettingsScreen() {
Column(
modifier = Modifier
.fillMaxSize()
.padding(16.dp)
) {
Text(
text = "Einstellungen",
style = MaterialTheme.typography.headlineMedium,
modifier = Modifier.padding(bottom = 16.dp)
)
Divider()
Spacer(modifier = Modifier.height(16.dp))
// Beispielhafte Einstellung
Row(
verticalAlignment = Alignment.CenterVertically,
modifier = Modifier.fillMaxWidth()
) {
Text(
text = "Dark Mode",
modifier = Modifier.weight(1f),
style = MaterialTheme.typography.bodyLarge
)
Switch(
checked = false,
onCheckedChange = { /* TODO: Dark Mode aktivieren */ }
)
}
Spacer(modifier = Modifier.height(16.dp))
Row(
verticalAlignment = Alignment.CenterVertically,
modifier = Modifier.fillMaxWidth()
) {
Text(
text = "Benachrichtigungen",
modifier = Modifier.weight(1f),
style = MaterialTheme.typography.bodyLarge
)
Switch(
checked = true,
onCheckedChange = { /* TODO: Benachrichtigungseinstellungen */ }
)
}
Spacer(modifier = Modifier.height(32.dp))
OutlinedButton(
onClick = { /* TODO: Impressum anzeigen */ },
modifier = Modifier.fillMaxWidth()
) {
Text("Impressum")
}
}
}