@@ -19,7 +19,10 @@ package com.ichi2.anki
1919import android.content.Context
2020import android.content.Intent
2121import android.net.Uri
22+ import android.os.Build
2223import android.os.Bundle
24+ import android.os.Handler
25+ import android.os.Looper
2326import android.os.Message
2427import androidx.annotation.CheckResult
2528import androidx.annotation.VisibleForTesting
@@ -54,6 +57,8 @@ import kotlinx.coroutines.Dispatchers
5457import kotlinx.coroutines.launch
5558import timber.log.Timber
5659import java.io.File
60+ import java.time.Duration
61+ import java.time.Instant
5762import kotlin.math.max
5863import kotlin.math.min
5964
@@ -67,54 +72,81 @@ import kotlin.math.min
6772class IntentHandler : AbstractIntentHandler () {
6873 override fun onCreate (savedInstanceState : Bundle ? ) {
6974 // Note: This is our entry point from the launcher with intent: android.intent.action.MAIN
70- super .onCreate(savedInstanceState)
71- val intent = intent
72- Timber .v(intent.toString())
73- val reloadIntent = Intent (this , DeckPicker ::class .java)
74- reloadIntent.setDataAndType(getIntent().data, getIntent().type)
75- val action = intent.action
76- // #6157 - We want to block actions that need permissions we don't have, but not the default case
77- // as this requires nothing
78- val runIfStoragePermissions = { runnable: () -> Unit -> performActionIfStorageAccessible(reloadIntent, action) { runnable() } }
79- val launchType = getLaunchType(intent)
80- // TODO block the UI with some kind of ProgressDialog instead of cancelling the sync work
81- if (requiresCollectionAccess(launchType)) {
82- // # 18899
83- if (WorkManager .isInitialized()) {
84- SyncWorker .cancel(this )
85- }
86- }
87- when (launchType) {
88- LaunchType .FILE_IMPORT ->
89- runIfStoragePermissions {
90- handleFileImport(fileIntent, reloadIntent, action)
91- finish()
92- }
93- LaunchType .TEXT_IMPORT ->
94- runIfStoragePermissions {
95- onSelectedCsvForImport(fileIntent)
96- finish()
75+
76+ val handleScreen = { delay: Long ->
77+ Handler (Looper .getMainLooper()).postDelayed({
78+ val intent = intent
79+ Timber .v(intent.toString())
80+ val reloadIntent = Intent (this , DeckPicker ::class .java)
81+ reloadIntent.setDataAndType(getIntent().data, getIntent().type)
82+ val action = intent.action
83+ // #6157 - We want to block actions that need permissions we don't have, but not the default case
84+ // as this requires nothing
85+ val runIfStoragePermissions = { runnable: () -> Unit ->
86+ performActionIfStorageAccessible(reloadIntent, action) { runnable() }
9787 }
98- LaunchType .IMAGE_IMPORT ->
99- runIfStoragePermissions {
100- handleImageImport(intent)
101- finish()
88+ val launchType = getLaunchType(intent)
89+ // TODO block the UI with some kind of ProgressDialog instead of cancelling the sync work
90+ if (requiresCollectionAccess(launchType)) {
91+ // # 18899
92+ if (WorkManager .isInitialized()) {
93+ SyncWorker .cancel(this )
94+ }
10295 }
103- LaunchType .SHARED_TEXT ->
104- runIfStoragePermissions {
105- handleSharedText(intent)
106- finish()
96+ when (launchType) {
97+ LaunchType .FILE_IMPORT ->
98+ runIfStoragePermissions {
99+ handleFileImport(fileIntent, reloadIntent, action)
100+ finish()
101+ }
102+ LaunchType .TEXT_IMPORT ->
103+ runIfStoragePermissions {
104+ onSelectedCsvForImport(fileIntent)
105+ finish()
106+ }
107+ LaunchType .IMAGE_IMPORT ->
108+ runIfStoragePermissions {
109+ handleImageImport(intent)
110+ finish()
111+ }
112+ LaunchType .SHARED_TEXT ->
113+ runIfStoragePermissions {
114+ handleSharedText(intent)
115+ finish()
116+ }
117+ LaunchType .SYNC -> runIfStoragePermissions { handleSyncIntent(reloadIntent, action) }
118+ LaunchType .REVIEW -> runIfStoragePermissions { handleReviewIntent(reloadIntent, intent) }
119+ LaunchType .DEFAULT_START_APP_IF_NEW -> {
120+ Timber .d(" onCreate() performing default action" )
121+ launchDeckPickerIfNoOtherTasks(reloadIntent)
122+ }
123+ LaunchType .COPY_DEBUG_INFO -> {
124+ copyDebugInfoToClipboard(intent)
125+ finish()
126+ }
107127 }
108- LaunchType .SYNC -> runIfStoragePermissions { handleSyncIntent(reloadIntent, action) }
109- LaunchType .REVIEW -> runIfStoragePermissions { handleReviewIntent(reloadIntent, intent) }
110- LaunchType .DEFAULT_START_APP_IF_NEW -> {
111- Timber .d(" onCreate() performing default action" )
112- launchDeckPickerIfNoOtherTasks(reloadIntent)
113- }
114- LaunchType .COPY_DEBUG_INFO -> {
115- copyDebugInfoToClipboard(intent)
116- finish()
128+ }, delay)
129+ }
130+
131+ if (Build .VERSION .SDK_INT >= Build .VERSION_CODES .S ) {
132+ splashScreen.setOnExitAnimationListener { splashScreenView ->
133+ val animationDuration = splashScreenView.iconAnimationDuration
134+ val animationStart = splashScreenView.iconAnimationStart
135+
136+ Timber .v(" duration: ${animationDuration?.toMillis()} start: $animationStart " )
137+ val remainingDuration =
138+ if (animationDuration != null && animationStart != null ) {
139+ (animationDuration - Duration .between(animationStart, Instant .now())).toMillis().coerceAtLeast(0L )
140+ } else {
141+ 0L
142+ }
143+ Timber .v(" remainDuration: $remainingDuration " )
144+ handleScreen(remainingDuration)
117145 }
146+ super .onCreate(savedInstanceState)
147+ } else {
148+ super .onCreate(savedInstanceState)
149+ handleScreen(0L ) // No delay for older Android versions
118150 }
119151 }
120152
0 commit comments