diff --git a/app/build.gradle.kts b/app/build.gradle.kts index 77377f7..1eca016 100644 --- a/app/build.gradle.kts +++ b/app/build.gradle.kts @@ -15,8 +15,8 @@ android { applicationId = "ru.tech.firenote" minSdk = 21 targetSdk = 32 - versionCode = 6 - versionName = "1.1.1" + versionCode = 7 + versionName = "1.1.2" testInstrumentationRunner = "androidx.test.runner.AndroidJUnitRunner" diff --git a/app/src/main/java/ru/tech/firenote/model/Type.kt b/app/src/main/java/ru/tech/firenote/model/Type.kt new file mode 100644 index 0000000..ae5eb6a --- /dev/null +++ b/app/src/main/java/ru/tech/firenote/model/Type.kt @@ -0,0 +1,11 @@ +package ru.tech.firenote.model + +import androidx.annotation.Keep +import com.google.firebase.database.IgnoreExtraProperties + +@Keep +@IgnoreExtraProperties +data class Type( + val color: Int? = null, + val type: String? = null +) \ No newline at end of file diff --git a/app/src/main/java/ru/tech/firenote/repository/NoteRepository.kt b/app/src/main/java/ru/tech/firenote/repository/NoteRepository.kt index fcd4338..8992e8a 100644 --- a/app/src/main/java/ru/tech/firenote/repository/NoteRepository.kt +++ b/app/src/main/java/ru/tech/firenote/repository/NoteRepository.kt @@ -5,6 +5,7 @@ import com.google.firebase.auth.FirebaseAuth import kotlinx.coroutines.flow.Flow import ru.tech.firenote.model.Goal import ru.tech.firenote.model.Note +import ru.tech.firenote.model.Type interface NoteRepository { @@ -29,4 +30,8 @@ interface NoteRepository { suspend fun insertGoal(goal: Goal) suspend fun deleteGoal(goal: Goal) + + suspend fun updateType(color: Int, type: String) + + suspend fun getTypes(): Flow>> } \ No newline at end of file diff --git a/app/src/main/java/ru/tech/firenote/repository/impl/NoteRepositoryImpl.kt b/app/src/main/java/ru/tech/firenote/repository/impl/NoteRepositoryImpl.kt index 1e9caa9..8721406 100644 --- a/app/src/main/java/ru/tech/firenote/repository/impl/NoteRepositoryImpl.kt +++ b/app/src/main/java/ru/tech/firenote/repository/impl/NoteRepositoryImpl.kt @@ -13,10 +13,7 @@ import kotlinx.coroutines.channels.awaitClose import kotlinx.coroutines.channels.trySendBlocking import kotlinx.coroutines.flow.Flow import kotlinx.coroutines.flow.callbackFlow -import ru.tech.firenote.model.Goal -import ru.tech.firenote.model.ImageUri -import ru.tech.firenote.model.Note -import ru.tech.firenote.model.Username +import ru.tech.firenote.model.* import ru.tech.firenote.repository.NoteRepository import javax.inject.Inject @@ -34,6 +31,7 @@ class NoteRepositoryImpl @Inject constructor( private val imageChild = "image/" private val usernameChild = "username/" private val goalsChild = "goals/" + private val typesChild = "types/" override suspend fun getNotes(): Flow>> { return callbackFlow { @@ -159,4 +157,30 @@ class NoteRepositoryImpl @Inject constructor( goal.id?.let { database.child(path).child(goalsChild + it).removeValue() } } + override suspend fun updateType(color: Int, type: String) { + database.child(path).child(typesChild + color).setValue(Type(color, type)) + } + + override suspend fun getTypes(): Flow>> { + return callbackFlow { + val postListener = object : ValueEventListener { + override fun onCancelled(error: DatabaseError) { + this@callbackFlow.trySendBlocking(Result.failure(error.toException())) + } + + override fun onDataChange(dataSnapshot: DataSnapshot) { + val items = dataSnapshot.children.map { ds -> + ds.getValue(Type::class.java) + } + this@callbackFlow.trySendBlocking(Result.success(items.filterNotNull())) + } + } + database.child(path).child(typesChild).addValueEventListener(postListener) + + awaitClose { + database.child(path).child(typesChild).removeEventListener(postListener) + } + } + } + } \ No newline at end of file diff --git a/app/src/main/java/ru/tech/firenote/ui/composable/screen/navigation/ProfileScreen.kt b/app/src/main/java/ru/tech/firenote/ui/composable/screen/navigation/ProfileScreen.kt index 81b0d8b..9b62e78 100644 --- a/app/src/main/java/ru/tech/firenote/ui/composable/screen/navigation/ProfileScreen.kt +++ b/app/src/main/java/ru/tech/firenote/ui/composable/screen/navigation/ProfileScreen.kt @@ -28,6 +28,7 @@ import androidx.compose.ui.Modifier import androidx.compose.ui.draw.alpha import androidx.compose.ui.draw.clip import androidx.compose.ui.graphics.Color +import androidx.compose.ui.graphics.toArgb import androidx.compose.ui.layout.ContentScale import androidx.compose.ui.platform.LocalConfiguration import androidx.compose.ui.platform.LocalContext @@ -45,6 +46,7 @@ import coil.compose.AsyncImage import coil.request.ImageRequest import com.google.accompanist.flowlayout.FlowRow import ru.tech.firenote.R +import ru.tech.firenote.model.Type import ru.tech.firenote.ui.composable.provider.LocalToastHost import ru.tech.firenote.ui.composable.provider.LocalWindowSize import ru.tech.firenote.ui.composable.screen.auth.isValid @@ -224,21 +226,42 @@ fun ProfileScreen( } } is UIState.Success<*> -> { + val typeState = viewModel.typeState.collectAsState().value + FlowRow { repeat(noteColors.size + 1) { if (it == 9) { Spacer( Modifier .fillMaxWidth(0.75f) - .height(20.dp)) + .height(20.dp) + ) } else { val index = if (it < 9) it else it - 1 + var type = "" + + if (typeState is UIState.Success<*>) { + val data = typeState.data as List + type = + data.firstOrNull { item -> item.color == noteColors[index].toArgb() }?.type + ?: "" + } else if (typeState is UIState.Empty) { + typeState.message?.let { msg -> + toastHost.sendToast(Icons.Outlined.Error, msg) + } + } + ProfileNoteItem( - noteColors[index] to ((state.data as? List)?.get(index) - ?: 0), - Modifier + pair = noteColors[index] to ((state.data as? List)?.get( + index + ) ?: 0), + typeText = type, + modifier = Modifier .padding(4.dp) - .fillMaxSize(0.25f) + .fillMaxSize(0.25f), + onValueChange = { newValue -> + viewModel.updateType(noteColors[index], newValue) + } ) } } diff --git a/app/src/main/java/ru/tech/firenote/ui/composable/single/lazyitem/ProfileNoteItem.kt b/app/src/main/java/ru/tech/firenote/ui/composable/single/lazyitem/ProfileNoteItem.kt index 866cc69..44fc27c 100644 --- a/app/src/main/java/ru/tech/firenote/ui/composable/single/lazyitem/ProfileNoteItem.kt +++ b/app/src/main/java/ru/tech/firenote/ui/composable/single/lazyitem/ProfileNoteItem.kt @@ -5,9 +5,11 @@ import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.Spacer import androidx.compose.foundation.layout.fillMaxSize import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.text.BasicTextField +import androidx.compose.foundation.text.KeyboardActions import androidx.compose.material3.MaterialTheme import androidx.compose.material3.Text -import androidx.compose.runtime.Composable +import androidx.compose.runtime.* import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.geometry.CornerRadius @@ -17,18 +19,27 @@ import androidx.compose.ui.graphics.Color import androidx.compose.ui.graphics.Path import androidx.compose.ui.graphics.drawscope.clipPath import androidx.compose.ui.graphics.toArgb +import androidx.compose.ui.platform.LocalFocusManager +import androidx.compose.ui.res.stringResource +import androidx.compose.ui.text.TextStyle +import androidx.compose.ui.text.style.TextAlign import androidx.compose.ui.text.style.TextOverflow import androidx.compose.ui.unit.Dp import androidx.compose.ui.unit.dp +import androidx.compose.ui.unit.sp +import ru.tech.firenote.R import ru.tech.firenote.utils.GlobalUtils.blend @Composable fun ProfileNoteItem( pair: Pair, + typeText: String, + onValueChange: (String) -> Unit, modifier: Modifier = Modifier, cornerRadius: Dp = 10.dp, cutCornerSize: Dp = 30.dp ) { + val localFocusManager = LocalFocusManager.current Box( modifier = modifier, ) { @@ -66,7 +77,42 @@ fun ProfileNoteItem( color = Color.Black, maxLines = 1, overflow = TextOverflow.Ellipsis, - modifier = Modifier.align(Alignment.Center) + modifier = Modifier + .align(Alignment.TopStart) + .padding(start = 10.dp, top = 10.dp, end = cutCornerSize) + ) + var txt by remember { mutableStateOf(typeText) } + BasicTextField( + value = txt, + onValueChange = { + txt = it + onValueChange(it) + }, + textStyle = TextStyle( + textAlign = TextAlign.Center, + fontSize = 11.sp + ), + keyboardActions = KeyboardActions( + onDone = { localFocusManager.clearFocus() } + ), + modifier = Modifier + .align(Alignment.BottomCenter) + .padding(end = 5.dp, start = 5.dp, bottom = 5.dp), + maxLines = 3 ) + + if (txt.isEmpty()) { + Text( + text = stringResource(R.string.noteType), + modifier = Modifier + .align(Alignment.BottomCenter) + .padding(end = 5.dp, start = 5.dp, bottom = 5.dp), + style = TextStyle( + textAlign = TextAlign.Center, + color = Color.DarkGray, + fontSize = 11.sp + ) + ) + } } } \ No newline at end of file diff --git a/app/src/main/java/ru/tech/firenote/ui/composable/single/toast/FancyToast.kt b/app/src/main/java/ru/tech/firenote/ui/composable/single/toast/FancyToast.kt index ec2db0f..8033256 100644 --- a/app/src/main/java/ru/tech/firenote/ui/composable/single/toast/FancyToast.kt +++ b/app/src/main/java/ru/tech/firenote/ui/composable/single/toast/FancyToast.kt @@ -3,6 +3,7 @@ package ru.tech.firenote.ui.composable.single.toast import android.widget.Toast import androidx.compose.animation.* import androidx.compose.animation.core.MutableTransitionState +import androidx.compose.foundation.BorderStroke import androidx.compose.foundation.layout.* import androidx.compose.foundation.shape.RoundedCornerShape import androidx.compose.material3.* @@ -39,13 +40,10 @@ fun FancyToast( val sizeMax = max(conf.screenWidthDp, conf.screenHeightDp).dp Box( - Modifier - .fillMaxSize() + modifier = Modifier.fillMaxSize() ) { AnimatedVisibility( modifier = Modifier - .wrapContentHeight() - .wrapContentWidth() .align(Alignment.BottomCenter) .padding(bottom = sizeMax * 0.15f), visibleState = showToast, @@ -53,12 +51,11 @@ fun FancyToast( exit = fadeOut() + scaleOut() ) { Card( - elevation = CardDefaults.cardElevation(10.dp), + border = BorderStroke(1.dp, MaterialTheme.colorScheme.tertiaryContainer), contentColor = MaterialTheme.colorScheme.onTertiaryContainer, modifier = Modifier - .alpha(0.95f) - .wrapContentHeight() - .wrapContentWidth() + .alpha(0.98f) + .heightIn(48.dp) .widthIn(0.dp, (sizeMin * 0.7f)), shape = RoundedCornerShape(24.dp) ) { diff --git a/app/src/main/java/ru/tech/firenote/viewModel/navigation/ProfileViewModel.kt b/app/src/main/java/ru/tech/firenote/viewModel/navigation/ProfileViewModel.kt index 746ee7d..f6531b1 100644 --- a/app/src/main/java/ru/tech/firenote/viewModel/navigation/ProfileViewModel.kt +++ b/app/src/main/java/ru/tech/firenote/viewModel/navigation/ProfileViewModel.kt @@ -1,6 +1,8 @@ package ru.tech.firenote.viewModel.navigation import android.net.Uri +import androidx.compose.ui.graphics.Color +import androidx.compose.ui.graphics.toArgb import androidx.lifecycle.ViewModel import androidx.lifecycle.viewModelScope import dagger.hilt.android.lifecycle.HiltViewModel @@ -32,10 +34,14 @@ class ProfileViewModel @Inject constructor( private val _username = MutableStateFlow(UIState.Success(email.split("@")[0])) var username: StateFlow = _username + private val _typeState = MutableStateFlow(UIState.Empty()) + val typeState: StateFlow = _typeState + init { loadUsername() loadProfileImage() getNotes() + getTypes() } private fun getNotes() { @@ -59,6 +65,19 @@ class ProfileViewModel @Inject constructor( } } + private fun getTypes() { + viewModelScope.launch { + repository.getTypes().collect { + if (it.isSuccess) { + val list = it.getOrNull() + _typeState.value = UIState.Success(list) + } else { + _typeState.value = UIState.Empty(it.exceptionOrNull()?.localizedMessage) + } + } + } + } + private fun loadProfileImage() { viewModelScope.launch { _photoState.value = UIState.Loading @@ -130,4 +149,10 @@ class ProfileViewModel @Inject constructor( } } } + + fun updateType(color: Color, type: String) { + viewModelScope.launch { + repository.updateType(color.toArgb(), type) + } + } } \ No newline at end of file diff --git a/app/src/main/res/values-ru-rRU/strings.xml b/app/src/main/res/values-ru-rRU/strings.xml index e116936..f8fb621 100644 --- a/app/src/main/res/values-ru-rRU/strings.xml +++ b/app/src/main/res/values-ru-rRU/strings.xml @@ -75,4 +75,5 @@ Ничего не найдено по вашему запросу "Никнейм изменен на " Успешно выбрано изображение + Тип заметки \ 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 52c9817..6ea5237 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -75,4 +75,5 @@ Nothing found, try to change your search query "Username changed to " Image picked succesfully + Note type \ No newline at end of file