auth to server-V99

This commit is contained in:
Eric85710 2026-05-14 14:57:57 +08:00
parent e5dfb736f0
commit f0c6b36a76

View file

@ -10,6 +10,7 @@ import androidx.compose.foundation.clickable
import androidx.compose.foundation.layout.Arrangement import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.PaddingValues
import androidx.compose.foundation.layout.Row import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.Spacer import androidx.compose.foundation.layout.Spacer
import androidx.compose.foundation.layout.fillMaxSize import androidx.compose.foundation.layout.fillMaxSize
@ -42,10 +43,13 @@ import androidx.compose.material3.Card
import androidx.compose.material3.CardDefaults import androidx.compose.material3.CardDefaults
import androidx.compose.material3.CircularProgressIndicator import androidx.compose.material3.CircularProgressIndicator
import androidx.compose.material3.Divider import androidx.compose.material3.Divider
import androidx.compose.material3.FilledTonalIconButton
import androidx.compose.material3.HorizontalDivider import androidx.compose.material3.HorizontalDivider
import androidx.compose.material3.Icon import androidx.compose.material3.Icon
import androidx.compose.material3.IconButton import androidx.compose.material3.IconButton
import androidx.compose.material3.IconButtonDefaults
import androidx.compose.material3.ListItem import androidx.compose.material3.ListItem
import androidx.compose.material3.ListItemDefaults
import androidx.compose.material3.MaterialTheme import androidx.compose.material3.MaterialTheme
import androidx.compose.material3.OutlinedTextField import androidx.compose.material3.OutlinedTextField
import androidx.compose.material3.Surface import androidx.compose.material3.Surface
@ -274,15 +278,6 @@ fun FriendRow(
placeholder = painterResource(id = R.drawable.avatar_v1), placeholder = painterResource(id = R.drawable.avatar_v1),
error = painterResource(id = R.drawable.avatar_v1) error = painterResource(id = R.drawable.avatar_v1)
) )
// 狀態圓點疊加在頭像右下角
Surface(
color = statusColor,
shape = CircleShape,
modifier = Modifier
.size(14.dp)
.border(2.dp, MaterialTheme.colorScheme.surface, CircleShape) // 白色外圈
) {}
} }
Spacer(modifier = Modifier.width(16.dp)) Spacer(modifier = Modifier.width(16.dp))
@ -373,39 +368,102 @@ fun FriendRow(
fun PendingFriendRow( fun PendingFriendRow(
request: PendingFriendApiModel, request: PendingFriendApiModel,
isLoading: Boolean, isLoading: Boolean,
onAccept: (String) -> Unit, // 增加回呼 onAccept: (String) -> Unit,
onReject: (String) -> Unit // 增加回呼 onReject: (String) -> Unit
) {
Card(
modifier = Modifier
.fillMaxWidth()
.padding(vertical = 4.dp, horizontal = 2.dp)
,
shape = RoundedCornerShape(12.dp), // 圓角
colors = CardDefaults.cardColors(
containerColor = MaterialTheme.colorScheme.primary // 使用 Surface 顏色
),
elevation = CardDefaults.cardElevation(defaultElevation = 0.dp)
) { ) {
ListItem( ListItem(
headlineContent = { Text("${request.displayName}") }, colors = ListItemDefaults.colors(
supportingContent = { Text("想加你為好友") }, containerColor = Color.Transparent // 讓底層 Card 的顏色透出來
leadingContent = { ),
AsyncImage( modifier = Modifier.padding(vertical = 4.dp),
// 這裡可以使用我們之前寫的擴充函式 .toFullImageUrl() headlineContent = {
model = request.fullPendingAvatarUrl, Text(
contentDescription = null, text = request.displayName ?: "未知用戶",
modifier = Modifier.size(40.dp).clip(CircleShape), style = MaterialTheme.typography.titleMedium,
error = painterResource(id = R.drawable.avatar_v1) fontWeight = FontWeight.Bold
) )
}, },
trailingContent = { supportingContent = {
Row { Text(
IconButton( text = "想加你為好友",
onClick = { request.friendshipId?.let { onReject(it) } }, style = MaterialTheme.typography.bodyMedium,
enabled = !isLoading // 正在載入時禁用 color = MaterialTheme.colorScheme.onSurfaceVariant
)
},
leadingContent = {
Surface(
shape = CircleShape,
tonalElevation = 2.dp
) { ) {
Icon(Icons.Default.Close, contentDescription = "拒絕", tint = Color.Red) AsyncImage(
model = request.fullPendingAvatarUrl,
contentDescription = null,
modifier = Modifier
.size(48.dp)
.clip(CircleShape),
contentScale = ContentScale.Crop,
error = painterResource(id = R.drawable.avatar_v1)
)
} }
IconButton( },
onClick = { request.friendshipId?.let { onAccept(it) } }, trailingContent = {
enabled = !isLoading // 正在載入時禁用 Row(
horizontalArrangement = Arrangement.spacedBy(8.dp),
verticalAlignment = Alignment.CenterVertically
) { ) {
Icon(Icons.Default.Check, contentDescription = "接受", tint = Color.Green) // 拒絕按鈕 (圓形、低調)
FilledTonalIconButton(
onClick = { request.friendshipId?.let { onReject(it) } },
enabled = !isLoading,
colors = IconButtonDefaults.filledTonalIconButtonColors(
containerColor = MaterialTheme.colorScheme.errorContainer.copy(alpha = 0.8f),
contentColor = MaterialTheme.colorScheme.error
)
) {
Icon(Icons.Default.Close, contentDescription = "拒絕", modifier = Modifier.size(20.dp))
}
// 接受按鈕 (綠色系)
FilledTonalIconButton(
onClick = { request.friendshipId?.let { onAccept(it) } },
enabled = !isLoading,
colors = IconButtonDefaults.filledTonalIconButtonColors(
// containerColor: 背景色 (淺綠)
containerColor = Color(0xFFE8F5E9),
// contentColor: 圖示與進度條顏色 (深綠)
contentColor = Color(0xFF2E7D32)
)
) {
if (isLoading) {
CircularProgressIndicator(
modifier = Modifier.size(20.dp),
color = Color(0xFF2E7D32), // 這裡也要同步改為深綠色
strokeWidth = 2.dp
)
} else {
Icon(
imageVector = Icons.Default.Check,
contentDescription = "接受",
modifier = Modifier.size(20.dp)
)
}
} }
} }
} }
) )
} }
}
//search user //search user