Fixed
Status Update
Comments
il...@google.com <il...@google.com>
jb...@google.com <jb...@google.com>
ap...@google.com <ap...@google.com> #2
Thank you for reporting this issue. For us to further investigate this issue, please provide the following additional information:
Android build
Which Android build are you using? (e.g. OPP1.170223.012)
Device used
Which device did you use to reproduce this issue?
Steps to reproduce
What steps are needed to reproduce this issue?
Please provide sample project or apk to reproduce the issue. Also mention the steps to be followed for reproducing the issue with the given sample project or apk.
Android bug report capturing
After reproducing the issue, press the volume up, volume down, and power button simultaneously. This will capture a bug report on your device in the “bug reports” directory. Attach the bug report file to this issue.
Alternate method
After reproducing the issue, navigate to “developer settings”, ensure “USB debugging” is enabled, then enable “Bug report shortcut”. Capture bug report by holding the power button and selecting the “Take bug report” option.
Screen capture of the issue
Press the volume down and power buttons simultaneously. The image will appear in your gallery. Attach the screenshot file to this issue.
NOTE : To avoid leaking private information, please share screenshots and bugreports only in Google Drive. Share files with android-bugreport@google.com and include only Google drive links in your bug. Bug report attachments should not be included directly in issue reports.
Android build
Which Android build are you using? (e.g. OPP1.170223.012)
Device used
Which device did you use to reproduce this issue?
Steps to reproduce
What steps are needed to reproduce this issue?
Please provide sample project or apk to reproduce the issue. Also mention the steps to be followed for reproducing the issue with the given sample project or apk.
Android bug report capturing
After reproducing the issue, press the volume up, volume down, and power button simultaneously. This will capture a bug report on your device in the “bug reports” directory. Attach the bug report file to this issue.
Alternate method
After reproducing the issue, navigate to “developer settings”, ensure “USB debugging” is enabled, then enable “Bug report shortcut”. Capture bug report by holding the power button and selecting the “Take bug report” option.
Screen capture of the issue
Press the volume down and power buttons simultaneously. The image will appear in your gallery. Attach the screenshot file to this issue.
NOTE : To avoid leaking private information, please share screenshots and bugreports only in Google Drive. Share files with android-bugreport@google.com and include only Google drive links in your bug. Bug report attachments should not be included directly in issue reports.
Description
Version used: androidx.fragment:fragment-ktx:1.3.0-alpha02
Devices/Android versions reproduced on: Emulator API level 29
When using the Activity Result API in a fragment, it crashes when receiving a result form an activity in a different configuration than when it was launched. The steps are like this:
1. Launch first activity.
2. Call second activity for result
3. Reorient the device/emulator
4. Finish the second activity (back button)
5. Crash with this stack:
```
2020-03-22 08:55:07.407 6338-6338/my.testapp E/AndroidRuntime: FATAL EXCEPTION: main
Process: my.testapp, PID: 6338
java.lang.RuntimeException: Unable to resume activity {my.testapp/my.testapp.activity.main.MainActivity}: java.lang.RuntimeException: Failure delivering result ResultInfo{who=null, request=0, result=0, data=null} to activity {my.testapp/my.testapp.activity.main.MainActivity}: java.lang.NullPointerException: Attempt to read from field 'androidx.activity.result.ActivityResultCallback androidx.activity.result.ActivityResultRegistry$CallbackAndContract.mCallback' on a null object reference
at android.app.ActivityThread.performResumeActivity(ActivityThread.java:4205)
at android.app.ActivityThread.handleResumeActivity(ActivityThread.java:4237)
at android.app.servertransaction.ResumeActivityItem.execute(ResumeActivityItem.java:52)
at android.app.servertransaction.TransactionExecutor.executeLifecycleState(TransactionExecutor.java:176)
at android.app.servertransaction.TransactionExecutor.execute(TransactionExecutor.java:97)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:2016)
at android.os.Handler.dispatchMessage(Handler.java:107)
at android.os.Looper.loop(Looper.java:214)
at android.app.ActivityThread.main(ActivityThread.java:7356)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:492)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:930)
Caused by: java.lang.RuntimeException: Failure delivering result ResultInfo{who=null, request=0, result=0, data=null} to activity {my.testapp/my.testapp.activity.main.MainActivity}: java.lang.NullPointerException: Attempt to read from field 'androidx.activity.result.ActivityResultCallback androidx.activity.result.ActivityResultRegistry$CallbackAndContract.mCallback' on a null object reference
at android.app.ActivityThread.deliverResults(ActivityThread.java:4845)
at android.app.ActivityThread.performResumeActivity(ActivityThread.java:4192)
at android.app.ActivityThread.handleResumeActivity(ActivityThread.java:4237)
at android.app.servertransaction.ResumeActivityItem.execute(ResumeActivityItem.java:52)
at android.app.servertransaction.TransactionExecutor.executeLifecycleState(TransactionExecutor.java:176)
at android.app.servertransaction.TransactionExecutor.execute(TransactionExecutor.java:97)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:2016)
at android.os.Handler.dispatchMessage(Handler.java:107)
at android.os.Looper.loop(Looper.java:214)
at android.app.ActivityThread.main(ActivityThread.java:7356)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:492)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:930)
Caused by: java.lang.NullPointerException: Attempt to read from field 'androidx.activity.result.ActivityResultCallback androidx.activity.result.ActivityResultRegistry$CallbackAndContract.mCallback' on a null object reference
at androidx.activity.result.ActivityResultRegistry.doDispatch(ActivityResultRegistry.java:281)
at androidx.activity.result.ActivityResultRegistry.dispatchResult(ActivityResultRegistry.java:275)
at androidx.activity.ComponentActivity.onActivityResult(ComponentActivity.java:444)
at androidx.fragment.app.FragmentActivity.onActivityResult(FragmentActivity.java:181)
at android.app.Activity.dispatchActivityResult(Activity.java:8110)
at android.app.ActivityThread.deliverResults(ActivityThread.java:4838)
at android.app.ActivityThread.performResumeActivity(ActivityThread.java:4192)
at android.app.ActivityThread.handleResumeActivity(ActivityThread.java:4237)
at android.app.servertransaction.ResumeActivityItem.execute(ResumeActivityItem.java:52)
at android.app.servertransaction.TransactionExecutor.executeLifecycleState(TransactionExecutor.java:176)
at android.app.servertransaction.TransactionExecutor.execute(TransactionExecutor.java:97)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:2016)
at android.os.Handler.dispatchMessage(Handler.java:107)
at android.os.Looper.loop(Looper.java:214)
at android.app.ActivityThread.main(ActivityThread.java:7356)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:492)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:930)
```
There are no problems if there was no configuration change. Also, oddly, there are no problems if there were two configuration changes (e.g. portrait -> landscape -> portrait).
Code for the fragment:
```kotlin
class MainFragment : Fragment() {
companion object {
fun newInstance() = MainFragment()
}
private val viewModel: MainViewModel by viewModels()
override fun onCreateView(
inflater: LayoutInflater,
container: ViewGroup?,
savedInstanceState: Bundle?
): View {
val binding = MainFragmentBinding.inflate(inflater, container, false)
binding.viewModel = viewModel
binding.lifecycleOwner = viewLifecycleOwner
return binding.root
}
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
super.onViewCreated(view, savedInstanceState)
observeViewModel()
}
private fun observeViewModel() {
// This is just effectively a listener on button press delivered through a BroadcastChannel
LifecycleChannelListener(viewLifecycleOwner.lifecycle, viewModel.navigateToFirebaseUi) {
onSignInButtonClicked()
}
}
private val onSignInButtonClicked = prepareCall(StartActivity()) { result ->
Log.d("@@@@", "R: $result")
}
private inner class StartActivity: ActivityResultContract<Unit, Int>() {
override fun createIntent(input: Unit?): Intent {
return Intent(requireContext(), MainActivity::class.java)
}
override fun parseResult(resultCode: Int, intent: Intent?): Int {
return 0
}
}
}
```