feat: Enhance DeviceConfirmScreen with animated color transitions and improved layout

This commit is contained in:
2026-02-19 17:50:25 +05:00
parent 53d0e44ef8
commit 5cf8b2866f

View File

@@ -1,7 +1,9 @@
package com.rosetta.messenger.ui.auth package com.rosetta.messenger.ui.auth
import android.os.Build import android.os.Build
import androidx.compose.animation.animateColorAsState
import androidx.compose.animation.core.FastOutSlowInEasing import androidx.compose.animation.core.FastOutSlowInEasing
import androidx.compose.animation.core.CubicBezierEasing
import androidx.compose.animation.core.animateFloat import androidx.compose.animation.core.animateFloat
import androidx.compose.animation.core.infiniteRepeatable import androidx.compose.animation.core.infiniteRepeatable
import androidx.compose.animation.core.rememberInfiniteTransition import androidx.compose.animation.core.rememberInfiniteTransition
@@ -16,6 +18,7 @@ import androidx.compose.foundation.layout.Spacer
import androidx.compose.foundation.layout.fillMaxSize import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.height import androidx.compose.foundation.layout.height
import androidx.compose.foundation.layout.statusBarsPadding
import androidx.compose.foundation.layout.navigationBarsPadding import androidx.compose.foundation.layout.navigationBarsPadding
import androidx.compose.foundation.layout.padding import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.layout.size import androidx.compose.foundation.layout.size
@@ -36,7 +39,6 @@ import androidx.compose.runtime.rememberUpdatedState
import androidx.compose.ui.Alignment import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.clip import androidx.compose.ui.draw.clip
import androidx.compose.ui.graphics.Brush
import androidx.compose.ui.graphics.Color import androidx.compose.ui.graphics.Color
import androidx.compose.ui.text.font.FontWeight import androidx.compose.ui.text.font.FontWeight
import androidx.compose.ui.text.style.TextAlign import androidx.compose.ui.text.style.TextAlign
@@ -62,15 +64,36 @@ fun DeviceConfirmScreen(
isDarkTheme: Boolean, isDarkTheme: Boolean,
onExit: () -> Unit onExit: () -> Unit
) { ) {
val backgroundTop = if (isDarkTheme) Color(0xFF17181D) else Color(0xFFF4F7FC) val themeAnimSpec =
val backgroundBottom = if (isDarkTheme) Color(0xFF121316) else Color(0xFFE9EEF7) tween<Color>(durationMillis = 500, easing = CubicBezierEasing(0.4f, 0f, 0.2f, 1f))
val cardColor = if (isDarkTheme) Color(0xFF23252B) else Color.White
val cardBorderColor = if (isDarkTheme) Color(0xFF343844) else Color(0xFFDCE4F0) val backgroundColor by
val textColor = if (isDarkTheme) Color(0xFFF2F3F5) else Color(0xFF1B1C1F) animateColorAsState(
val secondaryTextColor = if (isDarkTheme) Color(0xFFB2B5BD) else Color(0xFF6F7480) targetValue = if (isDarkTheme) AuthBackground else AuthBackgroundLight,
val accentColor = if (isDarkTheme) Color(0xFF4A9FFF) else PrimaryBlue animationSpec = themeAnimSpec
val deviceCardColor = if (isDarkTheme) Color(0xFF1A1C22) else Color(0xFFF5F8FD) )
val exitButtonColor = if (isDarkTheme) Color(0xFF3D2227) else Color(0xFFFFEAED) val surfaceColor by
animateColorAsState(
targetValue = if (isDarkTheme) AuthSurface else AuthSurfaceLight,
animationSpec = themeAnimSpec
)
val borderColor by
animateColorAsState(
targetValue = if (isDarkTheme) Color(0xFF3E3E43) else Color(0xFFE3E3E8),
animationSpec = themeAnimSpec
)
val textColor by
animateColorAsState(
targetValue = if (isDarkTheme) Color.White else Color.Black,
animationSpec = themeAnimSpec
)
val secondaryTextColor by
animateColorAsState(
targetValue = if (isDarkTheme) Color(0xFF8E8E93) else Color(0xFF666666),
animationSpec = themeAnimSpec
)
val accentColor = PrimaryBlue
val exitButtonColor = if (isDarkTheme) Color(0xFF3A2629) else Color(0xFFFFEAED)
val exitButtonTextColor = Color(0xFFFF5E61) val exitButtonTextColor = Color(0xFFFF5E61)
val onExitState by rememberUpdatedState(onExit) val onExitState by rememberUpdatedState(onExit)
val scope = rememberCoroutineScope() val scope = rememberCoroutineScope()
@@ -105,73 +128,66 @@ fun DeviceConfirmScreen(
Box( Box(
modifier = Modifier modifier = Modifier
.fillMaxSize() .fillMaxSize()
.background( .background(backgroundColor)
brush = .statusBarsPadding()
Brush.verticalGradient(
colors = listOf(backgroundTop, backgroundBottom)
)
)
.navigationBarsPadding() .navigationBarsPadding()
.padding(horizontal = 22.dp), .padding(horizontal = 22.dp),
contentAlignment = Alignment.Center contentAlignment = Alignment.Center
) {
Surface(
modifier = Modifier
.fillMaxWidth()
.widthIn(max = 400.dp),
color = cardColor,
shape = RoundedCornerShape(28.dp),
border = BorderStroke(1.dp, cardBorderColor)
) { ) {
Column( Column(
modifier = Modifier.padding(horizontal = 22.dp, vertical = 24.dp), modifier =
horizontalAlignment = Alignment.CenterHorizontally, Modifier
verticalArrangement = Arrangement.Center .fillMaxWidth()
.widthIn(max = 420.dp),
horizontalAlignment = Alignment.CenterHorizontally
) { ) {
Spacer(modifier = Modifier.weight(0.2f))
Box( Box(
modifier = modifier =
Modifier Modifier
.size(118.dp) .size(102.dp)
.clip(CircleShape) .clip(RoundedCornerShape(24.dp))
.background(accentColor.copy(alpha = if (isDarkTheme) 0.16f else 0.1f)), .background(accentColor.copy(alpha = if (isDarkTheme) 0.14f else 0.12f)),
contentAlignment = Alignment.Center contentAlignment = Alignment.Center
) { ) {
LottieAnimation( LottieAnimation(
composition = composition, composition = composition,
progress = { progress }, progress = { progress },
modifier = Modifier.size(96.dp) modifier = Modifier.size(82.dp)
) )
} }
Spacer(modifier = Modifier.height(16.dp)) Spacer(modifier = Modifier.height(18.dp))
Row(verticalAlignment = Alignment.CenterVertically) { Row(verticalAlignment = Alignment.CenterVertically) {
Icon( Icon(
imageVector = TablerIcons.DeviceMobile, imageVector = TablerIcons.DeviceMobile,
contentDescription = null, contentDescription = null,
tint = accentColor tint = accentColor,
modifier = Modifier.size(16.dp)
) )
Spacer(modifier = Modifier.size(6.dp)) Spacer(modifier = Modifier.size(6.dp))
Text( Text(
text = "NEW DEVICE REQUEST", text = "NEW DEVICE REQUEST",
color = accentColor, color = accentColor,
fontSize = 12.sp, fontSize = 12.sp,
fontWeight = FontWeight.Bold fontWeight = FontWeight.SemiBold
) )
} }
Spacer(modifier = Modifier.height(14.dp)) Spacer(modifier = Modifier.height(12.dp))
Text( Text(
text = "Waiting for approval", text = "Waiting for approval",
color = textColor, color = textColor,
fontSize = 34.sp, fontSize = 30.sp,
lineHeight = 38.sp, lineHeight = 36.sp,
fontWeight = FontWeight.Bold, fontWeight = FontWeight.Bold,
textAlign = TextAlign.Center textAlign = TextAlign.Center
) )
Spacer(modifier = Modifier.height(12.dp)) Spacer(modifier = Modifier.height(10.dp))
Text( Text(
text = "Open Rosetta on your first device and approve this login request.", text = "Open Rosetta on your first device and approve this login request.",
@@ -181,25 +197,24 @@ fun DeviceConfirmScreen(
lineHeight = 22.sp lineHeight = 22.sp
) )
Spacer(modifier = Modifier.height(18.dp)) Spacer(modifier = Modifier.height(20.dp))
Surface( Surface(
modifier = Modifier.fillMaxWidth(), modifier = Modifier.fillMaxWidth(),
color = deviceCardColor, color = surfaceColor,
shape = RoundedCornerShape(16.dp), shape = RoundedCornerShape(14.dp),
border = BorderStroke(1.dp, cardBorderColor.copy(alpha = if (isDarkTheme) 0.7f else 1f)) border = BorderStroke(1.dp, borderColor)
) { ) {
Column( Column(
modifier = Modifier.padding(horizontal = 14.dp, vertical = 12.dp), modifier = Modifier.padding(horizontal = 14.dp, vertical = 12.dp),
horizontalAlignment = Alignment.Start verticalArrangement = Arrangement.spacedBy(4.dp)
) { ) {
Text( Text(
text = "Device waiting for approval", text = "This device",
color = secondaryTextColor, color = secondaryTextColor,
fontSize = 12.sp, fontSize = 12.sp,
fontWeight = FontWeight.SemiBold fontWeight = FontWeight.Medium
) )
Spacer(modifier = Modifier.height(4.dp))
Text( Text(
text = localDeviceName, text = localDeviceName,
color = textColor, color = textColor,
@@ -209,14 +224,23 @@ fun DeviceConfirmScreen(
} }
} }
Spacer(modifier = Modifier.height(16.dp)) Spacer(modifier = Modifier.height(14.dp))
Text(
text = "If this wasn't you, tap Exit.",
color = secondaryTextColor,
fontSize = 13.sp,
textAlign = TextAlign.Center
)
Spacer(modifier = Modifier.height(18.dp))
Button( Button(
onClick = onExitState, onClick = onExitState,
modifier = modifier =
Modifier Modifier
.fillMaxWidth() .fillMaxWidth()
.height(46.dp), .height(52.dp),
colors = ButtonDefaults.buttonColors( colors = ButtonDefaults.buttonColors(
containerColor = exitButtonColor, containerColor = exitButtonColor,
contentColor = exitButtonTextColor contentColor = exitButtonTextColor
@@ -226,7 +250,7 @@ fun DeviceConfirmScreen(
) { ) {
Text( Text(
text = "Exit", text = "Exit",
fontSize = 16.sp, fontSize = 17.sp,
fontWeight = FontWeight.SemiBold fontWeight = FontWeight.SemiBold
) )
} }
@@ -245,7 +269,8 @@ fun DeviceConfirmScreen(
Spacer(modifier = Modifier.size(8.dp)) Spacer(modifier = Modifier.size(8.dp))
WaitingDots(color = secondaryTextColor) WaitingDots(color = secondaryTextColor)
} }
}
Spacer(modifier = Modifier.weight(0.24f))
} }
} }
} }