更新代码
This commit is contained in:
@@ -4,6 +4,7 @@ import android.os.Bundle
|
||||
import androidx.activity.ComponentActivity
|
||||
import androidx.activity.compose.setContent
|
||||
import androidx.activity.enableEdgeToEdge
|
||||
import androidx.activity.result.contract.ActivityResultContracts
|
||||
import androidx.compose.animation.AnimatedContentScope
|
||||
import androidx.compose.animation.ExperimentalSharedTransitionApi
|
||||
import androidx.compose.animation.SharedTransitionScope
|
||||
@@ -28,6 +29,7 @@ import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.graphics.Color
|
||||
import androidx.compose.ui.platform.LocalDensity
|
||||
import androidx.compose.ui.unit.dp
|
||||
import androidx.core.content.ContextCompat
|
||||
import androidx.core.view.WindowCompat
|
||||
import androidx.navigation.NavHostController
|
||||
import androidx.navigation.compose.currentBackStackEntryAsState
|
||||
@@ -44,10 +46,40 @@ import com.google.firebase.ktx.Firebase
|
||||
import kotlinx.coroutines.CoroutineScope
|
||||
import kotlinx.coroutines.Dispatchers
|
||||
import kotlinx.coroutines.launch
|
||||
import android.Manifest
|
||||
import android.app.NotificationChannel
|
||||
import android.app.NotificationManager
|
||||
import android.content.Context
|
||||
import android.content.Intent
|
||||
import android.content.pm.PackageManager
|
||||
import android.os.Build
|
||||
import android.util.Log
|
||||
import android.widget.Toast
|
||||
import androidx.lifecycle.ProcessLifecycleOwner
|
||||
import androidx.lifecycle.viewModelScope
|
||||
import androidx.navigation.findNavController
|
||||
import com.aiosman.riderpro.ui.post.PostViewModel
|
||||
import com.google.android.gms.tasks.OnCompleteListener
|
||||
import com.google.firebase.messaging.FirebaseMessaging
|
||||
|
||||
class MainActivity : ComponentActivity() {
|
||||
// Firebase Analytics
|
||||
private lateinit var analytics: FirebaseAnalytics
|
||||
private val scope = CoroutineScope(Dispatchers.Main)
|
||||
// 请求通知权限
|
||||
private val requestPermissionLauncher = registerForActivityResult(
|
||||
ActivityResultContracts.RequestPermission(),
|
||||
) { isGranted: Boolean ->
|
||||
if (isGranted) {
|
||||
// FCM SDK (and your app) can post notifications.
|
||||
} else {
|
||||
// TODO: Inform user that that your app will not show notifications.
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取账号信息
|
||||
*/
|
||||
suspend fun getAccount(): Boolean {
|
||||
val accountService: AccountService = AccountServiceImpl()
|
||||
try {
|
||||
@@ -60,26 +92,90 @@ class MainActivity : ComponentActivity() {
|
||||
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
// 监听应用生命周期
|
||||
ProcessLifecycleOwner.get().lifecycle.addObserver(MainActivityLifecycleObserver())
|
||||
// 创建通知渠道
|
||||
createNotificationChannel()
|
||||
// 沉浸式状态栏
|
||||
WindowCompat.setDecorFitsSystemWindows(window, false)
|
||||
// 初始化 Places SDK
|
||||
if (!Places.isInitialized()) {
|
||||
Places.initialize(applicationContext, "AIzaSyDpgLDH1-SECw_pdjJq_msynq1XrxwgKVI")
|
||||
}
|
||||
// 初始化 Firebase Analytics
|
||||
analytics = Firebase.analytics
|
||||
// 请求通知权限
|
||||
askNotificationPermission()
|
||||
// 加载一些本地化的配置
|
||||
AppStore.init(this)
|
||||
|
||||
enableEdgeToEdge()
|
||||
|
||||
scope.launch {
|
||||
// 检查是否有登录态
|
||||
val isAccountValidate = getAccount()
|
||||
var startDestination = NavigationRoute.Login.route
|
||||
// 如果有登录态,且记住登录状态,且账号有效,则初始化 FCM,下一步进入首页
|
||||
if (AppStore.token != null && AppStore.rememberMe && isAccountValidate) {
|
||||
Messaging.InitFCM(scope)
|
||||
startDestination = NavigationRoute.Index.route
|
||||
}
|
||||
setContent {
|
||||
Navigation(startDestination)
|
||||
Navigation(startDestination) { navController ->
|
||||
// 处理带有 postId 的通知点击
|
||||
val postId = intent.getStringExtra("POST_ID")
|
||||
if (postId != null) {
|
||||
Log.d("MainActivity", "Navigation to Post$postId")
|
||||
PostViewModel.postId = postId
|
||||
PostViewModel.viewModelScope.launch {
|
||||
PostViewModel.initData()
|
||||
navController.navigate(NavigationRoute.Post.route.replace("{id}", postId))
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 请求通知权限
|
||||
*/
|
||||
private fun askNotificationPermission() {
|
||||
// This is only necessary for API level >= 33 (TIRAMISU)
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.TIRAMISU) {
|
||||
if (ContextCompat.checkSelfPermission(this, Manifest.permission.POST_NOTIFICATIONS) ==
|
||||
PackageManager.PERMISSION_GRANTED
|
||||
) {
|
||||
// FCM SDK (and your app) can post notifications.
|
||||
} else if (shouldShowRequestPermissionRationale(android.Manifest.permission.POST_NOTIFICATIONS)) {
|
||||
|
||||
} else {
|
||||
// Directly ask for the permission
|
||||
requestPermissionLauncher.launch(Manifest.permission.POST_NOTIFICATIONS)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 创建通知渠道
|
||||
*/
|
||||
private fun createNotificationChannel() {
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
|
||||
val channelId = ConstVars.MOMENT_LIKE_CHANNEL_ID
|
||||
val channelName = ConstVars.MOMENT_LIKE_CHANNEL_NAME
|
||||
val channel =
|
||||
NotificationChannel(channelId, channelName, NotificationManager.IMPORTANCE_DEFAULT)
|
||||
val notificationManager =
|
||||
getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager
|
||||
notificationManager.createNotificationChannel(channel)
|
||||
}
|
||||
}
|
||||
|
||||
override fun onNewIntent(intent: Intent) {
|
||||
super.onNewIntent(intent)
|
||||
}
|
||||
}
|
||||
|
||||
val LocalNavController = compositionLocalOf<NavHostController> {
|
||||
@@ -96,97 +192,3 @@ val LocalAnimatedContentScope = compositionLocalOf<AnimatedContentScope> {
|
||||
}
|
||||
|
||||
|
||||
// 用于带导航栏的路由的可复用 composable
|
||||
@Composable
|
||||
fun ScaffoldWithNavigationBar(
|
||||
navController: NavHostController,
|
||||
content: @Composable () -> Unit
|
||||
) {
|
||||
val navigationBarHeight = with(LocalDensity.current) {
|
||||
WindowInsets.navigationBars.getBottom(this).toDp()
|
||||
}
|
||||
val item = listOf(
|
||||
NavigationItem.Home,
|
||||
NavigationItem.Street,
|
||||
NavigationItem.Add,
|
||||
NavigationItem.Message,
|
||||
NavigationItem.Profile
|
||||
)
|
||||
Scaffold(
|
||||
modifier = Modifier.statusBarsPadding(),
|
||||
bottomBar = {
|
||||
NavigationBar(
|
||||
modifier = Modifier.height(56.dp + navigationBarHeight),
|
||||
containerColor = Color.Black
|
||||
) {
|
||||
val navBackStackEntry by navController.currentBackStackEntryAsState()
|
||||
val currentRoute = navBackStackEntry?.destination?.route
|
||||
val systemUiController = rememberSystemUiController()
|
||||
item.forEach { it ->
|
||||
val isSelected = currentRoute == it.route
|
||||
val iconTint by animateColorAsState(
|
||||
targetValue = if (isSelected) Color.Red else Color.White,
|
||||
animationSpec = tween(durationMillis = 250), label = ""
|
||||
)
|
||||
NavigationBarItem(
|
||||
selected = currentRoute == it.route,
|
||||
onClick = {
|
||||
// Check if the current route is not the same as the tab's route to avoid unnecessary navigation
|
||||
if (currentRoute != it.route) {
|
||||
navController.navigate(it.route) {
|
||||
// Avoid creating a new layer on top of the navigation stack
|
||||
launchSingleTop = true
|
||||
// Attempt to pop up to the existing instance of the destination, if present
|
||||
popUpTo(navController.graph.startDestinationId) {
|
||||
saveState = true
|
||||
}
|
||||
// Restore state when navigating back to the composable
|
||||
restoreState = true
|
||||
}
|
||||
}
|
||||
// Additional logic for system UI color changes
|
||||
when (it.route) {
|
||||
NavigationItem.Add.route -> {
|
||||
systemUiController.setSystemBarsColor(color = Color.Black)
|
||||
}
|
||||
|
||||
NavigationItem.Message.route -> {
|
||||
systemUiController.setSystemBarsColor(color = Color.Black)
|
||||
}
|
||||
|
||||
else -> {
|
||||
systemUiController.setSystemBarsColor(color = Color.Transparent)
|
||||
}
|
||||
}
|
||||
},
|
||||
colors = NavigationBarItemColors(
|
||||
selectedTextColor = Color.Red,
|
||||
selectedIndicatorColor = Color.Black,
|
||||
unselectedTextColor = Color.Red,
|
||||
disabledIconColor = Color.Red,
|
||||
disabledTextColor = Color.Red,
|
||||
selectedIconColor = iconTint,
|
||||
unselectedIconColor = iconTint,
|
||||
),
|
||||
icon = {
|
||||
Icon(
|
||||
modifier = Modifier.size(24.dp),
|
||||
imageVector = if (currentRoute == it.route) it.selectedIcon() else it.icon(),
|
||||
contentDescription = null,
|
||||
tint = iconTint
|
||||
)
|
||||
}
|
||||
)
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
) { innerPadding ->
|
||||
Box(
|
||||
modifier = Modifier.padding(innerPadding)
|
||||
) {
|
||||
content()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user