Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Create UserStoryFlowPage #1737

Merged
merged 12 commits into from
Nov 7, 2023
Original file line number Diff line number Diff line change
Expand Up @@ -17,19 +17,16 @@
package io.element.android.features.lockscreen.impl.setup.biometric

import androidx.activity.compose.BackHandler
import androidx.compose.foundation.layout.Arrangement.spacedBy
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.padding
import androidx.compose.material.icons.Icons
import androidx.compose.material.icons.filled.Fingerprint
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.PreviewParameter
import androidx.compose.ui.unit.dp
import io.element.android.features.lockscreen.impl.R
import io.element.android.libraries.designsystem.atomic.molecules.ButtonColumnMolecule
import io.element.android.libraries.designsystem.atomic.molecules.IconTitleSubtitleMolecule
import io.element.android.libraries.designsystem.atomic.pages.HeaderFooterPage
import io.element.android.libraries.designsystem.preview.ElementPreview
Expand Down Expand Up @@ -76,10 +73,8 @@ private fun SetupBiometricFooter(
onSkipClicked: () -> Unit,
modifier: Modifier = Modifier
) {
Column(
modifier = modifier.fillMaxWidth(),
verticalArrangement = spacedBy(16.dp),
horizontalAlignment = Alignment.CenterHorizontally
ButtonColumnMolecule(
modifier = modifier,
) {
val biometricAuth = stringResource(id = R.string.screen_app_lock_biometric_authentication)
Button(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,9 +18,9 @@

import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.ColumnScope
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.padding
import androidx.compose.material3.ExperimentalMaterial3Api
import androidx.compose.runtime.Composable
import androidx.compose.runtime.LaunchedEffect
import androidx.compose.ui.Alignment
Expand All @@ -29,19 +29,15 @@
import androidx.compose.ui.tooling.preview.PreviewParameter
import androidx.compose.ui.unit.dp
import io.element.android.libraries.architecture.Async
import io.element.android.libraries.designsystem.atomic.molecules.ButtonColumnMolecule
import io.element.android.libraries.designsystem.atomic.molecules.IconTitleSubtitleMolecule
import io.element.android.libraries.designsystem.atomic.pages.HeaderFooterPage
import io.element.android.libraries.designsystem.atomic.pages.FlowStepPage
import io.element.android.libraries.designsystem.components.ProgressDialog
import io.element.android.libraries.designsystem.components.button.BackButton
import io.element.android.libraries.designsystem.components.dialogs.ConfirmationDialog
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.LinearProgressIndicator
import io.element.android.libraries.designsystem.theme.components.OutlinedButton
import io.element.android.libraries.designsystem.theme.components.Text
import io.element.android.libraries.designsystem.theme.components.TopAppBar
import io.element.android.libraries.designsystem.theme.progressIndicatorTrackColor
import io.element.android.libraries.designsystem.utils.CommonDrawables
import io.element.android.libraries.matrix.api.encryption.BackupUploadState
Expand All @@ -51,7 +47,6 @@
import io.element.android.libraries.theme.ElementTheme
import io.element.android.libraries.ui.strings.CommonStrings

@OptIn(ExperimentalMaterial3Api::class)
@Composable
fun LogoutView(
state: LogoutState,
Expand All @@ -62,39 +57,30 @@
) {
val eventSink = state.eventSink

HeaderFooterPage(
FlowStepPage(
onBackClicked = onBackClicked,
title = title(state),
subTitle = subtitle(state),
iconResourceId = CommonDrawables.ic_key,
modifier = modifier,
topBar = {
TopAppBar(
navigationIcon = { BackButton(onClick = onBackClicked) },
title = {},
)
},
header = {
HeaderContent(state = state)
},
footer = {
BottomMenu(
content = { Content(state) },
buttons = {
Buttons(
state = state,
onChangeRecoveryKeyClicked = onChangeRecoveryKeyClicked,
onLogoutClicked = {
eventSink(LogoutEvents.Logout(ignoreSdkError = false))
},
}
)
}
) {
Content(state = state)
}
},
)

// Log out confirmation dialog
if (state.showConfirmationDialog) {
ConfirmationDialog(
title = stringResource(id = CommonStrings.action_signout),
content = stringResource(id = R.string.screen_signout_confirmation_dialog_content),
submitText = stringResource(id = CommonStrings.action_signout),
onCancelClicked = {
eventSink(LogoutEvents.CloseDialogs)
},
onSubmitClicked = {
eventSink(LogoutEvents.Logout(ignoreSdkError = false))
},
Expand All @@ -112,9 +98,6 @@
title = stringResource(id = CommonStrings.dialog_title_error),
content = stringResource(id = CommonStrings.error_unknown),
submitText = stringResource(id = CommonStrings.action_signout_anyway),
onCancelClicked = {
eventSink(LogoutEvents.CloseDialogs)
},
onSubmitClicked = {
eventSink(LogoutEvents.Logout(ignoreSdkError = true))
},
Expand All @@ -132,30 +115,23 @@
}

@Composable
private fun HeaderContent(
state: LogoutState,
modifier: Modifier = Modifier,
) {
val title = when {
private fun title(state: LogoutState): String {

Check warning on line 118 in features/logout/impl/src/main/kotlin/io/element/android/features/logout/impl/LogoutView.kt

View check run for this annotation

Codecov / codecov/patch

features/logout/impl/src/main/kotlin/io/element/android/features/logout/impl/LogoutView.kt#L118

Added line #L118 was not covered by tests
return when {
state.backupUploadState.isBackingUp() -> stringResource(id = R.string.screen_signout_key_backup_ongoing_title)
state.isLastSession -> stringResource(id = R.string.screen_signout_key_backup_disabled_title)
else -> stringResource(CommonStrings.action_signout)
}
val subtitle = when {
}

@Composable
private fun subtitle(state: LogoutState): String? {

Check warning on line 127 in features/logout/impl/src/main/kotlin/io/element/android/features/logout/impl/LogoutView.kt

View check run for this annotation

Codecov / codecov/patch

features/logout/impl/src/main/kotlin/io/element/android/features/logout/impl/LogoutView.kt#L127

Added line #L127 was not covered by tests
return when {
(state.backupUploadState as? BackupUploadState.SteadyException)?.exception is SteadyStateException.Connection ->
stringResource(id = R.string.screen_signout_key_backup_offline_subtitle)
state.backupUploadState.isBackingUp() -> stringResource(id = R.string.screen_signout_key_backup_ongoing_subtitle)
state.isLastSession -> stringResource(id = R.string.screen_signout_key_backup_disabled_subtitle)
else -> null
}

val paddingTop = 0.dp
IconTitleSubtitleMolecule(
modifier = modifier.padding(top = paddingTop),
iconResourceId = CommonDrawables.ic_key,
title = title,
subTitle = subtitle,
)
}

private fun BackupUploadState.isBackingUp(): Boolean {
Expand All @@ -171,37 +147,33 @@
}

@Composable
private fun BottomMenu(
private fun ColumnScope.Buttons(
state: LogoutState,
onLogoutClicked: () -> Unit,
onChangeRecoveryKeyClicked: () -> Unit,
) {
val logoutAction = state.logoutAction
ButtonColumnMolecule(
modifier = Modifier.padding(bottom = 20.dp)
) {
if (state.isLastSession) {
OutlinedButton(
text = stringResource(id = CommonStrings.common_settings),
modifier = Modifier.fillMaxWidth(),
onClick = onChangeRecoveryKeyClicked,
)
}
val signOutSubmitRes = when {
logoutAction is Async.Loading -> R.string.screen_signout_in_progress_dialog_content
state.backupUploadState.isBackingUp() -> CommonStrings.action_signout_anyway
else -> CommonStrings.action_signout
}
Button(
text = stringResource(id = signOutSubmitRes),
showProgress = logoutAction is Async.Loading,
destructive = true,
modifier = Modifier
.fillMaxWidth()
.testTag(TestTags.signOut),
onClick = onLogoutClicked,
if (state.isLastSession) {
OutlinedButton(
text = stringResource(id = CommonStrings.common_settings),
modifier = Modifier.fillMaxWidth(),
onClick = onChangeRecoveryKeyClicked,
)
}
val signOutSubmitRes = when {
logoutAction is Async.Loading -> R.string.screen_signout_in_progress_dialog_content
state.backupUploadState.isBackingUp() -> CommonStrings.action_signout_anyway
else -> CommonStrings.action_signout
}
Button(
text = stringResource(id = signOutSubmitRes),
showProgress = logoutAction is Async.Loading,
destructive = true,
modifier = Modifier
.fillMaxWidth()
.testTag(TestTags.signOut),
onClick = onLogoutClicked,
)
}

@Composable
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,11 +18,11 @@

import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.ColumnScope
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.material3.ExperimentalMaterial3Api
import androidx.compose.runtime.Composable
import androidx.compose.runtime.LaunchedEffect
import androidx.compose.ui.Modifier
Expand All @@ -31,22 +31,17 @@
import androidx.compose.ui.unit.dp
import io.element.android.features.securebackup.impl.R
import io.element.android.libraries.architecture.Async
import io.element.android.libraries.designsystem.atomic.molecules.ButtonColumnMolecule
import io.element.android.libraries.designsystem.atomic.molecules.IconTitleSubtitleMolecule
import io.element.android.libraries.designsystem.atomic.pages.HeaderFooterPage
import io.element.android.libraries.designsystem.components.button.BackButton
import io.element.android.libraries.designsystem.atomic.pages.FlowStepPage
import io.element.android.libraries.designsystem.components.dialogs.ConfirmationDialog
import io.element.android.libraries.designsystem.components.dialogs.ErrorDialog
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.Icon
import io.element.android.libraries.designsystem.theme.components.Text
import io.element.android.libraries.designsystem.theme.components.TopAppBar
import io.element.android.libraries.designsystem.utils.CommonDrawables
import io.element.android.libraries.theme.ElementTheme

@OptIn(ExperimentalMaterial3Api::class)
@Composable
fun SecureBackupDisableView(
state: SecureBackupDisableState,
Expand All @@ -59,23 +54,16 @@
onDone()
}
}
HeaderFooterPage(
FlowStepPage(
modifier = modifier,
topBar = {
TopAppBar(
navigationIcon = { BackButton(onClick = onBackClicked) },
title = {},
)
},
header = {
HeaderContent()
},
footer = {
BottomMenu(state = state)
}
) {
Content(state = state)
}
onBackClicked = onBackClicked,
title = stringResource(id = R.string.screen_key_backup_disable_title),
subTitle = stringResource(id = R.string.screen_key_backup_disable_description),
iconResourceId = CommonDrawables.ic_key_off,
content = { Content(state = state) },
buttons = { Buttons(state = state) },
)

if (state.showConfirmationDialog) {
SecureBackupDisableConfirmationDialog(
onConfirm = { state.eventSink.invoke(SecureBackupDisableEvents.DisableBackup(force = true)) },
Expand All @@ -102,32 +90,16 @@
}

@Composable
private fun HeaderContent(
modifier: Modifier = Modifier,
) {
IconTitleSubtitleMolecule(
modifier = modifier.padding(top = 0.dp),
iconResourceId = CommonDrawables.ic_key_off,
title = stringResource(id = R.string.screen_key_backup_disable_title),
subTitle = stringResource(id = R.string.screen_key_backup_disable_description),
)
}

@Composable
private fun BottomMenu(
private fun ColumnScope.Buttons(
state: SecureBackupDisableState,
) {
ButtonColumnMolecule(
modifier = Modifier.padding(bottom = 20.dp)
) {
Button(
text = stringResource(id = R.string.screen_chat_backup_key_backup_action_disable),
showProgress = state.disableAction.isLoading(),
destructive = true,
modifier = Modifier.fillMaxWidth(),
onClick = { state.eventSink.invoke(SecureBackupDisableEvents.DisableBackup(force = false)) }
)
}
Button(
text = stringResource(id = R.string.screen_chat_backup_key_backup_action_disable),
showProgress = state.disableAction.isLoading(),
destructive = true,
modifier = Modifier.fillMaxWidth(),
onClick = { state.eventSink.invoke(SecureBackupDisableEvents.DisableBackup(force = false)) }

Check warning on line 101 in features/securebackup/impl/src/main/kotlin/io/element/android/features/securebackup/impl/disable/SecureBackupDisableView.kt

View check run for this annotation

Codecov / codecov/patch

features/securebackup/impl/src/main/kotlin/io/element/android/features/securebackup/impl/disable/SecureBackupDisableView.kt#L101

Added line #L101 was not covered by tests
)
}

@Composable
Expand Down
Loading