Android-onCreate中的finish()行为不一致
我想创建一个Android应用程序,它能够设置计时器,并处理隐式意图。这也将允许它对谷歌助手的“设置计时器”命令做出反应 收到此特殊目的后,我希望应用程序在不显示活动的情况下设置计时器(以表示尊重) 如果在我使用GoogleAssistant设置计时器时应用程序没有启动,它会按预期工作:活动不会显示,但设置计时器的代码会执行 但是,如果我使用launcher启动我的活动,然后使用home按钮返回主屏幕(即,该活动仍然可以在最近找到),则该行为是错误的。显示活动时,调用Android-onCreate中的finish()行为不一致,android,kotlin,android-intent,android-lifecycle,Android,Kotlin,Android Intent,Android Lifecycle,我想创建一个Android应用程序,它能够设置计时器,并处理隐式意图。这也将允许它对谷歌助手的“设置计时器”命令做出反应 收到此特殊目的后,我希望应用程序在不显示活动的情况下设置计时器(以表示尊重) 如果在我使用GoogleAssistant设置计时器时应用程序没有启动,它会按预期工作:活动不会显示,但设置计时器的代码会执行 但是,如果我使用launcher启动我的活动,然后使用home按钮返回主屏幕(即,该活动仍然可以在最近找到),则该行为是错误的。显示活动时,调用onStart()方法(即使
onStart()
方法(即使我从onCreate
调用finish()
)
据我所知,如果我从onCreate
调用finish()
,则不应调用其他生命周期回调,并且不应显示活动
更令人困惑的是,显然onCreate
和onStart
请参见不同的意图
从AndroidManifest.xml
:
MainActivity.kt
:
class MainActivity : AppCompatActivity() {
companion object {
const val TAG = "MainActivity"
}
override fun onCreate(savedInstanceState: Bundle?) {
Log.d(TAG, "onCreate called")
super.onCreate(savedInstanceState)
logIntent()
if (intent.action == AlarmClock.ACTION_SET_TIMER) {
Log.d(TAG, "Timer intent received, closing")
// Do something useful here
setResult(Activity.RESULT_OK)
finish()
return
}
setContentView(R.layout.activity_main)
}
override fun onStart() {
Log.d(TAG,"onStart called")
super.onStart()
logIntent()
}
private fun logIntent() {
Log.d(TAG, "Intent action ${intent.action}")
Log.d(TAG, "Intent flags ${intent.flags.toString(16)}")
intent.extras?.keySet()?.forEach {
Log.d(TAG, "Intent extra $it = ${intent.extras?.get(it)}")
}
}
}
情景1
应用程序未启动,请使用谷歌助手设置计时器。
这里一切正常
情景2
应用程序由启动器启动,按下Home按钮,然后使用GoogleAssistant设置计时器。
使用launcher启动应用程序,外观与预期一致:
2020-02-02 18:24:30.052 22269-22269/com.example.testlifycycle D/MainActivity: onCreate called
2020-02-02 18:24:30.055 22269-22269/com.example.testlifycycle D/MainActivity: Intent action android.intent.action.MAIN
2020-02-02 18:24:30.055 22269-22269/com.example.testlifycycle D/MainActivity: Intent flags 10200000
2020-02-02 18:24:30.055 22269-22269/com.example.testlifycycle D/MainActivity: Intent extra profile = 0
2020-02-02 18:24:30.158 22269-22269/com.example.testlifycycle D/MainActivity: onStart called
2020-02-02 18:24:30.158 22269-22269/com.example.testlifycycle D/MainActivity: Intent action android.intent.action.MAIN
2020-02-02 18:24:30.158 22269-22269/com.example.testlifycycle D/MainActivity: Intent flags 10200000
2020-02-02 18:24:30.158 22269-22269/com.example.testlifycycle D/MainActivity: Intent extra profile = 0
按home按钮,然后使用Google助手:
2020-02-02 18:26:21.398 23158-23158/com.example.testlifycycle D/MainActivity: onCreate called
2020-02-02 18:26:21.402 23158-23158/com.example.testlifycycle D/MainActivity: Intent action android.intent.action.SET_TIMER
2020-02-02 18:26:21.402 23158-23158/com.example.testlifycycle D/MainActivity: Intent flags 10400000
2020-02-02 18:26:21.402 23158-23158/com.example.testlifycycle D/MainActivity: Intent extra android.intent.extra.alarm.SKIP_UI = true
2020-02-02 18:26:21.402 23158-23158/com.example.testlifycycle D/MainActivity: Intent extra com.google.android.apps.gsa.shared.util.starter.IntentStarter.ERROR_TOAST_ID = 2131951799
2020-02-02 18:26:21.403 23158-23158/com.example.testlifycycle D/MainActivity: Intent extra android.intent.extra.REFERRER_NAME = android-app://com.google.android.googlequicksearchbox/https/www.google.com
2020-02-02 18:26:21.403 23158-23158/com.example.testlifycycle D/MainActivity: Intent extra android.intent.extra.alarm.LENGTH = 60
2020-02-02 18:26:21.403 23158-23158/com.example.testlifycycle D/MainActivity: Intent extra KEY_HANDOVER_THROUGH_VELVET = true
2020-02-02 18:26:21.403 23158-23158/com.example.testlifycycle D/MainActivity: Timer intent received, closing
2020-02-02 18:26:21.446 23158-23158/com.example.testlifycycle D/MainActivity: onStart called
2020-02-02 18:26:21.446 23158-23158/com.example.testlifycycle D/MainActivity: Intent action android.intent.action.MAIN
2020-02-02 18:26:21.446 23158-23158/com.example.testlifycycle D/MainActivity: Intent flags 10200000
2020-02-02 18:26:21.447 23158-23158/com.example.testlifycycle D/MainActivity: Intent extra profile = 0
我在这里看到的问题是:
onCreate
调用了finsh
,也会调用onStart
onStart
使用操作MAIN
记录意图,而onCreate
记录(预期)SET\u计时器
我想我可能对Android的意图/生命周期机制缺乏了解。我将非常感谢您对此事的帮助。您正在处理两个不同的
MainActivity
实例:
- 点击启动器图标
- Android创建了一个
的实例,并对其调用了MainActivity
/onCreate()
onStart()
- 你按回家
- 你做了一些辅助动作,触发了
implicitSET\u报警
Intent
- Android在现有任务中创建第二个
实例,并将该任务置于前台MainActivity
- 用
调用onCreate()
的第二个实例,然后在那里调用该实例MainActivity
- 由于您的任务位于前台,并且该任务中还有另一个活动(第一个实例是
),因此该活动将返回前台,并对其调用MainActivity
onStart()
我不能具体地和助手说话,因为我完全回避。但是,如果希望助手启动的活动位于单独的任务中,并且不将任何现有任务带到前台,则需要在清单中为此做一些工作。我的出发点是为不同的场景设置不同的活动,然后在
SET\u ALARM
活动上使用android:taskAffinity
将其路由到单独的任务。Hi,您是否在清单中传递了类似android:launchMode
的任何标志?调用finish()时仍将调用onStart()。您的完成请求在主线程上排队,直到您的应用程序处于启动状态时才会执行。(这种行为也没有任何问题,这不是你要寻找的答案)。@Blundell这一IMO反驳了:>你可以从这个函数中调用finish(),在这种情况下,onCreate(Bundle)之后将立即调用onDestroy(),而不需要任何其他活动生命周期(onStart()、onResume()、onPause()等)执行。@Mustansir,不,我不知道t@Nu-hin看来onStart调用是最近活动的“恢复”,这就是为什么它有主标志的原因。是的,我的解释错了!这正是我所想的。使用单独的意图过滤器将其拆分为两个活动+1但如果未设置EXTRA\u SKIP\u UI
,则会发生什么情况,因此仍然需要显示该活动?这是否意味着有两个具有(几乎)相同UI的活动?@Nu-hin:您可以尝试将
用于SET\u ALARM
操作和taskAffinity
设置,尽管我从未尝试过这种组合。或者,如果需要真正的用户界面,您可以让专用的SET\u报警
活动只需启动main活动
(然后是自己的finish()
调用以摆脱自身)。或者,您可以让设置\u报警
活动成为main活动
的子类。我怀疑还有其他选项,但我想到了三个。@commonware我最终创建了一个空活动,没有布局和taskafinity
set,正如您所建议的那样。这就解决了问题,非常感谢。
2020-02-02 18:26:21.398 23158-23158/com.example.testlifycycle D/MainActivity: onCreate called
2020-02-02 18:26:21.402 23158-23158/com.example.testlifycycle D/MainActivity: Intent action android.intent.action.SET_TIMER
2020-02-02 18:26:21.402 23158-23158/com.example.testlifycycle D/MainActivity: Intent flags 10400000
2020-02-02 18:26:21.402 23158-23158/com.example.testlifycycle D/MainActivity: Intent extra android.intent.extra.alarm.SKIP_UI = true
2020-02-02 18:26:21.402 23158-23158/com.example.testlifycycle D/MainActivity: Intent extra com.google.android.apps.gsa.shared.util.starter.IntentStarter.ERROR_TOAST_ID = 2131951799
2020-02-02 18:26:21.403 23158-23158/com.example.testlifycycle D/MainActivity: Intent extra android.intent.extra.REFERRER_NAME = android-app://com.google.android.googlequicksearchbox/https/www.google.com
2020-02-02 18:26:21.403 23158-23158/com.example.testlifycycle D/MainActivity: Intent extra android.intent.extra.alarm.LENGTH = 60
2020-02-02 18:26:21.403 23158-23158/com.example.testlifycycle D/MainActivity: Intent extra KEY_HANDOVER_THROUGH_VELVET = true
2020-02-02 18:26:21.403 23158-23158/com.example.testlifycycle D/MainActivity: Timer intent received, closing
2020-02-02 18:26:21.446 23158-23158/com.example.testlifycycle D/MainActivity: onStart called
2020-02-02 18:26:21.446 23158-23158/com.example.testlifycycle D/MainActivity: Intent action android.intent.action.MAIN
2020-02-02 18:26:21.446 23158-23158/com.example.testlifycycle D/MainActivity: Intent flags 10200000
2020-02-02 18:26:21.447 23158-23158/com.example.testlifycycle D/MainActivity: Intent extra profile = 0