From 160610e09c3b7c63ce7c7518df3abb06efe8d400 Mon Sep 17 00:00:00 2001 From: Azea Date: Sat, 21 Oct 2023 16:31:12 -0400 Subject: [PATCH 01/20] Home screen update --- app/build.gradle | 2 + .../com/menagerie/ophelia/MainActivity.kt | 7 +- .../polycule/PolyculeDatabaseManager.kt | 2 + .../database/polycule/PolyculeRepository.kt | 2 + .../com/menagerie/ophelia/ui/theme/Color.kt | 68 ++++++++- .../com/menagerie/ophelia/ui/theme/Theme.kt | 86 +++++++++--- .../com/menagerie/ophelia/ui/theme/Type.kt | 11 +- .../com/menagerie/ophelia/view/HomeScreen.kt | 131 +++++++++--------- .../com/menagerie/ophelia/view/PolyculeApp.kt | 66 +++++---- .../ophelia/view/biographies/BioCard.kt | 8 +- .../ophelia/view/polycule/PolyculeHomeView.kt | 93 +++++++++++++ app/src/main/res/values/strings.xml | 10 ++ 12 files changed, 363 insertions(+), 123 deletions(-) create mode 100644 app/src/main/java/com/menagerie/ophelia/view/polycule/PolyculeHomeView.kt diff --git a/app/build.gradle b/app/build.gradle index 9fd3fbf..95fc2fb 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -56,6 +56,8 @@ dependencies { def nav_version = "2.7.4" //Fragment def fragment_version = "1.6.1" + + implementation 'androidx.appcompat:appcompat:1.6.1' implementation "androidx.activity:activity-ktx:$activity_version" implementation 'androidx.core:core-ktx:1.9.0' implementation 'androidx.lifecycle:lifecycle-runtime-ktx:2.6.2' diff --git a/app/src/main/java/com/menagerie/ophelia/MainActivity.kt b/app/src/main/java/com/menagerie/ophelia/MainActivity.kt index 0eb5196..3549945 100644 --- a/app/src/main/java/com/menagerie/ophelia/MainActivity.kt +++ b/app/src/main/java/com/menagerie/ophelia/MainActivity.kt @@ -1,8 +1,10 @@ package com.menagerie.ophelia import android.os.Bundle +import android.view.Window import androidx.activity.ComponentActivity import androidx.activity.compose.setContent +import androidx.compose.material3.Surface import com.menagerie.ophelia.database.polycule.PolyculeApplication import com.menagerie.ophelia.database.polycule.PolyculeDatabaseManager import com.menagerie.ophelia.ui.theme.OpheliaTheme @@ -11,11 +13,14 @@ import com.menagerie.ophelia.view.PolyculeApp class MainActivity : ComponentActivity() { override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) + this.requestWindowFeature(Window.FEATURE_NO_TITLE); setContent { OpheliaTheme { val repository = (application as PolyculeApplication).repository PolyculeDatabaseManager.polyculeRepository = repository - PolyculeApp() + Surface { + PolyculeApp() + } } } } diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeDatabaseManager.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeDatabaseManager.kt index a119475..7e79955 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeDatabaseManager.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeDatabaseManager.kt @@ -8,4 +8,6 @@ object PolyculeDatabaseManager { suspend fun post(bio: Bio) { polyculeRepository.upsertBio(bio) } + + fun hasPolycule() = polyculeRepository.hasPolycule() } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt index bee114f..00cde6d 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt @@ -31,4 +31,6 @@ class PolyculeRepository( bioDao.delete(bio) } + fun hasPolycule() = false + } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/ui/theme/Color.kt b/app/src/main/java/com/menagerie/ophelia/ui/theme/Color.kt index ee64671..8f4024a 100644 --- a/app/src/main/java/com/menagerie/ophelia/ui/theme/Color.kt +++ b/app/src/main/java/com/menagerie/ophelia/ui/theme/Color.kt @@ -1,11 +1,65 @@ package com.menagerie.ophelia.ui.theme - import androidx.compose.ui.graphics.Color -val Purple80 = Color(0xFFFF00FF) -val PurpleGrey80 = Color(0xFFCCC2DC) -val Pink80 = Color(0xFFEFB8C8) +val md_theme_light_primary = Color(0xFF366A21) +val md_theme_light_onPrimary = Color(0xFFFFFFFF) +val md_theme_light_primaryContainer = Color(0xFFB6F398) +val md_theme_light_onPrimaryContainer = Color(0xFF052100) +val md_theme_light_secondary = Color(0xFF55624C) +val md_theme_light_onSecondary = Color(0xFFFFFFFF) +val md_theme_light_secondaryContainer = Color(0xFFD8E7CB) +val md_theme_light_onSecondaryContainer = Color(0xFF131F0D) +val md_theme_light_tertiary = Color(0xFF386667) +val md_theme_light_onTertiary = Color(0xFFFFFFFF) +val md_theme_light_tertiaryContainer = Color(0xFFBBEBEC) +val md_theme_light_onTertiaryContainer = Color(0xFF002021) +val md_theme_light_error = Color(0xFFBA1A1A) +val md_theme_light_errorContainer = Color(0xFFFFDAD6) +val md_theme_light_onError = Color(0xFFFFFFFF) +val md_theme_light_onErrorContainer = Color(0xFF410002) +val md_theme_light_background = Color(0xFFFDFDF6) +val md_theme_light_onBackground = Color(0xFF1A1C18) +val md_theme_light_outline = Color(0xFF73796E) +val md_theme_light_inverseOnSurface = Color(0xFFF1F1EA) +val md_theme_light_inverseSurface = Color(0xFF2F312D) +val md_theme_light_inversePrimary = Color(0xFF9BD67F) +val md_theme_light_surfaceTint = Color(0xFF366A21) +val md_theme_light_outlineVariant = Color(0xFFC3C8BB) +val md_theme_light_scrim = Color(0xFF000000) +val md_theme_light_surface = Color(0xFFFAFAF3) +val md_theme_light_onSurface = Color(0xFF1A1C18) +val md_theme_light_surfaceVariant = Color(0xFFDFE4D7) +val md_theme_light_onSurfaceVariant = Color(0xFF43483F) -val Purple40 = Color(0x0000FF22) -val PurpleGrey40 = Color(0xFF625b71) -val Pink40 = Color(0xFF7D5260) \ No newline at end of file +val md_theme_dark_primary = Color(0xFF9BD67F) +val md_theme_dark_onPrimary = Color(0xFF0E3900) +val md_theme_dark_primaryContainer = Color(0xFF1E5108) +val md_theme_dark_onPrimaryContainer = Color(0xFFB6F398) +val md_theme_dark_secondary = Color(0xFFBCCBB0) +val md_theme_dark_onSecondary = Color(0xFF273421) +val md_theme_dark_secondaryContainer = Color(0xFF3D4B36) +val md_theme_dark_onSecondaryContainer = Color(0xFFD8E7CB) +val md_theme_dark_tertiary = Color(0xFFA0CFD0) +val md_theme_dark_onTertiary = Color(0xFF003738) +val md_theme_dark_tertiaryContainer = Color(0xFF1E4E4F) +val md_theme_dark_onTertiaryContainer = Color(0xFFBBEBEC) +val md_theme_dark_error = Color(0xFFFFB4AB) +val md_theme_dark_errorContainer = Color(0xFF93000A) +val md_theme_dark_onError = Color(0xFF690005) +val md_theme_dark_onErrorContainer = Color(0xFFFFDAD6) +val md_theme_dark_background = Color(0xFF1A1C18) +val md_theme_dark_onBackground = Color(0xFFE3E3DC) +val md_theme_dark_outline = Color(0xFF8D9287) +val md_theme_dark_inverseOnSurface = Color(0xFF1A1C18) +val md_theme_dark_inverseSurface = Color(0xFFE3E3DC) +val md_theme_dark_inversePrimary = Color(0xFF366A21) +val md_theme_dark_surfaceTint = Color(0xFF9BD67F) +val md_theme_dark_outlineVariant = Color(0xFF43483F) +val md_theme_dark_scrim = Color(0xFF000000) +val md_theme_dark_surface = Color(0xFF121410) +val md_theme_dark_onSurface = Color(0xFFC6C7C0) +val md_theme_dark_surfaceVariant = Color(0xFF43483F) +val md_theme_dark_onSurfaceVariant = Color(0xFFC3C8BB) + + +val seed = Color(0xFF5E9546) \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/ui/theme/Theme.kt b/app/src/main/java/com/menagerie/ophelia/ui/theme/Theme.kt index c1fa312..a27b901 100644 --- a/app/src/main/java/com/menagerie/ophelia/ui/theme/Theme.kt +++ b/app/src/main/java/com/menagerie/ophelia/ui/theme/Theme.kt @@ -1,44 +1,93 @@ package com.menagerie.ophelia.ui.theme import android.app.Activity -import android.os.Build import androidx.compose.foundation.isSystemInDarkTheme import androidx.compose.material3.MaterialTheme import androidx.compose.material3.darkColorScheme -import androidx.compose.material3.dynamicDarkColorScheme -import androidx.compose.material3.dynamicLightColorScheme import androidx.compose.material3.lightColorScheme import androidx.compose.runtime.Composable import androidx.compose.runtime.SideEffect import androidx.compose.ui.graphics.toArgb -import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.platform.LocalView import androidx.core.view.WindowCompat -private val DarkColorScheme = darkColorScheme( - primary = Purple80, - secondary = PurpleGrey80, - tertiary = Pink80 -) private val LightColorScheme = lightColorScheme( - primary = Purple40, - secondary = PurpleGrey40, - tertiary = Pink40 + primary = md_theme_light_primary, + onPrimary = md_theme_light_onPrimary, + primaryContainer = md_theme_light_primaryContainer, + onPrimaryContainer = md_theme_light_onPrimaryContainer, + secondary = md_theme_light_secondary, + onSecondary = md_theme_light_onSecondary, + secondaryContainer = md_theme_light_secondaryContainer, + onSecondaryContainer = md_theme_light_onSecondaryContainer, + tertiary = md_theme_light_tertiary, + onTertiary = md_theme_light_onTertiary, + tertiaryContainer = md_theme_light_tertiaryContainer, + onTertiaryContainer = md_theme_light_onTertiaryContainer, + error = md_theme_light_error, + errorContainer = md_theme_light_errorContainer, + onError = md_theme_light_onError, + onErrorContainer = md_theme_light_onErrorContainer, + background = md_theme_light_background, + onBackground = md_theme_light_onBackground, + outline = md_theme_light_outline, + inverseOnSurface = md_theme_light_inverseOnSurface, + inverseSurface = md_theme_light_inverseSurface, + inversePrimary = md_theme_light_inversePrimary, + surfaceTint = md_theme_light_surfaceTint, + outlineVariant = md_theme_light_outlineVariant, + scrim = md_theme_light_scrim, + surface = md_theme_light_surface, + onSurface = md_theme_light_onSurface, + surfaceVariant = md_theme_light_surfaceVariant, + onSurfaceVariant = md_theme_light_onSurfaceVariant, +) + + +private val DarkColorScheme = darkColorScheme( + primary = md_theme_dark_primary, + onPrimary = md_theme_dark_onPrimary, + primaryContainer = md_theme_dark_primaryContainer, + onPrimaryContainer = md_theme_dark_onPrimaryContainer, + secondary = md_theme_dark_secondary, + onSecondary = md_theme_dark_onSecondary, + secondaryContainer = md_theme_dark_secondaryContainer, + onSecondaryContainer = md_theme_dark_onSecondaryContainer, + tertiary = md_theme_dark_tertiary, + onTertiary = md_theme_dark_onTertiary, + tertiaryContainer = md_theme_dark_tertiaryContainer, + onTertiaryContainer = md_theme_dark_onTertiaryContainer, + error = md_theme_dark_error, + errorContainer = md_theme_dark_errorContainer, + onError = md_theme_dark_onError, + onErrorContainer = md_theme_dark_onErrorContainer, + background = md_theme_dark_background, + onBackground = md_theme_dark_onBackground, + outline = md_theme_dark_outline, + inverseOnSurface = md_theme_dark_inverseOnSurface, + inverseSurface = md_theme_dark_inverseSurface, + inversePrimary = md_theme_dark_inversePrimary, + surfaceTint = md_theme_dark_surfaceTint, + outlineVariant = md_theme_dark_outlineVariant, + scrim = md_theme_dark_scrim, + surface = md_theme_dark_surface, + onSurface = md_theme_dark_onSurface, + surfaceVariant = md_theme_dark_surfaceVariant, + onSurfaceVariant = md_theme_dark_onSurfaceVariant, ) @Composable fun OpheliaTheme( darkTheme: Boolean = isSystemInDarkTheme(), // Dynamic color is available on Android 12+ - dynamicColor: Boolean = true, - content: @Composable () -> Unit + content: @Composable() () -> Unit ) { val colorScheme = when { - dynamicColor && Build.VERSION.SDK_INT >= Build.VERSION_CODES.S -> { - val context = LocalContext.current - if (darkTheme) dynamicDarkColorScheme(context) else dynamicLightColorScheme(context) - } +// dynamicColor && Build.VERSION.SDK_INT >= Build.VERSION_CODES.S -> { +// val context = LocalContext.current +// if (darkTheme) dynamicDarkColorScheme(context) else dynamicLightColorScheme(context) +// } darkTheme -> DarkColorScheme else -> LightColorScheme @@ -47,6 +96,7 @@ fun OpheliaTheme( if (!view.isInEditMode) { SideEffect { val window = (view.context as Activity).window + window.statusBarColor = colorScheme.primary.toArgb() WindowCompat.getInsetsController(window, view).isAppearanceLightStatusBars = darkTheme } } diff --git a/app/src/main/java/com/menagerie/ophelia/ui/theme/Type.kt b/app/src/main/java/com/menagerie/ophelia/ui/theme/Type.kt index 4be722c..fe80251 100644 --- a/app/src/main/java/com/menagerie/ophelia/ui/theme/Type.kt +++ b/app/src/main/java/com/menagerie/ophelia/ui/theme/Type.kt @@ -4,6 +4,7 @@ import androidx.compose.material3.Typography import androidx.compose.ui.text.TextStyle import androidx.compose.ui.text.font.FontFamily import androidx.compose.ui.text.font.FontWeight +import androidx.compose.ui.text.style.TextDecoration import androidx.compose.ui.unit.sp // Set of Material typography styles to start with @@ -14,7 +15,15 @@ val Typography = Typography( fontSize = 16.sp, lineHeight = 24.sp, letterSpacing = 0.5.sp - ) + ), + displayLarge = TextStyle( + fontFamily = FontFamily.Cursive, + fontWeight = FontWeight.Bold, + fontSize = 64.sp, + lineHeight = 24.sp, + letterSpacing = 0.5.sp, + textDecoration = TextDecoration.Underline + ), /* Other default text styles to override titleLarge = TextStyle( fontFamily = FontFamily.Default, diff --git a/app/src/main/java/com/menagerie/ophelia/view/HomeScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/HomeScreen.kt index 3d73f8b..5650b65 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/HomeScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/HomeScreen.kt @@ -1,97 +1,90 @@ package com.menagerie.ophelia.view +import android.content.res.Configuration import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Box 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.padding -import androidx.compose.foundation.layout.statusBarsPadding -import androidx.compose.material.icons.Icons -import androidx.compose.material.icons.filled.Add -import androidx.compose.material3.ExperimentalMaterial3Api -import androidx.compose.material3.FloatingActionButton -import androidx.compose.material3.Icon +import androidx.compose.material3.Button import androidx.compose.material3.MaterialTheme -import androidx.compose.material3.Scaffold +import androidx.compose.material3.Surface import androidx.compose.material3.Text -import androidx.compose.material3.TopAppBar -import androidx.compose.material3.TopAppBarDefaults -import androidx.compose.material3.TopAppBarScrollBehavior import androidx.compose.runtime.Composable -import androidx.compose.runtime.livedata.observeAsState +import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.res.stringResource -import androidx.lifecycle.viewmodel.compose.viewModel +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.dp import com.menagerie.ophelia.R -import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioListViewModel -import com.menagerie.ophelia.database.polycule.entity.Bio -import com.menagerie.ophelia.view.biographies.BioCardList +import com.menagerie.ophelia.ui.theme.OpheliaTheme -@OptIn(ExperimentalMaterial3Api::class) @Composable fun HomeScreen( - modifier: Modifier = Modifier, - onBioClick: (Bio) -> Unit = {}, - onAddClick: () -> Unit, + newUser: Boolean, + onClick: () -> Unit, + ) { - val scrollBehavior = TopAppBarDefaults.enterAlwaysScrollBehavior() - Scaffold( - modifier = modifier, - bottomBar = { - HomeTopAppBar( - onFilterClick = { }, - scrollBehavior = scrollBehavior - ) - } - ) { - HomeBioScreen( - onBioClick = onBioClick, - onAddClick = onAddClick, - modifier = modifier.padding(it) - ) - } + val text = if(newUser) R.string.welcome else R.string.welcome_back + HeaderText(text, onClick) } @Composable -fun HomeBioScreen( - onBioClick: (Bio) -> Unit, - onAddClick: () -> Unit = {}, - modifier: Modifier, +fun HeaderText( + text: Int, + onClick: () -> Unit ) { - val mBioListViewModel: BioListViewModel = viewModel( - factory = BioListViewModel.BioListViewModelFactory() - ) - val items = mBioListViewModel.allBios.observeAsState(listOf()).value - - Column( - modifier = modifier + Box( + modifier = Modifier + .fillMaxSize() ) { - BioCardList(bioList = items, onBioClick = onBioClick) - FloatingActionButton( - onClick = onAddClick + Column( + modifier = Modifier + .fillMaxWidth() + .padding(top = 10.dp) + .align(Alignment.Center), + horizontalAlignment = Alignment.CenterHorizontally, + verticalArrangement = Arrangement.Center, ) { - Icon(Icons.Filled.Add, "Add Bio") + Spacer(modifier = Modifier.weight(1f)) + Text( + text = stringResource(id = R.string.app_name), + style = MaterialTheme.typography.displayLarge + ) + Text( + text = stringResource(id = R.string.app_tag) + ) + Spacer(modifier = Modifier.weight(1f)) + Button( + modifier = Modifier.padding(12.dp), + onClick = onClick + ) { + Text(text = stringResource(id = text)) + } } } } -@OptIn(ExperimentalMaterial3Api::class) + +@Preview(showBackground = true, + uiMode = Configuration.UI_MODE_NIGHT_NO or Configuration.UI_MODE_TYPE_NORMAL, ) @Composable -fun HomeTopAppBar( - onFilterClick: () -> Unit, - modifier: Modifier = Modifier, - scrollBehavior: TopAppBarScrollBehavior, -) { - TopAppBar( - title = { - Row( - Modifier.fillMaxWidth(), - horizontalArrangement = Arrangement.Center, - ) { - } - }, - modifier = modifier.statusBarsPadding(), - actions = {}, - scrollBehavior = scrollBehavior - ) +fun HomeScreenPreview(){ + OpheliaTheme { + Surface { + HomeScreen(newUser = true) {} + } + } +} +@Preview(showBackground = true, + uiMode = Configuration.UI_MODE_NIGHT_YES or Configuration.UI_MODE_TYPE_NORMAL, ) +@Composable +fun HomeScreenPreview1(){ + OpheliaTheme { + Surface { + HomeScreen(newUser = true) {} + } + } } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt index d2331f5..d40e8f5 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt @@ -1,14 +1,20 @@ package com.menagerie.ophelia.view import androidx.compose.runtime.Composable +import androidx.compose.ui.res.stringResource +import androidx.navigation.NavController +import androidx.navigation.NavGraphBuilder import androidx.navigation.NavHostController import androidx.navigation.NavType import androidx.navigation.compose.NavHost import androidx.navigation.compose.composable import androidx.navigation.compose.rememberNavController import androidx.navigation.navArgument +import com.menagerie.ophelia.R +import com.menagerie.ophelia.database.polycule.PolyculeDatabaseManager import com.menagerie.ophelia.view.biographies.AddBiography import com.menagerie.ophelia.view.biographies.BioDetailsScreen +import com.menagerie.ophelia.view.polycule.PolyculeHomeView @Composable fun PolyculeApp() { @@ -22,33 +28,45 @@ fun PolyculeApp() { fun PolyculeNavHost( navController: NavHostController ) { + val home = stringResource(id = R.string.route_home) + val polycule = stringResource(id = R.string.route_polyculeHome) NavHost( navController = navController, - startDestination = "home" + startDestination = home ) { - composable("home") { - HomeScreen( - onBioClick = { - navController.navigate("bioDetail/${it.id}") - }, - onAddClick = { - navController.navigate("addBio") - } - ) - } - composable( - "bioDetail/{bioId}", - arguments = listOf(navArgument("bioId") { - type = NavType.IntType - }) - ) { - BioDetailsScreen( - id = it.arguments?.getInt("bioId") ?: 0, - onBackClick = { navController.navigateUp() }, - ) - } - composable("addBio") { - AddBiography() + polyculeGraph(navController) + composable(home) { + HomeScreen(!PolyculeDatabaseManager.hasPolycule()) { + navController.navigate(polycule) + } } + + } +} + +fun NavGraphBuilder.polyculeGraph(navController: NavController) { + composable("polyculeHome") { + PolyculeHomeView( + onBioClick = { + navController.navigate("bioDetail/${it.id}") + }, + onAddClick = { + navController.navigate("addBio") + } + ) + } + composable( + "bioDetail/{bioId}", + arguments = listOf(navArgument("bioId") { + type = NavType.IntType + }) + ) { + BioDetailsScreen( + id = it.arguments?.getInt("bioId") ?: 0, + onBackClick = { navController.navigateUp() }, + ) + } + composable("addBio") { + AddBiography() } } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/BioCard.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/BioCard.kt index f5eef54..302c147 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/BioCard.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/BioCard.kt @@ -1,7 +1,6 @@ package com.menagerie.ophelia.view.biographies import androidx.compose.foundation.BorderStroke -import androidx.compose.foundation.ExperimentalFoundationApi import androidx.compose.foundation.Image import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.Column @@ -35,6 +34,7 @@ import androidx.compose.ui.graphics.Color import androidx.compose.ui.layout.ContentScale import androidx.compose.ui.res.painterResource import androidx.compose.ui.unit.dp +import com.menagerie.ophelia.R @OptIn(ExperimentalMaterial3Api::class) @Composable @@ -66,7 +66,7 @@ fun BioCard( verticalAlignment = Alignment.CenterVertically, ) { Image( - painter = painterResource(id = image), + painter = painterResource(id = R.drawable.ic_app_logo), contentDescription = null, modifier = Modifier .size(130.dp) @@ -80,7 +80,9 @@ fun BioCard( color = MaterialTheme.colorScheme.onSurface, ) } - Spacer(modifier = Modifier.weight(1f).fillMaxSize()) + Spacer(modifier = Modifier + .weight(1f) + .fillMaxSize()) Box( modifier = Modifier .wrapContentSize(Alignment.TopStart) diff --git a/app/src/main/java/com/menagerie/ophelia/view/polycule/PolyculeHomeView.kt b/app/src/main/java/com/menagerie/ophelia/view/polycule/PolyculeHomeView.kt new file mode 100644 index 0000000..f07d99a --- /dev/null +++ b/app/src/main/java/com/menagerie/ophelia/view/polycule/PolyculeHomeView.kt @@ -0,0 +1,93 @@ +package com.menagerie.ophelia.view.polycule + +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.statusBarsPadding +import androidx.compose.material.icons.Icons +import androidx.compose.material.icons.filled.Add +import androidx.compose.material3.ExperimentalMaterial3Api +import androidx.compose.material3.FloatingActionButton +import androidx.compose.material3.Icon +import androidx.compose.material3.Scaffold +import androidx.compose.material3.TopAppBar +import androidx.compose.material3.TopAppBarDefaults +import androidx.compose.material3.TopAppBarScrollBehavior +import androidx.compose.runtime.Composable +import androidx.compose.runtime.livedata.observeAsState +import androidx.compose.ui.Modifier +import androidx.lifecycle.viewmodel.compose.viewModel +import com.menagerie.ophelia.database.polycule.entity.Bio +import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioListViewModel +import com.menagerie.ophelia.view.biographies.BioCardList + +@OptIn(ExperimentalMaterial3Api::class) +@Composable +fun PolyculeHomeView( + modifier: Modifier = Modifier, + onBioClick: (Bio) -> Unit = {}, + onAddClick: () -> Unit, +) { + val scrollBehavior = TopAppBarDefaults.enterAlwaysScrollBehavior() + Scaffold( + modifier = modifier, + bottomBar = { + PolyculeTopAppBar( + onFilterClick = { }, + scrollBehavior = scrollBehavior + ) + } + ) { + PolyculeHomeScreen( + onBioClick = onBioClick, + onAddClick = onAddClick, + modifier = modifier.padding(it) + ) + } +} + +@Composable +fun PolyculeHomeScreen( + onBioClick: (Bio) -> Unit, + onAddClick: () -> Unit = {}, + modifier: Modifier, +) { + val mBioListViewModel: BioListViewModel = viewModel( + factory = BioListViewModel.BioListViewModelFactory() + ) + val items = mBioListViewModel.allBios.observeAsState(listOf()).value + + Column( + modifier = modifier + ) { + BioCardList(bioList = items, onBioClick = onBioClick) + FloatingActionButton( + onClick = onAddClick + ) { + Icon(Icons.Filled.Add, "Add Bio") + } + } +} + +@OptIn(ExperimentalMaterial3Api::class) +@Composable +fun PolyculeTopAppBar( + onFilterClick: () -> Unit, + modifier: Modifier = Modifier, + scrollBehavior: TopAppBarScrollBehavior, +) { + TopAppBar( + title = { + Row( + Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.Center, + ) { + } + }, + modifier = modifier.statusBarsPadding(), + actions = {}, + scrollBehavior = scrollBehavior + ) +} \ No newline at end of file diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 16f9e48..f68b251 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -1,5 +1,15 @@ + ##App Main Ophelia + A Polycule Pocket-dex + Get Started + Welcome Back + + ##Routes + polyculeHome + home + + Add Bio Edit Bio Bio Loaded -- 2.47.2 From 2080658c4de1aac085acfa9c5587fd3cbdf76492 Mon Sep 17 00:00:00 2001 From: Azea Date: Sat, 21 Oct 2023 17:56:44 -0400 Subject: [PATCH 02/20] Start Pathing --- .../database/polycule/PolyculeDatabase.kt | 20 -------- .../ophelia/database/polycule/entity/Bio.kt | 5 +- .../ophelia/view/NewUserStartScreen.kt | 40 ++++++++++++++++ .../com/menagerie/ophelia/view/PolyculeApp.kt | 12 ++++- .../view/biographies/AddEditBiography.kt | 46 +++++++++++++------ .../ophelia/view/biographies/BioCard.kt | 1 - .../ophelia/view/biographies/BioCardList.kt | 1 - .../view/biographies/BioDetailsScreen.kt | 4 +- app/src/main/res/values/strings.xml | 5 +- 9 files changed, 91 insertions(+), 43 deletions(-) create mode 100644 app/src/main/java/com/menagerie/ophelia/view/NewUserStartScreen.kt diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeDatabase.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeDatabase.kt index 1b99dd1..0135c65 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeDatabase.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeDatabase.kt @@ -61,38 +61,18 @@ abstract class PolyculeDatabase : RoomDatabase() { } suspend fun populateDatabase(bioDao: BioDao) { - var desc = LoremIpsum(15).values.toList() - var init = "" - repeat(desc.size) { - init += ("${desc[it]} ") - } - var bio = Bio( name = "Azea", - description = init, ) bioDao.insert(bio) - desc = LoremIpsum(17).values.toList() - init = "" - repeat(desc.size) { - init += ("${desc[it]} ") - } - bio = Bio( name = "Darkwood Mill", - description = init, ) bioDao.insert(bio) - desc = LoremIpsum(42).values.toList() - init = "" - repeat(desc.size) { - init += ("${desc[it]} ") - } bio = Bio( name = "Blizzard", - description = init, ) bioDao.insert(bio) } diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/Bio.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/Bio.kt index 8c8e0ee..0472b1d 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/Bio.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/Bio.kt @@ -11,6 +11,9 @@ import com.menagerie.ophelia.R data class Bio( @PrimaryKey(autoGenerate = true) val id: Int = 0, @ColumnInfo(name = "name") val name: String = "", - @ColumnInfo(name = "description") val description: String = "", + @ColumnInfo(name = "subject_pronoun") val subjective: String = "", + @ColumnInfo(name = "object_pronoun") val objective: String = "", + @ColumnInfo(name = "possess_pronoun") val possessive: String = "", + @ColumnInfo(name = "reflex_pronoun") val reflexive: String = "", @ColumnInfo(name = "pfpRes") val pfpRes: Int = R.drawable.ic_app_logo, ) \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/NewUserStartScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/NewUserStartScreen.kt new file mode 100644 index 0000000..313026c --- /dev/null +++ b/app/src/main/java/com/menagerie/ophelia/view/NewUserStartScreen.kt @@ -0,0 +1,40 @@ +package com.menagerie.ophelia.view + +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.padding +import androidx.compose.material3.Button +import androidx.compose.material3.Text +import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier +import androidx.compose.ui.res.stringResource +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.dp +import com.menagerie.ophelia.R + +@Composable +fun NewUserStartScreen( + onGo: () -> Unit = {}, +) { + Column { + Box(modifier = Modifier + .fillMaxSize() + .padding(12.dp) + .weight(1f)){ + Text(text = stringResource(id = R.string.welcome_blurb)) + + } + Button(onClick = onGo) { + Text(text = "GO") + + } + } +} + +@Preview +@Composable +fun NewUserPreview(){ + NewUserStartScreen() +} \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt index d40e8f5..7f97f35 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt @@ -32,18 +32,26 @@ fun PolyculeNavHost( val polycule = stringResource(id = R.string.route_polyculeHome) NavHost( navController = navController, - startDestination = home + startDestination = "addBio" ) { polyculeGraph(navController) + welcomeGraph(navController) composable(home) { HomeScreen(!PolyculeDatabaseManager.hasPolycule()) { - navController.navigate(polycule) + navController.navigate("newUserStart") } } } } +fun NavGraphBuilder.welcomeGraph(navController: NavHostController) { + composable("newUserStart") { NewUserStartScreen(){ + navController.navigate("addBio") + } } + +} + fun NavGraphBuilder.polyculeGraph(navController: NavController) { composable("polyculeHome") { PolyculeHomeView( diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt index 02c7551..21dddb3 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt @@ -3,6 +3,7 @@ package com.menagerie.ophelia.view.biographies import android.annotation.SuppressLint import android.widget.Toast import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Row import androidx.compose.foundation.layout.Spacer import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.padding @@ -16,6 +17,7 @@ import androidx.compose.ui.Modifier import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.platform.LocalFocusManager import androidx.compose.ui.res.stringResource +import androidx.compose.ui.tooling.preview.Preview import androidx.compose.ui.tooling.preview.datasource.LoremIpsum import androidx.compose.ui.unit.dp import androidx.lifecycle.LiveData @@ -54,38 +56,53 @@ fun AddBiography() { } ) { - InputFieldState(inputViewModel) + Column { + val bio: Bio by inputViewModel.bio.observeAsState(Bio()) + + InputFieldState(inputViewModel, bio.name, "name") //Name + Row { + InputFieldState(inputViewModel, bio.subjective, "") + InputFieldState(inputViewModel, bio.objective, "") + } + Row { + InputFieldState(inputViewModel, bio.possessive, "") + InputFieldState(inputViewModel, bio.reflexive, "") + } + + } } } @Composable fun InputFieldState( inputViewModel: InputViewModel, + value: String, + label: String, ) { - val bio: Bio by inputViewModel.bio.observeAsState(Bio()) + Column( modifier = Modifier.padding(16.dp) ) { - InputField(bio.name) { inputViewModel.onInputChange(it) } + InputField(value, label) { inputViewModel.onInputChange(it) } Spacer(modifier = Modifier.padding(10.dp)) } } @Composable fun InputField( - name: String, + text: String, + label: String, onValChange: ((String) -> Unit)? ) { val focusManager = LocalFocusManager.current if (onValChange != null) { InputFieldComponent( - text = name, + text = text, onChange = onValChange, - label = "Enter Bio", + label = label, modifier = Modifier - .padding(all = 16.dp) - .fillMaxWidth(), + .padding(all = 16.dp), keyboardActions = KeyboardActions(onDone = { focusManager.clearFocus() }) ) } @@ -95,15 +112,16 @@ class InputViewModel : ViewModel() { private val _bio: MutableLiveData = MutableLiveData(Bio()) val bio: LiveData = _bio fun onInputChange(name: String) { - var desc = LoremIpsum(Random.nextInt(5,100)).values.toList() - var init = "" - repeat(desc.size) { - init += ("${desc[it]} ") - } val newBio = Bio( name = name, - description = init, ) _bio.value = newBio } } + +@Preview +@Composable +fun AddEditBioPreview() +{ + AddBiography() +} diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/BioCard.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/BioCard.kt index 302c147..ce1f33d 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/BioCard.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/BioCard.kt @@ -40,7 +40,6 @@ import com.menagerie.ophelia.R @Composable fun BioCard( name: String, - description: String, image: Int, onBioClick: () -> Unit, onDeleteClick: () -> Unit diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/BioCardList.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/BioCardList.kt index 6642c44..394e58f 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/BioCardList.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/BioCardList.kt @@ -53,7 +53,6 @@ fun BioCardList( items(bioList) { bio -> BioCard( name = bio.name, - description = bio.description, image = bio.pfpRes, onBioClick = { onBioClick(bio) }, onDeleteClick = { mBioListViewModel.delete(bio) }) diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt index b0acad9..a047c17 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt @@ -89,7 +89,6 @@ fun BioDetailContents( ) InfoDetails( name = bio.name, - description = bio.description, modifier = Modifier.constrainAs(info) { top.linkTo(image.bottom) } @@ -101,7 +100,6 @@ fun BioDetailContents( @Composable fun InfoDetails( name: String, - description: String, modifier: Modifier = Modifier ) { Column(modifier = modifier.padding(Dimens.PaddingLarge)) { @@ -125,7 +123,7 @@ fun InfoDetails( bottom = Dimens.PaddingNormal ) ) { - Text(text = description) + Text(text = "description") } } } diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index f68b251..68e4977 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -9,9 +9,12 @@ polyculeHome home - + ##Bio Add Bio Edit Bio Bio Loaded Open context menu + Name + + Ophelia is a Polycule resource management system designed to help you keep track of your metas, reference a charter, and find things in common with your polycule.\n\nOphelia is meant to work dynamically with your rule set, so what all those words mean will be defined by you later.\n\nFirst, we need to get to know "you".\n\nClick Go to get started. \ No newline at end of file -- 2.47.2 From 6eded27a9e472b378c8a91a833e0d91165850710 Mon Sep 17 00:00:00 2001 From: Azea Date: Sat, 21 Oct 2023 18:16:05 -0400 Subject: [PATCH 03/20] Start Pathing --- .../view/biographies/AddEditBiography.kt | 26 ++++++++++++------- .../view/components/InputFieldComponent.kt | 6 +++-- 2 files changed, 21 insertions(+), 11 deletions(-) diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt index 21dddb3..171bf7c 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt @@ -5,8 +5,11 @@ import android.widget.Toast 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.padding +import androidx.compose.foundation.layout.size +import androidx.compose.foundation.layout.width import androidx.compose.foundation.text.KeyboardActions import androidx.compose.material3.ExperimentalMaterial3Api import androidx.compose.material3.Scaffold @@ -57,16 +60,17 @@ fun AddBiography() { ) { Column { + val modifier = Modifier.width(120.dp) val bio: Bio by inputViewModel.bio.observeAsState(Bio()) - InputFieldState(inputViewModel, bio.name, "name") //Name + InputFieldState(inputViewModel, bio.name, "name", "Ophelia", modifier = Modifier) //Name Row { - InputFieldState(inputViewModel, bio.subjective, "") - InputFieldState(inputViewModel, bio.objective, "") + InputFieldState(inputViewModel, bio.subjective,"", "she", modifier) + InputFieldState(inputViewModel, bio.objective, "", "her", modifier) } Row { - InputFieldState(inputViewModel, bio.possessive, "") - InputFieldState(inputViewModel, bio.reflexive, "") + InputFieldState(inputViewModel, bio.possessive,"", "hers", modifier) + InputFieldState(inputViewModel, bio.reflexive, "","herself", modifier) } } @@ -78,12 +82,14 @@ fun InputFieldState( inputViewModel: InputViewModel, value: String, label: String, + placeholder: String, + modifier: Modifier ) { Column( - modifier = Modifier.padding(16.dp) + modifier = Modifier ) { - InputField(value, label) { inputViewModel.onInputChange(it) } + InputField(value, label, placeholder, modifier) { inputViewModel.onInputChange(it) } Spacer(modifier = Modifier.padding(10.dp)) } } @@ -92,6 +98,8 @@ fun InputFieldState( fun InputField( text: String, label: String, + placeholder: String, + modifier: Modifier, onValChange: ((String) -> Unit)? ) { val focusManager = LocalFocusManager.current @@ -101,8 +109,8 @@ fun InputField( text = text, onChange = onValChange, label = label, - modifier = Modifier - .padding(all = 16.dp), + placeHolder = placeholder, + modifier = modifier, keyboardActions = KeyboardActions(onDone = { focusManager.clearFocus() }) ) } diff --git a/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt b/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt index 688299d..cc2ad4b 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt @@ -13,12 +13,14 @@ fun InputFieldComponent( modifier: Modifier = Modifier, singleLine: Boolean = true, label: String = "Some val", + placeHolder: String = "some place", keyboardActions: KeyboardActions = KeyboardActions.Default, ) { OutlinedTextField( - text, - onChange, + value = text, + onValueChange = onChange, label = { Text(text = label)}, + placeholder = { Text(text = placeHolder)}, modifier = modifier, singleLine = singleLine, ) -- 2.47.2 From 7ee1d54964bd57ba9595fe461701dae7effdadf6 Mon Sep 17 00:00:00 2001 From: Azea Date: Sun, 22 Oct 2023 17:50:27 -0400 Subject: [PATCH 04/20] Push --- app/src/main/AndroidManifest.xml | 4 + .../database/polycule/PolyculeDatabase.kt | 5 +- .../ophelia/database/polycule/entity/Bio.kt | 2 +- .../com/menagerie/ophelia/ui/theme/Color.kt | 6 +- .../ophelia/view/NewUserStartScreen.kt | 27 ++- .../com/menagerie/ophelia/view/Ophelia.kt | 103 +++++++++++ .../com/menagerie/ophelia/view/PolyculeApp.kt | 13 +- .../view/biographies/AddEditBiography.kt | 8 +- .../view/components/InputFieldComponent.kt | 59 ++++++ .../ophelia/view/newUser/AddNameScreen.kt | 119 ++++++++++++ .../ophelia/view/newUser/AddPronounsScreen.kt | 18 ++ .../res/drawable/ic_launcher_background.xml | 170 ------------------ .../res/drawable/ic_launcher_foreground.xml | 30 ---- app/src/main/res/font/alex_brush.xml | 7 + app/src/main/res/font/allura.ttf | Bin 0 -> 88036 bytes app/src/main/res/font/calligraffitti.xml | 7 + app/src/main/res/font/mentho.xml | 7 + app/src/main/res/values/font_certs.xml | 17 ++ app/src/main/res/values/preloaded_fonts.xml | 7 + app/src/main/res/values/strings.xml | 16 +- 20 files changed, 393 insertions(+), 232 deletions(-) create mode 100644 app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt create mode 100644 app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt create mode 100644 app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt delete mode 100644 app/src/main/res/drawable/ic_launcher_background.xml delete mode 100644 app/src/main/res/drawable/ic_launcher_foreground.xml create mode 100644 app/src/main/res/font/alex_brush.xml create mode 100644 app/src/main/res/font/allura.ttf create mode 100644 app/src/main/res/font/calligraffitti.xml create mode 100644 app/src/main/res/font/mentho.xml create mode 100644 app/src/main/res/values/font_certs.xml create mode 100644 app/src/main/res/values/preloaded_fonts.xml diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml index a65e438..dc4d621 100644 --- a/app/src/main/AndroidManifest.xml +++ b/app/src/main/AndroidManifest.xml @@ -27,6 +27,10 @@ + + \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeDatabase.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeDatabase.kt index 0135c65..12ef002 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeDatabase.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeDatabase.kt @@ -13,7 +13,7 @@ import kotlinx.coroutines.launch @Database( - version = 2, + version = 3, exportSchema = false, entities = [ Bio::class @@ -50,12 +50,11 @@ abstract class PolyculeDatabase : RoomDatabase() { private class PolyculeDatabaseCallback( private val scope: CoroutineScope ) : Callback() { - override fun onCreate(db: SupportSQLiteDatabase) { super.onCreate(db) INSTANCE?.let { database -> scope.launch { - populateDatabase(database.bioDao()) + //populateDatabase(database.bioDao()) } } } diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/Bio.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/Bio.kt index 0472b1d..d094c59 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/Bio.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/Bio.kt @@ -10,7 +10,7 @@ import com.menagerie.ophelia.R ) data class Bio( @PrimaryKey(autoGenerate = true) val id: Int = 0, - @ColumnInfo(name = "name") val name: String = "", + @ColumnInfo(name = "name") var name: String = "", @ColumnInfo(name = "subject_pronoun") val subjective: String = "", @ColumnInfo(name = "object_pronoun") val objective: String = "", @ColumnInfo(name = "possess_pronoun") val possessive: String = "", diff --git a/app/src/main/java/com/menagerie/ophelia/ui/theme/Color.kt b/app/src/main/java/com/menagerie/ophelia/ui/theme/Color.kt index 8f4024a..e388112 100644 --- a/app/src/main/java/com/menagerie/ophelia/ui/theme/Color.kt +++ b/app/src/main/java/com/menagerie/ophelia/ui/theme/Color.kt @@ -26,7 +26,7 @@ val md_theme_light_inversePrimary = Color(0xFF9BD67F) val md_theme_light_surfaceTint = Color(0xFF366A21) val md_theme_light_outlineVariant = Color(0xFFC3C8BB) val md_theme_light_scrim = Color(0xFF000000) -val md_theme_light_surface = Color(0xFFFAFAF3) +val md_theme_light_surface = Color(0xFFD8D8C4) val md_theme_light_onSurface = Color(0xFF1A1C18) val md_theme_light_surfaceVariant = Color(0xFFDFE4D7) val md_theme_light_onSurfaceVariant = Color(0xFF43483F) @@ -47,7 +47,7 @@ val md_theme_dark_error = Color(0xFFFFB4AB) val md_theme_dark_errorContainer = Color(0xFF93000A) val md_theme_dark_onError = Color(0xFF690005) val md_theme_dark_onErrorContainer = Color(0xFFFFDAD6) -val md_theme_dark_background = Color(0xFF1A1C18) +val md_theme_dark_background = Color(0xFF1C1C18) val md_theme_dark_onBackground = Color(0xFFE3E3DC) val md_theme_dark_outline = Color(0xFF8D9287) val md_theme_dark_inverseOnSurface = Color(0xFF1A1C18) @@ -56,7 +56,7 @@ val md_theme_dark_inversePrimary = Color(0xFF366A21) val md_theme_dark_surfaceTint = Color(0xFF9BD67F) val md_theme_dark_outlineVariant = Color(0xFF43483F) val md_theme_dark_scrim = Color(0xFF000000) -val md_theme_dark_surface = Color(0xFF121410) +val md_theme_dark_surface = Color(0xFF2B2822) val md_theme_dark_onSurface = Color(0xFFC6C7C0) val md_theme_dark_surfaceVariant = Color(0xFF43483F) val md_theme_dark_onSurfaceVariant = Color(0xFFC3C8BB) diff --git a/app/src/main/java/com/menagerie/ophelia/view/NewUserStartScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/NewUserStartScreen.kt index 313026c..f2db424 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/NewUserStartScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/NewUserStartScreen.kt @@ -1,33 +1,32 @@ package com.menagerie.ophelia.view -import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.Column -import androidx.compose.foundation.layout.fillMaxSize -import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.padding import androidx.compose.material3.Button import androidx.compose.material3.Text import androidx.compose.runtime.Composable +import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier -import androidx.compose.ui.res.stringResource import androidx.compose.ui.tooling.preview.Preview import androidx.compose.ui.unit.dp -import com.menagerie.ophelia.R @Composable fun NewUserStartScreen( onGo: () -> Unit = {}, ) { - Column { - Box(modifier = Modifier - .fillMaxSize() - .padding(12.dp) - .weight(1f)){ - Text(text = stringResource(id = R.string.welcome_blurb)) - } - Button(onClick = onGo) { - Text(text = "GO") + Column { + OpheliaFace(modifier = Modifier + .align(Alignment.CenterHorizontally) + .padding(top = 12.dp)) + OpheliaWelcome(modifier = Modifier.weight(1f)) + Button( + onClick = onGo, + modifier = Modifier + .padding(12.dp) + .align(Alignment.End) + ) { + Text(text = "Go") } } diff --git a/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt b/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt new file mode 100644 index 0000000..ad2f4ee --- /dev/null +++ b/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt @@ -0,0 +1,103 @@ +package com.menagerie.ophelia.view + +import androidx.compose.foundation.Image +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.padding +import androidx.compose.material3.MaterialTheme +import androidx.compose.material3.Text +import androidx.compose.runtime.Composable +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.modifier.modifierLocalConsumer +import androidx.compose.ui.res.painterResource +import androidx.compose.ui.res.stringArrayResource +import androidx.compose.ui.res.stringResource +import androidx.compose.ui.text.AnnotatedString +import androidx.compose.ui.text.SpanStyle +import androidx.compose.ui.text.buildAnnotatedString +import androidx.compose.ui.text.font.Font +import androidx.compose.ui.text.font.FontFamily +import androidx.compose.ui.unit.dp +import com.menagerie.ophelia.R + +@Composable +fun OpheliaSpanStyle(): SpanStyle { + val fontFamily = FontFamily( + Font(R.font.calligraffitti) + ) + + return SpanStyle( + letterSpacing = MaterialTheme.typography.bodyLarge.letterSpacing, + fontFamily = fontFamily, + fontSize = MaterialTheme.typography.bodyLarge.fontSize) +} + +@Composable +fun OpheliaFace( + modifier: Modifier +) +{ + Image( + modifier = modifier, + painter = painterResource(id = R.drawable.ophelia_foreground), + contentDescription = OpheliaSays() + ) +} +@Composable +fun OpheliaSays( + id: Int +): AnnotatedString { + return buildAnnotatedString { + pushStyle(OpheliaSpanStyle()) + append(stringArrayResource(id = id).joinToString(separator = "\n\n")) + toAnnotatedString() + } +} + +@Composable +fun OpheliaSays(): String { + return stringResource(id = R.string.ophelia_says) +} + + +@Composable +fun OpheliaWelcome( + modifier: Modifier +) { + Box( + modifier = modifier + .fillMaxSize() + .padding(24.dp) + ) { + Text( + text = OpheliaSays(id = R.array.welcome_blurb) + ) + } +} + +@Composable +fun OpheliaWhatsYourName( + modifier: Modifier +) { + Box( + modifier = modifier + .fillMaxWidth() + .padding(12.dp) + ) + { + Text(text = OpheliaSays(id = R.array.whats_your_name)) + } +} + +@Composable +fun OpheliaPronounsIntroduction( + modifier: Modifier, + name: String +) { + Box(modifier = modifier + .fillMaxWidth() + .padding(12.dp)) + Text(text = "Nice to meet you, $name") +} diff --git a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt index 7f97f35..56b7ec4 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt @@ -14,6 +14,8 @@ import com.menagerie.ophelia.R import com.menagerie.ophelia.database.polycule.PolyculeDatabaseManager import com.menagerie.ophelia.view.biographies.AddBiography import com.menagerie.ophelia.view.biographies.BioDetailsScreen +import com.menagerie.ophelia.view.newUser.AddNameScreen +import com.menagerie.ophelia.view.newUser.AddPronounsScreen import com.menagerie.ophelia.view.polycule.PolyculeHomeView @Composable @@ -32,7 +34,7 @@ fun PolyculeNavHost( val polycule = stringResource(id = R.string.route_polyculeHome) NavHost( navController = navController, - startDestination = "addBio" + startDestination = "home" ) { polyculeGraph(navController) welcomeGraph(navController) @@ -47,9 +49,12 @@ fun PolyculeNavHost( fun NavGraphBuilder.welcomeGraph(navController: NavHostController) { composable("newUserStart") { NewUserStartScreen(){ - navController.navigate("addBio") + navController.navigate("newUserName") } } - + composable("newUserName") { AddNameScreen(){ + navController.navigate("newUserPronouns") + } } + composable("newUserPronouns"){AddPronounsScreen()} } fun NavGraphBuilder.polyculeGraph(navController: NavController) { @@ -59,7 +64,7 @@ fun NavGraphBuilder.polyculeGraph(navController: NavController) { navController.navigate("bioDetail/${it.id}") }, onAddClick = { - navController.navigate("addBio") + navController.navigate("addBio"){} } ) } diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt index 171bf7c..861a84c 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt @@ -1,17 +1,14 @@ package com.menagerie.ophelia.view.biographies import android.annotation.SuppressLint +import android.util.Log import android.widget.Toast 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.padding -import androidx.compose.foundation.layout.size import androidx.compose.foundation.layout.width import androidx.compose.foundation.text.KeyboardActions -import androidx.compose.material3.ExperimentalMaterial3Api import androidx.compose.material3.Scaffold import androidx.compose.runtime.Composable import androidx.compose.runtime.getValue @@ -21,7 +18,6 @@ import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.platform.LocalFocusManager import androidx.compose.ui.res.stringResource import androidx.compose.ui.tooling.preview.Preview -import androidx.compose.ui.tooling.preview.datasource.LoremIpsum import androidx.compose.ui.unit.dp import androidx.lifecycle.LiveData import androidx.lifecycle.MutableLiveData @@ -32,7 +28,6 @@ import com.menagerie.ophelia.database.polycule.entity.Bio import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioListViewModel import com.menagerie.ophelia.view.components.InputFieldComponent import com.menagerie.ophelia.view.components.fab.FABComponent -import kotlin.random.Random fun insertBioInDB(bio: Bio?, mBioListViewModel: BioListViewModel) { bio?.let { @@ -120,6 +115,7 @@ class InputViewModel : ViewModel() { private val _bio: MutableLiveData = MutableLiveData(Bio()) val bio: LiveData = _bio fun onInputChange(name: String) { + Log.d("Tawni", name) val newBio = Bio( name = name, ) diff --git a/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt b/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt index cc2ad4b..f17d59e 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt @@ -1,10 +1,21 @@ package com.menagerie.ophelia.view.components +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Spacer +import androidx.compose.foundation.layout.padding import androidx.compose.foundation.text.KeyboardActions import androidx.compose.material3.OutlinedTextField import androidx.compose.material3.Text import androidx.compose.runtime.Composable import androidx.compose.ui.Modifier +import androidx.compose.ui.platform.LocalFocusManager +import androidx.compose.ui.unit.dp +import androidx.lifecycle.LiveData +import androidx.lifecycle.MutableLiveData +import androidx.lifecycle.ViewModel +import androidx.lifecycle.viewmodel.compose.viewModel +import com.menagerie.ophelia.database.polycule.entity.Bio +import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioListViewModel @Composable fun InputFieldComponent( @@ -24,4 +35,52 @@ fun InputFieldComponent( modifier = modifier, singleLine = singleLine, ) +} + + +@Composable +fun InputFieldState( + value: String, + label: String, + placeholder: String, + modifier: Modifier, + onValChange: ((String) -> Unit)? +) { + + Column( + modifier = Modifier + ) { + InputField(value, label, placeholder, modifier) { onValChange } + Spacer(modifier = Modifier.padding(10.dp)) + } +} + +@Composable +fun InputField( + text: String, + label: String, + placeholder: String, + modifier: Modifier, + onValChange: ((String) -> Unit)? +) { + val focusManager = LocalFocusManager.current + + if (onValChange != null) { + InputFieldComponent( + text = text, + onChange = onValChange, + label = label, + placeHolder = placeholder, + modifier = modifier, + keyboardActions = KeyboardActions(onDone = { focusManager.clearFocus() }) + ) + } +} + +class InputViewModel : ViewModel() { + private var _bio: MutableLiveData = MutableLiveData(Bio()) + var bio: LiveData = _bio + fun onNameChange(name: String) { + _bio.value?.name ?: name + } } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt new file mode 100644 index 0000000..8112843 --- /dev/null +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt @@ -0,0 +1,119 @@ +package com.menagerie.ophelia.view.newUser + +import android.annotation.SuppressLint +import android.util.Log +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Spacer +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.text.KeyboardActions +import androidx.compose.material3.Button +import androidx.compose.material3.Scaffold +import androidx.compose.material3.Text +import androidx.compose.runtime.Composable +import androidx.compose.runtime.getValue +import androidx.compose.runtime.livedata.observeAsState +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.platform.LocalFocusManager +import androidx.compose.ui.unit.dp +import androidx.lifecycle.LiveData +import androidx.lifecycle.MutableLiveData +import androidx.lifecycle.ViewModel +import androidx.lifecycle.viewmodel.compose.viewModel +import com.menagerie.ophelia.database.polycule.entity.Bio +import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioListViewModel +import com.menagerie.ophelia.view.OpheliaFace +import com.menagerie.ophelia.view.OpheliaWhatsYourName +import com.menagerie.ophelia.view.biographies.insertBioInDB +import com.menagerie.ophelia.view.components.InputFieldComponent + +@SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") +@Composable +fun AddNameScreen( + onGo: () -> Unit = {}, +) { + val inputViewModel = InputViewModel() + val mBioListViewModel: BioListViewModel = viewModel( + factory = BioListViewModel.BioListViewModelFactory() + ) + + Scaffold() { + Column( + modifier = Modifier.fillMaxSize() + ) { + val bio: Bio by inputViewModel.bio.observeAsState(Bio()) + OpheliaFace( + modifier = Modifier + .align(Alignment.CenterHorizontally) + .padding(top = 12.dp) + ) + OpheliaWhatsYourName(modifier = Modifier) + InputFieldState( + inputViewModel, + bio.name, + "name", + "Ophelia", + modifier = Modifier + ) +// Button( +// onClick = onGo.also { +// Log.d("Tawni", "Why") +// insertBioInDB(inputViewModel.bio.value, mBioListViewModel) +// } +// ) { +// Text(text = "Continue") +// } + } + } +} + +@Composable +fun InputFieldState( + inputViewModel: InputViewModel, + value: String, + label: String, + placeholder: String, + modifier: Modifier +) { + + Column( + modifier = Modifier + ) { + InputField(value, label, placeholder, modifier) { inputViewModel.onInputChange(it) } + Spacer(modifier = Modifier.padding(10.dp)) + } +} + +@Composable +fun InputField( + text: String, + label: String, + placeholder: String, + modifier: Modifier, + onValChange: ((String) -> Unit)? +) { + val focusManager = LocalFocusManager.current + + if (onValChange != null) { + InputFieldComponent( + text = text, + onChange = onValChange, + label = label, + placeHolder = placeholder, + modifier = modifier, + keyboardActions = KeyboardActions(onDone = { focusManager.clearFocus() }) + ) + } +} + +class InputViewModel : ViewModel() { + private val _bio: MutableLiveData = MutableLiveData(Bio()) + val bio: LiveData = _bio + fun onInputChange(name: String) { + val newBio = Bio( + name = name, + ) + _bio.value = newBio + } +} \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt new file mode 100644 index 0000000..638a71e --- /dev/null +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt @@ -0,0 +1,18 @@ +package com.menagerie.ophelia.view.newUser + +import androidx.compose.foundation.layout.Column +import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier +import androidx.lifecycle.asLiveData +import com.menagerie.ophelia.database.polycule.PolyculeDatabaseManager +import com.menagerie.ophelia.view.OpheliaPronounsIntroduction + +@Composable +fun AddPronounsScreen() { + Column { + val name = PolyculeDatabaseManager.polyculeRepository.getBio(1).asLiveData().value?.name + name?.let { + OpheliaPronounsIntroduction(modifier = Modifier, name = it) + } + } +} \ No newline at end of file diff --git a/app/src/main/res/drawable/ic_launcher_background.xml b/app/src/main/res/drawable/ic_launcher_background.xml deleted file mode 100644 index 07d5da9..0000000 --- a/app/src/main/res/drawable/ic_launcher_background.xml +++ /dev/null @@ -1,170 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/app/src/main/res/drawable/ic_launcher_foreground.xml b/app/src/main/res/drawable/ic_launcher_foreground.xml deleted file mode 100644 index 2b068d1..0000000 --- a/app/src/main/res/drawable/ic_launcher_foreground.xml +++ /dev/null @@ -1,30 +0,0 @@ - - - - - - - - - - - \ No newline at end of file diff --git a/app/src/main/res/font/alex_brush.xml b/app/src/main/res/font/alex_brush.xml new file mode 100644 index 0000000..f047b6c --- /dev/null +++ b/app/src/main/res/font/alex_brush.xml @@ -0,0 +1,7 @@ + + + diff --git a/app/src/main/res/font/allura.ttf b/app/src/main/res/font/allura.ttf new file mode 100644 index 0000000000000000000000000000000000000000..6a426b52ad18e58da12310810a03a31ec3826a60 GIT binary patch literal 88036 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 + + diff --git a/app/src/main/res/font/mentho.xml b/app/src/main/res/font/mentho.xml new file mode 100644 index 0000000..69a1839 --- /dev/null +++ b/app/src/main/res/font/mentho.xml @@ -0,0 +1,7 @@ + + + + \ No newline at end of file diff --git a/app/src/main/res/values/font_certs.xml b/app/src/main/res/values/font_certs.xml new file mode 100644 index 0000000..d2226ac --- /dev/null +++ b/app/src/main/res/values/font_certs.xml @@ -0,0 +1,17 @@ + + + + @array/com_google_android_gms_fonts_certs_dev + @array/com_google_android_gms_fonts_certs_prod + + + + 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 + + + diff --git a/app/src/main/res/values/preloaded_fonts.xml b/app/src/main/res/values/preloaded_fonts.xml new file mode 100644 index 0000000..92ab30c --- /dev/null +++ b/app/src/main/res/values/preloaded_fonts.xml @@ -0,0 +1,7 @@ + + + + @font/alex_brush + @font/calligraffitti + + diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 68e4977..eb02842 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -16,5 +16,19 @@ Open context menu Name - Ophelia is a Polycule resource management system designed to help you keep track of your metas, reference a charter, and find things in common with your polycule.\n\nOphelia is meant to work dynamically with your rule set, so what all those words mean will be defined by you later.\n\nFirst, we need to get to know "you".\n\nClick Go to get started. + ##Ophelia + Ophelia Says + + Hi! + I\'m Ophelia, a Polycule companion system designed to help you keep track of your metas, reference a charter, and find things in common with your polycule. + I\'m meant to work dynamically with how polyamory works for you, so what all those words mean will be something we work out together later. + First, I need to get to know "you". + Click Go to get started. + + + I\'m Ophelia, what\'s your name\? + Your Name is how you\'ll be addressed in the app, and is the primary way you\'ll be referred to in polycules. + But don\'t worry; your name, like everything about you, can be changed at any time! + + \ No newline at end of file -- 2.47.2 From dcc1cb3010a21985352b8649411ae52d537ccab1 Mon Sep 17 00:00:00 2001 From: azea_laptop Date: Sun, 22 Oct 2023 22:25:07 -0400 Subject: [PATCH 05/20] Add edit --- .../database/polycule/PolyculeRepository.kt | 2 +- .../database/polycule/entity/BioDao.kt | 4 +-- .../com/menagerie/ophelia/view/Ophelia.kt | 34 ++++++++++++++----- .../com/menagerie/ophelia/view/PolyculeApp.kt | 15 ++++---- .../view/biographies/AddEditBiography.kt | 2 +- .../ophelia/view/newUser/AddNameScreen.kt | 21 +++++++----- .../ophelia/view/newUser/AddPronounsScreen.kt | 4 ++- app/src/main/res/values/strings.xml | 1 + 8 files changed, 54 insertions(+), 29 deletions(-) diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt index 00cde6d..ba2507b 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt @@ -8,7 +8,7 @@ class PolyculeRepository( private val bioDao: BioDao ) { suspend fun upsertBio(bio: Bio) { - return bioDao.upsert(bio) + bioDao.upsert(bio) } fun getAlphabetisedBios(): Flow> { diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/BioDao.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/BioDao.kt index febd7ea..f212769 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/BioDao.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/BioDao.kt @@ -12,7 +12,7 @@ import kotlinx.coroutines.flow.Flow abstract class BioDao { @Insert - abstract suspend fun insert(newBio: Bio) + abstract suspend fun insert(newBio: Bio): Long @Delete abstract suspend fun delete(bio: Bio) @@ -30,5 +30,5 @@ abstract class BioDao { abstract fun getBio(bioId: Int): Flow @Upsert - abstract suspend fun upsert(bio: Bio) + abstract suspend fun upsert(bio: Bio): Long } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt b/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt index ad2f4ee..845a2ea 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt @@ -2,6 +2,7 @@ package com.menagerie.ophelia.view import androidx.compose.foundation.Image import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.fillMaxSize import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.padding @@ -46,7 +47,7 @@ fun OpheliaFace( ) } @Composable -fun OpheliaSays( +fun OpheliaSaysArray( id: Int ): AnnotatedString { return buildAnnotatedString { @@ -55,6 +56,16 @@ fun OpheliaSays( toAnnotatedString() } } +@Composable +fun OpheliaSays( + id: Int +): AnnotatedString { + return buildAnnotatedString { + pushStyle(OpheliaSpanStyle()) + append(stringResource(id = id)) + toAnnotatedString() + } +} @Composable fun OpheliaSays(): String { @@ -72,7 +83,7 @@ fun OpheliaWelcome( .padding(24.dp) ) { Text( - text = OpheliaSays(id = R.array.welcome_blurb) + text = OpheliaSaysArray(id = R.array.welcome_blurb) ) } } @@ -85,9 +96,8 @@ fun OpheliaWhatsYourName( modifier = modifier .fillMaxWidth() .padding(12.dp) - ) - { - Text(text = OpheliaSays(id = R.array.whats_your_name)) + ) { + Text(text = OpheliaSaysArray(id = R.array.whats_your_name)) } } @@ -96,8 +106,14 @@ fun OpheliaPronounsIntroduction( modifier: Modifier, name: String ) { - Box(modifier = modifier - .fillMaxWidth() - .padding(12.dp)) - Text(text = "Nice to meet you, $name") + Box( + modifier = modifier + .fillMaxWidth() + .padding(12.dp) + ) { + Column { + Text(text = "${OpheliaSays(R.string.introduction_with_name)} $name!") + + } + } } diff --git a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt index 56b7ec4..f2ccd3d 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt @@ -2,6 +2,7 @@ package com.menagerie.ophelia.view import androidx.compose.runtime.Composable import androidx.compose.ui.res.stringResource +import androidx.lifecycle.viewmodel.compose.viewModel import androidx.navigation.NavController import androidx.navigation.NavGraphBuilder import androidx.navigation.NavHostController @@ -12,6 +13,7 @@ import androidx.navigation.compose.rememberNavController import androidx.navigation.navArgument import com.menagerie.ophelia.R import com.menagerie.ophelia.database.polycule.PolyculeDatabaseManager +import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioListViewModel import com.menagerie.ophelia.view.biographies.AddBiography import com.menagerie.ophelia.view.biographies.BioDetailsScreen import com.menagerie.ophelia.view.newUser.AddNameScreen @@ -31,10 +33,9 @@ fun PolyculeNavHost( navController: NavHostController ) { val home = stringResource(id = R.string.route_home) - val polycule = stringResource(id = R.string.route_polyculeHome) NavHost( navController = navController, - startDestination = "home" + startDestination = "newUserName" ) { polyculeGraph(navController) welcomeGraph(navController) @@ -51,10 +52,12 @@ fun NavGraphBuilder.welcomeGraph(navController: NavHostController) { composable("newUserStart") { NewUserStartScreen(){ navController.navigate("newUserName") } } - composable("newUserName") { AddNameScreen(){ - navController.navigate("newUserPronouns") - } } - composable("newUserPronouns"){AddPronounsScreen()} + composable("newUserName") { AddNameScreen( + onGo={ navController.navigate("newUserPronouns")} + )} + composable("newUserPronouns") { + AddPronounsScreen() + } } fun NavGraphBuilder.polyculeGraph(navController: NavController) { diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt index 861a84c..0521256 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt @@ -31,7 +31,7 @@ import com.menagerie.ophelia.view.components.fab.FABComponent fun insertBioInDB(bio: Bio?, mBioListViewModel: BioListViewModel) { bio?.let { - mBioListViewModel.upsert(it) + mBioListViewModel.upsert(it) } } diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt index 8112843..9512417 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt @@ -8,6 +8,7 @@ import androidx.compose.foundation.layout.fillMaxSize import androidx.compose.foundation.layout.padding import androidx.compose.foundation.text.KeyboardActions import androidx.compose.material3.Button +import androidx.compose.material3.ExperimentalMaterial3Api import androidx.compose.material3.Scaffold import androidx.compose.material3.Text import androidx.compose.runtime.Composable @@ -28,10 +29,11 @@ import com.menagerie.ophelia.view.OpheliaWhatsYourName import com.menagerie.ophelia.view.biographies.insertBioInDB import com.menagerie.ophelia.view.components.InputFieldComponent +@OptIn(ExperimentalMaterial3Api::class) @SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") @Composable fun AddNameScreen( - onGo: () -> Unit = {}, + onGo: (Bio) -> Unit = {}, ) { val inputViewModel = InputViewModel() val mBioListViewModel: BioListViewModel = viewModel( @@ -56,14 +58,15 @@ fun AddNameScreen( "Ophelia", modifier = Modifier ) -// Button( -// onClick = onGo.also { -// Log.d("Tawni", "Why") -// insertBioInDB(inputViewModel.bio.value, mBioListViewModel) -// } -// ) { -// Text(text = "Continue") -// } + Button( + onClick = { + insertBioInDB(inputViewModel.bio.value, mBioListViewModel) + onGo(bio) } + ) { + Text(text = "Continue") + } + + } } } diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt index 638a71e..eb55b32 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt @@ -1,5 +1,6 @@ package com.menagerie.ophelia.view.newUser +import android.util.Log import androidx.compose.foundation.layout.Column import androidx.compose.runtime.Composable import androidx.compose.ui.Modifier @@ -8,7 +9,8 @@ import com.menagerie.ophelia.database.polycule.PolyculeDatabaseManager import com.menagerie.ophelia.view.OpheliaPronounsIntroduction @Composable -fun AddPronounsScreen() { +fun AddPronounsScreen( +) { Column { val name = PolyculeDatabaseManager.polyculeRepository.getBio(1).asLiveData().value?.name name?.let { diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index eb02842..c609d38 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -30,5 +30,6 @@ Your Name is how you\'ll be addressed in the app, and is the primary way you\'ll be referred to in polycules. But don\'t worry; your name, like everything about you, can be changed at any time! + "Nice to meet you, \ No newline at end of file -- 2.47.2 From 25a73f0970549c1d776984a5bb72cb4937afa02a Mon Sep 17 00:00:00 2001 From: Azea Date: Mon, 23 Oct 2023 00:16:10 -0400 Subject: [PATCH 06/20] Push --- .../database/polycule/PolyculeRepository.kt | 2 + .../entity/viewmodel/BioListViewModel.kt | 4 ++ .../ophelia/view/NewUserStartScreen.kt | 31 +++++++++------ .../com/menagerie/ophelia/view/Ophelia.kt | 10 +++-- .../com/menagerie/ophelia/view/PolyculeApp.kt | 2 +- .../view/biographies/BioDetailsScreen.kt | 2 + .../ophelia/view/newUser/AddNameScreen.kt | 34 ++++++++++++----- .../ophelia/view/newUser/AddPronounsScreen.kt | 38 ++++++++++++++++--- app/src/main/res/values/strings.xml | 14 ++++++- 9 files changed, 103 insertions(+), 34 deletions(-) diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt index ba2507b..31cd472 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt @@ -1,5 +1,6 @@ package com.menagerie.ophelia.database.polycule +import android.util.Log import com.menagerie.ophelia.database.polycule.entity.Bio import com.menagerie.ophelia.database.polycule.entity.BioDao import kotlinx.coroutines.flow.Flow @@ -16,6 +17,7 @@ class PolyculeRepository( } fun getBio(bioId: Int): Flow { + Log.d("Tawni", "") return bioDao.getBio(bioId) } diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt index 83e4ebc..e077c1c 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt @@ -23,6 +23,10 @@ class BioListViewModel() : ViewModel() { PolyculeDatabaseManager.polyculeRepository.delete(bio) } + fun fetch(id: Int) = viewModelScope.launch { + PolyculeDatabaseManager.polyculeRepository.getBio(id) + } + class BioListViewModelFactory() : ViewModelProvider.Factory { override fun create(modelClass: Class): T { diff --git a/app/src/main/java/com/menagerie/ophelia/view/NewUserStartScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/NewUserStartScreen.kt index f2db424..0ffd1ba 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/NewUserStartScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/NewUserStartScreen.kt @@ -1,8 +1,10 @@ package com.menagerie.ophelia.view +import android.annotation.SuppressLint import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.padding import androidx.compose.material3.Button +import androidx.compose.material3.Scaffold import androidx.compose.material3.Text import androidx.compose.runtime.Composable import androidx.compose.ui.Alignment @@ -10,24 +12,29 @@ import androidx.compose.ui.Modifier import androidx.compose.ui.tooling.preview.Preview import androidx.compose.ui.unit.dp +@SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") @Composable fun NewUserStartScreen( onGo: () -> Unit = {}, ) { - Column { - OpheliaFace(modifier = Modifier - .align(Alignment.CenterHorizontally) - .padding(top = 12.dp)) - OpheliaWelcome(modifier = Modifier.weight(1f)) - Button( - onClick = onGo, - modifier = Modifier - .padding(12.dp) - .align(Alignment.End) - ) { - Text(text = "Go") + Scaffold { + Column { + OpheliaFace( + modifier = Modifier + .align(Alignment.CenterHorizontally) + .padding(top = 12.dp) + ) + OpheliaWelcome(modifier = Modifier.weight(1f)) + Button( + onClick = onGo, + modifier = Modifier + .padding(12.dp) + .align(Alignment.End) + ) { + Text(text = "Go") + } } } } diff --git a/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt b/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt index 845a2ea..a8083d1 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt @@ -12,6 +12,7 @@ import androidx.compose.runtime.Composable import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.modifier.modifierLocalConsumer +import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.res.painterResource import androidx.compose.ui.res.stringArrayResource import androidx.compose.ui.res.stringResource @@ -46,6 +47,7 @@ fun OpheliaFace( contentDescription = OpheliaSays() ) } + @Composable fun OpheliaSaysArray( id: Int @@ -58,11 +60,11 @@ fun OpheliaSaysArray( } @Composable fun OpheliaSays( - id: Int + say: String ): AnnotatedString { return buildAnnotatedString { pushStyle(OpheliaSpanStyle()) - append(stringResource(id = id)) + append(say) toAnnotatedString() } } @@ -112,8 +114,8 @@ fun OpheliaPronounsIntroduction( .padding(12.dp) ) { Column { - Text(text = "${OpheliaSays(R.string.introduction_with_name)} $name!") - + val context = LocalContext.current + Text(text = OpheliaSays(context.resources.getString(R.string.introduction_with_name, name))) } } } diff --git a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt index f2ccd3d..44b89c2 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt @@ -35,7 +35,7 @@ fun PolyculeNavHost( val home = stringResource(id = R.string.route_home) NavHost( navController = navController, - startDestination = "newUserName" + startDestination = "home" ) { polyculeGraph(navController) welcomeGraph(navController) diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt index a047c17..23a919a 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt @@ -1,5 +1,6 @@ package com.menagerie.ophelia.view.biographies +import android.util.Log import androidx.compose.foundation.Image import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.Column @@ -79,6 +80,7 @@ fun BioDetailContents( Column { ConstraintLayout { val (image, info) = createRefs() + Log.d("Tawni" ,"${bio.id}") Image( painter = painterResource(id = bio.pfpRes), contentDescription = null, diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt index 9512417..1fa3b05 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt @@ -1,14 +1,17 @@ package com.menagerie.ophelia.view.newUser import android.annotation.SuppressLint -import android.util.Log import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Spacer import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.size +import androidx.compose.foundation.layout.width import androidx.compose.foundation.text.KeyboardActions import androidx.compose.material3.Button import androidx.compose.material3.ExperimentalMaterial3Api +import androidx.compose.material3.LinearProgressIndicator import androidx.compose.material3.Scaffold import androidx.compose.material3.Text import androidx.compose.runtime.Composable @@ -29,7 +32,6 @@ import com.menagerie.ophelia.view.OpheliaWhatsYourName import com.menagerie.ophelia.view.biographies.insertBioInDB import com.menagerie.ophelia.view.components.InputFieldComponent -@OptIn(ExperimentalMaterial3Api::class) @SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") @Composable fun AddNameScreen( @@ -39,17 +41,21 @@ fun AddNameScreen( val mBioListViewModel: BioListViewModel = viewModel( factory = BioListViewModel.BioListViewModelFactory() ) - - Scaffold() { + Scaffold { Column( modifier = Modifier.fillMaxSize() ) { val bio: Bio by inputViewModel.bio.observeAsState(Bio()) + OpheliaFace( modifier = Modifier .align(Alignment.CenterHorizontally) .padding(top = 12.dp) ) + LinearProgressIndicator( + progress = 0f, + modifier = Modifier.fillMaxWidth() + ) OpheliaWhatsYourName(modifier = Modifier) InputFieldState( inputViewModel, @@ -57,16 +63,24 @@ fun AddNameScreen( "name", "Ophelia", modifier = Modifier + .width(120.dp) + ) + Spacer( + modifier = Modifier + .fillMaxSize() + .weight(1f) + ) Button( - onClick = { - insertBioInDB(inputViewModel.bio.value, mBioListViewModel) - onGo(bio) } - ) { + modifier = Modifier + .align(Alignment.End), + onClick = { + insertBioInDB(inputViewModel.bio.value, mBioListViewModel) + onGo(bio) + } + ) { Text(text = "Continue") } - - } } } diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt index eb55b32..2af37c2 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt @@ -1,20 +1,46 @@ package com.menagerie.ophelia.view.newUser +import android.annotation.SuppressLint import android.util.Log import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.padding +import androidx.compose.material3.LinearProgressIndicator +import androidx.compose.material3.Scaffold import androidx.compose.runtime.Composable +import androidx.compose.runtime.livedata.observeAsState +import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier -import androidx.lifecycle.asLiveData -import com.menagerie.ophelia.database.polycule.PolyculeDatabaseManager +import androidx.compose.ui.unit.dp +import androidx.lifecycle.viewmodel.compose.viewModel +import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioDetailViewModel +import com.menagerie.ophelia.view.OpheliaFace import com.menagerie.ophelia.view.OpheliaPronounsIntroduction +@SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") @Composable fun AddPronounsScreen( ) { - Column { - val name = PolyculeDatabaseManager.polyculeRepository.getBio(1).asLiveData().value?.name - name?.let { - OpheliaPronounsIntroduction(modifier = Modifier, name = it) + val mBioDetailViewModel: BioDetailViewModel = viewModel( + ) + mBioDetailViewModel.setBio(bioId = 1) + + val bio = mBioDetailViewModel.bio.observeAsState().value + + Scaffold { + if (bio != null) { + Column { + OpheliaFace( + modifier = Modifier + .align(Alignment.CenterHorizontally) + .padding(top = 12.dp) + ) + LinearProgressIndicator( + progress = .33f, + modifier = Modifier.fillMaxWidth() + ) + OpheliaPronounsIntroduction(modifier = Modifier.weight(1f), name = bio.name) + } } } } \ No newline at end of file diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index c609d38..0a42c06 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -30,6 +30,18 @@ Your Name is how you\'ll be addressed in the app, and is the primary way you\'ll be referred to in polycules. But don\'t worry; your name, like everything about you, can be changed at any time! - "Nice to meet you, + "Nice to meet you,%1$s! + + + + + + + + + + + + \ No newline at end of file -- 2.47.2 From 1f3c59c4079ccf81bcc77706fce107f651b1ca88 Mon Sep 17 00:00:00 2001 From: Azea Date: Mon, 23 Oct 2023 22:07:47 -0400 Subject: [PATCH 07/20] Push --- app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt | 9 +++++---- .../menagerie/ophelia/view/newUser/AddPronounsScreen.kt | 7 +++++++ app/src/main/res/values/strings.xml | 9 ++++++++- 3 files changed, 20 insertions(+), 5 deletions(-) diff --git a/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt b/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt index a8083d1..32b37bf 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt @@ -39,8 +39,7 @@ fun OpheliaSpanStyle(): SpanStyle { @Composable fun OpheliaFace( modifier: Modifier -) -{ +) { Image( modifier = modifier, painter = painterResource(id = R.drawable.ophelia_foreground), @@ -50,11 +49,12 @@ fun OpheliaFace( @Composable fun OpheliaSaysArray( - id: Int + id: Int, + seperator: String = "\n\n" ): AnnotatedString { return buildAnnotatedString { pushStyle(OpheliaSpanStyle()) - append(stringArrayResource(id = id).joinToString(separator = "\n\n")) + append(stringArrayResource(id = id).joinToString(separator = seperator)) toAnnotatedString() } } @@ -116,6 +116,7 @@ fun OpheliaPronounsIntroduction( Column { val context = LocalContext.current Text(text = OpheliaSays(context.resources.getString(R.string.introduction_with_name, name))) + Text(text = OpheliaSaysArray(id = R.array.introduction_to_pronouns)) } } } diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt index 2af37c2..1b9b934 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt @@ -40,7 +40,14 @@ fun AddPronounsScreen( modifier = Modifier.fillMaxWidth() ) OpheliaPronounsIntroduction(modifier = Modifier.weight(1f), name = bio.name) + PronounBox() } } } +} + +@Composable +fun PronounBox() +{ + } \ No newline at end of file diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 0a42c06..73fce62 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -31,8 +31,15 @@ But don\'t worry; your name, like everything about you, can be changed at any time! "Nice to meet you,%1$s! + + Personal Pronouns are words used to refer to a person without always using their name. + Since Pronouns are a personal choice, I want to leave them as open as possible for you! + We\'re dealing with four Personal Pronouns, and using mine as an example: She (subjective) / Her (objective) / Hers (possessive) / Herself (reflexive) + Your Pronouns will be used when referring to you in specific contexts, and are displayed alongside your name in most contexts. + - + + -- 2.47.2 From c92e657038417f8e4ffe7c6fd0e2cb37a51f4e18 Mon Sep 17 00:00:00 2001 From: azea_laptop Date: Mon, 23 Oct 2023 23:14:11 -0400 Subject: [PATCH 08/20] Add edit --- .../com/menagerie/ophelia/view/PolyculeApp.kt | 2 +- .../ophelia/view/newUser/AddPronounsScreen.kt | 83 +++++++++++++++++-- 2 files changed, 78 insertions(+), 7 deletions(-) diff --git a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt index 44b89c2..fdb12e8 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt @@ -35,7 +35,7 @@ fun PolyculeNavHost( val home = stringResource(id = R.string.route_home) NavHost( navController = navController, - startDestination = "home" + startDestination = "newUserPronouns" ) { polyculeGraph(navController) welcomeGraph(navController) diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt index 1b9b934..5f9c583 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt @@ -1,14 +1,24 @@ package com.menagerie.ophelia.view.newUser import android.annotation.SuppressLint -import android.util.Log +import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.Spacer import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.size +import androidx.compose.material3.Button import androidx.compose.material3.LinearProgressIndicator +import androidx.compose.material3.MaterialTheme import androidx.compose.material3.Scaffold +import androidx.compose.material3.Text import androidx.compose.runtime.Composable +import androidx.compose.runtime.getValue import androidx.compose.runtime.livedata.observeAsState +import androidx.compose.runtime.mutableStateOf +import androidx.compose.runtime.remember +import androidx.compose.runtime.setValue import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.unit.dp @@ -21,8 +31,7 @@ import com.menagerie.ophelia.view.OpheliaPronounsIntroduction @Composable fun AddPronounsScreen( ) { - val mBioDetailViewModel: BioDetailViewModel = viewModel( - ) + val mBioDetailViewModel: BioDetailViewModel = viewModel() mBioDetailViewModel.setBio(bioId = 1) val bio = mBioDetailViewModel.bio.observeAsState().value @@ -40,14 +49,76 @@ fun AddPronounsScreen( modifier = Modifier.fillMaxWidth() ) OpheliaPronounsIntroduction(modifier = Modifier.weight(1f), name = bio.name) - PronounBox() + PronounBox(Modifier.weight(1f)) { + //TODO + } } } } } @Composable -fun PronounBox() -{ +fun PronounBox( + modifier: Modifier, + onClick: (List) -> Unit, +) { + var subject by remember { mutableStateOf("") } + var objec by remember { mutableStateOf("") } + var possess by remember { mutableStateOf("") } + var reflex by remember { mutableStateOf("") } + + Box(modifier = Modifier.fillMaxWidth()) + { + Column { +// val modifier = modifier +// .fillMaxWidth() + Row { + InputField( + text = subject, + label = "subjective", + placeholder = "she", + modifier = modifier, + onValChange = { subject = it }) + Text(text = " / ", + style = MaterialTheme.typography.displayMedium) + InputField( + text = objec, + label = "objective", + placeholder = "her", + modifier = modifier, + onValChange = { objec = it }) + } + Row { + InputField( + text = possess, + label = "possessive", + placeholder = "hers", + modifier = modifier, + onValChange = { possess = it }) + Text(text = " / ", + style = MaterialTheme.typography.displayMedium) + InputField( + text = reflex, + label = "reflexive", + placeholder = "herself", + modifier = modifier, + onValChange = { reflex = it }) + } + Spacer( + modifier = Modifier.size(60.dp) + ) + Button(onClick = { + onClick(listOf(subject, objec, possess, reflex)) + }, + modifier = Modifier + .align( + alignment = Alignment.End + ) + .padding(8.dp) + ) { + Text(text = "Continue") + } + } + } } \ No newline at end of file -- 2.47.2 From 70468fbb4be65d7f358e16aef2865020ffd51a76 Mon Sep 17 00:00:00 2001 From: Azea Date: Fri, 27 Oct 2023 23:57:55 -0400 Subject: [PATCH 09/20] tags screen --- .../database/polycule/PolyculeRepository.kt | 2 - .../entity/viewmodel/BioListViewModel.kt | 4 - .../ophelia/view/NewUserStartScreen.kt | 1 - .../com/menagerie/ophelia/view/Ophelia.kt | 19 +- .../com/menagerie/ophelia/view/PolyculeApp.kt | 41 ++-- .../ophelia/view/biographies/TagCard.kt | 85 ++++++++ .../ophelia/view/newUser/AddPronounsScreen.kt | 20 +- .../ophelia/view/newUser/AddTagsScreen.kt | 185 ++++++++++++++++++ app/src/main/res/drawable/asexual_tag.xml | 5 + app/src/main/res/drawable/bdsm_tag.xml | 7 + app/src/main/res/drawable/mono_tag.xml | 5 + app/src/main/res/drawable/plural_tag.xml | 9 + app/src/main/res/drawable/therian_tag.xml | 5 + app/src/main/res/drawable/trans_tag.xml | 5 + app/src/main/res/drawable/weed_tag.xml | 5 + app/src/main/res/values/strings.xml | 16 +- 16 files changed, 375 insertions(+), 39 deletions(-) create mode 100644 app/src/main/java/com/menagerie/ophelia/view/biographies/TagCard.kt create mode 100644 app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt create mode 100644 app/src/main/res/drawable/asexual_tag.xml create mode 100644 app/src/main/res/drawable/bdsm_tag.xml create mode 100644 app/src/main/res/drawable/mono_tag.xml create mode 100644 app/src/main/res/drawable/plural_tag.xml create mode 100644 app/src/main/res/drawable/therian_tag.xml create mode 100644 app/src/main/res/drawable/trans_tag.xml create mode 100644 app/src/main/res/drawable/weed_tag.xml diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt index 31cd472..ba2507b 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt @@ -1,6 +1,5 @@ package com.menagerie.ophelia.database.polycule -import android.util.Log import com.menagerie.ophelia.database.polycule.entity.Bio import com.menagerie.ophelia.database.polycule.entity.BioDao import kotlinx.coroutines.flow.Flow @@ -17,7 +16,6 @@ class PolyculeRepository( } fun getBio(bioId: Int): Flow { - Log.d("Tawni", "") return bioDao.getBio(bioId) } diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt index e077c1c..83e4ebc 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt @@ -23,10 +23,6 @@ class BioListViewModel() : ViewModel() { PolyculeDatabaseManager.polyculeRepository.delete(bio) } - fun fetch(id: Int) = viewModelScope.launch { - PolyculeDatabaseManager.polyculeRepository.getBio(id) - } - class BioListViewModelFactory() : ViewModelProvider.Factory { override fun create(modelClass: Class): T { diff --git a/app/src/main/java/com/menagerie/ophelia/view/NewUserStartScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/NewUserStartScreen.kt index 0ffd1ba..05e40ef 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/NewUserStartScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/NewUserStartScreen.kt @@ -33,7 +33,6 @@ fun NewUserStartScreen( .align(Alignment.End) ) { Text(text = "Go") - } } } diff --git a/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt b/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt index 32b37bf..ac24503 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt @@ -50,11 +50,11 @@ fun OpheliaFace( @Composable fun OpheliaSaysArray( id: Int, - seperator: String = "\n\n" + separator: String = "\n\n" ): AnnotatedString { return buildAnnotatedString { pushStyle(OpheliaSpanStyle()) - append(stringArrayResource(id = id).joinToString(separator = seperator)) + append(stringArrayResource(id = id).joinToString(separator = separator)) toAnnotatedString() } } @@ -120,3 +120,18 @@ fun OpheliaPronounsIntroduction( } } } + +@Composable +fun OpheliaTagsIntroduction( + modifier: Modifier, +) { + Box( + modifier = modifier + .fillMaxWidth() + .padding(12.dp) + ) { + Column { + Text(text = OpheliaSaysArray(R.array.introduction_to_tags)) + } + } +} diff --git a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt index fdb12e8..6d5f641 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt @@ -1,8 +1,6 @@ package com.menagerie.ophelia.view import androidx.compose.runtime.Composable -import androidx.compose.ui.res.stringResource -import androidx.lifecycle.viewmodel.compose.viewModel import androidx.navigation.NavController import androidx.navigation.NavGraphBuilder import androidx.navigation.NavHostController @@ -11,13 +9,12 @@ import androidx.navigation.compose.NavHost import androidx.navigation.compose.composable import androidx.navigation.compose.rememberNavController import androidx.navigation.navArgument -import com.menagerie.ophelia.R import com.menagerie.ophelia.database.polycule.PolyculeDatabaseManager -import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioListViewModel import com.menagerie.ophelia.view.biographies.AddBiography import com.menagerie.ophelia.view.biographies.BioDetailsScreen import com.menagerie.ophelia.view.newUser.AddNameScreen import com.menagerie.ophelia.view.newUser.AddPronounsScreen +import com.menagerie.ophelia.view.newUser.AddTagsScreen import com.menagerie.ophelia.view.polycule.PolyculeHomeView @Composable @@ -32,14 +29,13 @@ fun PolyculeApp() { fun PolyculeNavHost( navController: NavHostController ) { - val home = stringResource(id = R.string.route_home) NavHost( navController = navController, - startDestination = "newUserPronouns" + startDestination = "newUserTags" ) { polyculeGraph(navController) welcomeGraph(navController) - composable(home) { + composable("home") { HomeScreen(!PolyculeDatabaseManager.hasPolycule()) { navController.navigate("newUserStart") } @@ -49,14 +45,31 @@ fun PolyculeNavHost( } fun NavGraphBuilder.welcomeGraph(navController: NavHostController) { - composable("newUserStart") { NewUserStartScreen(){ - navController.navigate("newUserName") - } } - composable("newUserName") { AddNameScreen( - onGo={ navController.navigate("newUserPronouns")} - )} + composable("newUserStart") { + NewUserStartScreen() { + navController.navigate("newUserName") + } + } + composable("newUserName") { + AddNameScreen( + onGo = { + navController.navigate("newUserPronouns") + } + ) + } composable("newUserPronouns") { - AddPronounsScreen() + AddPronounsScreen( + onGo = { + navController.navigate("newUserTags") + } + ) + } + composable("newUserTags") { + AddTagsScreen( + onGo = { + navController.navigate("") + } + ) } } diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/TagCard.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/TagCard.kt new file mode 100644 index 0000000..4e6ad21 --- /dev/null +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/TagCard.kt @@ -0,0 +1,85 @@ +package com.menagerie.ophelia.view.biographies + +import android.util.Log +import androidx.compose.foundation.BorderStroke +import androidx.compose.foundation.Image +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.size +import androidx.compose.foundation.layout.wrapContentHeight +import androidx.compose.material3.Card +import androidx.compose.material3.CardDefaults +import androidx.compose.material3.ExperimentalMaterial3Api +import androidx.compose.material3.MaterialTheme +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.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.graphics.Color +import androidx.compose.ui.graphics.painter.Painter +import androidx.compose.ui.layout.ContentScale +import androidx.compose.ui.unit.dp + +@OptIn(ExperimentalMaterial3Api::class) +@Composable +fun TagCard( + name: String, + painter: Painter, + details: String, + check: Boolean, + onClick: () -> Unit +) { + var checked by remember { mutableStateOf(check) } + + Card( + modifier = Modifier + .padding(8.dp) + .fillMaxWidth() + .wrapContentHeight(), + shape = MaterialTheme.shapes.medium, + elevation = CardDefaults.cardElevation( + defaultElevation = 6.dp + ), + colors = CardDefaults.cardColors( + containerColor = + if (checked) MaterialTheme.colorScheme.primaryContainer + else MaterialTheme.colorScheme.surface + ), + border = BorderStroke(1.dp, Color.Black), + onClick = { + checked = !checked + onClick() + }, + ) { + Row( + verticalAlignment = Alignment.CenterVertically, + ) { + Image( + painter = painter, + contentDescription = null, + modifier = Modifier + .size(80.dp) + .padding(8.dp), + contentScale = ContentScale.Fit, + ) + Column(modifier = Modifier.padding(8.dp)) { + Text( + text = name, + style = MaterialTheme.typography.headlineSmall, + color = MaterialTheme.colorScheme.onSurface, + ) + Text( + text = details, + style = MaterialTheme.typography.headlineSmall, + color = MaterialTheme.colorScheme.onSurface, + ) + } + } + } +} \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt index 5f9c583..67b8154 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt @@ -23,16 +23,23 @@ import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.unit.dp import androidx.lifecycle.viewmodel.compose.viewModel +import com.menagerie.ophelia.database.polycule.PolyculeDatabaseManager +import com.menagerie.ophelia.database.polycule.entity.Bio import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioDetailViewModel +import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioListViewModel import com.menagerie.ophelia.view.OpheliaFace import com.menagerie.ophelia.view.OpheliaPronounsIntroduction @SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") @Composable fun AddPronounsScreen( + onGo : () -> Unit ) { val mBioDetailViewModel: BioDetailViewModel = viewModel() mBioDetailViewModel.setBio(bioId = 1) + val mBioListViewModel: BioListViewModel = viewModel( + factory = BioListViewModel.BioListViewModelFactory() + ) val bio = mBioDetailViewModel.bio.observeAsState().value @@ -50,7 +57,16 @@ fun AddPronounsScreen( ) OpheliaPronounsIntroduction(modifier = Modifier.weight(1f), name = bio.name) PronounBox(Modifier.weight(1f)) { - //TODO + val updateBio = Bio( + id = bio.id, + name = bio.name, + subjective = it[0], + objective = it[1], + possessive = it[2], + reflexive = it[3], + ) + mBioListViewModel.upsert(updateBio) + onGo() } } } @@ -71,8 +87,6 @@ fun PronounBox( Box(modifier = Modifier.fillMaxWidth()) { Column { -// val modifier = modifier -// .fillMaxWidth() Row { InputField( text = subject, diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt new file mode 100644 index 0000000..8504d7d --- /dev/null +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt @@ -0,0 +1,185 @@ +package com.menagerie.ophelia.view.newUser + +import android.annotation.SuppressLint +import android.util.Log +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.lazy.LazyColumn +import androidx.compose.material3.Button +import androidx.compose.material3.LinearProgressIndicator +import androidx.compose.material3.Scaffold +import androidx.compose.material3.Text +import androidx.compose.runtime.Composable +import androidx.compose.runtime.getValue +import androidx.compose.runtime.mutableIntStateOf +import androidx.compose.runtime.remember +import androidx.compose.runtime.setValue +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.res.painterResource +import androidx.compose.ui.unit.dp +import androidx.lifecycle.viewmodel.compose.viewModel +import com.menagerie.ophelia.R +import com.menagerie.ophelia.database.polycule.entity.Bio +import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioListViewModel +import com.menagerie.ophelia.view.OpheliaFace +import com.menagerie.ophelia.view.OpheliaTagsIntroduction +import com.menagerie.ophelia.view.biographies.TagCard + +enum class Tags(val value: Int) +{ + TRANS(1), + FURRY(2), + ASEXUAL(4), + BDSM(8), + MONO(16), + ALCOHOL(32), + WEED(64), + THERIAN(128), + PLURAL(256), +} + +@SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") +@Composable +fun AddTagsScreen( + onGo : () -> Unit +) { + Scaffold { + Column { + OpheliaFace( + modifier = Modifier + .align(Alignment.CenterHorizontally) + .padding(top = 12.dp) + ) + LinearProgressIndicator( + progress = .66f, + modifier = Modifier.fillMaxWidth() + ) + OpheliaTagsIntroduction(modifier = Modifier.weight(1f)) + MakeDefaultTagCards(modifier = Modifier.weight(2f)) + Button( + onClick = onGo, + modifier = Modifier + .weight(.25f) + .align(Alignment.End)) { + Text(text = "Continue") + } + } + } +} + +@Composable +fun MakeDefaultTagCards( + modifier: Modifier, +) { + var flags by remember { mutableIntStateOf(0) } + + val mBioListViewModel: BioListViewModel = viewModel( + factory = BioListViewModel.BioListViewModelFactory() + ) + + Box(modifier = modifier){ + LazyColumn { + item { + TagCard( + name = "Transgender", + painter = painterResource(id = R.drawable.trans_tag), + details = "", + check = flags and Tags.TRANS.value == Tags.TRANS.value + ) { + flags = flags xor Tags.TRANS.value + } + } + item { + TagCard( + name = "Furry", + painter = painterResource(id = R.drawable.furry_tag), + details = "", + check = flags and Tags.FURRY.value == Tags.FURRY.value + ) { + flags = flags xor Tags.FURRY.value + Log.d("Tawni", flags.toString()) + } + } + item { + TagCard( + name = "Therian", + painter = painterResource(id = R.drawable.therian_tag), + details = "", + check = flags and Tags.THERIAN.value == Tags.THERIAN.value + ) { + flags = flags xor Tags.THERIAN.value + Log.d("Tawni", flags.toString()) + } + } + item { + TagCard( + name = "Monogamous", + painter = painterResource(id = R.drawable.mono_tag), + details = "", + check = flags and Tags.MONO.value == Tags.MONO.value + ){ + flags = flags xor Tags.MONO.value + Log.d("Tawni", flags.toString()) + } + } + item { + TagCard( + name = "BDSM", + painter = painterResource(id = R.drawable.bdsm_tag), + details = "", + check = flags and Tags.BDSM.value == Tags.BDSM.value + ) { + flags = flags xor Tags.BDSM.value + Log.d("Tawni", flags.toString()) + } + } + item { + TagCard( + name = "Plural", + painter = painterResource(id = R.drawable.plural_tag), + details = "", + check = flags and Tags.PLURAL.value == Tags.PLURAL.value + ) { + flags = flags xor Tags.PLURAL.value + Log.d("Tawni", flags.toString()) + } + } + item { + TagCard( + name = "Asexual", + painter = painterResource(id = R.drawable.asexual_tag), + details = "", + check = flags and Tags.ASEXUAL.value == Tags.ASEXUAL.value + ) { + flags = flags xor Tags.ASEXUAL.value + Log.d("Tawni", flags.toString()) + } + } + item { + TagCard( + name = "Alcohol", + painter = painterResource(id = R.drawable.liqour_tag), + details = "", + check = flags and Tags.ALCOHOL.value == Tags.ALCOHOL.value + ) { + flags = flags xor Tags.ALCOHOL.value + Log.d("Tawni", flags.toString()) + } + } + item { + TagCard( + name = "Weed", + painter = painterResource(id = R.drawable.weed_tag), + details = "", + check = flags and Tags.WEED.value == Tags.WEED.value + ) { + flags = flags xor Tags.WEED.value + Log.d("Tawni", flags.toString()) + } + } + } + } +} \ No newline at end of file diff --git a/app/src/main/res/drawable/asexual_tag.xml b/app/src/main/res/drawable/asexual_tag.xml new file mode 100644 index 0000000..ef6bfa4 --- /dev/null +++ b/app/src/main/res/drawable/asexual_tag.xml @@ -0,0 +1,5 @@ + + + diff --git a/app/src/main/res/drawable/bdsm_tag.xml b/app/src/main/res/drawable/bdsm_tag.xml new file mode 100644 index 0000000..f059ad3 --- /dev/null +++ b/app/src/main/res/drawable/bdsm_tag.xml @@ -0,0 +1,7 @@ + + + + + diff --git a/app/src/main/res/drawable/mono_tag.xml b/app/src/main/res/drawable/mono_tag.xml new file mode 100644 index 0000000..0a14708 --- /dev/null +++ b/app/src/main/res/drawable/mono_tag.xml @@ -0,0 +1,5 @@ + + + diff --git a/app/src/main/res/drawable/plural_tag.xml b/app/src/main/res/drawable/plural_tag.xml new file mode 100644 index 0000000..8038fe7 --- /dev/null +++ b/app/src/main/res/drawable/plural_tag.xml @@ -0,0 +1,9 @@ + + + + + + + diff --git a/app/src/main/res/drawable/therian_tag.xml b/app/src/main/res/drawable/therian_tag.xml new file mode 100644 index 0000000..d96049f --- /dev/null +++ b/app/src/main/res/drawable/therian_tag.xml @@ -0,0 +1,5 @@ + + + diff --git a/app/src/main/res/drawable/trans_tag.xml b/app/src/main/res/drawable/trans_tag.xml new file mode 100644 index 0000000..7e45dca --- /dev/null +++ b/app/src/main/res/drawable/trans_tag.xml @@ -0,0 +1,5 @@ + + + diff --git a/app/src/main/res/drawable/weed_tag.xml b/app/src/main/res/drawable/weed_tag.xml new file mode 100644 index 0000000..23ead7b --- /dev/null +++ b/app/src/main/res/drawable/weed_tag.xml @@ -0,0 +1,5 @@ + + + diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 73fce62..ac8794a 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -37,18 +37,8 @@ We\'re dealing with four Personal Pronouns, and using mine as an example: She (subjective) / Her (objective) / Hers (possessive) / Herself (reflexive) Your Pronouns will be used when referring to you in specific contexts, and are displayed alongside your name in most contexts. - - - + + Tags are a way to highlight important things about yourself. + They also lead to more detailed parts of you bio, where you can flesh out specific parts of your bio. - - - - - - - - - - \ No newline at end of file -- 2.47.2 From 1b43a34586ca804b92563021cd8f8b9ba5b08e04 Mon Sep 17 00:00:00 2001 From: Azea Date: Sat, 28 Oct 2023 15:21:20 -0400 Subject: [PATCH 10/20] Tags Added --- .../entity/viewmodel/BioDetailViewModel.kt | 36 +++++------ .../entity/viewmodel/BioListViewModel.kt | 5 ++ .../view/biographies/AddEditBiography.kt | 61 ++++++++++++++----- .../ophelia/view/biographies/TagCard.kt | 11 ++-- .../ophelia/view/newUser/AddTagsScreen.kt | 1 + app/src/main/res/drawable/furry_tag.xml | 9 +++ app/src/main/res/drawable/liqour_tag.xml | 6 ++ app/src/main/res/values/strings.xml | 11 ++++ 8 files changed, 104 insertions(+), 36 deletions(-) create mode 100644 app/src/main/res/drawable/furry_tag.xml create mode 100644 app/src/main/res/drawable/liqour_tag.xml diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioDetailViewModel.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioDetailViewModel.kt index 6f17c45..932fc7e 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioDetailViewModel.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioDetailViewModel.kt @@ -5,24 +5,26 @@ import androidx.lifecycle.ViewModelProvider import androidx.lifecycle.asLiveData import com.menagerie.ophelia.database.polycule.PolyculeDatabaseManager -class BioDetailViewModel() : ViewModel() { +class BioDetailViewModel( + id: Int +) : ViewModel() { - private var bioId: Int = 0 - var bio = PolyculeDatabaseManager.polyculeRepository.getBio(bioId).asLiveData() + //private var bioId: Int = 0 + var bio = PolyculeDatabaseManager.polyculeRepository.getBio(id).asLiveData() - fun setBio(bioId: Int) { - this.bioId = bioId - bio = PolyculeDatabaseManager.polyculeRepository.getBio(bioId).asLiveData() - } +// fun setBio(bioId: Int) { +// this.bioId = bioId +// bio = PolyculeDatabaseManager.polyculeRepository.getBio(bioId).asLiveData() +// } - class BioDetailViewModelFactory() : - ViewModelProvider.Factory { - override fun create(modelClass: Class, ): T { - if (modelClass.isAssignableFrom(BioDetailViewModel::class.java)) { - @Suppress("UNCHECKED_CAST") - return BioDetailViewModel() as T - } - throw IllegalArgumentException("Unknown ViewModel Class") - } - } +// class BioDetailViewModelFactory() : +// ViewModelProvider.Factory { +// override fun create(modelClass: Class, ): T { +// if (modelClass.isAssignableFrom(BioDetailViewModel::class.java)) { +// @Suppress("UNCHECKED_CAST") +// return BioDetailViewModel() as T +// } +// throw IllegalArgumentException("Unknown ViewModel Class") +// } +// } } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt index 83e4ebc..62a6a24 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt @@ -7,6 +7,7 @@ import androidx.lifecycle.asLiveData import androidx.lifecycle.viewModelScope import com.menagerie.ophelia.database.polycule.PolyculeDatabaseManager import com.menagerie.ophelia.database.polycule.entity.Bio +import com.menagerie.ophelia.view.PolyculeNavHost import kotlinx.coroutines.launch @@ -23,6 +24,10 @@ class BioListViewModel() : ViewModel() { PolyculeDatabaseManager.polyculeRepository.delete(bio) } + fun fetch(bioId: Int) = viewModelScope.launch{ + PolyculeDatabaseManager.polyculeRepository.getBio(bioId = bioId).asLiveData() + } + class BioListViewModelFactory() : ViewModelProvider.Factory { override fun create(modelClass: Class): T { diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt index 0521256..7f17adb 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt @@ -58,14 +58,39 @@ fun AddBiography() { val modifier = Modifier.width(120.dp) val bio: Bio by inputViewModel.bio.observeAsState(Bio()) - InputFieldState(inputViewModel, bio.name, "name", "Ophelia", modifier = Modifier) //Name + InputFieldState( + bio.name, + "name", + "Ophelia", + modifier = Modifier + ) { inputViewModel.onNameChange(it) } //Name Row { - InputFieldState(inputViewModel, bio.subjective,"", "she", modifier) - InputFieldState(inputViewModel, bio.objective, "", "her", modifier) + InputFieldState( + bio.subjective, + "", + "she", + modifier + ) { inputViewModel.onSubjectChange(it) } + InputFieldState( + bio.objective, + "", + "her", + modifier + ) { inputViewModel.onPossessChange(it) } } Row { - InputFieldState(inputViewModel, bio.possessive,"", "hers", modifier) - InputFieldState(inputViewModel, bio.reflexive, "","herself", modifier) + InputFieldState( + bio.possessive, + "", + "hers", + modifier + ) { inputViewModel.onObjectChange(it) } + InputFieldState( + bio.reflexive, + "", + "herself", + modifier + ) { inputViewModel.onReflexChange(it) } } } @@ -74,17 +99,17 @@ fun AddBiography() { @Composable fun InputFieldState( - inputViewModel: InputViewModel, value: String, label: String, placeholder: String, - modifier: Modifier + modifier: Modifier, + onVal: (String) -> Unit ) { Column( modifier = Modifier ) { - InputField(value, label, placeholder, modifier) { inputViewModel.onInputChange(it) } + InputField(value, label, placeholder, modifier, onValChange = onVal) Spacer(modifier = Modifier.padding(10.dp)) } } @@ -114,12 +139,20 @@ fun InputField( class InputViewModel : ViewModel() { private val _bio: MutableLiveData = MutableLiveData(Bio()) val bio: LiveData = _bio - fun onInputChange(name: String) { - Log.d("Tawni", name) - val newBio = Bio( - name = name, - ) - _bio.value = newBio + fun onNameChange(name: String) { + bio.value?.name ?: name + } + fun onSubjectChange(subjective: String) { + bio.value?.subjective ?: subjective + } + fun onObjectChange(objective: String) { + bio.value?.objective ?: objective + } + fun onPossessChange(possessive: String) { + bio.value?.possessive ?: possessive + } + fun onReflexChange(reflexive: String) { + bio.value?.reflexive ?: reflexive } } diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/TagCard.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/TagCard.kt index 4e6ad21..92a4079 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/TagCard.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/TagCard.kt @@ -74,11 +74,12 @@ fun TagCard( style = MaterialTheme.typography.headlineSmall, color = MaterialTheme.colorScheme.onSurface, ) - Text( - text = details, - style = MaterialTheme.typography.headlineSmall, - color = MaterialTheme.colorScheme.onSurface, - ) + //TODO: details blurbs +// Text( +// text = details, +// style = MaterialTheme.typography.headlineSmall, +// color = MaterialTheme.colorScheme.onSurface, +// ) } } } diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt index 8504d7d..41db16b 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt @@ -80,6 +80,7 @@ fun MakeDefaultTagCards( factory = BioListViewModel.BioListViewModelFactory() ) + Box(modifier = modifier){ LazyColumn { item { diff --git a/app/src/main/res/drawable/furry_tag.xml b/app/src/main/res/drawable/furry_tag.xml new file mode 100644 index 0000000..df83859 --- /dev/null +++ b/app/src/main/res/drawable/furry_tag.xml @@ -0,0 +1,9 @@ + + + + + + + diff --git a/app/src/main/res/drawable/liqour_tag.xml b/app/src/main/res/drawable/liqour_tag.xml new file mode 100644 index 0000000..086654f --- /dev/null +++ b/app/src/main/res/drawable/liqour_tag.xml @@ -0,0 +1,6 @@ + + + + diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index ac8794a..c012dfc 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -16,6 +16,17 @@ Open context menu Name + ##Tags + Monogamous + Plural + Furry + Therian + BDSM + Alcohol + Weed + Asexual + Transgender + ##Ophelia Ophelia Says -- 2.47.2 From 05822226af1180279e0ac3780dc174e9b0187d72 Mon Sep 17 00:00:00 2001 From: Azea Date: Sat, 28 Oct 2023 17:33:06 -0400 Subject: [PATCH 11/20] fuck that took way too long --- .../entity/viewmodel/BioDetailViewModel.kt | 18 --- .../entity/viewmodel/BioListViewModel.kt | 4 +- .../com/menagerie/ophelia/view/PolyculeApp.kt | 15 ++- .../{AddEditBiography.kt => AddBiography.kt} | 4 +- .../view/biographies/BioDetailsScreen.kt | 7 +- .../ophelia/view/biographies/EditBiography.kt | 122 ++++++++++++++++++ .../view/components/InputFieldComponent.kt | 2 +- .../ophelia/view/newUser/AddPronounsScreen.kt | 3 +- .../ophelia/view/newUser/AddTagsScreen.kt | 5 +- 9 files changed, 143 insertions(+), 37 deletions(-) rename app/src/main/java/com/menagerie/ophelia/view/biographies/{AddEditBiography.kt => AddBiography.kt} (98%) create mode 100644 app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioDetailViewModel.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioDetailViewModel.kt index 932fc7e..35d20af 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioDetailViewModel.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioDetailViewModel.kt @@ -8,23 +8,5 @@ import com.menagerie.ophelia.database.polycule.PolyculeDatabaseManager class BioDetailViewModel( id: Int ) : ViewModel() { - - //private var bioId: Int = 0 var bio = PolyculeDatabaseManager.polyculeRepository.getBio(id).asLiveData() - -// fun setBio(bioId: Int) { -// this.bioId = bioId -// bio = PolyculeDatabaseManager.polyculeRepository.getBio(bioId).asLiveData() -// } - -// class BioDetailViewModelFactory() : -// ViewModelProvider.Factory { -// override fun create(modelClass: Class, ): T { -// if (modelClass.isAssignableFrom(BioDetailViewModel::class.java)) { -// @Suppress("UNCHECKED_CAST") -// return BioDetailViewModel() as T -// } -// throw IllegalArgumentException("Unknown ViewModel Class") -// } -// } } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt index 62a6a24..471a360 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt @@ -24,9 +24,7 @@ class BioListViewModel() : ViewModel() { PolyculeDatabaseManager.polyculeRepository.delete(bio) } - fun fetch(bioId: Int) = viewModelScope.launch{ - PolyculeDatabaseManager.polyculeRepository.getBio(bioId = bioId).asLiveData() - } + fun fetch(bioId: Int) = PolyculeDatabaseManager.polyculeRepository.getBio(bioId = bioId).asLiveData() class BioListViewModelFactory() : ViewModelProvider.Factory { diff --git a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt index 6d5f641..8334daf 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt @@ -1,7 +1,9 @@ package com.menagerie.ophelia.view +import android.util.Log import androidx.compose.runtime.Composable import androidx.navigation.NavController +import androidx.navigation.NavDirections import androidx.navigation.NavGraphBuilder import androidx.navigation.NavHostController import androidx.navigation.NavType @@ -12,6 +14,7 @@ import androidx.navigation.navArgument import com.menagerie.ophelia.database.polycule.PolyculeDatabaseManager import com.menagerie.ophelia.view.biographies.AddBiography import com.menagerie.ophelia.view.biographies.BioDetailsScreen +import com.menagerie.ophelia.view.biographies.EditBiography import com.menagerie.ophelia.view.newUser.AddNameScreen import com.menagerie.ophelia.view.newUser.AddPronounsScreen import com.menagerie.ophelia.view.newUser.AddTagsScreen @@ -67,7 +70,7 @@ fun NavGraphBuilder.welcomeGraph(navController: NavHostController) { composable("newUserTags") { AddTagsScreen( onGo = { - navController.navigate("") + navController.navigate("editBio/${it}") } ) } @@ -80,7 +83,7 @@ fun NavGraphBuilder.polyculeGraph(navController: NavController) { navController.navigate("bioDetail/${it.id}") }, onAddClick = { - navController.navigate("addBio"){} + navController.navigate("addBio") {} } ) } @@ -98,4 +101,12 @@ fun NavGraphBuilder.polyculeGraph(navController: NavController) { composable("addBio") { AddBiography() } + composable( + "editBio/{bioId}", + arguments = listOf(navArgument("bioId") { type = NavType.IntType }) + ) { + EditBiography( + bioId = it.arguments?.getInt("bioId") ?: 0 + ) + } } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddBiography.kt similarity index 98% rename from app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt rename to app/src/main/java/com/menagerie/ophelia/view/biographies/AddBiography.kt index 7f17adb..df3b8b0 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBiography.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddBiography.kt @@ -1,7 +1,6 @@ package com.menagerie.ophelia.view.biographies import android.annotation.SuppressLint -import android.util.Log import android.widget.Toast import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Row @@ -92,7 +91,6 @@ fun AddBiography() { modifier ) { inputViewModel.onReflexChange(it) } } - } } } @@ -136,7 +134,7 @@ fun InputField( } } -class InputViewModel : ViewModel() { +class InputViewModel() : ViewModel() { private val _bio: MutableLiveData = MutableLiveData(Bio()) val bio: LiveData = _bio fun onNameChange(name: String) { diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt index 23a919a..ba71d24 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt @@ -20,7 +20,6 @@ import androidx.compose.ui.res.painterResource import androidx.compose.ui.unit.Dp import androidx.compose.ui.unit.dp import androidx.constraintlayout.compose.ConstraintLayout -import androidx.lifecycle.viewmodel.compose.viewModel import com.menagerie.ophelia.database.polycule.entity.Bio import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioDetailViewModel import com.menagerie.ophelia.view.components.utils.Dimens @@ -34,10 +33,7 @@ fun BioDetailsScreen( id: Int, onBackClick: () -> Unit, ) { - val mBioDetailViewModel: BioDetailViewModel = viewModel( - ) - - mBioDetailViewModel.setBio(bioId = id) + val mBioDetailViewModel = BioDetailViewModel(id) val bio = mBioDetailViewModel.bio.observeAsState().value @@ -80,7 +76,6 @@ fun BioDetailContents( Column { ConstraintLayout { val (image, info) = createRefs() - Log.d("Tawni" ,"${bio.id}") Image( painter = painterResource(id = bio.pfpRes), contentDescription = null, diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt new file mode 100644 index 0000000..b4898d9 --- /dev/null +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt @@ -0,0 +1,122 @@ +package com.menagerie.ophelia.view.biographies + +import android.annotation.SuppressLint +import android.util.Log +import android.widget.Toast +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.width +import androidx.compose.material3.Scaffold +import androidx.compose.runtime.Composable +import androidx.compose.runtime.getValue +import androidx.compose.runtime.livedata.observeAsState +import androidx.compose.runtime.mutableStateOf +import androidx.compose.runtime.remember +import androidx.compose.runtime.setValue +import androidx.compose.ui.Modifier +import androidx.compose.ui.platform.LocalContext +import androidx.compose.ui.res.stringResource +import androidx.compose.ui.unit.dp +import androidx.lifecycle.LiveData +import androidx.lifecycle.MutableLiveData +import androidx.lifecycle.ViewModel +import androidx.lifecycle.viewmodel.compose.viewModel +import com.menagerie.ophelia.R +import com.menagerie.ophelia.database.polycule.entity.Bio +import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioDetailViewModel +import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioListViewModel +import com.menagerie.ophelia.view.components.fab.FABComponent + + +@SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") +@Composable +fun EditBiography( + bioId : Int +) { + Log.d("Tawni", bioId.toString()) + + val context = LocalContext.current + val mBioListViewModel: BioListViewModel = viewModel( + factory = BioListViewModel.BioListViewModelFactory() + ) + + val mBioDetailViewModel = BioDetailViewModel(bioId) + + val bio = mBioDetailViewModel.bio.observeAsState().value + + if (bio != null) { + val inputViewModel = InputEditViewModel(bio) + val ioBio: Bio by inputViewModel.bio.observeAsState(bio) + var name by remember { mutableStateOf(ioBio.name) } + var sp by remember { mutableStateOf(ioBio.subjective) } + var op by remember { mutableStateOf(ioBio.objective) } + var pp by remember { mutableStateOf(ioBio.possessive) } + var rp by remember { mutableStateOf(ioBio.reflexive) } + + Scaffold( + floatingActionButton = { + FABComponent(text = "${stringResource(id = R.string.edit_bio)}", onClick = { + + insertBioInDB( + Bio( + id = bio.id, + name = name, + subjective = sp, + objective = op, + possessive = pp, + reflexive = rp + ), + mBioListViewModel + ) + + Toast.makeText(context, "Added Bio", Toast.LENGTH_SHORT).show() + }) + } + ) + { + Column { + val modifier = Modifier.width(120.dp) + InputFieldState( + name, + "name", + "Ophelia", + modifier = Modifier + ) { name = it } //Name + Row { + InputFieldState( + sp, + "", + "she", + modifier + ) { sp = it } + InputFieldState( + op, + "", + "her", + modifier + ) { op = it } + } + Row { + InputFieldState( + pp, + "", + "hers", + modifier + ) { pp = it } + InputFieldState( + rp, + "", + "herself", + modifier + ) { rp = it } + } + } + } + } +} +class InputEditViewModel( + bio: Bio +) : ViewModel() { + private val _bio: MutableLiveData = MutableLiveData(bio) + val bio: LiveData = _bio +} \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt b/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt index f17d59e..ab8211a 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt @@ -31,7 +31,7 @@ fun InputFieldComponent( value = text, onValueChange = onChange, label = { Text(text = label)}, - placeholder = { Text(text = placeHolder)}, + //placeholder = { Text(text = placeHolder)}, modifier = modifier, singleLine = singleLine, ) diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt index 67b8154..c3e5e29 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt @@ -35,8 +35,7 @@ import com.menagerie.ophelia.view.OpheliaPronounsIntroduction fun AddPronounsScreen( onGo : () -> Unit ) { - val mBioDetailViewModel: BioDetailViewModel = viewModel() - mBioDetailViewModel.setBio(bioId = 1) + val mBioDetailViewModel = BioDetailViewModel(1) val mBioListViewModel: BioListViewModel = viewModel( factory = BioListViewModel.BioListViewModelFactory() ) diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt index 41db16b..843ea46 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt @@ -44,7 +44,7 @@ enum class Tags(val value: Int) @SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") @Composable fun AddTagsScreen( - onGo : () -> Unit + onGo : (Int) -> Unit ) { Scaffold { Column { @@ -60,7 +60,7 @@ fun AddTagsScreen( OpheliaTagsIntroduction(modifier = Modifier.weight(1f)) MakeDefaultTagCards(modifier = Modifier.weight(2f)) Button( - onClick = onGo, + onClick = { onGo(1) }, modifier = Modifier .weight(.25f) .align(Alignment.End)) { @@ -81,6 +81,7 @@ fun MakeDefaultTagCards( ) + Box(modifier = modifier){ LazyColumn { item { -- 2.47.2 From 0dadceb1b87aa70e3bd1e35a6224768ecdb642b0 Mon Sep 17 00:00:00 2001 From: Azea Date: Sat, 28 Oct 2023 18:01:34 -0400 Subject: [PATCH 12/20] working on it --- .../com/menagerie/ophelia/view/Ophelia.kt | 15 +++ .../com/menagerie/ophelia/view/PolyculeApp.kt | 11 +- .../ophelia/view/biographies/EditBiography.kt | 101 ++++++++++++------ .../ophelia/view/newUser/AddTagsScreen.kt | 4 +- app/src/main/res/values/strings.xml | 1 + 5 files changed, 94 insertions(+), 38 deletions(-) diff --git a/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt b/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt index ac24503..86e3ccb 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt @@ -135,3 +135,18 @@ fun OpheliaTagsIntroduction( } } } + +@Composable +fun OpheliaNewUserFinalCheck( + modifier: Modifier, +){ + Box( + modifier = modifier + .fillMaxWidth() + .padding(12.dp) + ) { + Column { + Text(text = OpheliaSays(stringResource(id = R.string.final_check_in))) + } + } +} diff --git a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt index 8334daf..4c7025e 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt @@ -69,8 +69,8 @@ fun NavGraphBuilder.welcomeGraph(navController: NavHostController) { } composable("newUserTags") { AddTagsScreen( - onGo = { - navController.navigate("editBio/${it}") + onGo = { id, new -> + navController.navigate("editBio/${id}/${new}") } ) } @@ -102,11 +102,12 @@ fun NavGraphBuilder.polyculeGraph(navController: NavController) { AddBiography() } composable( - "editBio/{bioId}", - arguments = listOf(navArgument("bioId") { type = NavType.IntType }) + "editBio/{bioId}/{new}", + arguments = listOf(navArgument("bioId") { type = NavType.IntType },navArgument("new") { type = NavType.BoolType }) ) { EditBiography( - bioId = it.arguments?.getInt("bioId") ?: 0 + bioId = it.arguments?.getInt("bioId") ?: 0, + isNewUser = it.arguments?.getBoolean("new") ?: false, ) } } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt index b4898d9..3de239f 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt @@ -3,16 +3,24 @@ package com.menagerie.ophelia.view.biographies import android.annotation.SuppressLint import android.util.Log import android.widget.Toast +import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.Spacer +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.padding import androidx.compose.foundation.layout.width +import androidx.compose.material3.LinearProgressIndicator +import androidx.compose.material3.MaterialTheme import androidx.compose.material3.Scaffold +import androidx.compose.material3.Text import androidx.compose.runtime.Composable import androidx.compose.runtime.getValue import androidx.compose.runtime.livedata.observeAsState import androidx.compose.runtime.mutableStateOf import androidx.compose.runtime.remember import androidx.compose.runtime.setValue +import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.res.stringResource @@ -25,15 +33,18 @@ import com.menagerie.ophelia.R import com.menagerie.ophelia.database.polycule.entity.Bio import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioDetailViewModel import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioListViewModel +import com.menagerie.ophelia.view.OpheliaFace +import com.menagerie.ophelia.view.OpheliaNewUserFinalCheck import com.menagerie.ophelia.view.components.fab.FABComponent @SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") @Composable fun EditBiography( - bioId : Int + bioId : Int, + isNewUser: Boolean, ) { - Log.d("Tawni", bioId.toString()) + Log.d("Tawni", isNewUser.toString()) val context = LocalContext.current val mBioListViewModel: BioListViewModel = viewModel( @@ -75,40 +86,50 @@ fun EditBiography( ) { Column { - val modifier = Modifier.width(120.dp) + if (isNewUser) + NewUserHelp(modifier = Modifier) + val modifier = Modifier.weight(1f) InputFieldState( name, "name", "Ophelia", - modifier = Modifier + modifier = modifier ) { name = it } //Name - Row { - InputFieldState( - sp, - "", - "she", - modifier - ) { sp = it } - InputFieldState( - op, - "", - "her", - modifier - ) { op = it } - } - Row { - InputFieldState( - pp, - "", - "hers", - modifier - ) { pp = it } - InputFieldState( - rp, - "", - "herself", - modifier - ) { rp = it } + Box { + Column { + Row { + InputFieldState( + sp, + "", + "she", + modifier + ) { sp = it } + Text(text = " / ", + style = MaterialTheme.typography.displayMedium) + InputFieldState( + op, + "", + "her", + modifier + ) { op = it } + } + Row { + InputFieldState( + pp, + "", + "hers", + modifier + ) { pp = it } + Text(text = " / ", + style = MaterialTheme.typography.displayMedium) + InputFieldState( + rp, + "", + "herself", + modifier + ) { rp = it } + } + } } } } @@ -119,4 +140,22 @@ class InputEditViewModel( ) : ViewModel() { private val _bio: MutableLiveData = MutableLiveData(bio) val bio: LiveData = _bio +} + +@Composable +fun NewUserHelp( + modifier: Modifier +){ + Column { + OpheliaFace( + modifier = Modifier + .align(Alignment.CenterHorizontally) + .padding(top = 12.dp) + ) + LinearProgressIndicator( + progress = 1f, + modifier = Modifier.fillMaxWidth() + ) + OpheliaNewUserFinalCheck(modifier = modifier) + } } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt index 843ea46..4553b4c 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt @@ -44,7 +44,7 @@ enum class Tags(val value: Int) @SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") @Composable fun AddTagsScreen( - onGo : (Int) -> Unit + onGo : (Int, Boolean) -> Unit ) { Scaffold { Column { @@ -60,7 +60,7 @@ fun AddTagsScreen( OpheliaTagsIntroduction(modifier = Modifier.weight(1f)) MakeDefaultTagCards(modifier = Modifier.weight(2f)) Button( - onClick = { onGo(1) }, + onClick = { onGo(1, true) }, modifier = Modifier .weight(.25f) .align(Alignment.End)) { diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index c012dfc..e0df80a 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -29,6 +29,7 @@ ##Ophelia Ophelia Says + What do you think; looks like you? Hi! I\'m Ophelia, a Polycule companion system designed to help you keep track of your metas, reference a charter, and find things in common with your polycule. -- 2.47.2 From 847b8072c79c3cbe0fc223be6a0fdeca4e6b1ba4 Mon Sep 17 00:00:00 2001 From: azea_laptop Date: Sat, 28 Oct 2023 23:18:22 -0400 Subject: [PATCH 13/20] Add edit --- .../database/polycule/PolyculeRepository.kt | 4 +- .../ophelia/database/polycule/entity/Bio.kt | 1 + .../entity/viewmodel/BioListViewModel.kt | 2 +- .../ophelia/view/biographies/EditBiography.kt | 57 +++++- .../ophelia/view/newUser/AddTagsScreen.kt | 192 ++++++++++-------- 5 files changed, 161 insertions(+), 95 deletions(-) diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt index ba2507b..3f85acf 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt @@ -1,5 +1,8 @@ package com.menagerie.ophelia.database.polycule +import android.util.Log +import androidx.lifecycle.LiveData +import androidx.lifecycle.asLiveData import com.menagerie.ophelia.database.polycule.entity.Bio import com.menagerie.ophelia.database.polycule.entity.BioDao import kotlinx.coroutines.flow.Flow @@ -32,5 +35,4 @@ class PolyculeRepository( } fun hasPolycule() = false - } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/Bio.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/Bio.kt index d094c59..f9c9c47 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/Bio.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/Bio.kt @@ -15,5 +15,6 @@ data class Bio( @ColumnInfo(name = "object_pronoun") val objective: String = "", @ColumnInfo(name = "possess_pronoun") val possessive: String = "", @ColumnInfo(name = "reflex_pronoun") val reflexive: String = "", + @ColumnInfo(name="tags") var tags: Int = 0, @ColumnInfo(name = "pfpRes") val pfpRes: Int = R.drawable.ic_app_logo, ) \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt index 471a360..a786cd9 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt @@ -24,7 +24,7 @@ class BioListViewModel() : ViewModel() { PolyculeDatabaseManager.polyculeRepository.delete(bio) } - fun fetch(bioId: Int) = PolyculeDatabaseManager.polyculeRepository.getBio(bioId = bioId).asLiveData() +// fun fetch(bioId: Int) = PolyculeDatabaseManager.polyculeRepository.getBio(bioId = bioId).asLiveData() class BioListViewModelFactory() : ViewModelProvider.Factory { diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt index 3de239f..150a2e2 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt @@ -6,10 +6,12 @@ import android.widget.Toast import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Row -import androidx.compose.foundation.layout.Spacer import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.padding import androidx.compose.foundation.layout.width +import androidx.compose.material3.ExperimentalMaterial3Api +import androidx.compose.material3.FilterChip +import androidx.compose.material3.Icon import androidx.compose.material3.LinearProgressIndicator import androidx.compose.material3.MaterialTheme import androidx.compose.material3.Scaffold @@ -17,12 +19,14 @@ import androidx.compose.material3.Text import androidx.compose.runtime.Composable import androidx.compose.runtime.getValue import androidx.compose.runtime.livedata.observeAsState +import androidx.compose.runtime.mutableIntStateOf import androidx.compose.runtime.mutableStateOf import androidx.compose.runtime.remember import androidx.compose.runtime.setValue import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.platform.LocalContext +import androidx.compose.ui.res.painterResource import androidx.compose.ui.res.stringResource import androidx.compose.ui.unit.dp import androidx.lifecycle.LiveData @@ -36,6 +40,7 @@ import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioListViewModel import com.menagerie.ophelia.view.OpheliaFace import com.menagerie.ophelia.view.OpheliaNewUserFinalCheck import com.menagerie.ophelia.view.components.fab.FABComponent +import com.menagerie.ophelia.view.newUser.Tags @SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") @@ -44,7 +49,6 @@ fun EditBiography( bioId : Int, isNewUser: Boolean, ) { - Log.d("Tawni", isNewUser.toString()) val context = LocalContext.current val mBioListViewModel: BioListViewModel = viewModel( @@ -67,7 +71,6 @@ fun EditBiography( Scaffold( floatingActionButton = { FABComponent(text = "${stringResource(id = R.string.edit_bio)}", onClick = { - insertBioInDB( Bio( id = bio.id, @@ -75,7 +78,8 @@ fun EditBiography( subjective = sp, objective = op, possessive = pp, - reflexive = rp + reflexive = rp, + tags = bio.tags, ), mBioListViewModel ) @@ -88,7 +92,7 @@ fun EditBiography( Column { if (isNewUser) NewUserHelp(modifier = Modifier) - val modifier = Modifier.weight(1f) + val modifier = Modifier.width(164.dp) InputFieldState( name, "name", @@ -129,12 +133,55 @@ fun EditBiography( modifier ) { rp = it } } + tagsBox(bio) } } } } } } + +@OptIn(ExperimentalMaterial3Api::class) +@Composable +fun tagsBox( + bio : Bio +) { + + + val mBioDetailViewModel = BioDetailViewModel(1) + val mBioListViewModel: BioListViewModel = viewModel( + factory = BioListViewModel.BioListViewModelFactory() + ) + + //val bio = mBioDetailViewModel.bio.observeAsState().value + var tags by remember { mutableIntStateOf(bio.tags) } + var trans by remember { mutableStateOf(tags and Tags.TRANS.value == Tags.TRANS.value) } + + if (bio != null) { + val updateBio = Bio( + id = bio.id, + name = bio.name, + subjective = bio.subjective, + objective = bio.objective, + possessive = bio.possessive, + reflexive = bio.reflexive, + tags = tags + ) + mBioListViewModel.upsert(updateBio) + FilterChip( + selected = trans, + onClick = { tags = tags xor Tags.TRANS.value + Log.d("Tawnii", tags.toString())}, + label = { /*TODO*/ }, + leadingIcon = { + Icon( + painter = painterResource(id = R.drawable.trans_tag), + contentDescription = "" + ) + }) + } +} + class InputEditViewModel( bio: Bio ) : ViewModel() { diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt index 4553b4c..26be837 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt @@ -13,6 +13,7 @@ import androidx.compose.material3.Scaffold import androidx.compose.material3.Text import androidx.compose.runtime.Composable import androidx.compose.runtime.getValue +import androidx.compose.runtime.livedata.observeAsState import androidx.compose.runtime.mutableIntStateOf import androidx.compose.runtime.remember import androidx.compose.runtime.setValue @@ -23,6 +24,7 @@ import androidx.compose.ui.unit.dp import androidx.lifecycle.viewmodel.compose.viewModel import com.menagerie.ophelia.R import com.menagerie.ophelia.database.polycule.entity.Bio +import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioDetailViewModel import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioListViewModel import com.menagerie.ophelia.view.OpheliaFace import com.menagerie.ophelia.view.OpheliaTagsIntroduction @@ -76,110 +78,124 @@ fun MakeDefaultTagCards( ) { var flags by remember { mutableIntStateOf(0) } + val mBioDetailViewModel = BioDetailViewModel(1) val mBioListViewModel: BioListViewModel = viewModel( factory = BioListViewModel.BioListViewModelFactory() ) + val bio = mBioDetailViewModel.bio.observeAsState().value + if (bio != null) { + val updateBio = Bio( + id = bio.id, + name = bio.name, + subjective = bio.subjective, + objective = bio.objective, + possessive = bio.possessive, + reflexive = bio.reflexive, + tags = flags + ) + mBioListViewModel.upsert(updateBio) - Box(modifier = modifier){ - LazyColumn { - item { - TagCard( - name = "Transgender", - painter = painterResource(id = R.drawable.trans_tag), - details = "", - check = flags and Tags.TRANS.value == Tags.TRANS.value - ) { - flags = flags xor Tags.TRANS.value + Box(modifier = modifier) { + LazyColumn { + item { + TagCard( + name = "Transgender", + painter = painterResource(id = R.drawable.trans_tag), + details = "", + check = flags and Tags.TRANS.value == Tags.TRANS.value + ) { + flags = flags xor Tags.TRANS.value + } } - } - item { - TagCard( - name = "Furry", - painter = painterResource(id = R.drawable.furry_tag), - details = "", - check = flags and Tags.FURRY.value == Tags.FURRY.value - ) { - flags = flags xor Tags.FURRY.value - Log.d("Tawni", flags.toString()) + item { + TagCard( + name = "Furry", + painter = painterResource(id = R.drawable.furry_tag), + details = "", + check = flags and Tags.FURRY.value == Tags.FURRY.value + ) { + flags = flags xor Tags.FURRY.value + Log.d("Tawni", flags.toString()) + } } - } - item { - TagCard( - name = "Therian", - painter = painterResource(id = R.drawable.therian_tag), - details = "", - check = flags and Tags.THERIAN.value == Tags.THERIAN.value - ) { - flags = flags xor Tags.THERIAN.value - Log.d("Tawni", flags.toString()) + item { + TagCard( + name = "Therian", + painter = painterResource(id = R.drawable.therian_tag), + details = "", + check = flags and Tags.THERIAN.value == Tags.THERIAN.value + ) { + flags = flags xor Tags.THERIAN.value + Log.d("Tawni", flags.toString()) + } } - } - item { - TagCard( - name = "Monogamous", - painter = painterResource(id = R.drawable.mono_tag), - details = "", - check = flags and Tags.MONO.value == Tags.MONO.value - ){ + item { + TagCard( + name = "Monogamous", + painter = painterResource(id = R.drawable.mono_tag), + details = "", + check = flags and Tags.MONO.value == Tags.MONO.value + ) { flags = flags xor Tags.MONO.value Log.d("Tawni", flags.toString()) } - } - item { - TagCard( - name = "BDSM", - painter = painterResource(id = R.drawable.bdsm_tag), - details = "", - check = flags and Tags.BDSM.value == Tags.BDSM.value - ) { - flags = flags xor Tags.BDSM.value - Log.d("Tawni", flags.toString()) } - } - item { - TagCard( - name = "Plural", - painter = painterResource(id = R.drawable.plural_tag), - details = "", - check = flags and Tags.PLURAL.value == Tags.PLURAL.value - ) { - flags = flags xor Tags.PLURAL.value - Log.d("Tawni", flags.toString()) + item { + TagCard( + name = "BDSM", + painter = painterResource(id = R.drawable.bdsm_tag), + details = "", + check = flags and Tags.BDSM.value == Tags.BDSM.value + ) { + flags = flags xor Tags.BDSM.value + Log.d("Tawni", flags.toString()) + } } - } - item { - TagCard( - name = "Asexual", - painter = painterResource(id = R.drawable.asexual_tag), - details = "", - check = flags and Tags.ASEXUAL.value == Tags.ASEXUAL.value - ) { - flags = flags xor Tags.ASEXUAL.value - Log.d("Tawni", flags.toString()) + item { + TagCard( + name = "Plural", + painter = painterResource(id = R.drawable.plural_tag), + details = "", + check = flags and Tags.PLURAL.value == Tags.PLURAL.value + ) { + flags = flags xor Tags.PLURAL.value + Log.d("Tawni", flags.toString()) + } } - } - item { - TagCard( - name = "Alcohol", - painter = painterResource(id = R.drawable.liqour_tag), - details = "", - check = flags and Tags.ALCOHOL.value == Tags.ALCOHOL.value - ) { - flags = flags xor Tags.ALCOHOL.value - Log.d("Tawni", flags.toString()) + item { + TagCard( + name = "Asexual", + painter = painterResource(id = R.drawable.asexual_tag), + details = "", + check = flags and Tags.ASEXUAL.value == Tags.ASEXUAL.value + ) { + flags = flags xor Tags.ASEXUAL.value + Log.d("Tawni", flags.toString()) + } } - } - item { - TagCard( - name = "Weed", - painter = painterResource(id = R.drawable.weed_tag), - details = "", - check = flags and Tags.WEED.value == Tags.WEED.value - ) { - flags = flags xor Tags.WEED.value - Log.d("Tawni", flags.toString()) + item { + TagCard( + name = "Alcohol", + painter = painterResource(id = R.drawable.liqour_tag), + details = "", + check = flags and Tags.ALCOHOL.value == Tags.ALCOHOL.value + ) { + flags = flags xor Tags.ALCOHOL.value + Log.d("Tawni", flags.toString()) + } + } + item { + TagCard( + name = "Weed", + painter = painterResource(id = R.drawable.weed_tag), + details = "", + check = flags and Tags.WEED.value == Tags.WEED.value + ) { + flags = flags xor Tags.WEED.value + Log.d("Tawni", flags.toString()) + } } } } -- 2.47.2 From 6261f2da312fec7a4b81f0551494a30567cbdb81 Mon Sep 17 00:00:00 2001 From: Azea Date: Tue, 31 Oct 2023 18:54:14 -0400 Subject: [PATCH 14/20] Check state buttons that *finally* fucking work --- .../com/menagerie/ophelia/view/PolyculeApp.kt | 1 - .../ophelia/view/biographies/AddBiography.kt | 2 + .../ophelia/view/biographies/EditBiography.kt | 70 +++++++++---------- .../ophelia/view/newUser/AddTagsScreen.kt | 8 --- 4 files changed, 36 insertions(+), 45 deletions(-) diff --git a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt index 4c7025e..38c6fa6 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt @@ -43,7 +43,6 @@ fun PolyculeNavHost( navController.navigate("newUserStart") } } - } } diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddBiography.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddBiography.kt index df3b8b0..7d65ee4 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddBiography.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddBiography.kt @@ -1,6 +1,7 @@ package com.menagerie.ophelia.view.biographies import android.annotation.SuppressLint +import android.util.Log import android.widget.Toast import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Row @@ -30,6 +31,7 @@ import com.menagerie.ophelia.view.components.fab.FABComponent fun insertBioInDB(bio: Bio?, mBioListViewModel: BioListViewModel) { bio?.let { + Log.d("TawniInsert","") mBioListViewModel.upsert(it) } } diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt index 150a2e2..c2805da 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt @@ -59,7 +59,9 @@ fun EditBiography( val bio = mBioDetailViewModel.bio.observeAsState().value + if (bio != null) { + Log.d("Tawni", bio.tags.toString()) val inputViewModel = InputEditViewModel(bio) val ioBio: Bio by inputViewModel.bio.observeAsState(bio) var name by remember { mutableStateOf(ioBio.name) } @@ -67,6 +69,7 @@ fun EditBiography( var op by remember { mutableStateOf(ioBio.objective) } var pp by remember { mutableStateOf(ioBio.possessive) } var rp by remember { mutableStateOf(ioBio.reflexive) } + var tags by remember { mutableIntStateOf(ioBio.tags) } Scaffold( floatingActionButton = { @@ -79,12 +82,12 @@ fun EditBiography( objective = op, possessive = pp, reflexive = rp, - tags = bio.tags, + tags = tags, ), mBioListViewModel ) - Toast.makeText(context, "Added Bio", Toast.LENGTH_SHORT).show() + Toast.makeText(context, "Edited Bio", Toast.LENGTH_SHORT).show() }) } ) @@ -133,7 +136,21 @@ fun EditBiography( modifier ) { rp = it } } - tagsBox(bio) + tagsBox(tags){ + tags = it + insertBioInDB( + Bio( + id = bio.id, + name = name, + subjective = sp, + objective = op, + possessive = pp, + reflexive = rp, + tags = tags, + ), + mBioListViewModel + ) + } } } } @@ -144,42 +161,23 @@ fun EditBiography( @OptIn(ExperimentalMaterial3Api::class) @Composable fun tagsBox( - bio : Bio + tags: Int, + onValChange: (Int) -> Unit ) { + Log.d("Tawnii", tags.toString()) + var trans = tags and Tags.TRANS.value == Tags.TRANS.value - val mBioDetailViewModel = BioDetailViewModel(1) - val mBioListViewModel: BioListViewModel = viewModel( - factory = BioListViewModel.BioListViewModelFactory() - ) - - //val bio = mBioDetailViewModel.bio.observeAsState().value - var tags by remember { mutableIntStateOf(bio.tags) } - var trans by remember { mutableStateOf(tags and Tags.TRANS.value == Tags.TRANS.value) } - - if (bio != null) { - val updateBio = Bio( - id = bio.id, - name = bio.name, - subjective = bio.subjective, - objective = bio.objective, - possessive = bio.possessive, - reflexive = bio.reflexive, - tags = tags - ) - mBioListViewModel.upsert(updateBio) - FilterChip( - selected = trans, - onClick = { tags = tags xor Tags.TRANS.value - Log.d("Tawnii", tags.toString())}, - label = { /*TODO*/ }, - leadingIcon = { - Icon( - painter = painterResource(id = R.drawable.trans_tag), - contentDescription = "" - ) - }) - } + FilterChip( + selected = trans, + onClick = { onValChange(tags xor Tags.TRANS.value) }, + label = { /*TODO*/ }, + leadingIcon = { + Icon( + painter = painterResource(id = R.drawable.trans_tag), + contentDescription = "" + ) + }) } class InputEditViewModel( diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt index 26be837..00c893b 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt @@ -117,7 +117,6 @@ fun MakeDefaultTagCards( check = flags and Tags.FURRY.value == Tags.FURRY.value ) { flags = flags xor Tags.FURRY.value - Log.d("Tawni", flags.toString()) } } item { @@ -128,7 +127,6 @@ fun MakeDefaultTagCards( check = flags and Tags.THERIAN.value == Tags.THERIAN.value ) { flags = flags xor Tags.THERIAN.value - Log.d("Tawni", flags.toString()) } } item { @@ -139,7 +137,6 @@ fun MakeDefaultTagCards( check = flags and Tags.MONO.value == Tags.MONO.value ) { flags = flags xor Tags.MONO.value - Log.d("Tawni", flags.toString()) } } item { @@ -150,7 +147,6 @@ fun MakeDefaultTagCards( check = flags and Tags.BDSM.value == Tags.BDSM.value ) { flags = flags xor Tags.BDSM.value - Log.d("Tawni", flags.toString()) } } item { @@ -161,7 +157,6 @@ fun MakeDefaultTagCards( check = flags and Tags.PLURAL.value == Tags.PLURAL.value ) { flags = flags xor Tags.PLURAL.value - Log.d("Tawni", flags.toString()) } } item { @@ -172,7 +167,6 @@ fun MakeDefaultTagCards( check = flags and Tags.ASEXUAL.value == Tags.ASEXUAL.value ) { flags = flags xor Tags.ASEXUAL.value - Log.d("Tawni", flags.toString()) } } item { @@ -183,7 +177,6 @@ fun MakeDefaultTagCards( check = flags and Tags.ALCOHOL.value == Tags.ALCOHOL.value ) { flags = flags xor Tags.ALCOHOL.value - Log.d("Tawni", flags.toString()) } } item { @@ -194,7 +187,6 @@ fun MakeDefaultTagCards( check = flags and Tags.WEED.value == Tags.WEED.value ) { flags = flags xor Tags.WEED.value - Log.d("Tawni", flags.toString()) } } } -- 2.47.2 From 235a9c400b611f3bee5a85e9566ebb1e48ce53d5 Mon Sep 17 00:00:00 2001 From: Azea Date: Tue, 31 Oct 2023 21:24:30 -0400 Subject: [PATCH 15/20] hooray --- .../com/menagerie/ophelia/view/Ophelia.kt | 16 +++ .../com/menagerie/ophelia/view/PolyculeApp.kt | 43 +++--- .../ophelia/view/biographies/EditBiography.kt | 122 +++++++++++++----- .../ophelia/view/newUser/AddTagsScreen.kt | 4 +- .../ophelia/view/newUser/ConfirmBio.kt | 40 ++++++ .../view/polycule/AddPolyculeScreen.kt | 29 +++++ app/src/main/res/values/strings.xml | 7 + 7 files changed, 203 insertions(+), 58 deletions(-) create mode 100644 app/src/main/java/com/menagerie/ophelia/view/newUser/ConfirmBio.kt create mode 100644 app/src/main/java/com/menagerie/ophelia/view/polycule/AddPolyculeScreen.kt diff --git a/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt b/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt index 86e3ccb..d1efe41 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/Ophelia.kt @@ -58,6 +58,7 @@ fun OpheliaSaysArray( toAnnotatedString() } } + @Composable fun OpheliaSays( say: String @@ -150,3 +151,18 @@ fun OpheliaNewUserFinalCheck( } } } + +@Composable +fun OpheliaNewUserPolycule( + modifier: Modifier, +) { + Box( + modifier = modifier + .fillMaxWidth() + .padding(12.dp) + ) { + Column { + Text(text = OpheliaSaysArray(id = R.array.introduction_to_polycules)) + } + } +} diff --git a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt index 38c6fa6..bb16e69 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt @@ -1,9 +1,7 @@ package com.menagerie.ophelia.view -import android.util.Log import androidx.compose.runtime.Composable import androidx.navigation.NavController -import androidx.navigation.NavDirections import androidx.navigation.NavGraphBuilder import androidx.navigation.NavHostController import androidx.navigation.NavType @@ -18,6 +16,8 @@ import com.menagerie.ophelia.view.biographies.EditBiography import com.menagerie.ophelia.view.newUser.AddNameScreen import com.menagerie.ophelia.view.newUser.AddPronounsScreen import com.menagerie.ophelia.view.newUser.AddTagsScreen +import com.menagerie.ophelia.view.newUser.ConfirmBio +import com.menagerie.ophelia.view.polycule.AddPolyculeScreen import com.menagerie.ophelia.view.polycule.PolyculeHomeView @Composable @@ -34,7 +34,7 @@ fun PolyculeNavHost( ) { NavHost( navController = navController, - startDestination = "newUserTags" + startDestination = "confirmBio" ) { polyculeGraph(navController) welcomeGraph(navController) @@ -48,30 +48,22 @@ fun PolyculeNavHost( fun NavGraphBuilder.welcomeGraph(navController: NavHostController) { composable("newUserStart") { - NewUserStartScreen() { - navController.navigate("newUserName") - } + NewUserStartScreen { navController.navigate("newUserName") } } composable("newUserName") { - AddNameScreen( - onGo = { - navController.navigate("newUserPronouns") - } - ) + AddNameScreen { navController.navigate("newUserPronouns") } } composable("newUserPronouns") { - AddPronounsScreen( - onGo = { - navController.navigate("newUserTags") - } - ) + AddPronounsScreen { navController.navigate("newUserTags") } } composable("newUserTags") { - AddTagsScreen( - onGo = { id, new -> - navController.navigate("editBio/${id}/${new}") - } - ) + AddTagsScreen { navController.navigate("confirmBio") } + } + composable("confirmBio") { + ConfirmBio { navController.navigate("makePolycule") } + } + composable("makePolycule") { + AddPolyculeScreen() } } @@ -102,11 +94,10 @@ fun NavGraphBuilder.polyculeGraph(navController: NavController) { } composable( "editBio/{bioId}/{new}", - arguments = listOf(navArgument("bioId") { type = NavType.IntType },navArgument("new") { type = NavType.BoolType }) + arguments = listOf( + navArgument("bioId") { type = NavType.IntType }, + navArgument("new") { type = NavType.BoolType }) ) { - EditBiography( - bioId = it.arguments?.getInt("bioId") ?: 0, - isNewUser = it.arguments?.getBoolean("new") ?: false, - ) + EditBiography(bioId = it.arguments?.getInt("bioId") ?: 0) { navController.navigateUp() } } } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt index c2805da..e73d1ae 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt @@ -1,6 +1,8 @@ package com.menagerie.ophelia.view.biographies import android.annotation.SuppressLint +import android.graphics.drawable.shapes.Shape +import android.nfc.Tag import android.util.Log import android.widget.Toast import androidx.compose.foundation.layout.Box @@ -8,7 +10,9 @@ import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Row import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.size import androidx.compose.foundation.layout.width +import androidx.compose.foundation.shape.CircleShape import androidx.compose.material3.ExperimentalMaterial3Api import androidx.compose.material3.FilterChip import androidx.compose.material3.Icon @@ -25,6 +29,7 @@ import androidx.compose.runtime.remember import androidx.compose.runtime.setValue import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier +import androidx.compose.ui.graphics.painter.Painter import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.res.painterResource import androidx.compose.ui.res.stringResource @@ -47,9 +52,8 @@ import com.menagerie.ophelia.view.newUser.Tags @Composable fun EditBiography( bioId : Int, - isNewUser: Boolean, + onGo : () -> Unit ) { - val context = LocalContext.current val mBioListViewModel: BioListViewModel = viewModel( factory = BioListViewModel.BioListViewModelFactory() @@ -61,7 +65,6 @@ fun EditBiography( if (bio != null) { - Log.d("Tawni", bio.tags.toString()) val inputViewModel = InputEditViewModel(bio) val ioBio: Bio by inputViewModel.bio.observeAsState(bio) var name by remember { mutableStateOf(ioBio.name) } @@ -86,6 +89,7 @@ fun EditBiography( ), mBioListViewModel ) + onGo() Toast.makeText(context, "Edited Bio", Toast.LENGTH_SHORT).show() }) @@ -93,8 +97,6 @@ fun EditBiography( ) { Column { - if (isNewUser) - NewUserHelp(modifier = Modifier) val modifier = Modifier.width(164.dp) InputFieldState( name, @@ -136,7 +138,11 @@ fun EditBiography( modifier ) { rp = it } } - tagsBox(tags){ + tagsBox( + tags = tags, + modifier = Modifier + .padding(12.dp) + .size(48.dp)){ tags = it insertBioInDB( Bio( @@ -162,22 +168,96 @@ fun EditBiography( @Composable fun tagsBox( tags: Int, + modifier: Modifier, onValChange: (Int) -> Unit ) { - Log.d("Tawnii", tags.toString()) - var trans = tags and Tags.TRANS.value == Tags.TRANS.value + Row { + RememberableButton(tagList = tags, + tag = Tags.TRANS.value, + painter = painterResource(id = R.drawable.trans_tag), + modifier = modifier, + onValChange = onValChange) + + RememberableButton(tagList = tags, + tag = Tags.FURRY.value, + painter = painterResource(id = R.drawable.furry_tag), + modifier = modifier, + onValChange = onValChange) + + RememberableButton(tagList = tags, + tag = Tags.ASEXUAL.value, + painter = painterResource(id = R.drawable.asexual_tag), + modifier = modifier, + onValChange = onValChange) + } + + + Row { + RememberableButton(tagList = tags, + tag = Tags.BDSM.value, + painter = painterResource(id = R.drawable.bdsm_tag), + modifier = modifier, + onValChange = onValChange) + + RememberableButton(tagList = tags, + tag = Tags.MONO.value, + painter = painterResource(id = R.drawable.mono_tag), + modifier = modifier, + onValChange = onValChange) + + RememberableButton(tagList = tags, + tag = Tags.ALCOHOL.value, + painter = painterResource(id = R.drawable.liqour_tag), + modifier = modifier, + onValChange = onValChange) + } + + Row { + RememberableButton(tagList = tags, + tag = Tags.WEED.value, + painter = painterResource(id = R.drawable.weed_tag), + modifier = modifier, + onValChange = onValChange) + + RememberableButton(tagList = tags, + tag = Tags.THERIAN.value, + painter = painterResource(id = R.drawable.therian_tag), + modifier = modifier, + onValChange = onValChange) + + RememberableButton(tagList = tags, + tag = Tags.PLURAL.value, + painter = painterResource(id = R.drawable.plural_tag), + modifier = modifier, + onValChange = onValChange) + } +} + +@OptIn(ExperimentalMaterial3Api::class) +@Composable +fun RememberableButton( + tagList: Int, + tag: Int, + modifier: Modifier, + painter: Painter, + onValChange: (Int) -> Unit, +) { + var selected = tagList and tag == tag FilterChip( - selected = trans, - onClick = { onValChange(tags xor Tags.TRANS.value) }, - label = { /*TODO*/ }, + selected = selected, + onClick = { onValChange(tagList xor tag) }, + label = { Text(text = "")}, + shape = CircleShape, + modifier = modifier, leadingIcon = { Icon( - painter = painterResource(id = R.drawable.trans_tag), + painter = painter, contentDescription = "" ) }) + } class InputEditViewModel( @@ -185,22 +265,4 @@ class InputEditViewModel( ) : ViewModel() { private val _bio: MutableLiveData = MutableLiveData(bio) val bio: LiveData = _bio -} - -@Composable -fun NewUserHelp( - modifier: Modifier -){ - Column { - OpheliaFace( - modifier = Modifier - .align(Alignment.CenterHorizontally) - .padding(top = 12.dp) - ) - LinearProgressIndicator( - progress = 1f, - modifier = Modifier.fillMaxWidth() - ) - OpheliaNewUserFinalCheck(modifier = modifier) - } } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt index 00c893b..882ed58 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddTagsScreen.kt @@ -46,7 +46,7 @@ enum class Tags(val value: Int) @SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") @Composable fun AddTagsScreen( - onGo : (Int, Boolean) -> Unit + onGo : () -> Unit ) { Scaffold { Column { @@ -62,7 +62,7 @@ fun AddTagsScreen( OpheliaTagsIntroduction(modifier = Modifier.weight(1f)) MakeDefaultTagCards(modifier = Modifier.weight(2f)) Button( - onClick = { onGo(1, true) }, + onClick = onGo, modifier = Modifier .weight(.25f) .align(Alignment.End)) { diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/ConfirmBio.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/ConfirmBio.kt new file mode 100644 index 0000000..07c4ddd --- /dev/null +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/ConfirmBio.kt @@ -0,0 +1,40 @@ +package com.menagerie.ophelia.view.newUser + +import android.annotation.SuppressLint +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.padding +import androidx.compose.material3.LinearProgressIndicator +import androidx.compose.material3.Scaffold +import androidx.compose.runtime.Composable +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.unit.dp +import com.menagerie.ophelia.view.OpheliaFace +import com.menagerie.ophelia.view.OpheliaNewUserFinalCheck +import com.menagerie.ophelia.view.biographies.EditBiography + +@SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") +@Composable +fun ConfirmBio( + onGo: () -> Unit +) { + Scaffold { + Column { + OpheliaFace( + modifier = Modifier + .align(Alignment.CenterHorizontally) + .padding(top = 12.dp) + ) + LinearProgressIndicator( + progress = 1f, + modifier = Modifier.fillMaxWidth() + ) + OpheliaNewUserFinalCheck(modifier = Modifier) + EditBiography( + bioId = 1, + onGo = onGo, + ) + } + } +} \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/polycule/AddPolyculeScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/polycule/AddPolyculeScreen.kt new file mode 100644 index 0000000..45ce9dd --- /dev/null +++ b/app/src/main/java/com/menagerie/ophelia/view/polycule/AddPolyculeScreen.kt @@ -0,0 +1,29 @@ +package com.menagerie.ophelia.view.polycule + +import android.annotation.SuppressLint +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.padding +import androidx.compose.material3.Scaffold +import androidx.compose.runtime.Composable +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.unit.dp +import com.menagerie.ophelia.view.OpheliaFace +import com.menagerie.ophelia.view.OpheliaNewUserPolycule + +@SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") +@Composable +fun AddPolyculeScreen( +) { + Scaffold { + Column { + OpheliaFace( + modifier = Modifier + .align(Alignment.CenterHorizontally) + .padding(top = 12.dp) + ) + OpheliaNewUserPolycule(modifier = Modifier) + //TODO : Polycules + } + } +} \ No newline at end of file diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index e0df80a..ccefea5 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -53,4 +53,11 @@ Tags are a way to highlight important things about yourself. They also lead to more detailed parts of you bio, where you can flesh out specific parts of your bio. + + + Great! + Now, there\'s just one more thing! We need to create a polycule for you. A "polycule" for our purposes is defined as a group of people with a shared relationship process. + A person may be in a polycule with any number of people, including just themselves, and in any number of polycules. + All we need to get started is a name: + \ No newline at end of file -- 2.47.2 From 3a8209433f49a6247a08c156c9f15636d24e4501 Mon Sep 17 00:00:00 2001 From: Azea Date: Wed, 1 Nov 2023 20:16:00 -0400 Subject: [PATCH 16/20] Add Edit working --- .../com/menagerie/ophelia/view/PolyculeApp.kt | 14 +- .../ophelia/view/biographies/AddBiography.kt | 164 ---------- .../ophelia/view/biographies/AddEditBio.kt | 307 ++++++++++++++++++ .../view/biographies/BioDetailsScreen.kt | 93 +++--- .../ophelia/view/biographies/EditBiography.kt | 268 --------------- .../view/components/InputFieldComponent.kt | 9 +- .../ophelia/view/newUser/AddNameScreen.kt | 29 +- .../ophelia/view/newUser/AddPronounsScreen.kt | 2 +- app/src/main/res/values/strings.xml | 3 + 9 files changed, 375 insertions(+), 514 deletions(-) delete mode 100644 app/src/main/java/com/menagerie/ophelia/view/biographies/AddBiography.kt create mode 100644 app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBio.kt delete mode 100644 app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt diff --git a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt index bb16e69..6428ccf 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt @@ -11,6 +11,7 @@ import androidx.navigation.compose.rememberNavController import androidx.navigation.navArgument import com.menagerie.ophelia.database.polycule.PolyculeDatabaseManager import com.menagerie.ophelia.view.biographies.AddBiography +import com.menagerie.ophelia.view.biographies.AddEditBio import com.menagerie.ophelia.view.biographies.BioDetailsScreen import com.menagerie.ophelia.view.biographies.EditBiography import com.menagerie.ophelia.view.newUser.AddNameScreen @@ -34,7 +35,7 @@ fun PolyculeNavHost( ) { NavHost( navController = navController, - startDestination = "confirmBio" + startDestination = "polyculeHome" ) { polyculeGraph(navController) welcomeGraph(navController) @@ -87,17 +88,18 @@ fun NavGraphBuilder.polyculeGraph(navController: NavController) { BioDetailsScreen( id = it.arguments?.getInt("bioId") ?: 0, onBackClick = { navController.navigateUp() }, + onEditClick = { id -> navController.navigate("editBio/${id}")} ) } composable("addBio") { AddBiography() } composable( - "editBio/{bioId}/{new}", - arguments = listOf( - navArgument("bioId") { type = NavType.IntType }, - navArgument("new") { type = NavType.BoolType }) - ) { + "editBio/{bioId}", + arguments = listOf(navArgument("bioId") { + type = NavType.IntType + }) + ){ EditBiography(bioId = it.arguments?.getInt("bioId") ?: 0) { navController.navigateUp() } } } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddBiography.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddBiography.kt deleted file mode 100644 index 7d65ee4..0000000 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddBiography.kt +++ /dev/null @@ -1,164 +0,0 @@ -package com.menagerie.ophelia.view.biographies - -import android.annotation.SuppressLint -import android.util.Log -import android.widget.Toast -import androidx.compose.foundation.layout.Column -import androidx.compose.foundation.layout.Row -import androidx.compose.foundation.layout.Spacer -import androidx.compose.foundation.layout.padding -import androidx.compose.foundation.layout.width -import androidx.compose.foundation.text.KeyboardActions -import androidx.compose.material3.Scaffold -import androidx.compose.runtime.Composable -import androidx.compose.runtime.getValue -import androidx.compose.runtime.livedata.observeAsState -import androidx.compose.ui.Modifier -import androidx.compose.ui.platform.LocalContext -import androidx.compose.ui.platform.LocalFocusManager -import androidx.compose.ui.res.stringResource -import androidx.compose.ui.tooling.preview.Preview -import androidx.compose.ui.unit.dp -import androidx.lifecycle.LiveData -import androidx.lifecycle.MutableLiveData -import androidx.lifecycle.ViewModel -import androidx.lifecycle.viewmodel.compose.viewModel -import com.menagerie.ophelia.R -import com.menagerie.ophelia.database.polycule.entity.Bio -import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioListViewModel -import com.menagerie.ophelia.view.components.InputFieldComponent -import com.menagerie.ophelia.view.components.fab.FABComponent - -fun insertBioInDB(bio: Bio?, mBioListViewModel: BioListViewModel) { - bio?.let { - Log.d("TawniInsert","") - mBioListViewModel.upsert(it) - } -} - -@SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") -@Composable -fun AddBiography() { - val inputViewModel = InputViewModel() - val context = LocalContext.current - val mBioListViewModel: BioListViewModel = viewModel( - factory = BioListViewModel.BioListViewModelFactory() - ) - - Scaffold( - floatingActionButton = { - FABComponent(text = "${stringResource(id = R.string.add_bio)}", onClick = { - insertBioInDB(inputViewModel.bio.value, mBioListViewModel) - - Toast.makeText(context, "Added Bio", Toast.LENGTH_SHORT).show() - }) - } - ) - { - Column { - val modifier = Modifier.width(120.dp) - val bio: Bio by inputViewModel.bio.observeAsState(Bio()) - - InputFieldState( - bio.name, - "name", - "Ophelia", - modifier = Modifier - ) { inputViewModel.onNameChange(it) } //Name - Row { - InputFieldState( - bio.subjective, - "", - "she", - modifier - ) { inputViewModel.onSubjectChange(it) } - InputFieldState( - bio.objective, - "", - "her", - modifier - ) { inputViewModel.onPossessChange(it) } - } - Row { - InputFieldState( - bio.possessive, - "", - "hers", - modifier - ) { inputViewModel.onObjectChange(it) } - InputFieldState( - bio.reflexive, - "", - "herself", - modifier - ) { inputViewModel.onReflexChange(it) } - } - } - } -} - -@Composable -fun InputFieldState( - value: String, - label: String, - placeholder: String, - modifier: Modifier, - onVal: (String) -> Unit -) { - - Column( - modifier = Modifier - ) { - InputField(value, label, placeholder, modifier, onValChange = onVal) - Spacer(modifier = Modifier.padding(10.dp)) - } -} - -@Composable -fun InputField( - text: String, - label: String, - placeholder: String, - modifier: Modifier, - onValChange: ((String) -> Unit)? -) { - val focusManager = LocalFocusManager.current - - if (onValChange != null) { - InputFieldComponent( - text = text, - onChange = onValChange, - label = label, - placeHolder = placeholder, - modifier = modifier, - keyboardActions = KeyboardActions(onDone = { focusManager.clearFocus() }) - ) - } -} - -class InputViewModel() : ViewModel() { - private val _bio: MutableLiveData = MutableLiveData(Bio()) - val bio: LiveData = _bio - fun onNameChange(name: String) { - bio.value?.name ?: name - } - fun onSubjectChange(subjective: String) { - bio.value?.subjective ?: subjective - } - fun onObjectChange(objective: String) { - bio.value?.objective ?: objective - } - fun onPossessChange(possessive: String) { - bio.value?.possessive ?: possessive - } - fun onReflexChange(reflexive: String) { - bio.value?.reflexive ?: reflexive - } -} - -@Preview -@Composable -fun AddEditBioPreview() -{ - AddBiography() -} diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBio.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBio.kt new file mode 100644 index 0000000..b8c4be5 --- /dev/null +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBio.kt @@ -0,0 +1,307 @@ +package com.menagerie.ophelia.view.biographies + +import android.annotation.SuppressLint +import android.widget.Toast +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.height +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.size +import androidx.compose.foundation.layout.width +import androidx.compose.foundation.shape.CircleShape +import androidx.compose.material3.ExperimentalMaterial3Api +import androidx.compose.material3.FilterChip +import androidx.compose.material3.Icon +import androidx.compose.material3.MaterialTheme +import androidx.compose.material3.Scaffold +import androidx.compose.material3.Text +import androidx.compose.runtime.Composable +import androidx.compose.runtime.getValue +import androidx.compose.runtime.livedata.observeAsState +import androidx.compose.runtime.mutableIntStateOf +import androidx.compose.runtime.mutableStateOf +import androidx.compose.runtime.remember +import androidx.compose.runtime.setValue +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.graphics.painter.Painter +import androidx.compose.ui.platform.LocalContext +import androidx.compose.ui.res.painterResource +import androidx.compose.ui.res.stringResource +import androidx.compose.ui.unit.dp +import androidx.lifecycle.LiveData +import androidx.lifecycle.MutableLiveData +import androidx.lifecycle.ViewModel +import androidx.lifecycle.viewmodel.compose.viewModel +import com.menagerie.ophelia.R +import com.menagerie.ophelia.database.polycule.entity.Bio +import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioDetailViewModel +import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioListViewModel +import com.menagerie.ophelia.view.components.InputFieldState +import com.menagerie.ophelia.view.components.fab.FABComponent +import com.menagerie.ophelia.view.newUser.Tags + +fun insertBioInDB(bio: Bio?, mBioListViewModel: BioListViewModel) { + bio?.let { + mBioListViewModel.upsert(it) + } +} + +@Composable +fun EditBiography( + bioId: Int, + onGo: () -> Unit +) { + val mBioDetailViewModel = BioDetailViewModel(bioId) + val bio = mBioDetailViewModel.bio.observeAsState().value + + if (bio != null) { + val inputViewModel = InputEditViewModel(bio) + val ioBio: Bio by inputViewModel.bio.observeAsState(bio) + AddEditBio( + ioBio = ioBio, + btnLabel = stringResource(id = R.string.edit_bio), + toast = stringResource(id = R.string.bio_edit_toast), + onGo, + ) + } +} + +@Composable +fun AddBiography() { + + val inputViewModel = InputAddViewModel() + val ioBio: Bio by inputViewModel.bio.observeAsState(Bio()) + AddEditBio( + ioBio = ioBio, + btnLabel = stringResource(id = R.string.edit_bio), + toast = stringResource(id = R.string.bio_edit_toast), + ) { + + } +} + +@SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") +@Composable +fun AddEditBio( + ioBio: Bio, + btnLabel: String, + toast: String, + onGo: () -> Unit +) { + + val mBioListViewModel: BioListViewModel = viewModel( + factory = BioListViewModel.BioListViewModelFactory() + ) + val context = LocalContext.current + + var name by remember { mutableStateOf(ioBio.name) } + var sp by remember { mutableStateOf(ioBio.subjective) } + var op by remember { mutableStateOf(ioBio.objective) } + var pp by remember { mutableStateOf(ioBio.possessive) } + var rp by remember { mutableStateOf(ioBio.reflexive) } + var tags by remember { mutableIntStateOf(ioBio.tags) } + + Scaffold( + floatingActionButton = { + FABComponent(text = btnLabel, onClick = { + insertBioInDB( + Bio( + id = ioBio.id, + name = name, + subjective = sp, + objective = op, + possessive = pp, + reflexive = rp, + tags = tags, + ), + mBioListViewModel + ) + onGo() + Toast.makeText(context, toast, Toast.LENGTH_SHORT).show() + }) + } + ) + { + Column( + modifier = Modifier.padding(12.dp) + ) { + val modifier = Modifier + .width(164.dp) + .height(64.dp) + InputFieldState( + name, + "name", + "Ophelia", + modifier = modifier + ) { name = it } + Box { + Column { + Row { + InputFieldState( + sp, + "objective", + "she", + modifier + ) { sp = it } + Text( + text = " / ", + style = MaterialTheme.typography.displayMedium + ) + InputFieldState( + op, + "subjective", + "her", + modifier + ) { op = it } + } + Row { + InputFieldState( + pp, + "possessive", + "hers", + modifier + ) { pp = it } + Text( + text = " / ", + style = MaterialTheme.typography.displayMedium + ) + InputFieldState( + rp, + "reflexive", + "herself", + modifier + ) { rp = it } + } + tagsBox( + tags = tags, + modifier = Modifier + .padding(12.dp) + .size(64.dp) + ) { + tags = it + } + } + } + } + } +} + +@Composable +fun tagsBox( + tags: Int, + modifier: Modifier, + onValChange: (Int) -> Unit +) { + + Row { + RememberableButton( + tagList = tags, + tag = Tags.TRANS, + painter = painterResource(id = R.drawable.trans_tag), + modifier = modifier, + onValChange = onValChange) + + RememberableButton( + tagList = tags, + tag = Tags.FURRY, + painter = painterResource(id = R.drawable.furry_tag), + modifier = modifier, + onValChange = onValChange) + + RememberableButton( + tagList = tags, + tag = Tags.ASEXUAL, + painter = painterResource(id = R.drawable.asexual_tag), + modifier = modifier, + onValChange = onValChange) + } + + + Row { + RememberableButton( + tagList = tags, + tag = Tags.BDSM, + painter = painterResource(id = R.drawable.bdsm_tag), + modifier = modifier, + onValChange = onValChange) + + RememberableButton( + tagList = tags, + tag = Tags.MONO, + painter = painterResource(id = R.drawable.mono_tag), + modifier = modifier, + onValChange = onValChange) + + RememberableButton( + tagList = tags, + tag = Tags.ALCOHOL, + painter = painterResource(id = R.drawable.liqour_tag), + modifier = modifier, + onValChange = onValChange) + } + + Row { + RememberableButton( + tagList = tags, + tag = Tags.WEED, + painter = painterResource(id = R.drawable.weed_tag), + modifier = modifier, + onValChange = onValChange) + + RememberableButton( + tagList = tags, + tag = Tags.THERIAN, + painter = painterResource(id = R.drawable.therian_tag), + modifier = modifier, + onValChange = onValChange) + + RememberableButton( + tagList = tags, + tag = Tags.PLURAL, + painter = painterResource(id = R.drawable.plural_tag), + modifier = modifier, + onValChange = onValChange) + } +} + +@OptIn(ExperimentalMaterial3Api::class) +@Composable +fun RememberableButton( + tagList: Int, + tag: Tags, + modifier: Modifier, + painter: Painter, + onValChange: (Int) -> Unit, +) { + var selected = tagList and tag.value == tag.value + + Box { + FilterChip( + selected = selected, + onClick = { onValChange(tagList xor tag.value) }, + modifier = modifier, + shape = CircleShape, + label = { + Icon( + modifier = Modifier.padding(horizontal = 4.dp), + painter = painter, + contentDescription = "" + ) + }, + ) + } +} + +class InputEditViewModel( + bio: Bio +) : ViewModel() { + private val _bio: MutableLiveData = MutableLiveData(bio) + val bio: LiveData = _bio +} + +class InputAddViewModel() : ViewModel() { + private val _bio: MutableLiveData = MutableLiveData(Bio()) + val bio: LiveData = _bio +} \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt index ba71d24..9767b68 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt @@ -1,5 +1,6 @@ package com.menagerie.ophelia.view.biographies +import android.annotation.SuppressLint import android.util.Log import androidx.compose.foundation.Image import androidx.compose.foundation.layout.Box @@ -8,6 +9,7 @@ import androidx.compose.foundation.layout.fillMaxSize import androidx.compose.foundation.layout.padding import androidx.compose.foundation.layout.size import androidx.compose.material3.MaterialTheme +import androidx.compose.material3.Scaffold import androidx.compose.material3.Surface import androidx.compose.material3.Text import androidx.compose.runtime.Composable @@ -17,21 +19,26 @@ import androidx.compose.ui.Modifier import androidx.compose.ui.layout.ContentScale import androidx.compose.ui.platform.LocalDensity import androidx.compose.ui.res.painterResource +import androidx.compose.ui.res.stringResource import androidx.compose.ui.unit.Dp import androidx.compose.ui.unit.dp import androidx.constraintlayout.compose.ConstraintLayout +import com.menagerie.ophelia.R import com.menagerie.ophelia.database.polycule.entity.Bio import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioDetailViewModel +import com.menagerie.ophelia.view.components.fab.FABComponent import com.menagerie.ophelia.view.components.utils.Dimens data class BioDetailCallbacks( - val onBackClick: () -> Unit + val onBackClick: () -> Unit, + val onEditClick: (Int) -> Unit ) @Composable fun BioDetailsScreen( id: Int, onBackClick: () -> Unit, + onEditClick: (Int) -> Unit, ) { val mBioDetailViewModel = BioDetailViewModel(id) @@ -42,7 +49,8 @@ fun BioDetailsScreen( BioDetails( bio, BioDetailCallbacks( - onBackClick = onBackClick + onBackClick = onBackClick, + onEditClick = onEditClick, ) ) } @@ -64,6 +72,7 @@ fun BioDetails( imageHeight = with(LocalDensity.current) { 1.dp }, + onEdit = callbacks.onEditClick ) } } @@ -71,56 +80,56 @@ fun BioDetails( @Composable fun BioDetailContents( bio: Bio, + onEdit: (Int) -> Unit, imageHeight: Dp, ) { Column { - ConstraintLayout { - val (image, info) = createRefs() - Image( - painter = painterResource(id = bio.pfpRes), - contentDescription = null, - modifier = Modifier - .size(130.dp) - .padding(8.dp), - contentScale = ContentScale.Fit, - ) - InfoDetails( - name = bio.name, - modifier = Modifier.constrainAs(info) { - top.linkTo(image.bottom) - } - ) - } + InfoDetails( + bio = bio, + onEdit = onEdit, + modifier = Modifier + ) } } +@SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") @Composable fun InfoDetails( - name: String, + bio: Bio, + onEdit: (Int) -> Unit, modifier: Modifier = Modifier ) { - Column(modifier = modifier.padding(Dimens.PaddingLarge)) { - Text( - text = name, - style = MaterialTheme.typography.displaySmall, - modifier = Modifier - .padding( - start = Dimens.PaddingSmall, - end = Dimens.PaddingSmall, - bottom = Dimens.PaddingNormal - ) - .align(Alignment.CenterHorizontally) - ) - Box( - Modifier - .align(Alignment.CenterHorizontally) - .padding( - start = Dimens.PaddingSmall, - end = Dimens.PaddingSmall, - bottom = Dimens.PaddingNormal - ) - ) { - Text(text = "description") + Scaffold( + floatingActionButton = { + FABComponent( + text = "${stringResource(id = R.string.edit_bio)}", + onClick = { onEdit(bio.id) } + ) + } + ) { + Column(modifier = modifier.padding(Dimens.PaddingLarge)) { + Text( + text = bio.name, + style = MaterialTheme.typography.displaySmall, + modifier = Modifier + .padding( + start = Dimens.PaddingSmall, + end = Dimens.PaddingSmall, + bottom = Dimens.PaddingNormal + ) + .align(Alignment.CenterHorizontally) + ) + Box( + Modifier + .align(Alignment.CenterHorizontally) + .padding( + start = Dimens.PaddingSmall, + end = Dimens.PaddingSmall, + bottom = Dimens.PaddingNormal + ) + ) { + Text(text = "${bio.subjective} / ${bio.objective} / ${bio.possessive} / ${bio.reflexive}") + } } } } diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt deleted file mode 100644 index e73d1ae..0000000 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/EditBiography.kt +++ /dev/null @@ -1,268 +0,0 @@ -package com.menagerie.ophelia.view.biographies - -import android.annotation.SuppressLint -import android.graphics.drawable.shapes.Shape -import android.nfc.Tag -import android.util.Log -import android.widget.Toast -import androidx.compose.foundation.layout.Box -import androidx.compose.foundation.layout.Column -import androidx.compose.foundation.layout.Row -import androidx.compose.foundation.layout.fillMaxWidth -import androidx.compose.foundation.layout.padding -import androidx.compose.foundation.layout.size -import androidx.compose.foundation.layout.width -import androidx.compose.foundation.shape.CircleShape -import androidx.compose.material3.ExperimentalMaterial3Api -import androidx.compose.material3.FilterChip -import androidx.compose.material3.Icon -import androidx.compose.material3.LinearProgressIndicator -import androidx.compose.material3.MaterialTheme -import androidx.compose.material3.Scaffold -import androidx.compose.material3.Text -import androidx.compose.runtime.Composable -import androidx.compose.runtime.getValue -import androidx.compose.runtime.livedata.observeAsState -import androidx.compose.runtime.mutableIntStateOf -import androidx.compose.runtime.mutableStateOf -import androidx.compose.runtime.remember -import androidx.compose.runtime.setValue -import androidx.compose.ui.Alignment -import androidx.compose.ui.Modifier -import androidx.compose.ui.graphics.painter.Painter -import androidx.compose.ui.platform.LocalContext -import androidx.compose.ui.res.painterResource -import androidx.compose.ui.res.stringResource -import androidx.compose.ui.unit.dp -import androidx.lifecycle.LiveData -import androidx.lifecycle.MutableLiveData -import androidx.lifecycle.ViewModel -import androidx.lifecycle.viewmodel.compose.viewModel -import com.menagerie.ophelia.R -import com.menagerie.ophelia.database.polycule.entity.Bio -import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioDetailViewModel -import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioListViewModel -import com.menagerie.ophelia.view.OpheliaFace -import com.menagerie.ophelia.view.OpheliaNewUserFinalCheck -import com.menagerie.ophelia.view.components.fab.FABComponent -import com.menagerie.ophelia.view.newUser.Tags - - -@SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") -@Composable -fun EditBiography( - bioId : Int, - onGo : () -> Unit -) { - val context = LocalContext.current - val mBioListViewModel: BioListViewModel = viewModel( - factory = BioListViewModel.BioListViewModelFactory() - ) - - val mBioDetailViewModel = BioDetailViewModel(bioId) - - val bio = mBioDetailViewModel.bio.observeAsState().value - - - if (bio != null) { - val inputViewModel = InputEditViewModel(bio) - val ioBio: Bio by inputViewModel.bio.observeAsState(bio) - var name by remember { mutableStateOf(ioBio.name) } - var sp by remember { mutableStateOf(ioBio.subjective) } - var op by remember { mutableStateOf(ioBio.objective) } - var pp by remember { mutableStateOf(ioBio.possessive) } - var rp by remember { mutableStateOf(ioBio.reflexive) } - var tags by remember { mutableIntStateOf(ioBio.tags) } - - Scaffold( - floatingActionButton = { - FABComponent(text = "${stringResource(id = R.string.edit_bio)}", onClick = { - insertBioInDB( - Bio( - id = bio.id, - name = name, - subjective = sp, - objective = op, - possessive = pp, - reflexive = rp, - tags = tags, - ), - mBioListViewModel - ) - onGo() - - Toast.makeText(context, "Edited Bio", Toast.LENGTH_SHORT).show() - }) - } - ) - { - Column { - val modifier = Modifier.width(164.dp) - InputFieldState( - name, - "name", - "Ophelia", - modifier = modifier - ) { name = it } //Name - Box { - Column { - Row { - InputFieldState( - sp, - "", - "she", - modifier - ) { sp = it } - Text(text = " / ", - style = MaterialTheme.typography.displayMedium) - InputFieldState( - op, - "", - "her", - modifier - ) { op = it } - } - Row { - InputFieldState( - pp, - "", - "hers", - modifier - ) { pp = it } - Text(text = " / ", - style = MaterialTheme.typography.displayMedium) - InputFieldState( - rp, - "", - "herself", - modifier - ) { rp = it } - } - tagsBox( - tags = tags, - modifier = Modifier - .padding(12.dp) - .size(48.dp)){ - tags = it - insertBioInDB( - Bio( - id = bio.id, - name = name, - subjective = sp, - objective = op, - possessive = pp, - reflexive = rp, - tags = tags, - ), - mBioListViewModel - ) - } - } - } - } - } - } -} - -@OptIn(ExperimentalMaterial3Api::class) -@Composable -fun tagsBox( - tags: Int, - modifier: Modifier, - onValChange: (Int) -> Unit -) { - - Row { - RememberableButton(tagList = tags, - tag = Tags.TRANS.value, - painter = painterResource(id = R.drawable.trans_tag), - modifier = modifier, - onValChange = onValChange) - - RememberableButton(tagList = tags, - tag = Tags.FURRY.value, - painter = painterResource(id = R.drawable.furry_tag), - modifier = modifier, - onValChange = onValChange) - - RememberableButton(tagList = tags, - tag = Tags.ASEXUAL.value, - painter = painterResource(id = R.drawable.asexual_tag), - modifier = modifier, - onValChange = onValChange) - } - - - Row { - RememberableButton(tagList = tags, - tag = Tags.BDSM.value, - painter = painterResource(id = R.drawable.bdsm_tag), - modifier = modifier, - onValChange = onValChange) - - RememberableButton(tagList = tags, - tag = Tags.MONO.value, - painter = painterResource(id = R.drawable.mono_tag), - modifier = modifier, - onValChange = onValChange) - - RememberableButton(tagList = tags, - tag = Tags.ALCOHOL.value, - painter = painterResource(id = R.drawable.liqour_tag), - modifier = modifier, - onValChange = onValChange) - } - - Row { - RememberableButton(tagList = tags, - tag = Tags.WEED.value, - painter = painterResource(id = R.drawable.weed_tag), - modifier = modifier, - onValChange = onValChange) - - RememberableButton(tagList = tags, - tag = Tags.THERIAN.value, - painter = painterResource(id = R.drawable.therian_tag), - modifier = modifier, - onValChange = onValChange) - - RememberableButton(tagList = tags, - tag = Tags.PLURAL.value, - painter = painterResource(id = R.drawable.plural_tag), - modifier = modifier, - onValChange = onValChange) - } -} - -@OptIn(ExperimentalMaterial3Api::class) -@Composable -fun RememberableButton( - tagList: Int, - tag: Int, - modifier: Modifier, - painter: Painter, - onValChange: (Int) -> Unit, -) { - var selected = tagList and tag == tag - - FilterChip( - selected = selected, - onClick = { onValChange(tagList xor tag) }, - label = { Text(text = "")}, - shape = CircleShape, - modifier = modifier, - leadingIcon = { - Icon( - painter = painter, - contentDescription = "" - ) - }) - -} - -class InputEditViewModel( - bio: Bio -) : ViewModel() { - private val _bio: MutableLiveData = MutableLiveData(bio) - val bio: LiveData = _bio -} \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt b/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt index ab8211a..761a126 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt @@ -24,16 +24,15 @@ fun InputFieldComponent( modifier: Modifier = Modifier, singleLine: Boolean = true, label: String = "Some val", - placeHolder: String = "some place", keyboardActions: KeyboardActions = KeyboardActions.Default, ) { OutlinedTextField( value = text, onValueChange = onChange, label = { Text(text = label)}, - //placeholder = { Text(text = placeHolder)}, modifier = modifier, singleLine = singleLine, + keyboardActions = keyboardActions, ) } @@ -44,13 +43,13 @@ fun InputFieldState( label: String, placeholder: String, modifier: Modifier, - onValChange: ((String) -> Unit)? + onVal: (String) -> Unit ) { Column( modifier = Modifier ) { - InputField(value, label, placeholder, modifier) { onValChange } + InputField(value, label, placeholder, modifier, onValChange = onVal) Spacer(modifier = Modifier.padding(10.dp)) } } @@ -70,7 +69,7 @@ fun InputField( text = text, onChange = onValChange, label = label, - placeHolder = placeholder, + //placeHolder = placeholder, modifier = modifier, keyboardActions = KeyboardActions(onDone = { focusManager.clearFocus() }) ) diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt index 1fa3b05..e00fe7c 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt @@ -6,11 +6,8 @@ import androidx.compose.foundation.layout.Spacer import androidx.compose.foundation.layout.fillMaxSize import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.padding -import androidx.compose.foundation.layout.size import androidx.compose.foundation.layout.width -import androidx.compose.foundation.text.KeyboardActions import androidx.compose.material3.Button -import androidx.compose.material3.ExperimentalMaterial3Api import androidx.compose.material3.LinearProgressIndicator import androidx.compose.material3.Scaffold import androidx.compose.material3.Text @@ -19,7 +16,6 @@ import androidx.compose.runtime.getValue import androidx.compose.runtime.livedata.observeAsState import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier -import androidx.compose.ui.platform.LocalFocusManager import androidx.compose.ui.unit.dp import androidx.lifecycle.LiveData import androidx.lifecycle.MutableLiveData @@ -30,7 +26,7 @@ import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioListViewModel import com.menagerie.ophelia.view.OpheliaFace import com.menagerie.ophelia.view.OpheliaWhatsYourName import com.menagerie.ophelia.view.biographies.insertBioInDB -import com.menagerie.ophelia.view.components.InputFieldComponent +import com.menagerie.ophelia.view.components.InputField @SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") @Composable @@ -93,7 +89,6 @@ fun InputFieldState( placeholder: String, modifier: Modifier ) { - Column( modifier = Modifier ) { @@ -102,28 +97,6 @@ fun InputFieldState( } } -@Composable -fun InputField( - text: String, - label: String, - placeholder: String, - modifier: Modifier, - onValChange: ((String) -> Unit)? -) { - val focusManager = LocalFocusManager.current - - if (onValChange != null) { - InputFieldComponent( - text = text, - onChange = onValChange, - label = label, - placeHolder = placeholder, - modifier = modifier, - keyboardActions = KeyboardActions(onDone = { focusManager.clearFocus() }) - ) - } -} - class InputViewModel : ViewModel() { private val _bio: MutableLiveData = MutableLiveData(Bio()) val bio: LiveData = _bio diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt index c3e5e29..7fa09c0 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt @@ -23,12 +23,12 @@ import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.unit.dp import androidx.lifecycle.viewmodel.compose.viewModel -import com.menagerie.ophelia.database.polycule.PolyculeDatabaseManager import com.menagerie.ophelia.database.polycule.entity.Bio import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioDetailViewModel import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioListViewModel import com.menagerie.ophelia.view.OpheliaFace import com.menagerie.ophelia.view.OpheliaPronounsIntroduction +import com.menagerie.ophelia.view.components.InputField @SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") @Composable diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index ccefea5..74f3f10 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -15,6 +15,9 @@ Bio Loaded Open context menu Name + New Bio Added! + Bio Edited! + ##Tags Monogamous -- 2.47.2 From 11913f3f2e5a1f8a0f03f30180b56617d9ef915b Mon Sep 17 00:00:00 2001 From: Azea Date: Tue, 7 Nov 2023 21:26:05 -0500 Subject: [PATCH 17/20] Cherry Pick Patch 1 --- app/build.gradle | 2 +- .../polycule/PolyculeDatabaseManager.kt | 8 ------ .../database/polycule/PolyculeRepository.kt | 2 +- .../ophelia/database/polycule/entity/Bio.kt | 2 +- .../database/polycule/entity/BioDao.kt | 4 +-- .../database/polycule/entity/Identity.kt | 17 ------------- .../database/polycule/entity/IdentityDao.kt | 20 --------------- .../entity/viewmodel/BioDetailViewModel.kt | 2 +- .../com/menagerie/ophelia/view/HomeScreen.kt | 25 +------------------ .../com/menagerie/ophelia/view/PolyculeApp.kt | 10 ++++---- .../ophelia/view/biographies/AddEditBio.kt | 2 +- .../view/biographies/BioDetailsScreen.kt | 16 ++++-------- build.gradle | 2 +- 13 files changed, 19 insertions(+), 93 deletions(-) delete mode 100644 app/src/main/java/com/menagerie/ophelia/database/polycule/entity/Identity.kt delete mode 100644 app/src/main/java/com/menagerie/ophelia/database/polycule/entity/IdentityDao.kt diff --git a/app/build.gradle b/app/build.gradle index 95fc2fb..e4d2bda 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -59,7 +59,7 @@ dependencies { implementation 'androidx.appcompat:appcompat:1.6.1' implementation "androidx.activity:activity-ktx:$activity_version" - implementation 'androidx.core:core-ktx:1.9.0' + implementation 'androidx.core:core-ktx:1.12.0' implementation 'androidx.lifecycle:lifecycle-runtime-ktx:2.6.2' implementation 'androidx.activity:activity-compose:1.8.0' implementation platform('androidx.compose:compose-bom:2023.03.00') diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeDatabaseManager.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeDatabaseManager.kt index 7e79955..e89bc9d 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeDatabaseManager.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeDatabaseManager.kt @@ -1,13 +1,5 @@ package com.menagerie.ophelia.database.polycule -import com.menagerie.ophelia.database.polycule.entity.Bio object PolyculeDatabaseManager { - lateinit var polyculeRepository: PolyculeRepository - - suspend fun post(bio: Bio) { - polyculeRepository.upsertBio(bio) - } - - fun hasPolycule() = polyculeRepository.hasPolycule() } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt index 3f85acf..011ecc6 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/PolyculeRepository.kt @@ -18,7 +18,7 @@ class PolyculeRepository( return bioDao.getAllAlphabetisedBios() } - fun getBio(bioId: Int): Flow { + fun getBio(bioId: Long): Flow { return bioDao.getBio(bioId) } diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/Bio.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/Bio.kt index f9c9c47..23063c9 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/Bio.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/Bio.kt @@ -9,7 +9,7 @@ import com.menagerie.ophelia.R tableName = "bio_table", ) data class Bio( - @PrimaryKey(autoGenerate = true) val id: Int = 0, + @PrimaryKey(autoGenerate = true) val id: Long = 0, @ColumnInfo(name = "name") var name: String = "", @ColumnInfo(name = "subject_pronoun") val subjective: String = "", @ColumnInfo(name = "object_pronoun") val objective: String = "", diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/BioDao.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/BioDao.kt index f212769..efc1099 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/BioDao.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/BioDao.kt @@ -18,7 +18,7 @@ abstract class BioDao { abstract suspend fun delete(bio: Bio) @Update - abstract suspend fun update(existingBio: Bio): Int + abstract suspend fun update(existingBio: Bio) @Query("SELECT * FROM bio_table ORDER BY name ASC") abstract fun getAllAlphabetisedBios(): Flow> @@ -27,7 +27,7 @@ abstract class BioDao { abstract fun getAllBios(): Flow> @Query("SELECT * FROM bio_table WHERE id = :bioId") - abstract fun getBio(bioId: Int): Flow + abstract fun getBio(bioId: Long): Flow @Upsert abstract suspend fun upsert(bio: Bio): Long diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/Identity.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/Identity.kt deleted file mode 100644 index c2ed523..0000000 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/Identity.kt +++ /dev/null @@ -1,17 +0,0 @@ -package com.menagerie.ophelia.database.polycule.entity - -import androidx.room.Entity -import androidx.room.PrimaryKey - -@Entity( - foreignKeys = [ - - ], - indices = [ - - ] -) -class Identity ( - @PrimaryKey(autoGenerate = true) val id: Long = 0, - val name: String = "", - ) \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/IdentityDao.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/IdentityDao.kt deleted file mode 100644 index 3b524aa..0000000 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/IdentityDao.kt +++ /dev/null @@ -1,20 +0,0 @@ -package com.menagerie.ophelia.database.polycule.entity - -import androidx.room.Dao -import androidx.room.Insert -import androidx.room.Query -import androidx.room.Update - -@Dao -abstract class IdentityDao { - @Insert - abstract suspend fun insert(identity: Identity): Long - - @Update - abstract suspend fun update(idenity: Identity) - - @Query("SELECT * FROM Identity WHERE id = :uniqueId") - abstract suspend fun findByIdentity(uniqueId: Int): Identity? - - -} \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioDetailViewModel.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioDetailViewModel.kt index 35d20af..b89ac55 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioDetailViewModel.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioDetailViewModel.kt @@ -6,7 +6,7 @@ import androidx.lifecycle.asLiveData import com.menagerie.ophelia.database.polycule.PolyculeDatabaseManager class BioDetailViewModel( - id: Int + id: Long ) : ViewModel() { var bio = PolyculeDatabaseManager.polyculeRepository.getBio(id).asLiveData() } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/HomeScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/HomeScreen.kt index 5650b65..590b4db 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/HomeScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/HomeScreen.kt @@ -23,11 +23,10 @@ import com.menagerie.ophelia.ui.theme.OpheliaTheme @Composable fun HomeScreen( - newUser: Boolean, onClick: () -> Unit, ) { - val text = if(newUser) R.string.welcome else R.string.welcome_back + val text = if(true) R.string.welcome else R.string.welcome_back HeaderText(text, onClick) } @@ -65,26 +64,4 @@ fun HeaderText( } } } -} - - -@Preview(showBackground = true, - uiMode = Configuration.UI_MODE_NIGHT_NO or Configuration.UI_MODE_TYPE_NORMAL, ) -@Composable -fun HomeScreenPreview(){ - OpheliaTheme { - Surface { - HomeScreen(newUser = true) {} - } - } -} -@Preview(showBackground = true, - uiMode = Configuration.UI_MODE_NIGHT_YES or Configuration.UI_MODE_TYPE_NORMAL, ) -@Composable -fun HomeScreenPreview1(){ - OpheliaTheme { - Surface { - HomeScreen(newUser = true) {} - } - } } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt index 6428ccf..d11b117 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt @@ -40,7 +40,7 @@ fun PolyculeNavHost( polyculeGraph(navController) welcomeGraph(navController) composable("home") { - HomeScreen(!PolyculeDatabaseManager.hasPolycule()) { + HomeScreen() { navController.navigate("newUserStart") } } @@ -82,11 +82,11 @@ fun NavGraphBuilder.polyculeGraph(navController: NavController) { composable( "bioDetail/{bioId}", arguments = listOf(navArgument("bioId") { - type = NavType.IntType + type = NavType.LongType }) ) { BioDetailsScreen( - id = it.arguments?.getInt("bioId") ?: 0, + id = it.arguments?.getLong("bioId") ?: 0, onBackClick = { navController.navigateUp() }, onEditClick = { id -> navController.navigate("editBio/${id}")} ) @@ -97,9 +97,9 @@ fun NavGraphBuilder.polyculeGraph(navController: NavController) { composable( "editBio/{bioId}", arguments = listOf(navArgument("bioId") { - type = NavType.IntType + type = NavType.LongType }) ){ - EditBiography(bioId = it.arguments?.getInt("bioId") ?: 0) { navController.navigateUp() } + EditBiography(bioId = it.arguments?.getLong("bioId") ?: 0) { navController.navigateUp() } } } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBio.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBio.kt index b8c4be5..a9b01f9 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBio.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBio.kt @@ -50,7 +50,7 @@ fun insertBioInDB(bio: Bio?, mBioListViewModel: BioListViewModel) { @Composable fun EditBiography( - bioId: Int, + bioId: Long, onGo: () -> Unit ) { val mBioDetailViewModel = BioDetailViewModel(bioId) diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt index 9767b68..ca64191 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt @@ -1,13 +1,10 @@ package com.menagerie.ophelia.view.biographies import android.annotation.SuppressLint -import android.util.Log -import androidx.compose.foundation.Image import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.fillMaxSize import androidx.compose.foundation.layout.padding -import androidx.compose.foundation.layout.size import androidx.compose.material3.MaterialTheme import androidx.compose.material3.Scaffold import androidx.compose.material3.Surface @@ -16,13 +13,10 @@ import androidx.compose.runtime.Composable import androidx.compose.runtime.livedata.observeAsState import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier -import androidx.compose.ui.layout.ContentScale import androidx.compose.ui.platform.LocalDensity -import androidx.compose.ui.res.painterResource import androidx.compose.ui.res.stringResource import androidx.compose.ui.unit.Dp import androidx.compose.ui.unit.dp -import androidx.constraintlayout.compose.ConstraintLayout import com.menagerie.ophelia.R import com.menagerie.ophelia.database.polycule.entity.Bio import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioDetailViewModel @@ -31,14 +25,14 @@ import com.menagerie.ophelia.view.components.utils.Dimens data class BioDetailCallbacks( val onBackClick: () -> Unit, - val onEditClick: (Int) -> Unit + val onEditClick: (Long) -> Unit ) @Composable fun BioDetailsScreen( - id: Int, + id: Long, onBackClick: () -> Unit, - onEditClick: (Int) -> Unit, + onEditClick: (Long) -> Unit, ) { val mBioDetailViewModel = BioDetailViewModel(id) @@ -80,7 +74,7 @@ fun BioDetails( @Composable fun BioDetailContents( bio: Bio, - onEdit: (Int) -> Unit, + onEdit: (Long) -> Unit, imageHeight: Dp, ) { Column { @@ -96,7 +90,7 @@ fun BioDetailContents( @Composable fun InfoDetails( bio: Bio, - onEdit: (Int) -> Unit, + onEdit: (Long) -> Unit, modifier: Modifier = Modifier ) { Scaffold( diff --git a/build.gradle b/build.gradle index 39f3210..cc86467 100644 --- a/build.gradle +++ b/build.gradle @@ -1,6 +1,6 @@ // Top-level build file where you can add configuration options common to all sub-projects/modules. plugins { - id 'com.android.application' version '8.1.2' apply false + id 'com.android.application' version '8.1.3' apply false id 'org.jetbrains.kotlin.android' version '1.8.10' apply false id 'com.google.devtools.ksp' version '1.8.10-1.0.9' apply false } \ No newline at end of file -- 2.47.2 From 956095e51347e598a575f970d3123d9c55e84180 Mon Sep 17 00:00:00 2001 From: Azea Date: Fri, 10 Nov 2023 22:55:47 -0500 Subject: [PATCH 18/20] Cherry Pick Patch 1 --- .../entity/viewmodel/BioListViewModel.kt | 16 ++++-- .../com/menagerie/ophelia/view/PolyculeApp.kt | 2 +- .../ophelia/view/biographies/BioCardList.kt | 15 ------ .../view/biographies/BioDetailsScreen.kt | 7 --- .../view/components/InputFieldComponent.kt | 14 ----- .../ophelia/view/newUser/AddNameScreen.kt | 52 +++++-------------- 6 files changed, 28 insertions(+), 78 deletions(-) diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt index a786cd9..4597424 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt @@ -1,6 +1,7 @@ package com.menagerie.ophelia.database.polycule.entity.viewmodel import androidx.lifecycle.LiveData +import androidx.lifecycle.MutableLiveData import androidx.lifecycle.ViewModel import androidx.lifecycle.ViewModelProvider import androidx.lifecycle.asLiveData @@ -24,8 +25,6 @@ class BioListViewModel() : ViewModel() { PolyculeDatabaseManager.polyculeRepository.delete(bio) } -// fun fetch(bioId: Int) = PolyculeDatabaseManager.polyculeRepository.getBio(bioId = bioId).asLiveData() - class BioListViewModelFactory() : ViewModelProvider.Factory { override fun create(modelClass: Class): T { @@ -36,4 +35,15 @@ class BioListViewModel() : ViewModel() { throw IllegalArgumentException("Unknown ViewModel Class") } } -} \ No newline at end of file + class InputViewModel : ViewModel() { + private val _bio: MutableLiveData = MutableLiveData(Bio()) + val bio: LiveData = _bio + fun onNameChange(name: String) { + val newBio = Bio( + name = name, + ) + _bio.value = newBio + } + } +} + diff --git a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt index d11b117..ced0a58 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt @@ -35,7 +35,7 @@ fun PolyculeNavHost( ) { NavHost( navController = navController, - startDestination = "polyculeHome" + startDestination = "newUserName" ) { polyculeGraph(navController) welcomeGraph(navController) diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/BioCardList.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/BioCardList.kt index 394e58f..0f7eb27 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/BioCardList.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/BioCardList.kt @@ -35,21 +35,6 @@ fun BioCardList( modifier = Modifier.fillMaxWidth(), contentPadding = PaddingValues(8.dp) ) { - item { - Row( - modifier = Modifier - .fillMaxWidth() - .wrapContentHeight() - .padding(vertical = 24.dp), - horizontalArrangement = Arrangement.Center, - verticalAlignment = Alignment.CenterVertically - ) { - Text( - "The Menagerie", - style = MaterialTheme.typography.headlineLarge - ) - } - } items(bioList) { bio -> BioCard( name = bio.name, diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt index ca64191..6cb50fe 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/BioDetailsScreen.kt @@ -13,10 +13,7 @@ import androidx.compose.runtime.Composable import androidx.compose.runtime.livedata.observeAsState import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier -import androidx.compose.ui.platform.LocalDensity import androidx.compose.ui.res.stringResource -import androidx.compose.ui.unit.Dp -import androidx.compose.ui.unit.dp import com.menagerie.ophelia.R import com.menagerie.ophelia.database.polycule.entity.Bio import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioDetailViewModel @@ -63,9 +60,6 @@ fun BioDetails( ) { BioDetailContents( bio = bio, - imageHeight = with(LocalDensity.current) { - 1.dp - }, onEdit = callbacks.onEditClick ) } @@ -75,7 +69,6 @@ fun BioDetails( fun BioDetailContents( bio: Bio, onEdit: (Long) -> Unit, - imageHeight: Dp, ) { Column { InfoDetails( diff --git a/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt b/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt index 761a126..79bd6c5 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt @@ -10,12 +10,6 @@ import androidx.compose.runtime.Composable import androidx.compose.ui.Modifier import androidx.compose.ui.platform.LocalFocusManager import androidx.compose.ui.unit.dp -import androidx.lifecycle.LiveData -import androidx.lifecycle.MutableLiveData -import androidx.lifecycle.ViewModel -import androidx.lifecycle.viewmodel.compose.viewModel -import com.menagerie.ophelia.database.polycule.entity.Bio -import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioListViewModel @Composable fun InputFieldComponent( @@ -74,12 +68,4 @@ fun InputField( keyboardActions = KeyboardActions(onDone = { focusManager.clearFocus() }) ) } -} - -class InputViewModel : ViewModel() { - private var _bio: MutableLiveData = MutableLiveData(Bio()) - var bio: LiveData = _bio - fun onNameChange(name: String) { - _bio.value?.name ?: name - } } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt index e00fe7c..5d9f45e 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt @@ -14,26 +14,26 @@ import androidx.compose.material3.Text import androidx.compose.runtime.Composable import androidx.compose.runtime.getValue import androidx.compose.runtime.livedata.observeAsState +import androidx.compose.runtime.mutableStateOf +import androidx.compose.runtime.remember +import androidx.compose.runtime.setValue import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.unit.dp -import androidx.lifecycle.LiveData -import androidx.lifecycle.MutableLiveData -import androidx.lifecycle.ViewModel import androidx.lifecycle.viewmodel.compose.viewModel import com.menagerie.ophelia.database.polycule.entity.Bio import com.menagerie.ophelia.database.polycule.entity.viewmodel.BioListViewModel import com.menagerie.ophelia.view.OpheliaFace import com.menagerie.ophelia.view.OpheliaWhatsYourName import com.menagerie.ophelia.view.biographies.insertBioInDB -import com.menagerie.ophelia.view.components.InputField +import com.menagerie.ophelia.view.components.InputFieldState @SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") @Composable fun AddNameScreen( - onGo: (Bio) -> Unit = {}, + onGo: () -> Unit, ) { - val inputViewModel = InputViewModel() + val inputViewModel = BioListViewModel.InputViewModel() val mBioListViewModel: BioListViewModel = viewModel( factory = BioListViewModel.BioListViewModelFactory() ) @@ -43,6 +43,9 @@ fun AddNameScreen( ) { val bio: Bio by inputViewModel.bio.observeAsState(Bio()) + var name by remember { mutableStateOf(bio.name) } + + OpheliaFace( modifier = Modifier .align(Alignment.CenterHorizontally) @@ -54,13 +57,12 @@ fun AddNameScreen( ) OpheliaWhatsYourName(modifier = Modifier) InputFieldState( - inputViewModel, - bio.name, - "name", - "Ophelia", + value = name, + label = "name", + placeholder = "Ophelia", modifier = Modifier .width(120.dp) - ) + ) { inputViewModel.onNameChange(it) } Spacer( modifier = Modifier .fillMaxSize() @@ -72,7 +74,7 @@ fun AddNameScreen( .align(Alignment.End), onClick = { insertBioInDB(inputViewModel.bio.value, mBioListViewModel) - onGo(bio) + onGo() } ) { Text(text = "Continue") @@ -81,29 +83,3 @@ fun AddNameScreen( } } -@Composable -fun InputFieldState( - inputViewModel: InputViewModel, - value: String, - label: String, - placeholder: String, - modifier: Modifier -) { - Column( - modifier = Modifier - ) { - InputField(value, label, placeholder, modifier) { inputViewModel.onInputChange(it) } - Spacer(modifier = Modifier.padding(10.dp)) - } -} - -class InputViewModel : ViewModel() { - private val _bio: MutableLiveData = MutableLiveData(Bio()) - val bio: LiveData = _bio - fun onInputChange(name: String) { - val newBio = Bio( - name = name, - ) - _bio.value = newBio - } -} \ No newline at end of file -- 2.47.2 From 3d8451b8cf72f9e29442977e34694b464ac2ff57 Mon Sep 17 00:00:00 2001 From: Azea Date: Sat, 11 Nov 2023 15:29:13 -0500 Subject: [PATCH 19/20] Cherry Pick Patch 3 --- .../entity/viewmodel/BioListViewModel.kt | 5 +- .../com/menagerie/ophelia/view/PolyculeApp.kt | 7 +- .../ophelia/view/biographies/AddEditBio.kt | 74 ++++++++++++++----- .../view/components/InputFieldComponent.kt | 16 ++-- .../ophelia/view/newUser/AddNameScreen.kt | 8 +- .../ophelia/view/newUser/AddPronounsScreen.kt | 51 +++++++++---- .../ophelia/view/newUser/ConfirmBio.kt | 4 +- .../ophelia/view/polycule/PolyculeHomeView.kt | 2 +- app/src/main/res/values/strings.xml | 2 + 9 files changed, 112 insertions(+), 57 deletions(-) diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt index 4597424..5cf91a5 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt @@ -1,5 +1,6 @@ package com.menagerie.ophelia.database.polycule.entity.viewmodel +import android.util.Log import androidx.lifecycle.LiveData import androidx.lifecycle.MutableLiveData import androidx.lifecycle.ViewModel @@ -8,7 +9,6 @@ import androidx.lifecycle.asLiveData import androidx.lifecycle.viewModelScope import com.menagerie.ophelia.database.polycule.PolyculeDatabaseManager import com.menagerie.ophelia.database.polycule.entity.Bio -import com.menagerie.ophelia.view.PolyculeNavHost import kotlinx.coroutines.launch @@ -35,10 +35,11 @@ class BioListViewModel() : ViewModel() { throw IllegalArgumentException("Unknown ViewModel Class") } } - class InputViewModel : ViewModel() { + class InputBioViewModel : ViewModel() { private val _bio: MutableLiveData = MutableLiveData(Bio()) val bio: LiveData = _bio fun onNameChange(name: String) { + Log.d("Tawni", name) val newBio = Bio( name = name, ) diff --git a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt index ced0a58..9590961 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/PolyculeApp.kt @@ -35,7 +35,7 @@ fun PolyculeNavHost( ) { NavHost( navController = navController, - startDestination = "newUserName" + startDestination = "confirmBio" ) { polyculeGraph(navController) welcomeGraph(navController) @@ -61,7 +61,10 @@ fun NavGraphBuilder.welcomeGraph(navController: NavHostController) { AddTagsScreen { navController.navigate("confirmBio") } } composable("confirmBio") { - ConfirmBio { navController.navigate("makePolycule") } + ConfirmBio { + navController.popBackStack() + navController.navigate("polyculeHome") + } } composable("makePolycule") { AddPolyculeScreen() diff --git a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBio.kt b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBio.kt index a9b01f9..0d1e45e 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBio.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/biographies/AddEditBio.kt @@ -10,6 +10,7 @@ import androidx.compose.foundation.layout.padding import androidx.compose.foundation.layout.size import androidx.compose.foundation.layout.width import androidx.compose.foundation.shape.CircleShape +import androidx.compose.foundation.text.KeyboardActions import androidx.compose.material3.ExperimentalMaterial3Api import androidx.compose.material3.FilterChip import androidx.compose.material3.Icon @@ -25,8 +26,10 @@ import androidx.compose.runtime.remember import androidx.compose.runtime.setValue import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier +import androidx.compose.ui.focus.FocusDirection import androidx.compose.ui.graphics.painter.Painter import androidx.compose.ui.platform.LocalContext +import androidx.compose.ui.platform.LocalFocusManager import androidx.compose.ui.res.painterResource import androidx.compose.ui.res.stringResource import androidx.compose.ui.unit.dp @@ -48,6 +51,26 @@ fun insertBioInDB(bio: Bio?, mBioListViewModel: BioListViewModel) { } } +@Composable +fun FinishBiography( + bioId: Long, + onGo: () -> Unit +) { + val mBioDetailViewModel = BioDetailViewModel(bioId) + val bio = mBioDetailViewModel.bio.observeAsState().value + + if (bio != null) { + val inputViewModel = InputEditViewModel(bio) + val ioBio: Bio by inputViewModel.bio.observeAsState(bio) + AddEditBio( + ioBio = ioBio, + btnLabel = stringResource(id = R.string.finish), + toast = stringResource(id = R.string.bio_finish_toast), + onGo, + ) + } +} + @Composable fun EditBiography( bioId: Long, @@ -130,48 +153,59 @@ fun AddEditBio( val modifier = Modifier .width(164.dp) .height(64.dp) + val focusManager = LocalFocusManager.current InputFieldState( - name, - "name", - "Ophelia", - modifier = modifier + value = name, + label = "name", + modifier = modifier, + keyboardActions = KeyboardActions( + onDone = { focusManager.moveFocus(FocusDirection.Next) } + ) ) { name = it } Box { Column { Row { InputFieldState( - sp, - "objective", - "she", - modifier + value = sp, + label = "objective", + modifier = modifier, + keyboardActions = KeyboardActions( + onDone = { focusManager.moveFocus(FocusDirection.Next) } + ) ) { sp = it } Text( text = " / ", style = MaterialTheme.typography.displayMedium ) InputFieldState( - op, - "subjective", - "her", - modifier + value = op, + label = "subjective", + modifier = modifier, + keyboardActions = KeyboardActions( + onDone = { focusManager.moveFocus(FocusDirection.Next) } + ) ) { op = it } } Row { InputFieldState( - pp, - "possessive", - "hers", - modifier + value = pp, + label = "possessive", + modifier = modifier, + keyboardActions = KeyboardActions( + onDone = { focusManager.moveFocus(FocusDirection.Next) } + ) ) { pp = it } Text( text = " / ", style = MaterialTheme.typography.displayMedium ) InputFieldState( - rp, - "reflexive", - "herself", - modifier + value = rp, + label = "reflexive", + modifier = modifier, + keyboardActions = KeyboardActions( + onDone = { focusManager.clearFocus() } + ) ) { rp = it } } tagsBox( diff --git a/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt b/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt index 79bd6c5..4ff51b6 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/components/InputFieldComponent.kt @@ -8,6 +8,7 @@ import androidx.compose.material3.OutlinedTextField import androidx.compose.material3.Text import androidx.compose.runtime.Composable import androidx.compose.ui.Modifier +import androidx.compose.ui.focus.FocusDirection import androidx.compose.ui.platform.LocalFocusManager import androidx.compose.ui.unit.dp @@ -35,15 +36,15 @@ fun InputFieldComponent( fun InputFieldState( value: String, label: String, - placeholder: String, modifier: Modifier, - onVal: (String) -> Unit + keyboardActions: KeyboardActions = KeyboardActions.Default, + onVal: (String) -> Unit, ) { Column( modifier = Modifier ) { - InputField(value, label, placeholder, modifier, onValChange = onVal) + InputField(value, label, modifier, onVal, keyboardActions) Spacer(modifier = Modifier.padding(10.dp)) } } @@ -52,20 +53,17 @@ fun InputFieldState( fun InputField( text: String, label: String, - placeholder: String, modifier: Modifier, - onValChange: ((String) -> Unit)? + onValChange: ((String) -> Unit)?, + keyboardActions: KeyboardActions, ) { - val focusManager = LocalFocusManager.current - if (onValChange != null) { InputFieldComponent( text = text, onChange = onValChange, label = label, - //placeHolder = placeholder, modifier = modifier, - keyboardActions = KeyboardActions(onDone = { focusManager.clearFocus() }) + keyboardActions = keyboardActions, ) } } \ No newline at end of file diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt index 5d9f45e..3d923f2 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddNameScreen.kt @@ -33,7 +33,7 @@ import com.menagerie.ophelia.view.components.InputFieldState fun AddNameScreen( onGo: () -> Unit, ) { - val inputViewModel = BioListViewModel.InputViewModel() + val inputViewModel = BioListViewModel.InputBioViewModel() val mBioListViewModel: BioListViewModel = viewModel( factory = BioListViewModel.BioListViewModelFactory() ) @@ -43,9 +43,6 @@ fun AddNameScreen( ) { val bio: Bio by inputViewModel.bio.observeAsState(Bio()) - var name by remember { mutableStateOf(bio.name) } - - OpheliaFace( modifier = Modifier .align(Alignment.CenterHorizontally) @@ -57,9 +54,8 @@ fun AddNameScreen( ) OpheliaWhatsYourName(modifier = Modifier) InputFieldState( - value = name, + value = bio.name, label = "name", - placeholder = "Ophelia", modifier = Modifier .width(120.dp) ) { inputViewModel.onNameChange(it) } diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt index 7fa09c0..baf47fa 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/AddPronounsScreen.kt @@ -8,6 +8,7 @@ import androidx.compose.foundation.layout.Spacer import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.padding import androidx.compose.foundation.layout.size +import androidx.compose.foundation.text.KeyboardActions import androidx.compose.material3.Button import androidx.compose.material3.LinearProgressIndicator import androidx.compose.material3.MaterialTheme @@ -21,6 +22,8 @@ import androidx.compose.runtime.remember import androidx.compose.runtime.setValue import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier +import androidx.compose.ui.focus.FocusDirection +import androidx.compose.ui.platform.LocalFocusManager import androidx.compose.ui.unit.dp import androidx.lifecycle.viewmodel.compose.viewModel import com.menagerie.ophelia.database.polycule.entity.Bio @@ -86,44 +89,62 @@ fun PronounBox( Box(modifier = Modifier.fillMaxWidth()) { Column { + val focusManager = LocalFocusManager.current Row { InputField( text = subject, label = "subjective", - placeholder = "she", modifier = modifier, - onValChange = { subject = it }) - Text(text = " / ", - style = MaterialTheme.typography.displayMedium) + onValChange = { subject = it }, + keyboardActions = KeyboardActions( + onDone = { focusManager.moveFocus(FocusDirection.Next) } + ), + ) + Text( + text = " / ", + style = MaterialTheme.typography.displayMedium + ) InputField( text = objec, label = "objective", - placeholder = "her", modifier = modifier, - onValChange = { objec = it }) + onValChange = { objec = it }, + keyboardActions = KeyboardActions( + onDone = { focusManager.moveFocus(FocusDirection.Next) } + ), + ) } Row { InputField( text = possess, label = "possessive", - placeholder = "hers", modifier = modifier, - onValChange = { possess = it }) - Text(text = " / ", - style = MaterialTheme.typography.displayMedium) + onValChange = { possess = it }, + keyboardActions = KeyboardActions( + onDone = { focusManager.moveFocus(FocusDirection.Next) } + ), + ) + Text( + text = " / ", + style = MaterialTheme.typography.displayMedium + ) InputField( text = reflex, label = "reflexive", - placeholder = "herself", modifier = modifier, - onValChange = { reflex = it }) + onValChange = { reflex = it }, + keyboardActions = KeyboardActions( + onDone = { focusManager.clearFocus() } + ), + ) } Spacer( modifier = Modifier.size(60.dp) ) - Button(onClick = { - onClick(listOf(subject, objec, possess, reflex)) - }, + Button( + onClick = { + onClick(listOf(subject, objec, possess, reflex)) + }, modifier = Modifier .align( alignment = Alignment.End diff --git a/app/src/main/java/com/menagerie/ophelia/view/newUser/ConfirmBio.kt b/app/src/main/java/com/menagerie/ophelia/view/newUser/ConfirmBio.kt index 07c4ddd..ada8fae 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/newUser/ConfirmBio.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/newUser/ConfirmBio.kt @@ -12,7 +12,7 @@ import androidx.compose.ui.Modifier import androidx.compose.ui.unit.dp import com.menagerie.ophelia.view.OpheliaFace import com.menagerie.ophelia.view.OpheliaNewUserFinalCheck -import com.menagerie.ophelia.view.biographies.EditBiography +import com.menagerie.ophelia.view.biographies.FinishBiography @SuppressLint("UnusedMaterial3ScaffoldPaddingParameter") @Composable @@ -31,7 +31,7 @@ fun ConfirmBio( modifier = Modifier.fillMaxWidth() ) OpheliaNewUserFinalCheck(modifier = Modifier) - EditBiography( + FinishBiography( bioId = 1, onGo = onGo, ) diff --git a/app/src/main/java/com/menagerie/ophelia/view/polycule/PolyculeHomeView.kt b/app/src/main/java/com/menagerie/ophelia/view/polycule/PolyculeHomeView.kt index f07d99a..732baf7 100644 --- a/app/src/main/java/com/menagerie/ophelia/view/polycule/PolyculeHomeView.kt +++ b/app/src/main/java/com/menagerie/ophelia/view/polycule/PolyculeHomeView.kt @@ -33,7 +33,7 @@ fun PolyculeHomeView( val scrollBehavior = TopAppBarDefaults.enterAlwaysScrollBehavior() Scaffold( modifier = modifier, - bottomBar = { + topBar = { PolyculeTopAppBar( onFilterClick = { }, scrollBehavior = scrollBehavior diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 74f3f10..fe8f586 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -12,11 +12,13 @@ ##Bio Add Bio Edit Bio + Finish Bio Loaded Open context menu Name New Bio Added! Bio Edited! + Welcome Aboard! ##Tags -- 2.47.2 From e08986e8c1f63dda1e8cf7fcf80a2c15bdd8148b Mon Sep 17 00:00:00 2001 From: Azea Date: Sat, 11 Nov 2023 16:22:31 -0500 Subject: [PATCH 20/20] ver bump --- app/build.gradle | 2 +- .../database/polycule/entity/viewmodel/BioListViewModel.kt | 1 - 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/app/build.gradle b/app/build.gradle index e4d2bda..af3ca8b 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -13,7 +13,7 @@ android { minSdk 27 targetSdk 33 versionCode 1 - versionName "e1.0.0.b6" + versionName "e1.0.0.b7" testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner" vectorDrawables { diff --git a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt index 5cf91a5..48cc364 100644 --- a/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt +++ b/app/src/main/java/com/menagerie/ophelia/database/polycule/entity/viewmodel/BioListViewModel.kt @@ -39,7 +39,6 @@ class BioListViewModel() : ViewModel() { private val _bio: MutableLiveData = MutableLiveData(Bio()) val bio: LiveData = _bio fun onNameChange(name: String) { - Log.d("Tawni", name) val newBio = Bio( name = name, ) -- 2.47.2