feature(room preview): Add option to forget room, improve the room preview screen for banned rooms.
Some internal refactoring was done too: - Remove RoomInfo.isPublic to only use JoinRule. - Also take into account restricted access rooms for previews.
This commit is contained in:
parent
819503b162
commit
a73bcb71d5
50 changed files with 886 additions and 357 deletions
|
|
@ -9,4 +9,5 @@ package io.element.android.features.roomaliasresolver.impl
|
|||
|
||||
sealed interface RoomAliasResolverEvents {
|
||||
data object Retry : RoomAliasResolverEvents
|
||||
data object DismissError : RoomAliasResolverEvents
|
||||
}
|
||||
|
|
|
|||
|
|
@ -46,6 +46,7 @@ class RoomAliasResolverPresenter @AssistedInject constructor(
|
|||
fun handleEvents(event: RoomAliasResolverEvents) {
|
||||
when (event) {
|
||||
RoomAliasResolverEvents.Retry -> coroutineScope.resolveAlias(resolveState)
|
||||
RoomAliasResolverEvents.DismissError -> resolveState.value = AsyncData.Uninitialized
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -60,7 +61,7 @@ class RoomAliasResolverPresenter @AssistedInject constructor(
|
|||
suspend {
|
||||
matrixClient.resolveRoomAlias(roomAlias)
|
||||
.getOrThrow()
|
||||
.getOrElse { error("Failed to resolve room alias $roomAlias") }
|
||||
.getOrElse { throw RoomAliasResolverFailures.UnknownAlias }
|
||||
}.runCatchingUpdatingState(resolveState)
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -18,3 +18,7 @@ data class RoomAliasResolverState(
|
|||
val resolveState: AsyncData<ResolvedRoomAlias>,
|
||||
val eventSink: (RoomAliasResolverEvents) -> Unit
|
||||
)
|
||||
|
||||
sealed class RoomAliasResolverFailures : Exception() {
|
||||
data object UnknownAlias : RoomAliasResolverFailures()
|
||||
}
|
||||
|
|
|
|||
|
|
@ -10,6 +10,7 @@ package io.element.android.features.roomaliasresolver.impl
|
|||
import androidx.compose.ui.tooling.preview.PreviewParameterProvider
|
||||
import io.element.android.libraries.architecture.AsyncData
|
||||
import io.element.android.libraries.matrix.api.core.RoomAlias
|
||||
import io.element.android.libraries.matrix.api.exception.ClientException
|
||||
import io.element.android.libraries.matrix.api.room.alias.ResolvedRoomAlias
|
||||
|
||||
open class RoomAliasResolverStateProvider : PreviewParameterProvider<RoomAliasResolverState> {
|
||||
|
|
@ -17,10 +18,10 @@ open class RoomAliasResolverStateProvider : PreviewParameterProvider<RoomAliasRe
|
|||
get() = sequenceOf(
|
||||
aRoomAliasResolverState(),
|
||||
aRoomAliasResolverState(
|
||||
resolveState = AsyncData.Loading(),
|
||||
resolveState = AsyncData.Failure(ClientException.Generic("Something went wrong")),
|
||||
),
|
||||
aRoomAliasResolverState(
|
||||
resolveState = AsyncData.Failure(Exception("Error")),
|
||||
resolveState = AsyncData.Failure(RoomAliasResolverFailures.UnknownAlias),
|
||||
),
|
||||
)
|
||||
}
|
||||
|
|
|
|||
|
|
@ -7,12 +7,11 @@
|
|||
|
||||
package io.element.android.features.roomaliasresolver.impl
|
||||
|
||||
import androidx.compose.foundation.layout.Arrangement
|
||||
import androidx.compose.foundation.layout.Box
|
||||
import androidx.compose.foundation.layout.PaddingValues
|
||||
import androidx.compose.foundation.layout.Row
|
||||
import androidx.compose.foundation.layout.Spacer
|
||||
import androidx.compose.foundation.layout.fillMaxSize
|
||||
import androidx.compose.foundation.layout.fillMaxWidth
|
||||
import androidx.compose.foundation.layout.height
|
||||
import androidx.compose.material3.ExperimentalMaterial3Api
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.runtime.LaunchedEffect
|
||||
|
|
@ -21,25 +20,22 @@ import androidx.compose.runtime.rememberUpdatedState
|
|||
import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.graphics.Color
|
||||
import androidx.compose.ui.res.stringResource
|
||||
import androidx.compose.ui.text.style.TextAlign
|
||||
import androidx.compose.ui.tooling.preview.PreviewParameter
|
||||
import androidx.compose.ui.unit.dp
|
||||
import io.element.android.compound.theme.ElementTheme
|
||||
import io.element.android.libraries.architecture.AsyncData
|
||||
import io.element.android.libraries.designsystem.atomic.atoms.PlaceholderAtom
|
||||
import io.element.android.libraries.designsystem.atomic.atoms.RoomPreviewTitleAtom
|
||||
import io.element.android.libraries.designsystem.atomic.atoms.RoomPreviewSubtitleAtom
|
||||
import io.element.android.libraries.designsystem.atomic.organisms.RoomPreviewOrganism
|
||||
import io.element.android.libraries.designsystem.atomic.pages.HeaderFooterPage
|
||||
import io.element.android.libraries.designsystem.background.LightGradientBackground
|
||||
import io.element.android.libraries.designsystem.components.avatar.AvatarSize
|
||||
import io.element.android.libraries.designsystem.components.button.BackButton
|
||||
import io.element.android.libraries.designsystem.components.dialogs.ErrorDialog
|
||||
import io.element.android.libraries.designsystem.components.dialogs.RetryDialog
|
||||
import io.element.android.libraries.designsystem.preview.ElementPreview
|
||||
import io.element.android.libraries.designsystem.preview.PreviewsDayNight
|
||||
import io.element.android.libraries.designsystem.theme.components.Button
|
||||
import io.element.android.libraries.designsystem.theme.components.ButtonSize
|
||||
import io.element.android.libraries.designsystem.theme.components.CircularProgressIndicator
|
||||
import io.element.android.libraries.designsystem.theme.components.Text
|
||||
import io.element.android.libraries.designsystem.theme.components.TopAppBar
|
||||
import io.element.android.libraries.matrix.api.core.RoomAlias
|
||||
import io.element.android.libraries.matrix.api.room.alias.ResolvedRoomAlias
|
||||
import io.element.android.libraries.ui.strings.CommonStrings
|
||||
|
||||
|
|
@ -50,66 +46,72 @@ fun RoomAliasResolverView(
|
|||
onSuccess: (ResolvedRoomAlias) -> Unit,
|
||||
modifier: Modifier = Modifier,
|
||||
) {
|
||||
val latestOnSuccess by rememberUpdatedState(onSuccess)
|
||||
LaunchedEffect(state.resolveState) {
|
||||
if (state.resolveState is AsyncData.Success) {
|
||||
latestOnSuccess(state.resolveState.data)
|
||||
}
|
||||
}
|
||||
Box(
|
||||
modifier = modifier.fillMaxSize(),
|
||||
) {
|
||||
LightGradientBackground()
|
||||
HeaderFooterPage(
|
||||
containerColor = Color.Transparent,
|
||||
paddingValues = PaddingValues(16.dp),
|
||||
paddingValues = PaddingValues(
|
||||
horizontal = 16.dp,
|
||||
vertical = 32.dp
|
||||
),
|
||||
topBar = {
|
||||
RoomAliasResolverTopBar(onBackClick = onBackClick)
|
||||
},
|
||||
content = {
|
||||
RoomAliasResolverContent(state = state)
|
||||
RoomAliasResolverContent(roomAlias = state.roomAlias, isLoading = state.resolveState.isLoading())
|
||||
},
|
||||
footer = {
|
||||
RoomAliasResolverFooter(
|
||||
state = state,
|
||||
)
|
||||
)
|
||||
ResolvedRoomAliasView(
|
||||
resolvedRoomAlias = state.resolveState,
|
||||
onSuccess = onSuccess,
|
||||
onRetry = { state.eventSink(RoomAliasResolverEvents.Retry) },
|
||||
onDismissError = {
|
||||
state.eventSink(RoomAliasResolverEvents.DismissError)
|
||||
onBackClick()
|
||||
}
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
@Composable
|
||||
private fun RoomAliasResolverFooter(
|
||||
state: RoomAliasResolverState,
|
||||
modifier: Modifier = Modifier,
|
||||
private fun ResolvedRoomAliasView(
|
||||
resolvedRoomAlias: AsyncData<ResolvedRoomAlias>,
|
||||
onSuccess: (ResolvedRoomAlias) -> Unit,
|
||||
onRetry: () -> Unit,
|
||||
onDismissError: () -> Unit,
|
||||
) {
|
||||
when (state.resolveState) {
|
||||
is AsyncData.Failure -> {
|
||||
Button(
|
||||
text = stringResource(CommonStrings.action_retry),
|
||||
onClick = {
|
||||
state.eventSink(RoomAliasResolverEvents.Retry)
|
||||
},
|
||||
modifier = modifier.fillMaxWidth(),
|
||||
size = ButtonSize.Large,
|
||||
)
|
||||
}
|
||||
is AsyncData.Loading -> {
|
||||
Row(
|
||||
modifier = Modifier.fillMaxWidth(),
|
||||
horizontalArrangement = Arrangement.Center,
|
||||
) {
|
||||
CircularProgressIndicator()
|
||||
when (resolvedRoomAlias) {
|
||||
is AsyncData.Success -> {
|
||||
val latestOnSuccess by rememberUpdatedState(onSuccess)
|
||||
LaunchedEffect(Unit) {
|
||||
latestOnSuccess(resolvedRoomAlias.data)
|
||||
}
|
||||
}
|
||||
AsyncData.Uninitialized,
|
||||
is AsyncData.Success -> Unit
|
||||
is AsyncData.Failure -> {
|
||||
if (resolvedRoomAlias.error is RoomAliasResolverFailures.UnknownAlias) {
|
||||
ErrorDialog(
|
||||
title = stringResource(id = R.string.screen_join_room_loading_alert_title),
|
||||
content = stringResource(id = R.string.screen_room_alias_resolver_resolve_alias_failure),
|
||||
onSubmit = onDismissError
|
||||
)
|
||||
} else {
|
||||
RetryDialog(
|
||||
title = stringResource(id = R.string.screen_join_room_loading_alert_title),
|
||||
content = stringResource(id = CommonStrings.error_network_or_server_issue),
|
||||
onRetry = onRetry,
|
||||
onDismiss = onDismissError
|
||||
)
|
||||
}
|
||||
}
|
||||
else -> Unit
|
||||
}
|
||||
}
|
||||
|
||||
@Composable
|
||||
private fun RoomAliasResolverContent(
|
||||
state: RoomAliasResolverState,
|
||||
roomAlias: RoomAlias,
|
||||
isLoading: Boolean,
|
||||
modifier: Modifier = Modifier,
|
||||
) {
|
||||
RoomPreviewOrganism(
|
||||
|
|
@ -118,20 +120,13 @@ private fun RoomAliasResolverContent(
|
|||
PlaceholderAtom(width = AvatarSize.RoomHeader.dp, height = AvatarSize.RoomHeader.dp)
|
||||
},
|
||||
title = {
|
||||
RoomPreviewTitleAtom(state.roomAlias.value)
|
||||
RoomPreviewSubtitleAtom(roomAlias.value)
|
||||
},
|
||||
subtitle = {
|
||||
},
|
||||
description = {
|
||||
if (state.resolveState.isFailure()) {
|
||||
Text(
|
||||
text = stringResource(id = R.string.screen_room_alias_resolver_resolve_alias_failure),
|
||||
textAlign = TextAlign.Center,
|
||||
color = ElementTheme.colors.textCriticalPrimary,
|
||||
)
|
||||
if (isLoading) {
|
||||
Spacer(Modifier.height(8.dp))
|
||||
CircularProgressIndicator()
|
||||
}
|
||||
},
|
||||
memberCount = {
|
||||
}
|
||||
)
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,4 +1,5 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
|
||||
<string name="screen_join_room_loading_alert_title">"We couldn’t display this room preview"</string>
|
||||
<string name="screen_room_alias_resolver_resolve_alias_failure">"Failed to resolve room alias."</string>
|
||||
</resources>
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue