diff --git a/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/login/AboutSubViewModel.kt b/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/login/AboutSubViewModel.kt new file mode 100644 index 0000000000000000000000000000000000000000..63e2bfc697bef2bae09448b4218dc340af0e4df6 --- /dev/null +++ b/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/login/AboutSubViewModel.kt @@ -0,0 +1,23 @@ +/* + * Briar Desktop + * Copyright (C) 2021-2022 The Briar Project + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Affero General Public License as + * published by the Free Software Foundation, either version 3 of the + * License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License + * along with this program. If not, see <https://www.gnu.org/licenses/>. + */ + +package org.briarproject.briar.desktop.login + +class AboutSubViewModel( + val onBackButton: () -> Unit, +) : StartupViewModel.SubViewModel diff --git a/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/login/ErrorScreen.kt b/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/login/ErrorScreen.kt index 09c36ab1112e9127cb73a963b2189b44d8f3d479..498043f9c64792296f81d4ba0d31cabe9abf423d 100644 --- a/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/login/ErrorScreen.kt +++ b/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/login/ErrorScreen.kt @@ -53,6 +53,7 @@ import org.briarproject.bramble.api.lifecycle.LifecycleManager.StartResult.DB_ER import org.briarproject.bramble.api.lifecycle.LifecycleManager.StartResult.SERVICE_ERROR import org.briarproject.bramble.api.lifecycle.LifecycleManager.StartResult.SUCCESS import org.briarproject.briar.desktop.theme.Red500 +import org.briarproject.briar.desktop.ui.AboutScreen import org.briarproject.briar.desktop.ui.Constants.STARTUP_FIELDS_WIDTH import org.briarproject.briar.desktop.utils.InternationalizationUtils.i18n import org.briarproject.briar.desktop.utils.PreviewUtils.preview @@ -72,19 +73,17 @@ fun main() = preview { } } - ErrorScreen(error, {}) {} + ErrorScreen(error) {} } @Composable fun ErrorScreen( - onShowAbout: () -> Unit, viewHolder: ErrorSubViewModel -) = ErrorScreen(viewHolder.error, onShowAbout, viewHolder.onBackButton) +) = ErrorScreen(viewHolder.error, viewHolder.onBackButton) @Composable fun ErrorScreen( error: ErrorSubViewModel.Error, - onShowAbout: () -> Unit, onBackButton: (() -> Unit)?, ) { val text = when (error) { @@ -101,45 +100,50 @@ fun ErrorScreen( } } - ErrorScreen(text, onShowAbout, onBackButton) + ErrorScreen(text, onBackButton) } @Composable fun ErrorScreen( text: String, - onShowAbout: () -> Unit, onBackButton: (() -> Unit)? = null, ) = Box { - Column( - modifier = Modifier.fillMaxSize().padding(32.dp), - horizontalAlignment = CenterHorizontally, - verticalArrangement = spacedBy(32.dp) - ) { - Icon( - imageVector = Icons.Filled.Error, - contentDescription = i18n("error"), - modifier = Modifier.size(128.dp), - tint = Red500 - ) + var showAbout by remember { mutableStateOf(false) } - Text(i18n("sorry"), style = MaterialTheme.typography.h5) - Text( - text = text, - style = MaterialTheme.typography.body1, - modifier = Modifier.widthIn(max = STARTUP_FIELDS_WIDTH) - ) - } + if (showAbout) { + AboutScreen { showAbout = false } + } else { + Column( + modifier = Modifier.fillMaxSize().padding(32.dp), + horizontalAlignment = CenterHorizontally, + verticalArrangement = spacedBy(32.dp) + ) { + Icon( + imageVector = Icons.Filled.Error, + contentDescription = i18n("error"), + modifier = Modifier.size(128.dp), + tint = Red500 + ) - if (onBackButton != null) { - IconButton(onClick = onBackButton) { - Icon(Icons.Filled.ArrowBack, i18n("access.return_to_previous_screen")) + Text(i18n("sorry"), style = MaterialTheme.typography.h5) + Text( + text = text, + style = MaterialTheme.typography.body1, + modifier = Modifier.widthIn(max = STARTUP_FIELDS_WIDTH) + ) + } + + if (onBackButton != null) { + IconButton(onClick = onBackButton) { + Icon(Icons.Filled.ArrowBack, i18n("access.return_to_previous_screen")) + } } - } - IconButton( - onClick = onShowAbout, - modifier = Modifier.align(Alignment.BottomStart) - ) { - Icon(Icons.Filled.Info, i18n("access.mode.about")) + IconButton( + onClick = { showAbout = true }, + modifier = Modifier.align(Alignment.BottomStart) + ) { + Icon(Icons.Filled.Info, i18n("access.mode.about")) + } } } diff --git a/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/login/StartupScreen.kt b/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/login/StartupScreen.kt index 089cf83049e8f646104ab75fc5d0c058b5ba6cc4..5e5c17b864f50ec7e0a9c4475c781d979f050d7e 100644 --- a/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/login/StartupScreen.kt +++ b/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/login/StartupScreen.kt @@ -38,19 +38,29 @@ import androidx.compose.ui.Alignment.Companion.CenterHorizontally import androidx.compose.ui.Alignment.Companion.CenterVertically import androidx.compose.ui.Modifier import androidx.compose.ui.unit.dp +import org.briarproject.briar.desktop.ui.AboutScreen import org.briarproject.briar.desktop.ui.BriarLogo import org.briarproject.briar.desktop.utils.InternationalizationUtils.i18n import org.briarproject.briar.desktop.viewmodel.viewModel @Composable fun StartupScreen( - onShowAbout: () -> Unit, viewModel: StartupViewModel = viewModel(), ) { when (val holder = viewModel.currentSubViewModel.value) { - is LoginSubViewModel -> LoginScreen(onShowAbout, holder) - is RegistrationSubViewModel -> RegistrationScreen(onShowAbout, holder) - is ErrorSubViewModel -> ErrorScreen(onShowAbout, holder) + is LoginSubViewModel -> LoginScreen(viewModel::showAbout, holder) + is RegistrationSubViewModel -> RegistrationScreen(viewModel::showAbout, holder) + is ErrorSubViewModel -> ErrorScreen(holder) + is AboutSubViewModel -> Box { + AboutScreen(Modifier.padding(16.dp)) + + IconButton( + onClick = holder.onBackButton, + modifier = Modifier.align(Alignment.TopStart) + ) { + Icon(Icons.Filled.ArrowBack, i18n("back")) + } + } } } diff --git a/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/login/StartupViewModel.kt b/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/login/StartupViewModel.kt index 21af167213a438998facd91090c13c9611617ad6..a51ba875fe9fb08d3097be14f36f8b11c970a438 100644 --- a/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/login/StartupViewModel.kt +++ b/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/login/StartupViewModel.kt @@ -90,6 +90,13 @@ constructor( _currentSubViewModel.value = makeError(error) } + private fun makeAbout(previous: SubViewModel) = + AboutSubViewModel { _currentSubViewModel.value = previous } + + fun showAbout() { + _currentSubViewModel.value = makeAbout(_currentSubViewModel.value) + } + override fun eventOccurred(e: Event) { if (e is LifecycleEvent) _currentSubViewModel.value.lifecycleStateChanged(e.lifecycleState) } diff --git a/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/navigation/BriarSidebar.kt b/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/navigation/BriarSidebar.kt index 418a6a339d411d4a2021247b757d0a59d25f2ec3..93416d2d82496611ad1c7dfdc8fb26ba8e5dc778 100644 --- a/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/navigation/BriarSidebar.kt +++ b/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/navigation/BriarSidebar.kt @@ -102,7 +102,6 @@ fun BriarSidebarButton( i18n(mode.contentDescriptionKey) ) - @Composable fun BriarSidebarButton( selected: Boolean, diff --git a/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/ui/AboutDialog.kt b/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/ui/AboutScreen.kt similarity index 89% rename from briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/ui/AboutDialog.kt rename to briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/ui/AboutScreen.kt index 252d749cc0c83c2aa9e1dc75ada19289bfd2438b..7d4867d9cfc02ec1460e69f0ac4aad1bdbf5a24d 100644 --- a/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/ui/AboutDialog.kt +++ b/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/ui/AboutScreen.kt @@ -10,14 +10,17 @@ import androidx.compose.foundation.layout.fillMaxHeight import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.height import androidx.compose.foundation.layout.padding -import androidx.compose.foundation.layout.requiredSize import androidx.compose.foundation.lazy.LazyColumn import androidx.compose.foundation.lazy.items import androidx.compose.foundation.lazy.rememberLazyListState import androidx.compose.foundation.rememberScrollbarAdapter import androidx.compose.foundation.text.selection.SelectionContainer +import androidx.compose.material.Icon +import androidx.compose.material.IconButton import androidx.compose.material.MaterialTheme import androidx.compose.material.Text +import androidx.compose.material.icons.Icons +import androidx.compose.material.icons.filled.ArrowBack import androidx.compose.runtime.Composable import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier @@ -35,30 +38,28 @@ fun main() = preview( "visible" to true, ) { if (getBooleanParameter("visible")) { - AboutDialog( - onClose = { setBooleanParameter("visible", false) }, + AboutScreen( + onBackButton = { setBooleanParameter("visible", false) }, ) } } @Composable -fun AboutDialog( - onClose: () -> Unit, -) { - BriarDialog(onClose = onClose) { - val box = this - Column( - modifier = Modifier.requiredSize( - box.maxWidth.times(0.8f), box.maxHeight.times(0.8f) - ).padding(16.dp) - ) { - AboutScreen() - } +fun AboutScreen( + onBackButton: () -> Unit, +) = Box { + AboutScreen(Modifier.padding(16.dp)) + + IconButton( + onClick = onBackButton, + modifier = Modifier.align(Alignment.TopStart) + ) { + Icon(Icons.Filled.ArrowBack, i18n("back")) } } @Composable -fun AboutScreen() { +fun AboutScreen(modifier: Modifier = Modifier) { // sizes of the two columns val colSizes = listOf(0.3f, 0.7f) @@ -80,7 +81,7 @@ fun AboutScreen() { add(i18n("about.contact") to "desktop@briarproject.org") // NON-NLS } - Column { + Column(modifier) { Row( modifier = Modifier.padding(bottom = 8.dp).fillMaxWidth(), verticalAlignment = Alignment.CenterVertically, diff --git a/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/ui/BriarDialog.kt b/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/ui/BriarDialog.kt deleted file mode 100644 index f2929d55169c2b67b606b308889c0fe11333c7ae..0000000000000000000000000000000000000000 --- a/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/ui/BriarDialog.kt +++ /dev/null @@ -1,46 +0,0 @@ -package org.briarproject.briar.desktop.ui - -import androidx.compose.foundation.ExperimentalFoundationApi -import androidx.compose.foundation.background -import androidx.compose.foundation.clickable -import androidx.compose.foundation.interaction.MutableInteractionSource -import androidx.compose.foundation.layout.Box -import androidx.compose.foundation.layout.BoxWithConstraints -import androidx.compose.foundation.layout.BoxWithConstraintsScope -import androidx.compose.foundation.layout.fillMaxSize -import androidx.compose.foundation.layout.requiredSize -import androidx.compose.foundation.shape.RoundedCornerShape -import androidx.compose.material.ExperimentalMaterialApi -import androidx.compose.material.MaterialTheme -import androidx.compose.material.Surface -import androidx.compose.runtime.Composable -import androidx.compose.runtime.remember -import androidx.compose.ui.Alignment -import androidx.compose.ui.Modifier -import androidx.compose.ui.unit.dp - -@OptIn(ExperimentalMaterialApi::class, ExperimentalFoundationApi::class) -@Composable -fun BriarDialog( - onClose: () -> Unit, - content: @Composable BoxWithConstraintsScope.() -> Unit, -) { - BoxWithConstraints(Modifier.fillMaxSize()) { - // This adds a scrim that dims the background to make the dialog stand out visually - Box( - modifier = Modifier.requiredSize(maxWidth, maxHeight) - .background(MaterialTheme.colors.onSurface.copy(alpha = 0.32f)) - .clickable( - // prevent visual indication - interactionSource = remember { MutableInteractionSource() }, - indication = null - ) { - onClose() - } - ) - - Surface(modifier = Modifier.align(Alignment.Center), shape = RoundedCornerShape(8.dp)) { - content() - } - } -} diff --git a/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/ui/BriarUi.kt b/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/ui/BriarUi.kt index 5f0f7eb729953b588418a07a4fb99e12f73a1162..cb7000b2706d0cba532ce6b6f6bfc57007a3fbc1 100644 --- a/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/ui/BriarUi.kt +++ b/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/ui/BriarUi.kt @@ -178,21 +178,17 @@ constructor( return@CompositionLocalProvider } - var showAbout by remember { mutableStateOf(false) } val isDarkTheme = unencryptedSettings.theme == DARK || (unencryptedSettings.theme == AUTO && isSystemInDarkTheme()) BriarTheme(isDarkTheme) { Column(Modifier.fillMaxSize()) { ExpirationBanner { screenState = EXPIRED; stop() } when (screenState) { - STARTUP -> StartupScreen(onShowAbout = { showAbout = true }) - MAIN -> MainScreen(onShowAbout = { showAbout = true }) - EXPIRED -> ErrorScreen(i18n("startup.failed.expired"), onShowAbout = { showAbout = true }) + STARTUP -> StartupScreen() + MAIN -> MainScreen() + EXPIRED -> ErrorScreen(i18n("startup.failed.expired")) } } - if (showAbout) { - AboutDialog(onClose = { showAbout = false }) - } } } } diff --git a/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/ui/MainScreen.kt b/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/ui/MainScreen.kt index 196a5748a627f9d750ed039ce55584600afea298..582ab6ab4c499692feef548752b464a2c88243c5 100644 --- a/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/ui/MainScreen.kt +++ b/briar-desktop/src/main/kotlin/org/briarproject/briar/desktop/ui/MainScreen.kt @@ -33,10 +33,7 @@ import org.briarproject.briar.desktop.viewmodel.viewModel * Multiplatform, stateless, composable are found in briarCompose (possible briar-compose project in the future) */ @Composable -fun MainScreen( - viewModel: SidebarViewModel = viewModel(), - onShowAbout: () -> Unit, -) { +fun MainScreen(viewModel: SidebarViewModel = viewModel()) { Row { BriarSidebar( viewModel.account.value,