Pin setup with fake lock

This commit is contained in:
ganfra 2023-10-11 16:25:27 +02:00
parent 9ded4284b2
commit 2d5a3a473c
12 changed files with 211 additions and 40 deletions

View file

@ -16,6 +16,12 @@
package io.element.android.appnav
import android.content.Context
import android.content.ContextWrapper
import androidx.activity.ComponentActivity
import androidx.activity.compose.BackHandler
import androidx.compose.runtime.Composable
import androidx.compose.ui.platform.LocalContext
import com.bumble.appyx.navmodel.backstack.BackStack
import com.bumble.appyx.navmodel.backstack.operation.NewRoot
import com.bumble.appyx.navmodel.backstack.operation.Remove
@ -41,3 +47,18 @@ fun <T : Any> BackStack<T>.removeLast(element: T) {
accept(Remove(lastExpectedNavElement.key))
}
@Composable
fun FinishActivityBackHandler(enabled: Boolean = true) {
fun Context.findActivity(): ComponentActivity? = when (this) {
is ComponentActivity -> this
is ContextWrapper -> baseContext.findActivity()
else -> null
}
val context = LocalContext.current
BackHandler(enabled = enabled) {
context.findActivity()?.finish()
}
}

View file

@ -50,6 +50,9 @@ import io.element.android.features.ftue.api.state.FtueState
import io.element.android.features.invitelist.api.InviteListEntryPoint
import io.element.android.features.networkmonitor.api.NetworkMonitor
import io.element.android.features.networkmonitor.api.NetworkStatus
import io.element.android.features.pin.api.PinEntryPoint
import io.element.android.features.pin.api.PinState
import io.element.android.features.pin.api.PinStateDataSource
import io.element.android.features.preferences.api.PreferencesEntryPoint
import io.element.android.features.roomlist.api.RoomListEntryPoint
import io.element.android.features.verifysession.api.VerifySessionEntryPoint
@ -90,6 +93,8 @@ class LoggedInFlowNode @AssistedInject constructor(
private val networkMonitor: NetworkMonitor,
private val notificationDrawerManager: NotificationDrawerManager,
private val ftueState: FtueState,
private val pinEntryPoint: PinEntryPoint,
private val pinStateDataSource: PinStateDataSource,
private val matrixClient: MatrixClient,
snackbarDispatcher: SnackbarDispatcher,
) : BackstackNode<LoggedInFlowNode.NavTarget>(
@ -98,7 +103,7 @@ class LoggedInFlowNode @AssistedInject constructor(
savedStateMap = buildContext.savedStateMap,
),
permanentNavModel = PermanentNavModel(
NavTarget.Permanent,
navTargets = setOf(NavTarget.LoggedInPermanent, NavTarget.LockPermanent),
savedStateMap = buildContext.savedStateMap,
),
buildContext = buildContext,
@ -130,6 +135,7 @@ class LoggedInFlowNode @AssistedInject constructor(
}
},
onStop = {
pinStateDataSource.lock()
//Counterpart startSync is done in observeSyncStateAndNetworkStatus method.
coroutineScope.launch {
syncService.stopSync()
@ -167,7 +173,10 @@ class LoggedInFlowNode @AssistedInject constructor(
sealed interface NavTarget : Parcelable {
@Parcelize
data object Permanent : NavTarget
data object LoggedInPermanent : NavTarget
@Parcelize
data object LockPermanent : NavTarget
@Parcelize
data object RoomList : NavTarget
@ -196,9 +205,12 @@ class LoggedInFlowNode @AssistedInject constructor(
override fun resolve(navTarget: NavTarget, buildContext: BuildContext): Node {
return when (navTarget) {
NavTarget.Permanent -> {
NavTarget.LoggedInPermanent -> {
createNode<LoggedInNode>(buildContext)
}
NavTarget.LockPermanent -> {
pinEntryPoint.nodeBuilder(this, buildContext).build()
}
NavTarget.RoomList -> {
val callback = object : RoomListEntryPoint.Callback {
override fun onRoomClicked(roomId: RoomId) {
@ -324,17 +336,24 @@ class LoggedInFlowNode @AssistedInject constructor(
@Composable
override fun View(modifier: Modifier) {
Box(modifier = modifier) {
Children(
navModel = backstack,
modifier = Modifier,
// Animate navigation to settings and to a room
transitionHandler = rememberDefaultTransitionHandler(),
)
val isFtueDisplayed by ftueState.shouldDisplayFlow.collectAsState()
if (!isFtueDisplayed) {
PermanentChild(permanentNavModel = permanentNavModel, navTarget = NavTarget.Permanent)
val pinState by pinStateDataSource.pinState.collectAsState()
when (pinState) {
PinState.Unlocked -> {
Children(
navModel = backstack,
modifier = Modifier,
// Animate navigation to settings and to a room
transitionHandler = rememberDefaultTransitionHandler(),
)
val isFtueDisplayed by ftueState.shouldDisplayFlow.collectAsState()
if (!isFtueDisplayed) {
PermanentChild(permanentNavModel = permanentNavModel, navTarget = NavTarget.LoggedInPermanent)
}
}
PinState.Locked -> {
FinishActivityBackHandler()
PermanentChild(permanentNavModel = permanentNavModel, navTarget = NavTarget.LockPermanent)
}
}
}
}

View file

@ -44,6 +44,7 @@ import io.element.android.appnav.root.RootPresenter
import io.element.android.appnav.root.RootView
import io.element.android.features.login.api.oidc.OidcAction
import io.element.android.features.login.api.oidc.OidcActionFlow
import io.element.android.features.pin.api.PinEntryPoint
import io.element.android.features.rageshake.api.bugreport.BugReportEntryPoint
import io.element.android.libraries.architecture.BackstackNode
import io.element.android.libraries.architecture.animation.rememberDefaultTransitionHandler

View file

@ -31,7 +31,10 @@ class LoggedInNode @AssistedInject constructor(
@Assisted buildContext: BuildContext,
@Assisted plugins: List<Plugin>,
private val loggedInPresenter: LoggedInPresenter,
) : Node(buildContext, plugins = plugins) {
) : Node(
buildContext = buildContext,
plugins = plugins
) {
@Composable
override fun View(modifier: Modifier) {