1 package org.robolectric.shadows; 2 3 import static com.google.common.truth.Truth.assertThat; 4 import static org.junit.Assert.assertEquals; 5 import static org.junit.Assert.assertNotNull; 6 import static org.junit.Assert.assertNull; 7 import static org.junit.Assert.assertSame; 8 import static org.junit.Assert.assertTrue; 9 import static org.robolectric.Shadows.shadowOf; 10 import static org.robolectric.shadows.ShadowLooper.shadowMainLooper; 11 12 import android.app.Application; 13 import android.app.Dialog; 14 import android.content.Context; 15 import android.content.DialogInterface; 16 import android.os.Bundle; 17 import android.view.View; 18 import android.widget.TextView; 19 import androidx.test.core.app.ApplicationProvider; 20 import androidx.test.ext.junit.runners.AndroidJUnit4; 21 import java.util.ArrayList; 22 import java.util.List; 23 import org.junit.Before; 24 import org.junit.Test; 25 import org.junit.runner.RunWith; 26 import org.robolectric.R; 27 28 @RunWith(AndroidJUnit4.class) 29 public class ShadowDialogTest { 30 31 private Application context; 32 33 @Before setUp()34 public void setUp() throws Exception { 35 context = ApplicationProvider.getApplicationContext(); 36 } 37 38 @Test shouldCallOnDismissListener()39 public void shouldCallOnDismissListener() { 40 final List<String> transcript = new ArrayList<>(); 41 42 final Dialog dialog = new Dialog(context); 43 dialog.show(); 44 dialog.setOnDismissListener( 45 dialogInListener -> { 46 assertThat(dialogInListener).isSameInstanceAs(dialog); 47 transcript.add("onDismiss called!"); 48 }); 49 50 dialog.dismiss(); 51 shadowMainLooper().idle(); 52 53 assertThat(transcript).containsExactly("onDismiss called!"); 54 } 55 56 @Test setContentViewWithViewAllowsFindById()57 public void setContentViewWithViewAllowsFindById() { 58 final int viewId = 1234; 59 final Dialog dialog = new Dialog(context); 60 final View view = new View(context); 61 view.setId(viewId); 62 dialog.setContentView(view); 63 64 assertSame(view, dialog.findViewById(viewId)); 65 } 66 67 @Test shouldGetLayoutInflater()68 public void shouldGetLayoutInflater() { 69 Dialog dialog = new Dialog(context); 70 assertNotNull(dialog.getLayoutInflater()); 71 } 72 73 @Test shouldCallOnStartFromShow()74 public void shouldCallOnStartFromShow() { 75 TestDialog dialog = new TestDialog(context); 76 dialog.show(); 77 78 assertTrue(dialog.onStartCalled); 79 } 80 81 @Test shouldSetCancelable()82 public void shouldSetCancelable() { 83 Dialog dialog = new Dialog(context); 84 ShadowDialog shadow = shadowOf(dialog); 85 86 dialog.setCancelable(false); 87 assertThat(shadow.isCancelable()).isFalse(); 88 } 89 90 @Test shouldDismissTheRealDialogWhenCancelled()91 public void shouldDismissTheRealDialogWhenCancelled() { 92 TestDialog dialog = new TestDialog(context); 93 dialog.cancel(); 94 assertThat(dialog.wasDismissed).isTrue(); 95 } 96 97 @Test shouldDefaultCancelableToTrueAsTheSDKDoes()98 public void shouldDefaultCancelableToTrueAsTheSDKDoes() { 99 Dialog dialog = new Dialog(context); 100 ShadowDialog shadow = shadowOf(dialog); 101 102 assertThat(shadow.isCancelable()).isTrue(); 103 } 104 105 @Test shouldOnlyCallOnCreateOnce()106 public void shouldOnlyCallOnCreateOnce() { 107 final List<String> transcript = new ArrayList<>(); 108 109 Dialog dialog = 110 new Dialog(context) { 111 @Override 112 protected void onCreate(Bundle savedInstanceState) { 113 super.onCreate(savedInstanceState); 114 transcript.add("onCreate called"); 115 } 116 }; 117 118 dialog.show(); 119 assertThat(transcript).containsExactly("onCreate called"); 120 transcript.clear(); 121 122 dialog.dismiss(); 123 dialog.show(); 124 assertThat(transcript).isEmpty(); 125 } 126 127 @Test show_setsLatestDialog()128 public void show_setsLatestDialog() { 129 Dialog dialog = new Dialog(context); 130 assertNull(ShadowDialog.getLatestDialog()); 131 132 dialog.show(); 133 134 assertSame(dialog, ShadowDialog.getLatestDialog()); 135 assertNull(ShadowAlertDialog.getLatestAlertDialog()); 136 } 137 138 @Test getLatestDialog_shouldReturnARealDialog()139 public void getLatestDialog_shouldReturnARealDialog() { 140 assertThat(ShadowDialog.getLatestDialog()).isNull(); 141 142 Dialog dialog = new Dialog(context); 143 dialog.show(); 144 assertThat(ShadowDialog.getLatestDialog()).isSameInstanceAs(dialog); 145 } 146 147 @Test shouldKeepListOfOpenedDialogs()148 public void shouldKeepListOfOpenedDialogs() { 149 assertEquals(0, ShadowDialog.getShownDialogs().size()); 150 151 TestDialog dialog = new TestDialog(context); 152 dialog.show(); 153 154 assertEquals(1, ShadowDialog.getShownDialogs().size()); 155 assertEquals(dialog, ShadowDialog.getShownDialogs().get(0)); 156 157 TestDialog dialog2 = new TestDialog(context); 158 dialog2.show(); 159 160 assertEquals(2, ShadowDialog.getShownDialogs().size()); 161 assertEquals(dialog2, ShadowDialog.getShownDialogs().get(1)); 162 163 dialog.dismiss(); 164 165 assertEquals(2, ShadowDialog.getShownDialogs().size()); 166 167 ShadowDialog.reset(); 168 169 assertEquals(0, ShadowDialog.getShownDialogs().size()); 170 } 171 172 @Test shouldPopulateListOfRecentDialogsInCorrectOrder()173 public void shouldPopulateListOfRecentDialogsInCorrectOrder() { 174 new NestingTestDialog().show(); 175 176 assertEquals(TestDialog.class, ShadowDialog.getLatestDialog().getClass()); 177 } 178 179 @Test shouldFindViewsWithinAContentViewThatWasPreviouslySet()180 public void shouldFindViewsWithinAContentViewThatWasPreviouslySet() { 181 Dialog dialog = new Dialog(context); 182 dialog.setContentView(dialog.getLayoutInflater().inflate(R.layout.main, null)); 183 assertThat(dialog.<TextView>findViewById(R.id.title)).isInstanceOf(TextView.class); 184 } 185 186 @Test show_shouldWorkWithAPI19()187 public void show_shouldWorkWithAPI19() { 188 Dialog dialog = new Dialog(context); 189 dialog.show(); 190 } 191 192 @Test canSetAndGetOnCancelListener()193 public void canSetAndGetOnCancelListener() { 194 Dialog dialog = new Dialog(context); 195 DialogInterface.OnCancelListener onCancelListener = dialog1 -> {}; 196 dialog.setOnCancelListener(onCancelListener); 197 assertThat(onCancelListener).isSameInstanceAs(shadowOf(dialog).getOnCancelListener()); 198 } 199 200 private static class TestDialog extends Dialog { 201 boolean onStartCalled = false; 202 boolean wasDismissed = false; 203 TestDialog(Context context)204 public TestDialog(Context context) { 205 super(context); 206 } 207 208 @Override onStart()209 protected void onStart() { 210 onStartCalled = true; 211 } 212 213 @Override dismiss()214 public void dismiss() { 215 super.dismiss(); 216 wasDismissed = true; 217 } 218 } 219 220 private static class NestingTestDialog extends Dialog { NestingTestDialog()221 public NestingTestDialog() { 222 super(ApplicationProvider.getApplicationContext()); 223 } 224 225 @Override onCreate(Bundle savedInstanceState)226 protected void onCreate(Bundle savedInstanceState) { 227 super.onCreate(savedInstanceState); 228 new TestDialog(getContext()).show(); 229 } 230 } 231 } 232