From 460a99d95d3dc87aaffb66b764d19ee18df75242 Mon Sep 17 00:00:00 2001 From: Vitor Pamplona Date: Wed, 25 Oct 2023 17:22:26 -0400 Subject: [PATCH] Avoids creation of the LiveData in every recomposition. --- .../com/vitorpamplona/amethyst/model/Note.kt | 4 +++ .../amethyst/ui/navigation/DrawerContent.kt | 8 +++--- .../ui/note/ChatroomMessageCompose.kt | 9 ++++--- .../amethyst/ui/note/NoteCompose.kt | 26 +++++++++++-------- .../amethyst/ui/note/ReactionsRow.kt | 8 +++--- .../amethyst/ui/note/UserProfilePicture.kt | 10 +++---- .../amethyst/ui/note/UsernameDisplay.kt | 6 +---- 7 files changed, 39 insertions(+), 32 deletions(-) diff --git a/app/src/main/java/com/vitorpamplona/amethyst/model/Note.kt b/app/src/main/java/com/vitorpamplona/amethyst/model/Note.kt index d3bacac2f..b7d2db63a 100644 --- a/app/src/main/java/com/vitorpamplona/amethyst/model/Note.kt +++ b/app/src/main/java/com/vitorpamplona/amethyst/model/Note.kt @@ -777,6 +777,10 @@ class NoteLiveSet(u: Note) { }.toImmutableList() } + val content = innerMetadata.map { + it.note.event?.content() ?: "" + } + fun isInUse(): Boolean { return metadata.hasObservers() || reactions.hasObservers() || diff --git a/app/src/main/java/com/vitorpamplona/amethyst/ui/navigation/DrawerContent.kt b/app/src/main/java/com/vitorpamplona/amethyst/ui/navigation/DrawerContent.kt index 3592aeacb..428df7a19 100644 --- a/app/src/main/java/com/vitorpamplona/amethyst/ui/navigation/DrawerContent.kt +++ b/app/src/main/java/com/vitorpamplona/amethyst/ui/navigation/DrawerContent.kt @@ -60,7 +60,6 @@ import androidx.compose.ui.text.style.TextOverflow import androidx.compose.ui.unit.dp import androidx.compose.ui.unit.sp import androidx.lifecycle.compose.collectAsStateWithLifecycle -import androidx.lifecycle.map import coil.compose.AsyncImage import com.vitorpamplona.amethyst.BuildConfig import com.vitorpamplona.amethyst.LocalPreferences @@ -178,7 +177,8 @@ fun ProfileContent( painter = painterResource(R.drawable.profile_banner), contentDescription = stringResource(R.string.profile_banner), contentScale = ContentScale.FillWidth, - modifier = Modifier.fillMaxWidth() + modifier = Modifier + .fillMaxWidth() .height(120.dp) ) } @@ -290,9 +290,7 @@ private fun EditStatusBoxes(baseAccountUser: User, accountViewModel: AccountView ) } else { statuses.forEach { - val originalStatus by it.live().metadata.map { - it.note.event?.content() ?: "" - }.observeAsState(it.event?.content() ?: "") + val originalStatus by it.live().content.observeAsState("") val thisStatus = remember { mutableStateOf(originalStatus) diff --git a/app/src/main/java/com/vitorpamplona/amethyst/ui/note/ChatroomMessageCompose.kt b/app/src/main/java/com/vitorpamplona/amethyst/ui/note/ChatroomMessageCompose.kt index 6448c8ac6..ff73e40e6 100644 --- a/app/src/main/java/com/vitorpamplona/amethyst/ui/note/ChatroomMessageCompose.kt +++ b/app/src/main/java/com/vitorpamplona/amethyst/ui/note/ChatroomMessageCompose.kt @@ -41,6 +41,7 @@ import androidx.compose.ui.res.painterResource import androidx.compose.ui.res.stringResource import androidx.compose.ui.text.font.FontWeight import androidx.compose.ui.unit.dp +import androidx.lifecycle.distinctUntilChanged import androidx.lifecycle.map import com.vitorpamplona.amethyst.R import com.vitorpamplona.amethyst.model.Note @@ -121,9 +122,11 @@ fun CheckHiddenChatMessage( nav: (String) -> Unit, onWantsToReply: (Note) -> Unit ) { - val isHidden by accountViewModel.account.liveHiddenUsers.map { - baseNote.isHiddenFor(it) - }.observeAsState(accountViewModel.isNoteHidden(baseNote)) + val isHidden by remember { + accountViewModel.account.liveHiddenUsers.map { + baseNote.isHiddenFor(it) + }.distinctUntilChanged() + }.observeAsState(false) if (!isHidden) { LoadedChatMessageCompose( diff --git a/app/src/main/java/com/vitorpamplona/amethyst/ui/note/NoteCompose.kt b/app/src/main/java/com/vitorpamplona/amethyst/ui/note/NoteCompose.kt index 7a9ad342e..029a7082f 100644 --- a/app/src/main/java/com/vitorpamplona/amethyst/ui/note/NoteCompose.kt +++ b/app/src/main/java/com/vitorpamplona/amethyst/ui/note/NoteCompose.kt @@ -302,9 +302,11 @@ fun CheckHiddenNoteCompose( nav = nav ) } else { - val isHidden by accountViewModel.account.liveHiddenUsers.map { - note.isHiddenFor(it) - }.observeAsState(accountViewModel.isNoteHidden(note)) + val isHidden by remember(note) { + accountViewModel.account.liveHiddenUsers.map { + note.isHiddenFor(it) + }.distinctUntilChanged() + }.observeAsState(false) Crossfade(targetState = isHidden) { if (!it) { @@ -791,11 +793,11 @@ private fun ShortCommunityActionOptions( @Composable fun WatchAddressableNoteFollows(note: AddressableNote, accountViewModel: AccountViewModel, onFollowChanges: @Composable (Boolean) -> Unit) { - val showFollowingMark by accountViewModel.userFollows.map { - it.user.latestContactList?.isTaggedAddressableNote(note.idHex) ?: false - }.distinctUntilChanged().observeAsState( - accountViewModel.userProfile().latestContactList?.isTaggedAddressableNote(note.idHex) ?: false - ) + val showFollowingMark by remember { + accountViewModel.userFollows.map { + it.user.latestContactList?.isTaggedAddressableNote(note.idHex) ?: false + }.distinctUntilChanged() + }.observeAsState(false) onFollowChanges(showFollowingMark) } @@ -2212,9 +2214,11 @@ private fun EmojiListOptions( accountViewModel ) { it?.let { usersEmojiList -> - val hasAddedThis by usersEmojiList.live().metadata.map { - usersEmojiList.event?.isTaggedAddressableNote(emojiPackNote.idHex) - }.distinctUntilChanged().observeAsState() + val hasAddedThis by remember { + usersEmojiList.live().metadata.map { + usersEmojiList.event?.isTaggedAddressableNote(emojiPackNote.idHex) + }.distinctUntilChanged() + }.observeAsState() Crossfade(targetState = hasAddedThis) { val scope = rememberCoroutineScope() diff --git a/app/src/main/java/com/vitorpamplona/amethyst/ui/note/ReactionsRow.kt b/app/src/main/java/com/vitorpamplona/amethyst/ui/note/ReactionsRow.kt index 68bbf43be..0e2d6b8ed 100644 --- a/app/src/main/java/com/vitorpamplona/amethyst/ui/note/ReactionsRow.kt +++ b/app/src/main/java/com/vitorpamplona/amethyst/ui/note/ReactionsRow.kt @@ -692,9 +692,11 @@ fun BoostReaction( @Composable fun BoostIcon(baseNote: Note, iconSize: Dp = Size20dp, grayTint: Color, accountViewModel: AccountViewModel) { - val iconTint by baseNote.live().boosts.map { - if (it.note.isBoostedBy(accountViewModel.userProfile())) Color.Unspecified else grayTint - }.distinctUntilChanged().observeAsState(grayTint) + val iconTint by remember(baseNote) { + baseNote.live().boosts.map { + if (it.note.isBoostedBy(accountViewModel.userProfile())) Color.Unspecified else grayTint + }.distinctUntilChanged() + }.observeAsState(grayTint) val iconModifier = remember { Modifier.size(iconSize) diff --git a/app/src/main/java/com/vitorpamplona/amethyst/ui/note/UserProfilePicture.kt b/app/src/main/java/com/vitorpamplona/amethyst/ui/note/UserProfilePicture.kt index 72280d34c..437242f44 100644 --- a/app/src/main/java/com/vitorpamplona/amethyst/ui/note/UserProfilePicture.kt +++ b/app/src/main/java/com/vitorpamplona/amethyst/ui/note/UserProfilePicture.kt @@ -363,11 +363,11 @@ fun ObserveAndDisplayFollowingMark(userHex: String, iconSize: Dp, accountViewMod @Composable fun WatchUserFollows(userHex: String, accountViewModel: AccountViewModel, onFollowChanges: @Composable (Boolean) -> Unit) { - val showFollowingMark by accountViewModel.userFollows.map { - it.user.isFollowingCached(userHex) || (userHex == accountViewModel.account.userProfile().pubkeyHex) - }.distinctUntilChanged().observeAsState( - accountViewModel.account.userProfile().isFollowingCached(userHex) || (userHex == accountViewModel.account.userProfile().pubkeyHex) - ) + val showFollowingMark by remember { + accountViewModel.userFollows.map { + it.user.isFollowingCached(userHex) || (userHex == accountViewModel.account.userProfile().pubkeyHex) + }.distinctUntilChanged() + }.observeAsState(false) onFollowChanges(showFollowingMark) } diff --git a/app/src/main/java/com/vitorpamplona/amethyst/ui/note/UsernameDisplay.kt b/app/src/main/java/com/vitorpamplona/amethyst/ui/note/UsernameDisplay.kt index 21c9ba047..82ee13575 100644 --- a/app/src/main/java/com/vitorpamplona/amethyst/ui/note/UsernameDisplay.kt +++ b/app/src/main/java/com/vitorpamplona/amethyst/ui/note/UsernameDisplay.kt @@ -21,8 +21,6 @@ import androidx.compose.ui.platform.LocalLifecycleOwner import androidx.compose.ui.text.font.FontWeight import androidx.compose.ui.text.style.TextOverflow import androidx.lifecycle.LifecycleOwner -import androidx.lifecycle.distinctUntilChanged -import androidx.lifecycle.map import com.vitorpamplona.amethyst.model.Note import com.vitorpamplona.amethyst.model.User import com.vitorpamplona.amethyst.service.tts.TextToSpeechHelper @@ -34,9 +32,7 @@ import com.vitorpamplona.quartz.events.ImmutableListOfLists @Composable fun NoteUsernameDisplay(baseNote: Note, weight: Modifier = Modifier, showPlayButton: Boolean = true, textColor: Color = Color.Unspecified) { - val authorState by baseNote.live().metadata.map { - it.note.author - }.distinctUntilChanged().observeAsState(baseNote.author) + val authorState by baseNote.live().authorChanges.observeAsState(baseNote.author) Crossfade(targetState = authorState, modifier = weight) { it?.let {