From d5c7c7cd5e322ffccda9d01c55811c6977a6d21b Mon Sep 17 00:00:00 2001 From: Alexandru Cristescu Date: Thu, 6 Jun 2024 16:22:55 +0400 Subject: [PATCH] Fix for notification issues. --- .../localai/middlewares/UserMoveMiddleware.kt | 48 +++++---- .../onlinego/ui/screens/main/MainActivity.kt | 101 +++++++++--------- .../onlinego/utils/NotificationUtils.kt | 75 +++++++------ .../onlinego/utils/WhatsNewUtils.kt | 2 + 4 files changed, 123 insertions(+), 103 deletions(-) diff --git a/app/src/main/java/io/zenandroid/onlinego/ui/screens/localai/middlewares/UserMoveMiddleware.kt b/app/src/main/java/io/zenandroid/onlinego/ui/screens/localai/middlewares/UserMoveMiddleware.kt index c442c7b3..35e9d102 100644 --- a/app/src/main/java/io/zenandroid/onlinego/ui/screens/localai/middlewares/UserMoveMiddleware.kt +++ b/app/src/main/java/io/zenandroid/onlinego/ui/screens/localai/middlewares/UserMoveMiddleware.kt @@ -1,33 +1,41 @@ package io.zenandroid.onlinego.ui.screens.localai.middlewares +import com.google.firebase.crashlytics.FirebaseCrashlytics import io.reactivex.Observable import io.reactivex.rxkotlin.withLatestFrom import io.zenandroid.onlinego.data.model.Cell +import io.zenandroid.onlinego.data.model.StoneType import io.zenandroid.onlinego.gamelogic.RulesManager import io.zenandroid.onlinego.mvi.Middleware import io.zenandroid.onlinego.ui.screens.localai.AiGameAction import io.zenandroid.onlinego.ui.screens.localai.AiGameState class UserMoveMiddleware : Middleware { - override fun bind(actions: Observable, state: Observable): Observable { - val source = Observable.merge( - actions.ofType(AiGameAction.UserTappedCoordinate::class.java).map { it.coordinate }, - actions.ofType(AiGameAction.UserPressedPass::class.java).map { Cell(-1, -1) } - ) + override fun bind(actions: Observable, state: Observable): Observable { + val source = Observable.merge( + actions.ofType(AiGameAction.UserTappedCoordinate::class.java).map { it.coordinate }, + actions.ofType(AiGameAction.UserPressedPass::class.java).map { Cell(-1, -1) } + ) - return source - .withLatestFrom(state) - .filter { (_, state) -> state.position != null } - .flatMap { (coordinate, state) -> - val newPos = RulesManager.makeMove(state.position!!, state.position.nextToMove, coordinate) - when { - newPos == null && state.position.getStoneAt(coordinate) != null -> Observable.empty() - newPos == null -> Observable.just(AiGameAction.UserTriedSuicidalMove(coordinate)) - coordinate.x != -1 && RulesManager.isIllegalKO(state.history, newPos) -> Observable.just(AiGameAction.UserTriedKoMove(coordinate)) - else -> { - Observable.just(AiGameAction.NewPosition(newPos)) - } - } - } - } + return source + .withLatestFrom(state) + .filter { (_, state) -> state.position != null } + .flatMap { (coordinate, state) -> + val isBlacksTurn = state.position?.nextToMove != StoneType.WHITE + if (isBlacksTurn == state.enginePlaysBlack) { + FirebaseCrashlytics.getInstance().log("User tried to move when it's not their turn") + return@flatMap Observable.empty() + } + + val newPos = RulesManager.makeMove(state.position!!, state.position.nextToMove, coordinate) + when { + newPos == null && state.position.getStoneAt(coordinate) != null -> Observable.empty() + newPos == null -> Observable.just(AiGameAction.UserTriedSuicidalMove(coordinate)) + coordinate.x != -1 && RulesManager.isIllegalKO(state.history, newPos) -> Observable.just(AiGameAction.UserTriedKoMove(coordinate)) + else -> { + Observable.just(AiGameAction.NewPosition(newPos)) + } + } + } + } } \ No newline at end of file diff --git a/app/src/main/java/io/zenandroid/onlinego/ui/screens/main/MainActivity.kt b/app/src/main/java/io/zenandroid/onlinego/ui/screens/main/MainActivity.kt index a00cb225..4f928e37 100644 --- a/app/src/main/java/io/zenandroid/onlinego/ui/screens/main/MainActivity.kt +++ b/app/src/main/java/io/zenandroid/onlinego/ui/screens/main/MainActivity.kt @@ -138,56 +138,61 @@ class MainActivity : AppCompatActivity(), MainContract.View { val notificationManager = getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager listOf( - NotificationChannelGroup("correspondence", "Correspondence"), - NotificationChannelGroup("live", "Live"), - NotificationChannelGroup("blitz", "Blitz"), - ).map(notificationManager::createNotificationChannelGroup) + NotificationChannelGroup("correspondence", "Correspondence"), + NotificationChannelGroup("live", "Live"), + NotificationChannelGroup("blitz", "Blitz"), + ) + .map { it.id } + .map(notificationManager::deleteNotificationChannelGroup) + + notificationManager.createNotificationChannelGroup( + NotificationChannelGroup("your_turn", "Your Turn") + ) notificationManager.createNotificationChannels( - listOf( - NotificationChannel("active_correspondence_games", "Your Turn", NotificationManager.IMPORTANCE_LOW).apply { - setGroup("correspondence") - enableLights(true) - lightColor = Color.WHITE - enableVibration(true) - vibrationPattern = longArrayOf(0, 200, 0, 200) - - }, - NotificationChannel("active_live_games", "Your Turn", NotificationManager.IMPORTANCE_LOW).apply { - setGroup("live") - enableLights(true) - lightColor = Color.WHITE - enableVibration(true) - vibrationPattern = longArrayOf(0, 200, 0, 200) - - }, - NotificationChannel("active_blitz_games", "Your Turn", NotificationManager.IMPORTANCE_LOW).apply { - setGroup("blitz") - enableLights(true) - lightColor = Color.WHITE - enableVibration(true) - vibrationPattern = longArrayOf(0, 200, 0, 200) - - }, - NotificationChannel("active_games", "Your Turn", NotificationManager.IMPORTANCE_NONE).apply { - enableLights(true) - lightColor = Color.WHITE - enableVibration(true) - vibrationPattern = longArrayOf(0, 200, 0, 200) - - }, - NotificationChannel("challenges", "Challenges", NotificationManager.IMPORTANCE_LOW).apply { - enableLights(true) - lightColor = Color.WHITE - enableVibration(true) - vibrationPattern = longArrayOf(0, 200, 0, 200) - - }, - NotificationChannel("logout", "Logout", NotificationManager.IMPORTANCE_LOW).apply { - enableLights(false) - enableVibration(false) - } - ) + listOf( + NotificationChannel("active_correspondence_games", "Correspondence Games", NotificationManager.IMPORTANCE_LOW).apply { + group = "your_turn" + enableLights(true) + lightColor = Color.WHITE + enableVibration(true) + vibrationPattern = longArrayOf(0, 200, 0, 200) + + }, + NotificationChannel("active_live_games", "Live Games", NotificationManager.IMPORTANCE_LOW).apply { + group = "your_turn" + enableLights(true) + lightColor = Color.WHITE + enableVibration(true) + vibrationPattern = longArrayOf(0, 200, 0, 200) + + }, + NotificationChannel("active_blitz_games", "Blitz Games", NotificationManager.IMPORTANCE_LOW).apply { + group = "your_turn" + enableLights(true) + lightColor = Color.WHITE + enableVibration(true) + vibrationPattern = longArrayOf(0, 200, 0, 200) + + }, + NotificationChannel("active_games", "Your Turn", NotificationManager.IMPORTANCE_LOW).apply { + enableLights(true) + lightColor = Color.WHITE + enableVibration(true) + vibrationPattern = longArrayOf(0, 200, 0, 200) + }, + NotificationChannel("challenges", "Challenges", NotificationManager.IMPORTANCE_LOW).apply { + enableLights(true) + lightColor = Color.WHITE + enableVibration(true) + vibrationPattern = longArrayOf(0, 200, 0, 200) + + }, + NotificationChannel("logout", "Logout", NotificationManager.IMPORTANCE_LOW).apply { + enableLights(false) + enableVibration(false) + } + ) ) } } diff --git a/app/src/main/java/io/zenandroid/onlinego/utils/NotificationUtils.kt b/app/src/main/java/io/zenandroid/onlinego/utils/NotificationUtils.kt index b08d03f4..60d56bd5 100644 --- a/app/src/main/java/io/zenandroid/onlinego/utils/NotificationUtils.kt +++ b/app/src/main/java/io/zenandroid/onlinego/utils/NotificationUtils.kt @@ -172,39 +172,43 @@ class NotificationUtils { games.forEach { context.resources.getDimensionPixelSize(android.R.dimen.notification_large_icon_width) val pendingIntent = NavDeepLinkBuilder(context) - .setComponentName(MainActivity::class.java) - .setGraph(R.navigation.graph) - .setDestination(R.id.gameFragment) - .setArguments(bundleOf( - GAME_ID to it.id, - GAME_WIDTH to it.width, - GAME_HEIGHT to it.height - )) - .createPendingIntent() + .setComponentName(MainActivity::class.java) + .setGraph(R.navigation.graph) + .setDestination(R.id.gameFragment) + .setArguments(bundleOf( + GAME_ID to it.id, + GAME_WIDTH to it.width, + GAME_HEIGHT to it.height + )) + .createPendingIntent() val opponent = if (userId == it.blackPlayer.id) it.whitePlayer.username else it.blackPlayer.username - val message = when(it.phase) { + val message = when (it.phase) { Phase.FINISHED -> { val outcome = when { it.outcome == "Cancellation" -> "Cancelled" userId == it.blackPlayer.id -> if (it.blackLost == true) "Lost by ${it.outcome}" else "Won by ${it.outcome}" + userId == it.whitePlayer.id -> if (it.whiteLost == true) "Lost by ${it.outcome}" else "Won by ${it.outcome}" + it.whiteLost == true -> "Black won by ${it.outcome}" + else -> "White won by ${it.outcome}" } "Game ended - $outcome" } + Phase.PLAY -> "Your turn" Phase.STONE_REMOVAL -> "Stone removal phase" - else -> "Requires your attention" + else -> "${it.phase} Requires your attention" } - val category = when(it.timeControl?.speed?.uppercase(Locale.ROOT)) { + val category = when (it.timeControl?.speed?.lowercase(Locale.ROOT)) { "correspondence" -> "active_correspondence_games" "live" -> "active_live_games" "blitz" -> "active_blitz_games" @@ -218,29 +222,30 @@ class NotificationUtils { board.position = RulesManager.replay(it, computeTerritory = false) remoteView.setImageViewBitmap(R.id.notification_bitmap, board.convertToContentBitmap()) val notification = - NotificationCompat.Builder(context, category) - .setContentTitle(opponent) - .setContentText(message) - .setContentIntent(pendingIntent) - .setVibrate(arrayOf(0L, 200L, 0L, 200L).toLongArray()) - .setLargeIcon(board.convertToIconBitmap()) - .setSmallIcon(R.drawable.ic_notification_go_board) - .setColor(ResourcesCompat.getColor(context.resources, R.color.colorTextSecondary, null)) - .setGroup("GAME_NOTIFICATIONS") - .setGroupAlertBehavior(NotificationCompat.GROUP_ALERT_SUMMARY) - .setStyle(NotificationCompat.DecoratedCustomViewStyle()) - .setCustomBigContentView(remoteView) - .apply { - if (it.phase == Phase.PLAY) - setChronometerCountDown(true) - .setUsesChronometer(true) - .setShowWhen(true) - .setWhen(timeLimit) - .setOngoing(true) - else - setAutoCancel(true) - } - .build() + NotificationCompat.Builder(context, category) + .setContentTitle(opponent) + .setContentText(message) + .setContentIntent(pendingIntent) + .setVibrate(arrayOf(0L, 200L, 0L, 200L).toLongArray()) + .setLargeIcon(board.convertToIconBitmap()) + .setSmallIcon(R.drawable.ic_notification_go_board) + .setColor(ResourcesCompat.getColor(context.resources, R.color.colorTextSecondary, null)) + .setGroup("GAME_NOTIFICATIONS") + .setGroupAlertBehavior(NotificationCompat.GROUP_ALERT_SUMMARY) + .setStyle(NotificationCompat.DecoratedCustomViewStyle()) + .setCustomBigContentView(remoteView) + .apply { + if (it.phase == Phase.PLAY && it.timeControl?.speed != "correspondence" && Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) { + setChronometerCountDown(true) + .setUsesChronometer(true) + .setShowWhen(true) + .setWhen(timeLimit) + .setOngoing(true) + } else { + setAutoCancel(true) + } + } + .build() val notificationManager = context.getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager notificationManager.notify(it.id.toInt(), notification) diff --git a/app/src/main/java/io/zenandroid/onlinego/utils/WhatsNewUtils.kt b/app/src/main/java/io/zenandroid/onlinego/utils/WhatsNewUtils.kt index 755e9aca..6d49c50e 100644 --- a/app/src/main/java/io/zenandroid/onlinego/utils/WhatsNewUtils.kt +++ b/app/src/main/java/io/zenandroid/onlinego/utils/WhatsNewUtils.kt @@ -32,6 +32,8 @@ private val annotatedCurrentText = AnnotatedString.Builder().run { pop() pushStyle(SpanStyle(fontWeight = FontWeight.Normal)) + append("· Hot fix for some notification issues that were introduced in the previous version.") + append("\n") append("· Puzzles screen (thanks to bqv for the contribution)") append("\n") append("· More notifications controls. You can now disable notifications for live games for example.")