Приложение
This commit is contained in:
206
client-mobile/navigation/AppNavigation.kt
Normal file
206
client-mobile/navigation/AppNavigation.kt
Normal file
@@ -0,0 +1,206 @@
|
||||
package navigation
|
||||
|
||||
import androidx.compose.foundation.layout.Box
|
||||
import androidx.compose.foundation.layout.PaddingValues
|
||||
import androidx.compose.foundation.layout.padding
|
||||
import androidx.compose.material3.Scaffold
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.runtime.collectAsState
|
||||
import androidx.compose.runtime.getValue
|
||||
import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.unit.dp
|
||||
import androidx.hilt.navigation.compose.hiltViewModel
|
||||
import androidx.navigation.NavHostController
|
||||
import androidx.navigation.NavType
|
||||
import androidx.navigation.compose.NavHost
|
||||
import androidx.navigation.compose.composable
|
||||
import androidx.navigation.compose.currentBackStackEntryAsState
|
||||
import androidx.navigation.compose.rememberNavController
|
||||
import androidx.navigation.navArgument
|
||||
import auth.presentation.LoginScreen
|
||||
import auth.presentation.RegisterScreen
|
||||
import auth.presentation.AuthViewModel
|
||||
import core.presentation.settings.SettingsScreen
|
||||
import core.presentation.settings.SettingsViewModel
|
||||
import chats.presentation.chat_list.ChatListScreen
|
||||
import chats.presentation.chat_list.ChatListViewModel
|
||||
import chats.presentation.chat_detail.ChatDetailScreen
|
||||
import chats.presentation.chat_detail.ChatDetailViewModel
|
||||
import contacts.presentation.ContactListScreen
|
||||
import contacts.presentation.ContactListViewModel
|
||||
import core.presentation.components.GlassNavigationBar
|
||||
import profiles.presentation.ProfileScreen
|
||||
import profiles.presentation.EditProfileScreen
|
||||
import profiles.presentation.viewmodel.ProfileViewModel
|
||||
import stories.presentation.StoryViewModel
|
||||
|
||||
sealed class Screen(val route: String) {
|
||||
object Login : Screen("login")
|
||||
object Register : Screen("register")
|
||||
object ChatList : Screen("chat_list")
|
||||
object ChatDetail : Screen("chat_detail/{chatId}/{chatName}") {
|
||||
fun createRoute(chatId: String, chatName: String) = "chat_detail/$chatId/$chatName"
|
||||
}
|
||||
object Profile : Screen("profile?profileId={profileId}") {
|
||||
fun createRoute(profileId: String? = null) = if (profileId != null) "profile?profileId=$profileId" else "profile"
|
||||
}
|
||||
object EditProfile : Screen("edit_profile")
|
||||
object Settings : Screen("settings")
|
||||
object Contacts : Screen("contacts")
|
||||
}
|
||||
|
||||
@Composable
|
||||
fun AppNavigation(
|
||||
navController: NavHostController = rememberNavController(),
|
||||
startDestination: String = Screen.Login.route
|
||||
) {
|
||||
val navBackStackEntry by navController.currentBackStackEntryAsState()
|
||||
val currentRoute = navBackStackEntry?.destination?.route
|
||||
|
||||
// Определяем, нужно ли показывать нижнюю панель
|
||||
val showBottomBar = currentRoute in listOf(
|
||||
Screen.ChatList.route,
|
||||
Screen.Contacts.route,
|
||||
Screen.Settings.route,
|
||||
Screen.Profile.route
|
||||
)
|
||||
|
||||
Scaffold(
|
||||
bottomBar = {
|
||||
if (showBottomBar) {
|
||||
GlassNavigationBar(
|
||||
currentRoute = currentRoute ?: "",
|
||||
onNavigate = { route ->
|
||||
navController.navigate(route) {
|
||||
popUpTo(Screen.ChatList.route) { saveState = true }
|
||||
launchSingleTop = true
|
||||
restoreState = true
|
||||
}
|
||||
},
|
||||
userAvatarUrl = null,
|
||||
username = "Me"
|
||||
)
|
||||
}
|
||||
}
|
||||
) { paddingValues ->
|
||||
Box(modifier = Modifier.padding(if (showBottomBar) paddingValues else PaddingValues(0.dp))) {
|
||||
NavHost(
|
||||
navController = navController,
|
||||
startDestination = startDestination
|
||||
) {
|
||||
composable(Screen.Login.route) {
|
||||
val viewModel: AuthViewModel = hiltViewModel()
|
||||
LoginScreen(
|
||||
viewModel = viewModel,
|
||||
onNavigateToRegister = { navController.navigate(Screen.Register.route) },
|
||||
onNavigateToSettings = { navController.navigate(Screen.Settings.route) },
|
||||
onLoginSuccess = {
|
||||
navController.navigate(Screen.ChatList.route) {
|
||||
popUpTo(Screen.Login.route) { inclusive = true }
|
||||
}
|
||||
}
|
||||
)
|
||||
}
|
||||
composable(Screen.Register.route) {
|
||||
val viewModel: AuthViewModel = hiltViewModel()
|
||||
RegisterScreen(
|
||||
viewModel = viewModel,
|
||||
onNavigateToLogin = { navController.popBackStack() },
|
||||
onRegisterSuccess = {
|
||||
navController.navigate(Screen.ChatList.route) {
|
||||
popUpTo(Screen.Login.route) { inclusive = true }
|
||||
}
|
||||
}
|
||||
)
|
||||
}
|
||||
composable(Screen.ChatList.route) {
|
||||
val viewModel: ChatListViewModel = hiltViewModel()
|
||||
val storyViewModel: StoryViewModel = hiltViewModel()
|
||||
ChatListScreen(
|
||||
viewModel = viewModel,
|
||||
storyViewModel = storyViewModel,
|
||||
onChatClick = { chatId ->
|
||||
navController.navigate(Screen.ChatDetail.createRoute(chatId, "Chat"))
|
||||
},
|
||||
onStoryClick = { /* Story click logic */ }
|
||||
)
|
||||
}
|
||||
composable(
|
||||
route = Screen.ChatDetail.route,
|
||||
arguments = listOf(
|
||||
navArgument("chatId") { type = NavType.StringType },
|
||||
navArgument("chatName") { type = NavType.StringType }
|
||||
)
|
||||
) { backStackEntry ->
|
||||
val chatId = backStackEntry.arguments?.getString("chatId") ?: ""
|
||||
val chatName = backStackEntry.arguments?.getString("chatName") ?: "Chat"
|
||||
val viewModel: ChatDetailViewModel = hiltViewModel()
|
||||
|
||||
ChatDetailScreen(
|
||||
chatName = chatName,
|
||||
viewModel = viewModel,
|
||||
onBack = { navController.popBackStack() }
|
||||
)
|
||||
}
|
||||
composable(Screen.Contacts.route) {
|
||||
val viewModel: ContactListViewModel = hiltViewModel()
|
||||
val state by viewModel.state.collectAsState()
|
||||
ContactListScreen(
|
||||
contacts = state.contacts,
|
||||
isLoading = state.isLoading,
|
||||
onContactClick = { id -> navController.navigate(Screen.Profile.createRoute(id)) },
|
||||
onSearchChange = { viewModel.onSearchChange(it) }
|
||||
)
|
||||
}
|
||||
composable(
|
||||
route = Screen.Profile.route,
|
||||
arguments = listOf(
|
||||
navArgument("profileId") {
|
||||
type = NavType.StringType
|
||||
nullable = true
|
||||
}
|
||||
)
|
||||
) { backStackEntry ->
|
||||
val profileId = backStackEntry.arguments?.getString("profileId")
|
||||
val viewModel: ProfileViewModel = hiltViewModel()
|
||||
|
||||
ProfileScreen(
|
||||
profileId = profileId,
|
||||
viewModel = viewModel,
|
||||
onEditProfile = { navController.navigate(Screen.EditProfile.route) },
|
||||
onBack = { navController.popBackStack() },
|
||||
onSendMessage = { id -> navController.navigate(Screen.ChatDetail.createRoute(id, "Chat")) }
|
||||
)
|
||||
}
|
||||
composable(Screen.EditProfile.route) {
|
||||
val viewModel: ProfileViewModel = hiltViewModel()
|
||||
val state by viewModel.state.collectAsState()
|
||||
|
||||
EditProfileScreen(
|
||||
currentDisplayName = state.profile?.displayName,
|
||||
currentUsername = state.profile?.username ?: "",
|
||||
currentBio = state.profile?.bio,
|
||||
currentAvatarUrl = state.profile?.avatarUrl,
|
||||
onSave = { name, bio, uri ->
|
||||
viewModel.updateProfile(name, bio, uri)
|
||||
navController.popBackStack()
|
||||
},
|
||||
onBack = { navController.popBackStack() }
|
||||
)
|
||||
}
|
||||
composable(Screen.Settings.route) {
|
||||
val viewModel: SettingsViewModel = hiltViewModel()
|
||||
SettingsScreen(
|
||||
viewModel = viewModel,
|
||||
onBack = { navController.popBackStack() },
|
||||
onLogout = {
|
||||
navController.navigate(Screen.Login.route) {
|
||||
popUpTo(0) { inclusive = true }
|
||||
}
|
||||
}
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user