diff --git a/common/src/commonMain/composeResources/values/strings.xml b/common/src/commonMain/composeResources/values/strings.xml index e090bc04..4d7be3ec 100644 --- a/common/src/commonMain/composeResources/values/strings.xml +++ b/common/src/commonMain/composeResources/values/strings.xml @@ -175,6 +175,7 @@ Passkey available Two-factor authentication available Custom + Create account Follow system settings Coming soon diff --git a/common/src/commonMain/kotlin/com/artemchep/keyguard/feature/auth/login/LoginScreen.kt b/common/src/commonMain/kotlin/com/artemchep/keyguard/feature/auth/login/LoginScreen.kt index 5c442375..e122011a 100644 --- a/common/src/commonMain/kotlin/com/artemchep/keyguard/feature/auth/login/LoginScreen.kt +++ b/common/src/commonMain/kotlin/com/artemchep/keyguard/feature/auth/login/LoginScreen.kt @@ -7,6 +7,7 @@ import androidx.compose.foundation.layout.Arrangement import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.RowScope import androidx.compose.foundation.layout.Spacer import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.height @@ -20,10 +21,12 @@ import androidx.compose.foundation.text.KeyboardOptions import androidx.compose.material.icons.Icons import androidx.compose.material.icons.automirrored.outlined.Login import androidx.compose.material.icons.outlined.Add +import androidx.compose.material.icons.outlined.AppRegistration import androidx.compose.material.icons.outlined.Security import androidx.compose.material3.CircularProgressIndicator import androidx.compose.material3.DropdownMenu import androidx.compose.material3.ExperimentalMaterial3Api +import androidx.compose.material3.HorizontalDivider import androidx.compose.material3.Icon import androidx.compose.material3.LocalContentColor import androidx.compose.material3.MaterialTheme @@ -73,14 +76,17 @@ import com.artemchep.keyguard.ui.ExpandedIfNotEmpty import com.artemchep.keyguard.ui.FabState import com.artemchep.keyguard.ui.FlatDropdown import com.artemchep.keyguard.ui.FlatItem +import com.artemchep.keyguard.ui.FlatItemLayout import com.artemchep.keyguard.ui.FlatItemTextContent import com.artemchep.keyguard.ui.MediumEmphasisAlpha import com.artemchep.keyguard.ui.OptionsButton import com.artemchep.keyguard.ui.PasswordFlatTextField import com.artemchep.keyguard.ui.ScaffoldColumn import com.artemchep.keyguard.ui.UrlFlatTextField +import com.artemchep.keyguard.ui.icons.ChevronIcon import com.artemchep.keyguard.ui.icons.DropdownIcon import com.artemchep.keyguard.ui.icons.IconBox +import com.artemchep.keyguard.ui.icons.icon import com.artemchep.keyguard.ui.skeleton.SkeletonText import com.artemchep.keyguard.ui.skeleton.SkeletonTextField import com.artemchep.keyguard.ui.theme.Dimens @@ -391,6 +397,30 @@ fun LoginContent( items = loginState.items, ) } + loginState.onRegisterClick?.let { onClick -> + HorizontalDivider( + modifier = Modifier + .padding( + top = 32.dp, + bottom = 8.dp, + ), + ) + FlatItemLayout( + content = { + FlatItemTextContent( + title = { + Text( + text = "Create an account", + ) + }, + ) + }, + trailing = { + ChevronIcon() + }, + onClick = onClick, + ) + } } } diff --git a/common/src/commonMain/kotlin/com/artemchep/keyguard/feature/auth/login/LoginState.kt b/common/src/commonMain/kotlin/com/artemchep/keyguard/feature/auth/login/LoginState.kt index c470af12..21804e3c 100644 --- a/common/src/commonMain/kotlin/com/artemchep/keyguard/feature/auth/login/LoginState.kt +++ b/common/src/commonMain/kotlin/com/artemchep/keyguard/feature/auth/login/LoginState.kt @@ -22,6 +22,7 @@ data class LoginState( val regionItems: List = emptyList(), val items: List = emptyList(), val isLoading: Boolean = false, + val onRegisterClick: (() -> Unit)? = null, val onLoginClick: (() -> Unit)? = null, ) { companion object; diff --git a/common/src/commonMain/kotlin/com/artemchep/keyguard/feature/auth/login/LoginStateProducer.kt b/common/src/commonMain/kotlin/com/artemchep/keyguard/feature/auth/login/LoginStateProducer.kt index f5b2965d..61b6ea9e 100644 --- a/common/src/commonMain/kotlin/com/artemchep/keyguard/feature/auth/login/LoginStateProducer.kt +++ b/common/src/commonMain/kotlin/com/artemchep/keyguard/feature/auth/login/LoginStateProducer.kt @@ -29,6 +29,7 @@ import com.artemchep.keyguard.feature.auth.login.otp.LoginTwofaRoute import com.artemchep.keyguard.feature.confirmation.createConfirmationDialogIntent import com.artemchep.keyguard.feature.localization.TextHolder import com.artemchep.keyguard.feature.localization.wrap +import com.artemchep.keyguard.feature.navigation.NavigationIntent import com.artemchep.keyguard.feature.navigation.state.RememberStateFlowScope import com.artemchep.keyguard.feature.navigation.state.onClick import com.artemchep.keyguard.feature.navigation.state.produceScreenState @@ -566,6 +567,23 @@ fun produceLoginScreenState( !output.error && !taskIsExecuting + val onRegister = kotlin.run { + val registerUrl = when (val region = output.region) { + is LoginRegion.Predefined -> when (region.region) { + ServerEnv.Region.US -> "https://vault.bitwarden.com/#/register" + ServerEnv.Region.EU -> "https://vault.bitwarden.eu/#/register" + } + else -> null + } + registerUrl?.let { + // lambda + { + val intent = NavigationIntent.NavigateToBrowser(it) + navigate(intent) + } + } + } + val emailField = TextFieldModel2.of( state = emailState, validated = validatedEmail, @@ -598,6 +616,7 @@ fun produceLoginScreenState( regionItems = globalItems, items = envServerItems + items, isLoading = taskIsExecuting, + onRegisterClick = onRegister, onLoginClick = if (canLogin) { { val env = if (args.envEditable) {