Using rc version and @nativescript/core i am facing an issue with modal views.
To counter that isssue https://github.com/NativeScript/NativeScript/issues/7744 i need to wrap my modal views inside a Frame
Something like this
<Frame>
<Page actionBarHidden ref="page">
<StackLayout class="page" height="100%">
</StackLayout>
</Page>
</Frame>
But now it crashes on Android when closing the modal with this error:
System.err: Error: java.lang.IllegalStateException: Cannot remove Fragment attached to a different FragmentManager. Fragment fragment2[2]<Page(65)> is already attached to a FragmentManager.
System.err:
System.err: StackTrace:
System.err: Frame.disposeCurrentFragment(file:///data/data/com.microoled.activelook.mobile/files/app/vendor.js:27493:17)
System.err: at Frame.onUnloaded(file:///data/data/com.microoled.activelook.mobile/files/app/vendor.js:27475:10)
System.err: at (file:///data/data/com.microoled.activelook.mobile/files/app/vendor.js:20445:20)
System.err: at ViewBase.callFunctionWithSuper(file:///data/data/com.microoled.activelook.mobile/files/app/vendor.js:20426:5)
System.err: at ViewBase.callUnloaded(file:///data/data/com.microoled.activelook.mobile/files/app/vendor.js:20444:10)
System.err: at DialogFragmentImpl.onDismiss(file:///data/data/com.microoled.activelook.mobile/files/app/vendor.js:22626:15)
System.err: at com.tns.Runtime.callJSMethodNative(Native Method)
I think the issue comes indeed from the fact that the manager used to opened the modal window
https://github.com/NativeScript/NativeScript/blob/cc97a1680009f1bf6dbf97c421f6e8dc535295b5/nativescript-core/ui/core/view/view.android.ts#L657
is not the same as the one used in disposeCurrentFragment
https://github.com/NativeScript/NativeScript/blob/cc97a1680009f1bf6dbf97c421f6e8dc535295b5/nativescript-core/ui/frame/frame.android.ts#L260
which gets the FragmentManager here
https://github.com/NativeScript/NativeScript/blob/cc97a1680009f1bf6dbf97c421f6e8dc535295b5/nativescript-core/ui/core/view/view.android.ts#L339
Actually found the reason for the bug and it is not what i thought.
The issue is with Frame
calling super.onUnloaded
before disposeCurrentFragment
https://github.com/NativeScript/NativeScript/blob/cc97a1680009f1bf6dbf97c421f6e8dc535295b5/nativescript-core/ui/frame/frame.android.ts#L250
Doing so _manager
is set to null but then after in disposeCurrentFragment
, a call to this._getFragmentManager
is made. At that point there is _manager
anymore and so the root manager is returned.
Inversing the order in Frame.onUnloaded
solves the issue.
Any workarounds for this?
It's crashing on Android when I have my Modal open and then click on the OS back button.
My Modal content is wrapped inside a Frame as well.
@JuanDeLeon i keep on modyfing the node modules files for now :s
Well I can confirm your solution seems to be working fine for me as well.
Edit: It is now causing an issue when picking an image using the nativescript-image-picker plugin... so I guess I should remove the Frame and redesign my Modals slightly.
The workaround seems to be working for our issue as well! We however have a different stacktrace which happens while closing a modal (NS6.2):
JS: ERROR Error: Uncaught (in promise): Error: java.lang.NullPointerException: Attempt to invoke virtual method 'void android.util.SparseArray.put(int, java.lang.Object)' on a null object reference
JS: push.../node_modules/@nativescript/core/ui/frame/frame.js.Frame.disposeCurrentFragment(file:///node_modules/@nativescript/core/ui/frame/frame.js:198:0)
JS: at push.../node_modules/@nativescript/core/ui/frame/frame.js.Frame.onUnloaded(file:///node_modules/@nativescript/core/ui/frame/frame.js:182:0)
JS: at (file:///node_modules/@nativescript/core/ui/core/view-base/view-base.js:316:77)
JS: at push.../node_modules/@nativescript/core/ui/core/view-base/view-base.js.ViewBase.callFunctionWithSuper(file:///node_modules/@nativescript/core/ui/core/view-base/view-base.js:305:0)
JS: at push.../node_modules/@nativescript/core/ui/core/view-base/view-base.js.ViewBase.callUnloaded(file:///node_modules/@nativescript/core/ui/core/view-base/view-base.js:316:0)
JS: at push.../node_modules/@nativescript/core/ui/core/view-base/view-base.js.Vi...
I'm currently trying to investigate this issue in order to validate that the proposed solution does not break any other scenarios.
@farfromrefug and @bartsg can provide a repro project of the issue? I have tried (unsuccessfully) to reproduce the issue here: https://github.com/vakrilov/fragment-manager-crash. I had to separate the page and the frame into separate files as having the following xml:
<Frame>
<Page>
<StackLayout class="page" height="100%">
</StackLayout>
</Page>
</Frame>
is throwing Frame should not have a view. Use 'defaultPage' property instead.
error
Feel free to try to reproduce in the repo above, so that we can further investigate.
@farfromrefug inverting the order as in calling this.disposeCurrentFragment();
then super.onUnloaded()
?
@nikoTM yes
@farfromrefug did you notice any side effects with this move?
Most helpful comment
Actually found the reason for the bug and it is not what i thought.
The issue is with
Frame
callingsuper.onUnloaded
beforedisposeCurrentFragment
https://github.com/NativeScript/NativeScript/blob/cc97a1680009f1bf6dbf97c421f6e8dc535295b5/nativescript-core/ui/frame/frame.android.ts#L250Doing so
_manager
is set to null but then after indisposeCurrentFragment
, a call tothis._getFragmentManager
is made. At that point there is_manager
anymore and so the root manager is returned.Inversing the order in
Frame.onUnloaded
solves the issue.