mirror of
https://github.com/anyproto/anytype-kotlin.git
synced 2025-06-07 21:37:02 +09:00
DROID-3637 Chats | Enhancement | Open chat by push notification (#2425)
This commit is contained in:
parent
89c9ef6ad9
commit
6ff5b57790
4 changed files with 96 additions and 10 deletions
|
@ -11,6 +11,8 @@ import androidx.core.app.NotificationCompat
|
|||
import com.anytypeio.anytype.R
|
||||
import com.anytypeio.anytype.app.AndroidApplication
|
||||
import com.anytypeio.anytype.core_models.DecryptedPushContent
|
||||
import com.anytypeio.anytype.core_models.Relations
|
||||
import com.anytypeio.anytype.core_ui.views.Relations1
|
||||
import com.anytypeio.anytype.domain.device.DeviceTokenStoringService
|
||||
import com.anytypeio.anytype.presentation.notifications.DecryptionPushContentService
|
||||
import com.anytypeio.anytype.ui.main.MainActivity
|
||||
|
@ -87,11 +89,11 @@ class AnytypePushService : FirebaseMessagingService() {
|
|||
Timber.d("New message received: $message")
|
||||
|
||||
// Create an intent to open the app when notification is tapped
|
||||
//todo extra task on Navigation
|
||||
val intent = Intent(this, MainActivity::class.java).apply {
|
||||
action = ACTION_OPEN_CHAT
|
||||
flags = Intent.FLAG_ACTIVITY_NEW_TASK or Intent.FLAG_ACTIVITY_CLEAR_TOP
|
||||
putExtra(EXTRA_CHAT_ID, message.chatId)
|
||||
putExtra(EXTRA_SPACE_ID, message.spaceName)
|
||||
putExtra(Relations.CHAT_ID, message.chatId)
|
||||
putExtra(Relations.SPACE_ID, message.spaceName)
|
||||
}
|
||||
|
||||
val pendingIntent = PendingIntent.getActivity(
|
||||
|
@ -145,9 +147,7 @@ class AnytypePushService : FirebaseMessagingService() {
|
|||
private const val PAYLOAD_KEY = "x-any-payload"
|
||||
private const val KEY_ID_KEY = "x-any-key-id"
|
||||
private const val CHANNEL_NAME = "Chat Messages"
|
||||
val EXTRA_CHAT_ID = "chatId"
|
||||
val EXTRA_SPACE_ID = "spaceId"
|
||||
|
||||
private const val NOTIFICATION_REQUEST_CODE = 100
|
||||
const val ACTION_OPEN_CHAT = "com.anytype.ACTION_OPEN_CHAT"
|
||||
}
|
||||
}
|
|
@ -69,7 +69,7 @@ class ChatFragment : BaseComposeFragment() {
|
|||
|
||||
private val vm by viewModels<ChatViewModel> { factory }
|
||||
|
||||
private val ctx get() = arg<Id>(CTX_KEY)
|
||||
val ctx get() = arg<Id>(CTX_KEY)
|
||||
private val space get() = arg<Id>(SPACE_KEY)
|
||||
|
||||
// Rendering
|
||||
|
|
|
@ -20,6 +20,7 @@ import androidx.lifecycle.repeatOnLifecycle
|
|||
import androidx.navigation.NavOptions
|
||||
import androidx.navigation.NavOptions.*
|
||||
import androidx.navigation.findNavController
|
||||
import androidx.navigation.fragment.NavHostFragment
|
||||
import com.anytypeio.anytype.BuildConfig
|
||||
import com.anytypeio.anytype.R
|
||||
import com.anytypeio.anytype.analytics.base.EventsDictionary
|
||||
|
@ -29,6 +30,7 @@ import com.anytypeio.anytype.app.DefaultAppActionManager
|
|||
import com.anytypeio.anytype.core_models.Relations
|
||||
import com.anytypeio.anytype.core_models.ThemeMode
|
||||
import com.anytypeio.anytype.core_models.Wallpaper
|
||||
import com.anytypeio.anytype.core_models.multiplayer.SpaceType
|
||||
import com.anytypeio.anytype.core_models.primitives.SpaceId
|
||||
import com.anytypeio.anytype.core_utils.ext.Mimetype
|
||||
import com.anytypeio.anytype.core_utils.ext.parseActionSendMultipleUris
|
||||
|
@ -36,6 +38,7 @@ import com.anytypeio.anytype.core_utils.ext.parseActionSendUri
|
|||
import com.anytypeio.anytype.core_utils.ext.toast
|
||||
import com.anytypeio.anytype.core_utils.insets.EDGE_TO_EDGE_MIN_SDK
|
||||
import com.anytypeio.anytype.core_utils.tools.FeatureToggles
|
||||
import com.anytypeio.anytype.device.AnytypePushService
|
||||
import com.anytypeio.anytype.di.common.componentManager
|
||||
import com.anytypeio.anytype.domain.base.BaseUseCase
|
||||
import com.anytypeio.anytype.domain.theme.GetTheme
|
||||
|
@ -205,13 +208,37 @@ class MainActivity : AppCompatActivity(R.layout.activity_main), AppNavigation.Pr
|
|||
is Command.Deeplink.DeepLinkToObjectNotWorking -> {
|
||||
toast(getString(R.string.multiplayer_deeplink_to_your_object_error))
|
||||
}
|
||||
is Command.LaunchChat -> {
|
||||
runCatching {
|
||||
val controller = findNavController(R.id.fragment)
|
||||
controller.popBackStack(R.id.vaultScreen, false)
|
||||
controller.navigate(
|
||||
R.id.actionOpenSpaceFromVault,
|
||||
HomeScreenFragment.args(
|
||||
space = command.space,
|
||||
deeplink = null
|
||||
)
|
||||
)
|
||||
controller.navigate(
|
||||
R.id.chatScreen,
|
||||
ChatFragment.args(
|
||||
space = command.space,
|
||||
ctx = command.chat
|
||||
)
|
||||
)
|
||||
}.onFailure {
|
||||
if (BuildConfig.DEBUG) {
|
||||
toast("Failed to open chat from push notification")
|
||||
}
|
||||
}
|
||||
}
|
||||
is Command.Deeplink.DeepLinkToObject -> {
|
||||
when(val effect = command.sideEffect) {
|
||||
is Command.Deeplink.DeepLinkToObject.SideEffect.SwitchSpace -> {
|
||||
runCatching {
|
||||
val controller = findNavController(R.id.fragment)
|
||||
controller.popBackStack(R.id.vaultScreen, false)
|
||||
if (effect.chat != null) {
|
||||
if (effect.chat != null && effect.spaceType == SpaceType.CHAT) {
|
||||
controller.navigate(
|
||||
R.id.actionOpenChatFromVault,
|
||||
ChatFragment.args(
|
||||
|
@ -449,6 +476,34 @@ class MainActivity : AppCompatActivity(R.layout.activity_main), AppNavigation.Pr
|
|||
AnytypeNotificationService.NOTIFICATION_INTENT_ACTION -> {
|
||||
proceedWithNotificationIntent(intent)
|
||||
}
|
||||
AnytypePushService.ACTION_OPEN_CHAT -> {
|
||||
proceedWithOpenChatIntent(intent)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private fun proceedWithOpenChatIntent(intent: Intent) {
|
||||
val chatId = intent.getStringExtra(Relations.CHAT_ID)
|
||||
val spaceId = intent.getStringExtra(Relations.SPACE_ID)
|
||||
if (!chatId.isNullOrEmpty() && !spaceId.isNullOrEmpty()) {
|
||||
if (!isChatFragmentVisible(chatId)) {
|
||||
vm.onOpenChatTriggeredByPush(
|
||||
chatId = chatId,
|
||||
spaceId = spaceId
|
||||
)
|
||||
} else {
|
||||
// Do nothing, already there.
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private fun isChatFragmentVisible(chatId: String): Boolean {
|
||||
val navHostFragment = supportFragmentManager.findFragmentById(R.id.fragment) as? NavHostFragment
|
||||
val currentFragment = navHostFragment?.childFragmentManager?.fragments?.firstOrNull()
|
||||
return if (currentFragment is ChatFragment) {
|
||||
currentFragment.ctx == chatId
|
||||
} else {
|
||||
false
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -720,7 +775,6 @@ class MainActivity : AppCompatActivity(R.layout.activity_main), AppNavigation.Pr
|
|||
}
|
||||
|
||||
companion object {
|
||||
const val AUTO_UPDATE_URL = "https://fra1.digitaloceanspaces.com/anytype-release/latest-android.json"
|
||||
const val SHARE_DIALOG_LABEL = "anytype.dialog.share.label"
|
||||
const val SHARE_IMAGE_INTENT_PATTERN = "image/"
|
||||
const val SHARE_VIDEO_INTENT_PATTERN = "video/"
|
||||
|
|
|
@ -12,6 +12,7 @@ import com.anytypeio.anytype.core_models.NotificationPayload
|
|||
import com.anytypeio.anytype.core_models.NotificationStatus
|
||||
import com.anytypeio.anytype.core_models.Wallpaper
|
||||
import com.anytypeio.anytype.core_models.exceptions.NeedToUpdateApplicationException
|
||||
import com.anytypeio.anytype.core_models.multiplayer.SpaceType
|
||||
import com.anytypeio.anytype.core_utils.ext.cancel
|
||||
import com.anytypeio.anytype.domain.account.AwaitAccountStartManager
|
||||
import com.anytypeio.anytype.domain.account.InterceptAccountStatus
|
||||
|
@ -451,6 +452,31 @@ class MainViewModel(
|
|||
}
|
||||
}
|
||||
|
||||
fun onOpenChatTriggeredByPush(chatId: String, spaceId: String) {
|
||||
viewModelScope.launch {
|
||||
if (spaceManager.get() != spaceId) {
|
||||
spaceManager.set(spaceId)
|
||||
.onSuccess {
|
||||
commands.emit(
|
||||
Command.LaunchChat(
|
||||
space = spaceId,
|
||||
chat = chatId
|
||||
)
|
||||
)
|
||||
}.onFailure {
|
||||
Timber.e(it, "Error while switching space when launching chat from push notification")
|
||||
}
|
||||
} else {
|
||||
commands.emit(
|
||||
Command.LaunchChat(
|
||||
space = spaceId,
|
||||
chat = chatId
|
||||
)
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
sealed class Command {
|
||||
data class ShowDeletedAccountScreen(val deadline: Long) : Command()
|
||||
data object LogoutDueToAccountDeletion : Command()
|
||||
|
@ -467,6 +493,11 @@ class MainViewModel(
|
|||
data object Notifications: Command()
|
||||
data object RequestNotificationPermission: Command()
|
||||
|
||||
data class LaunchChat(
|
||||
val space: Id,
|
||||
val chat: Id
|
||||
): Command()
|
||||
|
||||
data class Navigate(val destination: OpenObjectNavigation): Command()
|
||||
|
||||
sealed class Deeplink : Command() {
|
||||
|
@ -480,7 +511,8 @@ class MainViewModel(
|
|||
sealed class SideEffect {
|
||||
data class SwitchSpace(
|
||||
val home: Id,
|
||||
val chat: Id?
|
||||
val chat: Id? = null,
|
||||
val spaceType: SpaceType? = null
|
||||
): SideEffect()
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue