Browse Source

Ensure component view is not created by mergeOptions (#6102)

When mergeOptions is called before a view is created or after it's destroyed, don't attempt to create the view.

Fixes #6097
Guy Carmeli 4 years ago
parent
commit
111df5a3ba
No account linked to committer's email address

+ 1
- 1
lib/android/app/src/main/java/com/reactnativenavigation/viewcontrollers/ComponentViewController.java View File

@@ -96,7 +96,7 @@ public class ComponentViewController extends ChildController<ComponentLayout> {
96 96
     @Override
97 97
     public void mergeOptions(Options options) {
98 98
         if (options == Options.EMPTY) return;
99
-        presenter.mergeOptions(getView(), options);
99
+        if (isViewShown()) presenter.mergeOptions(getView(), options);
100 100
         super.mergeOptions(options);
101 101
     }
102 102
 

+ 1
- 1
lib/android/app/src/main/java/com/reactnativenavigation/viewcontrollers/ViewController.java View File

@@ -326,8 +326,8 @@ public abstract class ViewController<T extends ViewGroup> implements ViewTreeObs
326 326
 
327 327
     public boolean isViewShown() {
328 328
         return !isDestroyed &&
329
-               getView().isShown() &&
330 329
                view != null &&
330
+               view.isShown() &&
331 331
                isRendered();
332 332
     }
333 333
 

+ 9
- 3
lib/android/app/src/test/java/com/reactnativenavigation/viewcontrollers/ComponentViewControllerTest.java View File

@@ -21,6 +21,7 @@ import static org.mockito.ArgumentMatchers.any;
21 21
 import static org.mockito.Mockito.spy;
22 22
 import static org.mockito.Mockito.times;
23 23
 import static org.mockito.Mockito.verify;
24
+import static org.mockito.Mockito.verifyZeroInteractions;
24 25
 import static org.mockito.Mockito.when;
25 26
 
26 27
 public class ComponentViewControllerTest extends BaseTest {
@@ -40,12 +41,12 @@ public class ComponentViewControllerTest extends BaseTest {
40 41
         parent = TestUtils.newStackController(activity).build();
41 42
         Presenter presenter = new Presenter(activity, new Options());
42 43
         this.presenter = spy(new ComponentPresenter(Options.EMPTY));
43
-        uut = new ComponentViewController(activity, new ChildControllersRegistry(), "componentId1", "componentName", (activity1, componentId, componentName) -> view, new Options(), presenter, this.presenter) {
44
+        uut = spy(new ComponentViewController(activity, new ChildControllersRegistry(), "componentId1", "componentName", (activity1, componentId, componentName) -> view, new Options(), presenter, this.presenter) {
44 45
             @Override
45 46
             public Options resolveCurrentOptions(Options defaultOptions) {
46 47
                 return resolvedOptions;
47 48
             }
48
-        };
49
+        });
49 50
         uut.setParentController(parent);
50 51
         parent.ensureViewIsCreated();
51 52
     }
@@ -117,8 +118,13 @@ public class ComponentViewControllerTest extends BaseTest {
117 118
     }
118 119
 
119 120
     @Test
120
-    public void mergeOptions_delegatesToPresenter() {
121
+    public void mergeOptions_delegatesToPresenterIfViewIsNotShown() {
121 122
         Options options = new Options();
123
+        assertThat(uut.isViewShown()).isFalse();
124
+        uut.mergeOptions(options);
125
+        verifyZeroInteractions(presenter);
126
+
127
+        when(uut.isViewShown()).thenReturn(true);
122 128
         uut.mergeOptions(options);
123 129
         verify(presenter).mergeOptions(uut.getView(), options);
124 130
     }

+ 8
- 1
lib/android/app/src/test/java/com/reactnativenavigation/viewcontrollers/ViewControllerTest.java View File

@@ -1,7 +1,6 @@
1 1
 package com.reactnativenavigation.viewcontrollers;
2 2
 
3 3
 import android.app.Activity;
4
-import androidx.coordinatorlayout.widget.CoordinatorLayout;
5 4
 import android.view.View;
6 5
 import android.view.ViewGroup;
7 6
 import android.view.ViewParent;
@@ -27,6 +26,8 @@ import org.robolectric.Shadows;
27 26
 
28 27
 import java.lang.reflect.Field;
29 28
 
29
+import androidx.coordinatorlayout.widget.CoordinatorLayout;
30
+
30 31
 import static org.assertj.core.api.Java6Assertions.assertThat;
31 32
 import static org.mockito.Mockito.mock;
32 33
 import static org.mockito.Mockito.spy;
@@ -183,6 +184,12 @@ public class ViewControllerTest extends BaseTest {
183 184
         verify(spy, times(1)).onViewAppeared();
184 185
     }
185 186
 
187
+    @Test
188
+    public void isViewShown_doesNotCreateView() {
189
+        assertThat(uut.isViewShown()).isFalse();
190
+        assertThat(uut.view).isNull();
191
+    }
192
+
186 193
     @Test
187 194
     public void onDisappear_WhenNotShown_AfterOnAppearWasCalled() {
188 195
         ViewController spy = spy(uut);