1 /*
2  * Copyright (C) 2008 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package android.view.cts;
18 
19 import com.android.cts.view.R;
20 import com.android.internal.view.menu.ContextMenuBuilder;
21 
22 import android.content.Context;
23 import android.content.res.ColorStateList;
24 import android.content.res.Resources;
25 import android.content.res.XmlResourceParser;
26 import android.cts.util.PollingCheck;
27 import android.graphics.Bitmap;
28 import android.graphics.Canvas;
29 import android.graphics.Color;
30 import android.graphics.ColorFilter;
31 import android.graphics.Point;
32 import android.graphics.PorterDuff;
33 import android.graphics.Rect;
34 import android.graphics.drawable.BitmapDrawable;
35 import android.graphics.drawable.ColorDrawable;
36 import android.graphics.drawable.Drawable;
37 import android.graphics.drawable.StateListDrawable;
38 import android.os.Bundle;
39 import android.os.Parcelable;
40 import android.os.SystemClock;
41 import android.os.Vibrator;
42 import android.test.ActivityInstrumentationTestCase2;
43 import android.test.TouchUtils;
44 import android.test.UiThreadTest;
45 import android.text.format.DateUtils;
46 import android.util.AttributeSet;
47 import android.util.Log;
48 import android.util.SparseArray;
49 import android.util.Xml;
50 import android.view.ActionMode;
51 import android.view.ContextMenu;
52 import android.view.ContextMenu.ContextMenuInfo;
53 import android.view.Display;
54 import android.view.HapticFeedbackConstants;
55 import android.view.InputDevice;
56 import android.view.KeyEvent;
57 import android.view.Menu;
58 import android.view.MenuInflater;
59 import android.view.MotionEvent;
60 import android.view.SoundEffectConstants;
61 import android.view.TouchDelegate;
62 import android.view.View;
63 import android.view.View.BaseSavedState;
64 import android.view.View.OnClickListener;
65 import android.view.View.OnContextClickListener;
66 import android.view.View.OnCreateContextMenuListener;
67 import android.view.View.OnFocusChangeListener;
68 import android.view.View.OnKeyListener;
69 import android.view.View.OnLongClickListener;
70 import android.view.View.OnTouchListener;
71 import android.view.ViewConfiguration;
72 import android.view.ViewGroup;
73 import android.view.ViewParent;
74 import android.view.WindowManager;
75 import android.view.accessibility.AccessibilityEvent;
76 import android.view.animation.AlphaAnimation;
77 import android.view.animation.Animation;
78 import android.view.inputmethod.EditorInfo;
79 import android.view.inputmethod.InputConnection;
80 import android.view.inputmethod.InputMethodManager;
81 import android.widget.ArrayAdapter;
82 import android.widget.Button;
83 import android.widget.EditText;
84 import android.widget.LinearLayout;
85 import android.widget.ListView;
86 
87 import java.util.ArrayList;
88 import java.util.Arrays;
89 import java.util.List;
90 
91 /**
92  * Test {@link View}.
93  */
94 public class ViewTest extends ActivityInstrumentationTestCase2<ViewTestCtsActivity> {
ViewTest()95     public ViewTest() {
96         super(ViewTestCtsActivity.class);
97     }
98 
99     private Resources mResources;
100     private MockViewParent mMockParent;
101     private ViewTestCtsActivity mActivity;
102 
103     /** timeout delta when wait in case the system is sluggish */
104     private static final long TIMEOUT_DELTA = 10000;
105 
106     private static final String LOG_TAG = "ViewTest";
107 
108     @Override
setUp()109     protected void setUp() throws Exception {
110         super.setUp();
111         mActivity = getActivity();
112         new PollingCheck() {
113             @Override
114                 protected boolean check() {
115                 return mActivity.hasWindowFocus();
116             }
117         }.run();
118         mResources = mActivity.getResources();
119         mMockParent = new MockViewParent(mActivity);
120         assertTrue(mActivity.waitForWindowFocus(5 * DateUtils.SECOND_IN_MILLIS));
121     }
122 
testConstructor()123     public void testConstructor() {
124         new View(mActivity);
125 
126         final XmlResourceParser parser = mResources.getLayout(R.layout.view_layout);
127         final AttributeSet attrs = Xml.asAttributeSet(parser);
128         new View(mActivity, attrs);
129 
130         new View(mActivity, null);
131 
132         try {
133             new View(null, attrs);
134             fail("should throw NullPointerException");
135         } catch (NullPointerException e) {
136         }
137 
138         new View(mActivity, attrs, 0);
139 
140         new View(mActivity, null, 1);
141 
142         try {
143             new View(null, null, 1);
144             fail("should throw NullPointerException");
145         } catch (NullPointerException e) {
146         }
147     }
148 
testGetContext()149     public void testGetContext() {
150         View view = new View(mActivity);
151         assertSame(mActivity, view.getContext());
152     }
153 
testGetResources()154     public void testGetResources() {
155         View view = new View(mActivity);
156         assertSame(mResources, view.getResources());
157     }
158 
testGetAnimation()159     public void testGetAnimation() {
160         Animation animation = new AlphaAnimation(0.0f, 1.0f);
161         View view = new View(mActivity);
162         assertNull(view.getAnimation());
163 
164         view.setAnimation(animation);
165         assertSame(animation, view.getAnimation());
166 
167         view.clearAnimation();
168         assertNull(view.getAnimation());
169     }
170 
testSetAnimation()171     public void testSetAnimation() {
172         Animation animation = new AlphaAnimation(0.0f, 1.0f);
173         View view = new View(mActivity);
174         assertNull(view.getAnimation());
175 
176         animation.initialize(100, 100, 100, 100);
177         assertTrue(animation.isInitialized());
178         view.setAnimation(animation);
179         assertSame(animation, view.getAnimation());
180         assertFalse(animation.isInitialized());
181 
182         view.setAnimation(null);
183         assertNull(view.getAnimation());
184     }
185 
testClearAnimation()186     public void testClearAnimation() {
187         Animation animation = new AlphaAnimation(0.0f, 1.0f);
188         View view = new View(mActivity);
189 
190         assertNull(view.getAnimation());
191         view.clearAnimation();
192         assertNull(view.getAnimation());
193 
194         view.setAnimation(animation);
195         assertNotNull(view.getAnimation());
196         view.clearAnimation();
197         assertNull(view.getAnimation());
198     }
199 
testStartAnimation()200     public void testStartAnimation() {
201         Animation animation = new AlphaAnimation(0.0f, 1.0f);
202         View view = new View(mActivity);
203 
204         try {
205             view.startAnimation(null);
206             fail("should throw NullPointerException");
207         } catch (NullPointerException e) {
208         }
209 
210         animation.setStartTime(1L);
211         assertEquals(1L, animation.getStartTime());
212         view.startAnimation(animation);
213         assertEquals(Animation.START_ON_FIRST_FRAME, animation.getStartTime());
214     }
215 
testOnAnimation()216     public void testOnAnimation() throws Throwable {
217         final Animation animation = new AlphaAnimation(0.0f, 1.0f);
218         long duration = 2000L;
219         animation.setDuration(duration);
220         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
221 
222         // check whether it has started
223         runTestOnUiThread(new Runnable() {
224             public void run() {
225                 view.startAnimation(animation);
226             }
227         });
228         getInstrumentation().waitForIdleSync();
229 
230         new PollingCheck() {
231             @Override
232             protected boolean check() {
233                 return view.hasCalledOnAnimationStart();
234             }
235         }.run();
236 
237         // check whether it has ended after duration, and alpha changed during this time.
238         new PollingCheck(duration + TIMEOUT_DELTA) {
239             @Override
240             protected boolean check() {
241                 return view.hasCalledOnSetAlpha() && view.hasCalledOnAnimationEnd();
242             }
243         }.run();
244     }
245 
testGetParent()246     public void testGetParent() {
247         MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
248         ViewGroup parent = (ViewGroup) mActivity.findViewById(R.id.viewlayout_root);
249         assertSame(parent, view.getParent());
250     }
251 
testAccessScrollIndicators()252     public void testAccessScrollIndicators() {
253         View view = mActivity.findViewById(R.id.viewlayout_root);
254 
255         assertEquals(View.SCROLL_INDICATOR_LEFT | View.SCROLL_INDICATOR_RIGHT,
256                 view.getScrollIndicators());
257     }
258 
testSetScrollIndicators()259     public void testSetScrollIndicators() {
260         View view = new View(mActivity);
261 
262         view.setScrollIndicators(0);
263         assertEquals(0, view.getScrollIndicators());
264 
265         view.setScrollIndicators(View.SCROLL_INDICATOR_LEFT | View.SCROLL_INDICATOR_RIGHT);
266         assertEquals(View.SCROLL_INDICATOR_LEFT | View.SCROLL_INDICATOR_RIGHT,
267                 view.getScrollIndicators());
268 
269         view.setScrollIndicators(View.SCROLL_INDICATOR_TOP, View.SCROLL_INDICATOR_TOP);
270         assertEquals(View.SCROLL_INDICATOR_LEFT | View.SCROLL_INDICATOR_RIGHT
271                         | View.SCROLL_INDICATOR_TOP, view.getScrollIndicators());
272 
273         view.setScrollIndicators(0, view.getScrollIndicators());
274         assertEquals(0, view.getScrollIndicators());
275     }
276 
testFindViewById()277     public void testFindViewById() {
278         View parent = mActivity.findViewById(R.id.viewlayout_root);
279         assertSame(parent, parent.findViewById(R.id.viewlayout_root));
280 
281         View view = parent.findViewById(R.id.mock_view);
282         assertTrue(view instanceof MockView);
283     }
284 
testAccessTouchDelegate()285     public void testAccessTouchDelegate() throws Throwable {
286         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
287         Rect rect = new Rect();
288         final Button button = new Button(mActivity);
289         final int WRAP_CONTENT = ViewGroup.LayoutParams.WRAP_CONTENT;
290         final int btnHeight = view.getHeight()/3;
291         runTestOnUiThread(new Runnable() {
292             public void run() {
293                 mActivity.addContentView(button,
294                         new LinearLayout.LayoutParams(WRAP_CONTENT, btnHeight));
295             }
296         });
297         getInstrumentation().waitForIdleSync();
298         button.getHitRect(rect);
299         MockTouchDelegate delegate = new MockTouchDelegate(rect, button);
300 
301         assertNull(view.getTouchDelegate());
302 
303         view.setTouchDelegate(delegate);
304         assertSame(delegate, view.getTouchDelegate());
305         assertFalse(delegate.hasCalledOnTouchEvent());
306         TouchUtils.clickView(this, view);
307         assertTrue(view.hasCalledOnTouchEvent());
308         assertTrue(delegate.hasCalledOnTouchEvent());
309 
310         view.setTouchDelegate(null);
311         assertNull(view.getTouchDelegate());
312     }
313 
314     @UiThreadTest
testAccessTag()315     public void testAccessTag() {
316         ViewGroup viewGroup = (ViewGroup) mActivity.findViewById(R.id.viewlayout_root);
317         MockView mockView = (MockView) mActivity.findViewById(R.id.mock_view);
318         MockView scrollView = (MockView) mActivity.findViewById(R.id.scroll_view);
319 
320         ViewData viewData = new ViewData();
321         viewData.childCount = 3;
322         viewData.tag = "linearLayout";
323         viewData.firstChild = mockView;
324         viewGroup.setTag(viewData);
325         viewGroup.setFocusable(true);
326         assertSame(viewData, viewGroup.getTag());
327 
328         final String tag = "mock";
329         assertNull(mockView.getTag());
330         mockView.setTag(tag);
331         assertEquals(tag, mockView.getTag());
332 
333         scrollView.setTag(viewGroup);
334         assertSame(viewGroup, scrollView.getTag());
335 
336         assertSame(viewGroup, viewGroup.findViewWithTag(viewData));
337         assertSame(mockView, viewGroup.findViewWithTag(tag));
338         assertSame(scrollView, viewGroup.findViewWithTag(viewGroup));
339 
340         mockView.setTag(null);
341         assertNull(mockView.getTag());
342     }
343 
testOnSizeChanged()344     public void testOnSizeChanged() throws Throwable {
345         final ViewGroup viewGroup = (ViewGroup) mActivity.findViewById(R.id.viewlayout_root);
346         final MockView mockView = new MockView(mActivity);
347         assertEquals(-1, mockView.getOldWOnSizeChanged());
348         assertEquals(-1, mockView.getOldHOnSizeChanged());
349         runTestOnUiThread(new Runnable() {
350             public void run() {
351                 viewGroup.addView(mockView);
352             }
353         });
354         getInstrumentation().waitForIdleSync();
355         assertTrue(mockView.hasCalledOnSizeChanged());
356         assertEquals(0, mockView.getOldWOnSizeChanged());
357         assertEquals(0, mockView.getOldHOnSizeChanged());
358 
359         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
360         assertTrue(view.hasCalledOnSizeChanged());
361         view.reset();
362         assertEquals(-1, view.getOldWOnSizeChanged());
363         assertEquals(-1, view.getOldHOnSizeChanged());
364         int oldw = view.getWidth();
365         int oldh = view.getHeight();
366         final LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(200, 100);
367         runTestOnUiThread(new Runnable() {
368             public void run() {
369                 view.setLayoutParams(layoutParams);
370             }
371         });
372         getInstrumentation().waitForIdleSync();
373         assertTrue(view.hasCalledOnSizeChanged());
374         assertEquals(oldw, view.getOldWOnSizeChanged());
375         assertEquals(oldh, view.getOldHOnSizeChanged());
376     }
377 
testGetHitRect()378     public void testGetHitRect() {
379         MockView view = new MockView(mActivity);
380         Rect outRect = new Rect();
381 
382         try {
383             view.getHitRect(null);
384             fail("should throw NullPointerException");
385         } catch (NullPointerException e) {
386         }
387 
388         View mockView = mActivity.findViewById(R.id.mock_view);
389         mockView.getHitRect(outRect);
390         assertEquals(0, outRect.left);
391         assertEquals(0, outRect.top);
392         assertEquals(mockView.getWidth(), outRect.right);
393         assertEquals(mockView.getHeight(), outRect.bottom);
394     }
395 
testForceLayout()396     public void testForceLayout() {
397         View view = new View(mActivity);
398 
399         assertFalse(view.isLayoutRequested());
400         view.forceLayout();
401         assertTrue(view.isLayoutRequested());
402 
403         view.forceLayout();
404         assertTrue(view.isLayoutRequested());
405     }
406 
testIsLayoutRequested()407     public void testIsLayoutRequested() {
408         View view = new View(mActivity);
409 
410         assertFalse(view.isLayoutRequested());
411         view.forceLayout();
412         assertTrue(view.isLayoutRequested());
413 
414         view.layout(0, 0, 0, 0);
415         assertFalse(view.isLayoutRequested());
416     }
417 
testRequestLayout()418     public void testRequestLayout() {
419         MockView view = new MockView(mActivity);
420         assertFalse(view.isLayoutRequested());
421         assertNull(view.getParent());
422 
423         view.requestLayout();
424         assertTrue(view.isLayoutRequested());
425 
426         view.setParent(mMockParent);
427         assertTrue(mMockParent.hasRequestLayout());
428 
429         mMockParent.reset();
430         view.requestLayout();
431         assertTrue(view.isLayoutRequested());
432         assertTrue(mMockParent.hasRequestLayout());
433     }
434 
testLayout()435     public void testLayout() throws Throwable {
436         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
437         assertTrue(view.hasCalledOnLayout());
438 
439         view.reset();
440         assertFalse(view.hasCalledOnLayout());
441         runTestOnUiThread(new Runnable() {
442             public void run() {
443                 view.requestLayout();
444             }
445         });
446         getInstrumentation().waitForIdleSync();
447         assertTrue(view.hasCalledOnLayout());
448     }
449 
testGetBaseline()450     public void testGetBaseline() {
451         View view = new View(mActivity);
452 
453         assertEquals(-1, view.getBaseline());
454     }
455 
testAccessBackground()456     public void testAccessBackground() {
457         View view = new View(mActivity);
458         Drawable d1 = mResources.getDrawable(R.drawable.scenery);
459         Drawable d2 = mResources.getDrawable(R.drawable.pass);
460 
461         assertNull(view.getBackground());
462 
463         view.setBackgroundDrawable(d1);
464         assertEquals(d1, view.getBackground());
465 
466         view.setBackgroundDrawable(d2);
467         assertEquals(d2, view.getBackground());
468 
469         view.setBackgroundDrawable(null);
470         assertNull(view.getBackground());
471     }
472 
testSetBackgroundResource()473     public void testSetBackgroundResource() {
474         View view = new View(mActivity);
475 
476         assertNull(view.getBackground());
477 
478         view.setBackgroundResource(R.drawable.pass);
479         assertNotNull(view.getBackground());
480 
481         view.setBackgroundResource(0);
482         assertNull(view.getBackground());
483     }
484 
testAccessDrawingCacheBackgroundColor()485     public void testAccessDrawingCacheBackgroundColor() {
486         View view = new View(mActivity);
487 
488         assertEquals(0, view.getDrawingCacheBackgroundColor());
489 
490         view.setDrawingCacheBackgroundColor(0xFF00FF00);
491         assertEquals(0xFF00FF00, view.getDrawingCacheBackgroundColor());
492 
493         view.setDrawingCacheBackgroundColor(-1);
494         assertEquals(-1, view.getDrawingCacheBackgroundColor());
495     }
496 
testSetBackgroundColor()497     public void testSetBackgroundColor() {
498         View view = new View(mActivity);
499         ColorDrawable colorDrawable;
500         assertNull(view.getBackground());
501 
502         view.setBackgroundColor(0xFFFF0000);
503         colorDrawable = (ColorDrawable) view.getBackground();
504         assertNotNull(colorDrawable);
505         assertEquals(0xFF, colorDrawable.getAlpha());
506 
507         view.setBackgroundColor(0);
508         colorDrawable = (ColorDrawable) view.getBackground();
509         assertNotNull(colorDrawable);
510         assertEquals(0, colorDrawable.getAlpha());
511     }
512 
testVerifyDrawable()513     public void testVerifyDrawable() {
514         MockView view = new MockView(mActivity);
515         Drawable d1 = mResources.getDrawable(R.drawable.scenery);
516         Drawable d2 = mResources.getDrawable(R.drawable.pass);
517 
518         assertNull(view.getBackground());
519         assertTrue(view.verifyDrawable(null));
520         assertFalse(view.verifyDrawable(d1));
521 
522         view.setBackgroundDrawable(d1);
523         assertTrue(view.verifyDrawable(d1));
524         assertFalse(view.verifyDrawable(d2));
525     }
526 
testGetDrawingRect()527     public void testGetDrawingRect() {
528         MockView view = new MockView(mActivity);
529         Rect outRect = new Rect();
530 
531         view.getDrawingRect(outRect);
532         assertEquals(0, outRect.left);
533         assertEquals(0, outRect.top);
534         assertEquals(0, outRect.right);
535         assertEquals(0, outRect.bottom);
536 
537         view.scrollTo(10, 100);
538         view.getDrawingRect(outRect);
539         assertEquals(10, outRect.left);
540         assertEquals(100, outRect.top);
541         assertEquals(10, outRect.right);
542         assertEquals(100, outRect.bottom);
543 
544         View mockView = mActivity.findViewById(R.id.mock_view);
545         mockView.getDrawingRect(outRect);
546         assertEquals(0, outRect.left);
547         assertEquals(0, outRect.top);
548         assertEquals(mockView.getWidth(), outRect.right);
549         assertEquals(mockView.getHeight(), outRect.bottom);
550     }
551 
testGetFocusedRect()552     public void testGetFocusedRect() {
553         MockView view = new MockView(mActivity);
554         Rect outRect = new Rect();
555 
556         view.getFocusedRect(outRect);
557         assertEquals(0, outRect.left);
558         assertEquals(0, outRect.top);
559         assertEquals(0, outRect.right);
560         assertEquals(0, outRect.bottom);
561 
562         view.scrollTo(10, 100);
563         view.getFocusedRect(outRect);
564         assertEquals(10, outRect.left);
565         assertEquals(100, outRect.top);
566         assertEquals(10, outRect.right);
567         assertEquals(100, outRect.bottom);
568     }
569 
testGetGlobalVisibleRectPoint()570     public void testGetGlobalVisibleRectPoint() throws Throwable {
571         final View view = mActivity.findViewById(R.id.mock_view);
572         final ViewGroup viewGroup = (ViewGroup) mActivity.findViewById(R.id.viewlayout_root);
573         Rect rect = new Rect();
574         Point point = new Point();
575 
576         assertTrue(view.getGlobalVisibleRect(rect, point));
577         Rect rcParent = new Rect();
578         Point ptParent = new Point();
579         viewGroup.getGlobalVisibleRect(rcParent, ptParent);
580         assertEquals(rcParent.left, rect.left);
581         assertEquals(rcParent.top, rect.top);
582         assertEquals(rect.left + view.getWidth(), rect.right);
583         assertEquals(rect.top + view.getHeight(), rect.bottom);
584         assertEquals(ptParent.x, point.x);
585         assertEquals(ptParent.y, point.y);
586 
587         // width is 0
588         final LinearLayout.LayoutParams layoutParams1 = new LinearLayout.LayoutParams(0, 300);
589         runTestOnUiThread(new Runnable() {
590             public void run() {
591                 view.setLayoutParams(layoutParams1);
592             }
593         });
594         getInstrumentation().waitForIdleSync();
595         assertFalse(view.getGlobalVisibleRect(rect, point));
596 
597         // height is -10
598         final LinearLayout.LayoutParams layoutParams2 = new LinearLayout.LayoutParams(200, -10);
599         runTestOnUiThread(new Runnable() {
600             public void run() {
601                 view.setLayoutParams(layoutParams2);
602             }
603         });
604         getInstrumentation().waitForIdleSync();
605         assertFalse(view.getGlobalVisibleRect(rect, point));
606 
607         Display display = getActivity().getWindowManager().getDefaultDisplay();
608         int halfWidth = display.getWidth() / 2;
609         int halfHeight = display.getHeight() /2;
610 
611         final LinearLayout.LayoutParams layoutParams3 =
612                 new LinearLayout.LayoutParams(halfWidth, halfHeight);
613         runTestOnUiThread(new Runnable() {
614             public void run() {
615                 view.setLayoutParams(layoutParams3);
616             }
617         });
618         getInstrumentation().waitForIdleSync();
619         assertTrue(view.getGlobalVisibleRect(rect, point));
620         assertEquals(rcParent.left, rect.left);
621         assertEquals(rcParent.top, rect.top);
622         assertEquals(rect.left + halfWidth, rect.right);
623         assertEquals(rect.top + halfHeight, rect.bottom);
624         assertEquals(ptParent.x, point.x);
625         assertEquals(ptParent.y, point.y);
626     }
627 
testGetGlobalVisibleRect()628     public void testGetGlobalVisibleRect() throws Throwable {
629         final View view = mActivity.findViewById(R.id.mock_view);
630         final ViewGroup viewGroup = (ViewGroup) mActivity.findViewById(R.id.viewlayout_root);
631         Rect rect = new Rect();
632 
633         assertTrue(view.getGlobalVisibleRect(rect));
634         Rect rcParent = new Rect();
635         viewGroup.getGlobalVisibleRect(rcParent);
636         assertEquals(rcParent.left, rect.left);
637         assertEquals(rcParent.top, rect.top);
638         assertEquals(rect.left + view.getWidth(), rect.right);
639         assertEquals(rect.top + view.getHeight(), rect.bottom);
640 
641         // width is 0
642         final LinearLayout.LayoutParams layoutParams1 = new LinearLayout.LayoutParams(0, 300);
643         runTestOnUiThread(new Runnable() {
644             public void run() {
645                 view.setLayoutParams(layoutParams1);
646             }
647         });
648         getInstrumentation().waitForIdleSync();
649         assertFalse(view.getGlobalVisibleRect(rect));
650 
651         // height is -10
652         final LinearLayout.LayoutParams layoutParams2 = new LinearLayout.LayoutParams(200, -10);
653         runTestOnUiThread(new Runnable() {
654             public void run() {
655                 view.setLayoutParams(layoutParams2);
656             }
657         });
658         getInstrumentation().waitForIdleSync();
659         assertFalse(view.getGlobalVisibleRect(rect));
660 
661         Display display = getActivity().getWindowManager().getDefaultDisplay();
662         int halfWidth = display.getWidth() / 2;
663         int halfHeight = display.getHeight() /2;
664 
665         final LinearLayout.LayoutParams layoutParams3 =
666                 new LinearLayout.LayoutParams(halfWidth, halfHeight);
667         runTestOnUiThread(new Runnable() {
668             public void run() {
669                 view.setLayoutParams(layoutParams3);
670             }
671         });
672         getInstrumentation().waitForIdleSync();
673         assertTrue(view.getGlobalVisibleRect(rect));
674         assertEquals(rcParent.left, rect.left);
675         assertEquals(rcParent.top, rect.top);
676         assertEquals(rect.left + halfWidth, rect.right);
677         assertEquals(rect.top + halfHeight, rect.bottom);
678     }
679 
testComputeHorizontalScroll()680     public void testComputeHorizontalScroll() throws Throwable {
681         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
682 
683         assertEquals(0, view.computeHorizontalScrollOffset());
684         assertEquals(view.getWidth(), view.computeHorizontalScrollRange());
685         assertEquals(view.getWidth(), view.computeHorizontalScrollExtent());
686 
687         runTestOnUiThread(new Runnable() {
688             public void run() {
689                 view.scrollTo(12, 0);
690             }
691         });
692         getInstrumentation().waitForIdleSync();
693         assertEquals(12, view.computeHorizontalScrollOffset());
694         assertEquals(view.getWidth(), view.computeHorizontalScrollRange());
695         assertEquals(view.getWidth(), view.computeHorizontalScrollExtent());
696 
697         runTestOnUiThread(new Runnable() {
698             public void run() {
699                 view.scrollBy(12, 0);
700             }
701         });
702         getInstrumentation().waitForIdleSync();
703         assertEquals(24, view.computeHorizontalScrollOffset());
704         assertEquals(view.getWidth(), view.computeHorizontalScrollRange());
705         assertEquals(view.getWidth(), view.computeHorizontalScrollExtent());
706 
707         int newWidth = 200;
708         final LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(newWidth, 100);
709         runTestOnUiThread(new Runnable() {
710             public void run() {
711                 view.setLayoutParams(layoutParams);
712             }
713         });
714         getInstrumentation().waitForIdleSync();
715         assertEquals(24, view.computeHorizontalScrollOffset());
716         assertEquals(newWidth, view.getWidth());
717         assertEquals(view.getWidth(), view.computeHorizontalScrollRange());
718         assertEquals(view.getWidth(), view.computeHorizontalScrollExtent());
719     }
720 
testComputeVerticalScroll()721     public void testComputeVerticalScroll() throws Throwable {
722         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
723 
724         assertEquals(0, view.computeVerticalScrollOffset());
725         assertEquals(view.getHeight(), view.computeVerticalScrollRange());
726         assertEquals(view.getHeight(), view.computeVerticalScrollExtent());
727 
728         final int scrollToY = 34;
729         runTestOnUiThread(new Runnable() {
730             public void run() {
731                 view.scrollTo(0, scrollToY);
732             }
733         });
734         getInstrumentation().waitForIdleSync();
735         assertEquals(scrollToY, view.computeVerticalScrollOffset());
736         assertEquals(view.getHeight(), view.computeVerticalScrollRange());
737         assertEquals(view.getHeight(), view.computeVerticalScrollExtent());
738 
739         final int scrollByY = 200;
740         runTestOnUiThread(new Runnable() {
741             public void run() {
742                 view.scrollBy(0, scrollByY);
743             }
744         });
745         getInstrumentation().waitForIdleSync();
746         assertEquals(scrollToY + scrollByY, view.computeVerticalScrollOffset());
747         assertEquals(view.getHeight(), view.computeVerticalScrollRange());
748         assertEquals(view.getHeight(), view.computeVerticalScrollExtent());
749 
750         int newHeight = 333;
751         final LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(200, newHeight);
752         runTestOnUiThread(new Runnable() {
753             public void run() {
754                 view.setLayoutParams(layoutParams);
755             }
756         });
757         getInstrumentation().waitForIdleSync();
758         assertEquals(scrollToY + scrollByY, view.computeVerticalScrollOffset());
759         assertEquals(newHeight, view.getHeight());
760         assertEquals(view.getHeight(), view.computeVerticalScrollRange());
761         assertEquals(view.getHeight(), view.computeVerticalScrollExtent());
762     }
763 
testGetFadingEdgeStrength()764     public void testGetFadingEdgeStrength() throws Throwable {
765         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
766 
767         assertEquals(0f, view.getLeftFadingEdgeStrength());
768         assertEquals(0f, view.getRightFadingEdgeStrength());
769         assertEquals(0f, view.getTopFadingEdgeStrength());
770         assertEquals(0f, view.getBottomFadingEdgeStrength());
771 
772         runTestOnUiThread(new Runnable() {
773             public void run() {
774                 view.scrollTo(10, 10);
775             }
776         });
777         getInstrumentation().waitForIdleSync();
778         assertEquals(1f, view.getLeftFadingEdgeStrength());
779         assertEquals(0f, view.getRightFadingEdgeStrength());
780         assertEquals(1f, view.getTopFadingEdgeStrength());
781         assertEquals(0f, view.getBottomFadingEdgeStrength());
782 
783         runTestOnUiThread(new Runnable() {
784             public void run() {
785                 view.scrollTo(-10, -10);
786             }
787         });
788         getInstrumentation().waitForIdleSync();
789         assertEquals(0f, view.getLeftFadingEdgeStrength());
790         assertEquals(1f, view.getRightFadingEdgeStrength());
791         assertEquals(0f, view.getTopFadingEdgeStrength());
792         assertEquals(1f, view.getBottomFadingEdgeStrength());
793     }
794 
testGetLeftFadingEdgeStrength()795     public void testGetLeftFadingEdgeStrength() {
796         MockView view = new MockView(mActivity);
797 
798         assertEquals(0.0f, view.getLeftFadingEdgeStrength());
799 
800         view.scrollTo(1, 0);
801         assertEquals(1.0f, view.getLeftFadingEdgeStrength());
802     }
803 
testGetRightFadingEdgeStrength()804     public void testGetRightFadingEdgeStrength() {
805         MockView view = new MockView(mActivity);
806 
807         assertEquals(0.0f, view.getRightFadingEdgeStrength());
808 
809         view.scrollTo(-1, 0);
810         assertEquals(1.0f, view.getRightFadingEdgeStrength());
811     }
812 
testGetBottomFadingEdgeStrength()813     public void testGetBottomFadingEdgeStrength() {
814         MockView view = new MockView(mActivity);
815 
816         assertEquals(0.0f, view.getBottomFadingEdgeStrength());
817 
818         view.scrollTo(0, -2);
819         assertEquals(1.0f, view.getBottomFadingEdgeStrength());
820     }
821 
testGetTopFadingEdgeStrength()822     public void testGetTopFadingEdgeStrength() {
823         MockView view = new MockView(mActivity);
824 
825         assertEquals(0.0f, view.getTopFadingEdgeStrength());
826 
827         view.scrollTo(0, 2);
828         assertEquals(1.0f, view.getTopFadingEdgeStrength());
829     }
830 
testResolveSize()831     public void testResolveSize() {
832         assertEquals(50, View.resolveSize(50, View.MeasureSpec.UNSPECIFIED));
833 
834         assertEquals(40, View.resolveSize(50, 40 | View.MeasureSpec.EXACTLY));
835 
836         assertEquals(30, View.resolveSize(50, 30 | View.MeasureSpec.AT_MOST));
837 
838         assertEquals(20, View.resolveSize(20, 30 | View.MeasureSpec.AT_MOST));
839     }
840 
testGetDefaultSize()841     public void testGetDefaultSize() {
842         assertEquals(50, View.getDefaultSize(50, View.MeasureSpec.UNSPECIFIED));
843 
844         assertEquals(40, View.getDefaultSize(50, 40 | View.MeasureSpec.EXACTLY));
845 
846         assertEquals(30, View.getDefaultSize(50, 30 | View.MeasureSpec.AT_MOST));
847 
848         assertEquals(30, View.getDefaultSize(20, 30 | View.MeasureSpec.AT_MOST));
849     }
850 
testAccessId()851     public void testAccessId() {
852         View view = new View(mActivity);
853 
854         assertEquals(View.NO_ID, view.getId());
855 
856         view.setId(10);
857         assertEquals(10, view.getId());
858 
859         view.setId(0xFFFFFFFF);
860         assertEquals(0xFFFFFFFF, view.getId());
861     }
862 
testAccessLongClickable()863     public void testAccessLongClickable() {
864         View view = new View(mActivity);
865 
866         assertFalse(view.isLongClickable());
867 
868         view.setLongClickable(true);
869         assertTrue(view.isLongClickable());
870 
871         view.setLongClickable(false);
872         assertFalse(view.isLongClickable());
873     }
874 
testAccessClickable()875     public void testAccessClickable() {
876         View view = new View(mActivity);
877 
878         assertFalse(view.isClickable());
879 
880         view.setClickable(true);
881         assertTrue(view.isClickable());
882 
883         view.setClickable(false);
884         assertFalse(view.isClickable());
885     }
886 
testAccessContextClickable()887     public void testAccessContextClickable() {
888         View view = new View(mActivity);
889 
890         assertFalse(view.isContextClickable());
891 
892         view.setContextClickable(true);
893         assertTrue(view.isContextClickable());
894 
895         view.setContextClickable(false);
896         assertFalse(view.isContextClickable());
897     }
898 
testGetContextMenuInfo()899     public void testGetContextMenuInfo() {
900         MockView view = new MockView(mActivity);
901 
902         assertNull(view.getContextMenuInfo());
903     }
904 
testSetOnCreateContextMenuListener()905     public void testSetOnCreateContextMenuListener() {
906         View view = new View(mActivity);
907         assertFalse(view.isLongClickable());
908 
909         view.setOnCreateContextMenuListener(null);
910         assertTrue(view.isLongClickable());
911 
912         view.setOnCreateContextMenuListener(new OnCreateContextMenuListenerImpl());
913         assertTrue(view.isLongClickable());
914     }
915 
testCreateContextMenu()916     public void testCreateContextMenu() {
917         OnCreateContextMenuListenerImpl listener = new OnCreateContextMenuListenerImpl();
918         MockView view = new MockView(mActivity);
919         ContextMenu contextMenu = new ContextMenuBuilder(mActivity);
920         view.setParent(mMockParent);
921         view.setOnCreateContextMenuListener(listener);
922         assertFalse(view.hasCalledOnCreateContextMenu());
923         assertFalse(mMockParent.hasCreateContextMenu());
924         assertFalse(listener.hasOnCreateContextMenu());
925 
926         view.createContextMenu(contextMenu);
927         assertTrue(view.hasCalledOnCreateContextMenu());
928         assertTrue(mMockParent.hasCreateContextMenu());
929         assertTrue(listener.hasOnCreateContextMenu());
930 
931         try {
932             view.createContextMenu(null);
933             fail("should throw NullPointerException");
934         } catch (NullPointerException e) {
935         }
936     }
937 
testAddFocusables()938     public void testAddFocusables() {
939         View view = new View(mActivity);
940         ArrayList<View> viewList = new ArrayList<View>();
941 
942         // view is not focusable
943         assertFalse(view.isFocusable());
944         assertEquals(0, viewList.size());
945         view.addFocusables(viewList, 0);
946         assertEquals(0, viewList.size());
947 
948         // view is focusable
949         view.setFocusable(true);
950         view.addFocusables(viewList, 0);
951         assertEquals(1, viewList.size());
952         assertEquals(view, viewList.get(0));
953 
954         // null array should be ignored
955         view.addFocusables(null, 0);
956     }
957 
testGetFocusables()958     public void testGetFocusables() {
959         View view = new View(mActivity);
960         ArrayList<View> viewList;
961 
962         // view is not focusable
963         assertFalse(view.isFocusable());
964         viewList = view.getFocusables(0);
965         assertEquals(0, viewList.size());
966 
967         // view is focusable
968         view.setFocusable(true);
969         viewList = view.getFocusables(0);
970         assertEquals(1, viewList.size());
971         assertEquals(view, viewList.get(0));
972 
973         viewList = view.getFocusables(-1);
974         assertEquals(1, viewList.size());
975         assertEquals(view, viewList.get(0));
976     }
977 
testGetRootView()978     public void testGetRootView() {
979         MockView view = new MockView(mActivity);
980 
981         assertNull(view.getParent());
982         assertEquals(view, view.getRootView());
983 
984         view.setParent(mMockParent);
985         assertEquals(mMockParent, view.getRootView());
986     }
987 
testGetSolidColor()988     public void testGetSolidColor() {
989         View view = new View(mActivity);
990 
991         assertEquals(0, view.getSolidColor());
992     }
993 
testSetMinimumWidth()994     public void testSetMinimumWidth() {
995         MockView view = new MockView(mActivity);
996         assertEquals(0, view.getSuggestedMinimumWidth());
997 
998         view.setMinimumWidth(100);
999         assertEquals(100, view.getSuggestedMinimumWidth());
1000 
1001         view.setMinimumWidth(-100);
1002         assertEquals(-100, view.getSuggestedMinimumWidth());
1003     }
1004 
testGetSuggestedMinimumWidth()1005     public void testGetSuggestedMinimumWidth() {
1006         MockView view = new MockView(mActivity);
1007         Drawable d = mResources.getDrawable(R.drawable.scenery);
1008         int drawableMinimumWidth = d.getMinimumWidth();
1009 
1010         // drawable is null
1011         view.setMinimumWidth(100);
1012         assertNull(view.getBackground());
1013         assertEquals(100, view.getSuggestedMinimumWidth());
1014 
1015         // drawable minimum width is larger than mMinWidth
1016         view.setBackgroundDrawable(d);
1017         view.setMinimumWidth(drawableMinimumWidth - 10);
1018         assertEquals(drawableMinimumWidth, view.getSuggestedMinimumWidth());
1019 
1020         // drawable minimum width is smaller than mMinWidth
1021         view.setMinimumWidth(drawableMinimumWidth + 10);
1022         assertEquals(drawableMinimumWidth + 10, view.getSuggestedMinimumWidth());
1023     }
1024 
testSetMinimumHeight()1025     public void testSetMinimumHeight() {
1026         MockView view = new MockView(mActivity);
1027         assertEquals(0, view.getSuggestedMinimumHeight());
1028 
1029         view.setMinimumHeight(100);
1030         assertEquals(100, view.getSuggestedMinimumHeight());
1031 
1032         view.setMinimumHeight(-100);
1033         assertEquals(-100, view.getSuggestedMinimumHeight());
1034     }
1035 
testGetSuggestedMinimumHeight()1036     public void testGetSuggestedMinimumHeight() {
1037         MockView view = new MockView(mActivity);
1038         Drawable d = mResources.getDrawable(R.drawable.scenery);
1039         int drawableMinimumHeight = d.getMinimumHeight();
1040 
1041         // drawable is null
1042         view.setMinimumHeight(100);
1043         assertNull(view.getBackground());
1044         assertEquals(100, view.getSuggestedMinimumHeight());
1045 
1046         // drawable minimum height is larger than mMinHeight
1047         view.setBackgroundDrawable(d);
1048         view.setMinimumHeight(drawableMinimumHeight - 10);
1049         assertEquals(drawableMinimumHeight, view.getSuggestedMinimumHeight());
1050 
1051         // drawable minimum height is smaller than mMinHeight
1052         view.setMinimumHeight(drawableMinimumHeight + 10);
1053         assertEquals(drawableMinimumHeight + 10, view.getSuggestedMinimumHeight());
1054     }
1055 
testAccessWillNotCacheDrawing()1056     public void testAccessWillNotCacheDrawing() {
1057         View view = new View(mActivity);
1058 
1059         assertFalse(view.willNotCacheDrawing());
1060 
1061         view.setWillNotCacheDrawing(true);
1062         assertTrue(view.willNotCacheDrawing());
1063     }
1064 
testAccessDrawingCacheEnabled()1065     public void testAccessDrawingCacheEnabled() {
1066         View view = new View(mActivity);
1067 
1068         assertFalse(view.isDrawingCacheEnabled());
1069 
1070         view.setDrawingCacheEnabled(true);
1071         assertTrue(view.isDrawingCacheEnabled());
1072     }
1073 
testGetDrawingCache()1074     public void testGetDrawingCache() {
1075         MockView view = new MockView(mActivity);
1076 
1077         // should not call buildDrawingCache when getDrawingCache
1078         assertNull(view.getDrawingCache());
1079 
1080         // should call buildDrawingCache when getDrawingCache
1081         view = (MockView) mActivity.findViewById(R.id.mock_view);
1082         view.setDrawingCacheEnabled(true);
1083         Bitmap bitmap1 = view.getDrawingCache();
1084         assertNotNull(bitmap1);
1085         assertEquals(view.getWidth(), bitmap1.getWidth());
1086         assertEquals(view.getHeight(), bitmap1.getHeight());
1087 
1088         view.setWillNotCacheDrawing(true);
1089         assertNull(view.getDrawingCache());
1090 
1091         view.setWillNotCacheDrawing(false);
1092         // build a new drawingcache
1093         Bitmap bitmap2 = view.getDrawingCache();
1094         assertNotSame(bitmap1, bitmap2);
1095     }
1096 
testBuildAndDestroyDrawingCache()1097     public void testBuildAndDestroyDrawingCache() {
1098         MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
1099 
1100         assertNull(view.getDrawingCache());
1101 
1102         view.buildDrawingCache();
1103         Bitmap bitmap = view.getDrawingCache();
1104         assertNotNull(bitmap);
1105         assertEquals(view.getWidth(), bitmap.getWidth());
1106         assertEquals(view.getHeight(), bitmap.getHeight());
1107 
1108         view.destroyDrawingCache();
1109         assertNull(view.getDrawingCache());
1110     }
1111 
testAccessWillNotDraw()1112     public void testAccessWillNotDraw() {
1113         View view = new View(mActivity);
1114 
1115         assertFalse(view.willNotDraw());
1116 
1117         view.setWillNotDraw(true);
1118         assertTrue(view.willNotDraw());
1119     }
1120 
testAccessDrawingCacheQuality()1121     public void testAccessDrawingCacheQuality() {
1122         View view = new View(mActivity);
1123 
1124         assertEquals(0, view.getDrawingCacheQuality());
1125 
1126         view.setDrawingCacheQuality(1);
1127         assertEquals(0, view.getDrawingCacheQuality());
1128 
1129         view.setDrawingCacheQuality(0x00100000);
1130         assertEquals(0x00100000, view.getDrawingCacheQuality());
1131 
1132         view.setDrawingCacheQuality(0x00080000);
1133         assertEquals(0x00080000, view.getDrawingCacheQuality());
1134 
1135         view.setDrawingCacheQuality(0xffffffff);
1136         // 0x00180000 is View.DRAWING_CACHE_QUALITY_MASK
1137         assertEquals(0x00180000, view.getDrawingCacheQuality());
1138     }
1139 
testDispatchSetSelected()1140     public void testDispatchSetSelected() {
1141         MockView mockView1 = new MockView(mActivity);
1142         MockView mockView2 = new MockView(mActivity);
1143         mockView1.setParent(mMockParent);
1144         mockView2.setParent(mMockParent);
1145 
1146         mMockParent.dispatchSetSelected(true);
1147         assertTrue(mockView1.isSelected());
1148         assertTrue(mockView2.isSelected());
1149 
1150         mMockParent.dispatchSetSelected(false);
1151         assertFalse(mockView1.isSelected());
1152         assertFalse(mockView2.isSelected());
1153     }
1154 
testAccessSelected()1155     public void testAccessSelected() {
1156         View view = new View(mActivity);
1157 
1158         assertFalse(view.isSelected());
1159 
1160         view.setSelected(true);
1161         assertTrue(view.isSelected());
1162     }
1163 
testDispatchSetPressed()1164     public void testDispatchSetPressed() {
1165         MockView mockView1 = new MockView(mActivity);
1166         MockView mockView2 = new MockView(mActivity);
1167         mockView1.setParent(mMockParent);
1168         mockView2.setParent(mMockParent);
1169 
1170         mMockParent.dispatchSetPressed(true);
1171         assertTrue(mockView1.isPressed());
1172         assertTrue(mockView2.isPressed());
1173 
1174         mMockParent.dispatchSetPressed(false);
1175         assertFalse(mockView1.isPressed());
1176         assertFalse(mockView2.isPressed());
1177     }
1178 
testAccessPressed()1179     public void testAccessPressed() {
1180         View view = new View(mActivity);
1181 
1182         assertFalse(view.isPressed());
1183 
1184         view.setPressed(true);
1185         assertTrue(view.isPressed());
1186     }
1187 
testAccessSoundEffectsEnabled()1188     public void testAccessSoundEffectsEnabled() {
1189         View view = new View(mActivity);
1190 
1191         assertTrue(view.isSoundEffectsEnabled());
1192 
1193         view.setSoundEffectsEnabled(false);
1194         assertFalse(view.isSoundEffectsEnabled());
1195     }
1196 
testAccessKeepScreenOn()1197     public void testAccessKeepScreenOn() {
1198         View view = new View(mActivity);
1199 
1200         assertFalse(view.getKeepScreenOn());
1201 
1202         view.setKeepScreenOn(true);
1203         assertTrue(view.getKeepScreenOn());
1204     }
1205 
testAccessDuplicateParentStateEnabled()1206     public void testAccessDuplicateParentStateEnabled() {
1207         View view = new View(mActivity);
1208 
1209         assertFalse(view.isDuplicateParentStateEnabled());
1210 
1211         view.setDuplicateParentStateEnabled(true);
1212         assertTrue(view.isDuplicateParentStateEnabled());
1213     }
1214 
testAccessEnabled()1215     public void testAccessEnabled() {
1216         View view = new View(mActivity);
1217 
1218         assertTrue(view.isEnabled());
1219 
1220         view.setEnabled(false);
1221         assertFalse(view.isEnabled());
1222     }
1223 
testAccessSaveEnabled()1224     public void testAccessSaveEnabled() {
1225         View view = new View(mActivity);
1226 
1227         assertTrue(view.isSaveEnabled());
1228 
1229         view.setSaveEnabled(false);
1230         assertFalse(view.isSaveEnabled());
1231     }
1232 
testShowContextMenu()1233     public void testShowContextMenu() {
1234         MockView view = new MockView(mActivity);
1235 
1236         assertNull(view.getParent());
1237         try {
1238             view.showContextMenu();
1239             fail("should throw NullPointerException");
1240         } catch (NullPointerException e) {
1241         }
1242 
1243         view.setParent(mMockParent);
1244         assertFalse(mMockParent.hasShowContextMenuForChild());
1245 
1246         assertFalse(view.showContextMenu());
1247         assertTrue(mMockParent.hasShowContextMenuForChild());
1248     }
1249 
testFitSystemWindows()1250     public void testFitSystemWindows() {
1251         final XmlResourceParser parser = mResources.getLayout(R.layout.view_layout);
1252         final AttributeSet attrs = Xml.asAttributeSet(parser);
1253         Rect insets = new Rect(10, 20, 30, 50);
1254 
1255         MockView view = new MockView(mActivity);
1256         assertFalse(view.fitSystemWindows(insets));
1257         assertFalse(view.fitSystemWindows(null));
1258 
1259         view = new MockView(mActivity, attrs, android.R.attr.fitsSystemWindows);
1260         assertFalse(view.fitSystemWindows(insets));
1261         assertFalse(view.fitSystemWindows(null));
1262     }
1263 
testPerformClick()1264     public void testPerformClick() {
1265         View view = new View(mActivity);
1266         OnClickListenerImpl listener = new OnClickListenerImpl();
1267 
1268         assertFalse(view.performClick());
1269 
1270         assertFalse(listener.hasOnClick());
1271         view.setOnClickListener(listener);
1272 
1273         assertTrue(view.performClick());
1274         assertTrue(listener.hasOnClick());
1275 
1276         view.setOnClickListener(null);
1277         assertFalse(view.performClick());
1278     }
1279 
testSetOnClickListener()1280     public void testSetOnClickListener() {
1281         View view = new View(mActivity);
1282         assertFalse(view.performClick());
1283         assertFalse(view.isClickable());
1284 
1285         view.setOnClickListener(null);
1286         assertFalse(view.performClick());
1287         assertTrue(view.isClickable());
1288 
1289         view.setOnClickListener(new OnClickListenerImpl());
1290         assertTrue(view.performClick());
1291         assertTrue(view.isClickable());
1292     }
1293 
testPerformLongClick()1294     public void testPerformLongClick() {
1295         MockView view = new MockView(mActivity);
1296         OnLongClickListenerImpl listener = new OnLongClickListenerImpl();
1297 
1298         try {
1299             view.performLongClick();
1300             fail("should throw NullPointerException");
1301         } catch (NullPointerException e) {
1302         }
1303 
1304         view.setParent(mMockParent);
1305         assertFalse(mMockParent.hasShowContextMenuForChild());
1306         assertFalse(view.performLongClick());
1307         assertTrue(mMockParent.hasShowContextMenuForChild());
1308 
1309         view.setOnLongClickListener(listener);
1310         mMockParent.reset();
1311         assertFalse(mMockParent.hasShowContextMenuForChild());
1312         assertFalse(listener.hasOnLongClick());
1313         assertTrue(view.performLongClick());
1314         assertFalse(mMockParent.hasShowContextMenuForChild());
1315         assertTrue(listener.hasOnLongClick());
1316     }
1317 
testSetOnLongClickListener()1318     public void testSetOnLongClickListener() {
1319         MockView view = new MockView(mActivity);
1320         view.setParent(mMockParent);
1321         assertFalse(view.performLongClick());
1322         assertFalse(view.isLongClickable());
1323 
1324         view.setOnLongClickListener(null);
1325         assertFalse(view.performLongClick());
1326         assertTrue(view.isLongClickable());
1327 
1328         view.setOnLongClickListener(new OnLongClickListenerImpl());
1329         assertTrue(view.performLongClick());
1330         assertTrue(view.isLongClickable());
1331     }
1332 
testPerformContextClick()1333     public void testPerformContextClick() {
1334         MockView view = new MockView(mActivity);
1335         view.setParent(mMockParent);
1336         OnContextClickListenerImpl listener = new OnContextClickListenerImpl();
1337 
1338         view.setOnContextClickListener(listener);
1339         assertFalse(listener.hasOnContextClick());
1340 
1341         assertTrue(view.performContextClick());
1342         assertTrue(listener.hasOnContextClick());
1343         assertSame(view, listener.getLastViewContextClicked());
1344     }
1345 
testSetOnContextClickListener()1346     public void testSetOnContextClickListener() {
1347         MockView view = new MockView(mActivity);
1348         view.setParent(mMockParent);
1349 
1350         assertFalse(view.performContextClick());
1351         assertFalse(view.isContextClickable());
1352 
1353         view.setOnContextClickListener(new OnContextClickListenerImpl());
1354         assertTrue(view.performContextClick());
1355         assertTrue(view.isContextClickable());
1356     }
1357 
testAccessOnFocusChangeListener()1358     public void testAccessOnFocusChangeListener() {
1359         View view = new View(mActivity);
1360         OnFocusChangeListener listener = new OnFocusChangeListenerImpl();
1361 
1362         assertNull(view.getOnFocusChangeListener());
1363 
1364         view.setOnFocusChangeListener(listener);
1365         assertSame(listener, view.getOnFocusChangeListener());
1366     }
1367 
testAccessNextFocusUpId()1368     public void testAccessNextFocusUpId() {
1369         View view = new View(mActivity);
1370 
1371         assertEquals(View.NO_ID, view.getNextFocusUpId());
1372 
1373         view.setNextFocusUpId(1);
1374         assertEquals(1, view.getNextFocusUpId());
1375 
1376         view.setNextFocusUpId(Integer.MAX_VALUE);
1377         assertEquals(Integer.MAX_VALUE, view.getNextFocusUpId());
1378 
1379         view.setNextFocusUpId(Integer.MIN_VALUE);
1380         assertEquals(Integer.MIN_VALUE, view.getNextFocusUpId());
1381     }
1382 
testAccessNextFocusDownId()1383     public void testAccessNextFocusDownId() {
1384         View view = new View(mActivity);
1385 
1386         assertEquals(View.NO_ID, view.getNextFocusDownId());
1387 
1388         view.setNextFocusDownId(1);
1389         assertEquals(1, view.getNextFocusDownId());
1390 
1391         view.setNextFocusDownId(Integer.MAX_VALUE);
1392         assertEquals(Integer.MAX_VALUE, view.getNextFocusDownId());
1393 
1394         view.setNextFocusDownId(Integer.MIN_VALUE);
1395         assertEquals(Integer.MIN_VALUE, view.getNextFocusDownId());
1396     }
1397 
testAccessNextFocusLeftId()1398     public void testAccessNextFocusLeftId() {
1399         View view = new View(mActivity);
1400 
1401         assertEquals(View.NO_ID, view.getNextFocusLeftId());
1402 
1403         view.setNextFocusLeftId(1);
1404         assertEquals(1, view.getNextFocusLeftId());
1405 
1406         view.setNextFocusLeftId(Integer.MAX_VALUE);
1407         assertEquals(Integer.MAX_VALUE, view.getNextFocusLeftId());
1408 
1409         view.setNextFocusLeftId(Integer.MIN_VALUE);
1410         assertEquals(Integer.MIN_VALUE, view.getNextFocusLeftId());
1411     }
1412 
testAccessNextFocusRightId()1413     public void testAccessNextFocusRightId() {
1414         View view = new View(mActivity);
1415 
1416         assertEquals(View.NO_ID, view.getNextFocusRightId());
1417 
1418         view.setNextFocusRightId(1);
1419         assertEquals(1, view.getNextFocusRightId());
1420 
1421         view.setNextFocusRightId(Integer.MAX_VALUE);
1422         assertEquals(Integer.MAX_VALUE, view.getNextFocusRightId());
1423 
1424         view.setNextFocusRightId(Integer.MIN_VALUE);
1425         assertEquals(Integer.MIN_VALUE, view.getNextFocusRightId());
1426     }
1427 
testAccessMeasuredDimension()1428     public void testAccessMeasuredDimension() {
1429         MockView view = new MockView(mActivity);
1430         assertEquals(0, view.getMeasuredWidth());
1431         assertEquals(0, view.getMeasuredHeight());
1432 
1433         view.setMeasuredDimensionWrapper(20, 30);
1434         assertEquals(20, view.getMeasuredWidth());
1435         assertEquals(30, view.getMeasuredHeight());
1436     }
1437 
testMeasure()1438     public void testMeasure() throws Throwable {
1439         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
1440         assertTrue(view.hasCalledOnMeasure());
1441         assertEquals(100, view.getMeasuredWidth());
1442         assertEquals(200, view.getMeasuredHeight());
1443 
1444         view.reset();
1445         runTestOnUiThread(new Runnable() {
1446             public void run() {
1447                 view.requestLayout();
1448             }
1449         });
1450         getInstrumentation().waitForIdleSync();
1451         assertTrue(view.hasCalledOnMeasure());
1452         assertEquals(100, view.getMeasuredWidth());
1453         assertEquals(200, view.getMeasuredHeight());
1454 
1455         view.reset();
1456         final LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(200, 100);
1457         runTestOnUiThread(new Runnable() {
1458             public void run() {
1459                 view.setLayoutParams(layoutParams);
1460             }
1461         });
1462         getInstrumentation().waitForIdleSync();
1463         assertTrue(view.hasCalledOnMeasure());
1464         assertEquals(200, view.getMeasuredWidth());
1465         assertEquals(100, view.getMeasuredHeight());
1466     }
1467 
testAccessLayoutParams()1468     public void testAccessLayoutParams() {
1469         View view = new View(mActivity);
1470         ViewGroup.LayoutParams params = new ViewGroup.LayoutParams(10, 20);
1471 
1472         assertNull(view.getLayoutParams());
1473 
1474         try {
1475             view.setLayoutParams(null);
1476             fail("should throw NullPointerException");
1477         } catch (NullPointerException e) {
1478         }
1479 
1480         assertFalse(view.isLayoutRequested());
1481         view.setLayoutParams(params);
1482         assertSame(params, view.getLayoutParams());
1483         assertTrue(view.isLayoutRequested());
1484     }
1485 
testIsShown()1486     public void testIsShown() {
1487         MockView view = new MockView(mActivity);
1488 
1489         view.setVisibility(View.INVISIBLE);
1490         assertFalse(view.isShown());
1491 
1492         view.setVisibility(View.VISIBLE);
1493         assertNull(view.getParent());
1494         assertFalse(view.isShown());
1495 
1496         view.setParent(mMockParent);
1497         // mMockParent is not a instance of ViewRoot
1498         assertFalse(view.isShown());
1499     }
1500 
testGetDrawingTime()1501     public void testGetDrawingTime() {
1502         View view = new View(mActivity);
1503         // mAttachInfo is null
1504         assertEquals(0, view.getDrawingTime());
1505 
1506         // mAttachInfo is not null
1507         view = mActivity.findViewById(R.id.fit_windows);
1508         assertEquals(SystemClock.uptimeMillis(), view.getDrawingTime(), 1000);
1509     }
1510 
testScheduleDrawable()1511     public void testScheduleDrawable() {
1512         View view = new View(mActivity);
1513         Drawable drawable = new StateListDrawable();
1514         Runnable what = new Runnable() {
1515             public void run() {
1516                 // do nothing
1517             }
1518         };
1519 
1520         // mAttachInfo is null
1521         view.scheduleDrawable(drawable, what, 1000);
1522 
1523         view.setBackgroundDrawable(drawable);
1524         view.scheduleDrawable(drawable, what, 1000);
1525 
1526         view.scheduleDrawable(null, null, -1000);
1527 
1528         // mAttachInfo is not null
1529         view = mActivity.findViewById(R.id.fit_windows);
1530         view.scheduleDrawable(drawable, what, 1000);
1531 
1532         view.scheduleDrawable(view.getBackground(), what, 1000);
1533         view.unscheduleDrawable(view.getBackground(), what);
1534 
1535         view.scheduleDrawable(null, null, -1000);
1536     }
1537 
testUnscheduleDrawable()1538     public void testUnscheduleDrawable() {
1539         View view = new View(mActivity);
1540         Drawable drawable = new StateListDrawable();
1541         Runnable what = new Runnable() {
1542             public void run() {
1543                 // do nothing
1544             }
1545         };
1546 
1547         // mAttachInfo is null
1548         view.unscheduleDrawable(drawable, what);
1549 
1550         view.setBackgroundDrawable(drawable);
1551         view.unscheduleDrawable(drawable);
1552 
1553         view.unscheduleDrawable(null, null);
1554         view.unscheduleDrawable(null);
1555 
1556         // mAttachInfo is not null
1557         view = mActivity.findViewById(R.id.fit_windows);
1558         view.unscheduleDrawable(drawable);
1559 
1560         view.scheduleDrawable(view.getBackground(), what, 1000);
1561         view.unscheduleDrawable(view.getBackground(), what);
1562 
1563         view.unscheduleDrawable(null);
1564         view.unscheduleDrawable(null, null);
1565     }
1566 
testGetWindowVisibility()1567     public void testGetWindowVisibility() {
1568         View view = new View(mActivity);
1569         // mAttachInfo is null
1570         assertEquals(View.GONE, view.getWindowVisibility());
1571 
1572         // mAttachInfo is not null
1573         view = mActivity.findViewById(R.id.fit_windows);
1574         assertEquals(View.VISIBLE, view.getWindowVisibility());
1575     }
1576 
testGetWindowToken()1577     public void testGetWindowToken() {
1578         View view = new View(mActivity);
1579         // mAttachInfo is null
1580         assertNull(view.getWindowToken());
1581 
1582         // mAttachInfo is not null
1583         view = mActivity.findViewById(R.id.fit_windows);
1584         assertNotNull(view.getWindowToken());
1585     }
1586 
testHasWindowFocus()1587     public void testHasWindowFocus() {
1588         View view = new View(mActivity);
1589         // mAttachInfo is null
1590         assertFalse(view.hasWindowFocus());
1591 
1592         // mAttachInfo is not null
1593         final View view2 = mActivity.findViewById(R.id.fit_windows);
1594         // Wait until the window has been focused.
1595         new PollingCheck(TIMEOUT_DELTA) {
1596             @Override
1597             protected boolean check() {
1598                 return view2.hasWindowFocus();
1599             }
1600         }.run();
1601     }
1602 
testGetHandler()1603     public void testGetHandler() {
1604         MockView view = new MockView(mActivity);
1605         // mAttachInfo is null
1606         assertNull(view.getHandler());
1607     }
1608 
testRemoveCallbacks()1609     public void testRemoveCallbacks() throws InterruptedException {
1610         final long delay = 500L;
1611         View view = mActivity.findViewById(R.id.mock_view);
1612         MockRunnable runner = new MockRunnable();
1613         assertTrue(view.postDelayed(runner, delay));
1614         assertTrue(view.removeCallbacks(runner));
1615         assertTrue(view.removeCallbacks(null));
1616         assertTrue(view.removeCallbacks(new MockRunnable()));
1617         Thread.sleep(delay * 2);
1618         assertFalse(runner.hasRun);
1619         // check that the runner actually works
1620         runner = new MockRunnable();
1621         assertTrue(view.postDelayed(runner, delay));
1622         Thread.sleep(delay * 2);
1623         assertTrue(runner.hasRun);
1624     }
1625 
testCancelLongPress()1626     public void testCancelLongPress() {
1627         View view = new View(mActivity);
1628         // mAttachInfo is null
1629         view.cancelLongPress();
1630 
1631         // mAttachInfo is not null
1632         view = mActivity.findViewById(R.id.fit_windows);
1633         view.cancelLongPress();
1634     }
1635 
testGetViewTreeObserver()1636     public void testGetViewTreeObserver() {
1637         View view = new View(mActivity);
1638         // mAttachInfo is null
1639         assertNotNull(view.getViewTreeObserver());
1640 
1641         // mAttachInfo is not null
1642         view = mActivity.findViewById(R.id.fit_windows);
1643         assertNotNull(view.getViewTreeObserver());
1644     }
1645 
testGetWindowAttachCount()1646     public void testGetWindowAttachCount() {
1647         MockView view = new MockView(mActivity);
1648         // mAttachInfo is null
1649         assertEquals(0, view.getWindowAttachCount());
1650     }
1651 
1652     @UiThreadTest
testOnAttachedToAndDetachedFromWindow()1653     public void testOnAttachedToAndDetachedFromWindow() {
1654         MockView mockView = new MockView(mActivity);
1655         ViewGroup viewGroup = (ViewGroup) mActivity.findViewById(R.id.viewlayout_root);
1656 
1657         viewGroup.addView(mockView);
1658         assertTrue(mockView.hasCalledOnAttachedToWindow());
1659 
1660         viewGroup.removeView(mockView);
1661         assertTrue(mockView.hasCalledOnDetachedFromWindow());
1662 
1663         mockView.reset();
1664         mActivity.setContentView(mockView);
1665         assertTrue(mockView.hasCalledOnAttachedToWindow());
1666 
1667         mActivity.setContentView(R.layout.view_layout);
1668         assertTrue(mockView.hasCalledOnDetachedFromWindow());
1669     }
1670 
testGetLocationInWindow()1671     public void testGetLocationInWindow() {
1672         int[] location = new int[] { -1, -1 };
1673 
1674         View layout = mActivity.findViewById(R.id.viewlayout_root);
1675         int[] layoutLocation = new int[] { -1, -1 };
1676         layout.getLocationInWindow(layoutLocation);
1677 
1678         final View mockView = mActivity.findViewById(R.id.mock_view);
1679         mockView.getLocationInWindow(location);
1680         assertEquals(layoutLocation[0], location[0]);
1681         assertEquals(layoutLocation[1], location[1]);
1682 
1683         View scrollView = mActivity.findViewById(R.id.scroll_view);
1684         scrollView.getLocationInWindow(location);
1685         assertEquals(layoutLocation[0], location[0]);
1686         assertEquals(layoutLocation[1] + mockView.getHeight(), location[1]);
1687 
1688         try {
1689             mockView.getLocationInWindow(null);
1690             fail("should throw IllegalArgumentException");
1691         } catch (IllegalArgumentException e) {
1692         }
1693 
1694         try {
1695             mockView.getLocationInWindow(new int[] { 0 });
1696             fail("should throw IllegalArgumentException");
1697         } catch (IllegalArgumentException e) {
1698         }
1699     }
1700 
testGetLocationOnScreen()1701     public void testGetLocationOnScreen() {
1702         View view = new View(mActivity);
1703         int[] location = new int[] { -1, -1 };
1704 
1705         // mAttachInfo is not null
1706         View layout = mActivity.findViewById(R.id.viewlayout_root);
1707         int[] layoutLocation = new int[] { -1, -1 };
1708         layout.getLocationOnScreen(layoutLocation);
1709 
1710         View mockView = mActivity.findViewById(R.id.mock_view);
1711         mockView.getLocationOnScreen(location);
1712         assertEquals(layoutLocation[0], location[0]);
1713         assertEquals(layoutLocation[1], location[1]);
1714 
1715         View scrollView = mActivity.findViewById(R.id.scroll_view);
1716         scrollView.getLocationOnScreen(location);
1717         assertEquals(layoutLocation[0], location[0]);
1718         assertEquals(layoutLocation[1] + mockView.getHeight(), location[1]);
1719 
1720         try {
1721             scrollView.getLocationOnScreen(null);
1722             fail("should throw IllegalArgumentException");
1723         } catch (IllegalArgumentException e) {
1724         }
1725 
1726         try {
1727             scrollView.getLocationOnScreen(new int[] { 0 });
1728             fail("should throw IllegalArgumentException");
1729         } catch (IllegalArgumentException e) {
1730         }
1731     }
1732 
testAddTouchables()1733     public void testAddTouchables() {
1734         View view = new View(mActivity);
1735         ArrayList<View> result = new ArrayList<View>();
1736         assertEquals(0, result.size());
1737 
1738         view.addTouchables(result);
1739         assertEquals(0, result.size());
1740 
1741         view.setClickable(true);
1742         view.addTouchables(result);
1743         assertEquals(1, result.size());
1744         assertSame(view, result.get(0));
1745 
1746         try {
1747             view.addTouchables(null);
1748             fail("should throw NullPointerException");
1749         } catch (NullPointerException e) {
1750         }
1751 
1752         result.clear();
1753         view.setEnabled(false);
1754         assertTrue(view.isClickable());
1755         view.addTouchables(result);
1756         assertEquals(0, result.size());
1757     }
1758 
testGetTouchables()1759     public void testGetTouchables() {
1760         View view = new View(mActivity);
1761         ArrayList<View> result;
1762 
1763         result = view.getTouchables();
1764         assertEquals(0, result.size());
1765 
1766         view.setClickable(true);
1767         result = view.getTouchables();
1768         assertEquals(1, result.size());
1769         assertSame(view, result.get(0));
1770 
1771         result.clear();
1772         view.setEnabled(false);
1773         assertTrue(view.isClickable());
1774         result = view.getTouchables();
1775         assertEquals(0, result.size());
1776     }
1777 
testInflate()1778     public void testInflate() {
1779         View view = View.inflate(mActivity, R.layout.view_layout, null);
1780         assertNotNull(view);
1781         assertTrue(view instanceof LinearLayout);
1782 
1783         MockView mockView = (MockView) view.findViewById(R.id.mock_view);
1784         assertNotNull(mockView);
1785         assertTrue(mockView.hasCalledOnFinishInflate());
1786     }
1787 
testIsInTouchMode()1788     public void testIsInTouchMode() {
1789         View view = new View(mActivity);
1790         // mAttachInfo is null
1791         assertFalse(view.isInTouchMode());
1792 
1793         // mAttachInfo is not null
1794         view = mActivity.findViewById(R.id.fit_windows);
1795         assertFalse(view.isInTouchMode());
1796     }
1797 
testIsInEditMode()1798     public void testIsInEditMode() {
1799         View view = new View(mActivity);
1800         assertFalse(view.isInEditMode());
1801     }
1802 
testPostInvalidate1()1803     public void testPostInvalidate1() {
1804         View view = new View(mActivity);
1805         // mAttachInfo is null
1806         view.postInvalidate();
1807 
1808         // mAttachInfo is not null
1809         view = mActivity.findViewById(R.id.fit_windows);
1810         view.postInvalidate();
1811     }
1812 
testPostInvalidate2()1813     public void testPostInvalidate2() {
1814         View view = new View(mActivity);
1815         // mAttachInfo is null
1816         view.postInvalidate(0, 1, 2, 3);
1817 
1818         // mAttachInfo is not null
1819         view = mActivity.findViewById(R.id.fit_windows);
1820         view.postInvalidate(10, 20, 30, 40);
1821         view.postInvalidate(0, -20, -30, -40);
1822     }
1823 
testPostInvalidateDelayed()1824     public void testPostInvalidateDelayed() {
1825         View view = new View(mActivity);
1826         // mAttachInfo is null
1827         view.postInvalidateDelayed(1000);
1828         view.postInvalidateDelayed(500, 0, 0, 100, 200);
1829 
1830         // mAttachInfo is not null
1831         view = mActivity.findViewById(R.id.fit_windows);
1832         view.postInvalidateDelayed(1000);
1833         view.postInvalidateDelayed(500, 0, 0, 100, 200);
1834         view.postInvalidateDelayed(-1);
1835     }
1836 
testPost()1837     public void testPost() {
1838         View view = new View(mActivity);
1839         MockRunnable action = new MockRunnable();
1840 
1841         // mAttachInfo is null
1842         assertTrue(view.post(action));
1843         assertTrue(view.post(null));
1844 
1845         // mAttachInfo is not null
1846         view = mActivity.findViewById(R.id.fit_windows);
1847         assertTrue(view.post(action));
1848         assertTrue(view.post(null));
1849     }
1850 
testPostDelayed()1851     public void testPostDelayed() {
1852         View view = new View(mActivity);
1853         MockRunnable action = new MockRunnable();
1854 
1855         // mAttachInfo is null
1856         assertTrue(view.postDelayed(action, 1000));
1857         assertTrue(view.postDelayed(null, -1));
1858 
1859         // mAttachInfo is not null
1860         view = mActivity.findViewById(R.id.fit_windows);
1861         assertTrue(view.postDelayed(action, 1000));
1862         assertTrue(view.postDelayed(null, 0));
1863     }
1864 
1865     @UiThreadTest
testPlaySoundEffect()1866     public void testPlaySoundEffect() {
1867         MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
1868         // sound effect enabled
1869         view.playSoundEffect(SoundEffectConstants.CLICK);
1870 
1871         // sound effect disabled
1872         view.setSoundEffectsEnabled(false);
1873         view.playSoundEffect(SoundEffectConstants.NAVIGATION_DOWN);
1874 
1875         // no way to assert the soundConstant be really played.
1876     }
1877 
testOnKeyShortcut()1878     public void testOnKeyShortcut() throws Throwable {
1879         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
1880         runTestOnUiThread(new Runnable() {
1881             public void run() {
1882                 view.setFocusable(true);
1883                 view.requestFocus();
1884             }
1885         });
1886         getInstrumentation().waitForIdleSync();
1887         assertTrue(view.isFocused());
1888 
1889         KeyEvent event = new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_MENU);
1890         getInstrumentation().sendKeySync(event);
1891         event = new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_0);
1892         getInstrumentation().sendKeySync(event);
1893         assertTrue(view.hasCalledOnKeyShortcut());
1894     }
1895 
testOnKeyMultiple()1896     public void testOnKeyMultiple() throws Throwable {
1897         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
1898         runTestOnUiThread(new Runnable() {
1899             public void run() {
1900                 view.setFocusable(true);
1901             }
1902         });
1903 
1904         assertFalse(view.hasCalledOnKeyMultiple());
1905         view.dispatchKeyEvent(new KeyEvent(KeyEvent.ACTION_MULTIPLE, KeyEvent.KEYCODE_ENTER));
1906         assertTrue(view.hasCalledOnKeyMultiple());
1907     }
1908 
1909     @UiThreadTest
testDispatchKeyShortcutEvent()1910     public void testDispatchKeyShortcutEvent() {
1911         MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
1912         view.setFocusable(true);
1913 
1914         KeyEvent event = new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_0);
1915         view.dispatchKeyShortcutEvent(event);
1916         assertTrue(view.hasCalledOnKeyShortcut());
1917 
1918         try {
1919             view.dispatchKeyShortcutEvent(null);
1920             fail("should throw NullPointerException");
1921         } catch (NullPointerException e) {
1922         }
1923     }
1924 
testOnTrackballEvent()1925     public void testOnTrackballEvent() throws Throwable {
1926         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
1927         runTestOnUiThread(new Runnable() {
1928             public void run() {
1929                 view.setEnabled(true);
1930                 view.setFocusable(true);
1931                 view.requestFocus();
1932             }
1933         });
1934         getInstrumentation().waitForIdleSync();
1935 
1936         long downTime = SystemClock.uptimeMillis();
1937         long eventTime = downTime;
1938         MotionEvent event = MotionEvent.obtain(downTime, eventTime, MotionEvent.ACTION_MOVE,
1939                 1, 2, 0);
1940         getInstrumentation().sendTrackballEventSync(event);
1941         getInstrumentation().waitForIdleSync();
1942         assertTrue(view.hasCalledOnTrackballEvent());
1943     }
1944 
1945     @UiThreadTest
testDispatchTrackballMoveEvent()1946     public void testDispatchTrackballMoveEvent() {
1947         ViewGroup viewGroup = (ViewGroup) mActivity.findViewById(R.id.viewlayout_root);
1948         MockView mockView1 = new MockView(mActivity);
1949         MockView mockView2 = new MockView(mActivity);
1950         viewGroup.addView(mockView1);
1951         viewGroup.addView(mockView2);
1952         mockView1.setFocusable(true);
1953         mockView2.setFocusable(true);
1954         mockView2.requestFocus();
1955 
1956         long downTime = SystemClock.uptimeMillis();
1957         long eventTime = downTime;
1958         MotionEvent event = MotionEvent.obtain(downTime, eventTime, MotionEvent.ACTION_MOVE,
1959                 1, 2, 0);
1960         mockView1.dispatchTrackballEvent(event);
1961         // issue 1695243
1962         // It passes a trackball motion event down to itself even if it is not the focused view.
1963         assertTrue(mockView1.hasCalledOnTrackballEvent());
1964         assertFalse(mockView2.hasCalledOnTrackballEvent());
1965 
1966         mockView1.reset();
1967         mockView2.reset();
1968         downTime = SystemClock.uptimeMillis();
1969         eventTime = downTime;
1970         event = MotionEvent.obtain(downTime, eventTime, MotionEvent.ACTION_MOVE, 1, 2, 0);
1971         mockView2.dispatchTrackballEvent(event);
1972         assertFalse(mockView1.hasCalledOnTrackballEvent());
1973         assertTrue(mockView2.hasCalledOnTrackballEvent());
1974     }
1975 
testDispatchUnhandledMove()1976     public void testDispatchUnhandledMove() throws Throwable {
1977         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
1978         runTestOnUiThread(new Runnable() {
1979             public void run() {
1980                 view.setFocusable(true);
1981                 view.requestFocus();
1982             }
1983         });
1984         getInstrumentation().waitForIdleSync();
1985 
1986         KeyEvent event = new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_DPAD_RIGHT);
1987         getInstrumentation().sendKeySync(event);
1988 
1989         assertTrue(view.hasCalledDispatchUnhandledMove());
1990     }
1991 
testWindowVisibilityChanged()1992     public void testWindowVisibilityChanged() throws Throwable {
1993         final MockView mockView = new MockView(mActivity);
1994         final ViewGroup viewGroup = (ViewGroup) mActivity.findViewById(R.id.viewlayout_root);
1995 
1996         runTestOnUiThread(new Runnable() {
1997             public void run() {
1998                 viewGroup.addView(mockView);
1999             }
2000         });
2001         getInstrumentation().waitForIdleSync();
2002         assertTrue(mockView.hasCalledOnWindowVisibilityChanged());
2003 
2004         mockView.reset();
2005         runTestOnUiThread(new Runnable() {
2006             public void run() {
2007                 getActivity().setVisible(false);
2008             }
2009         });
2010         getInstrumentation().waitForIdleSync();
2011         assertTrue(mockView.hasCalledDispatchWindowVisibilityChanged());
2012         assertTrue(mockView.hasCalledOnWindowVisibilityChanged());
2013 
2014         mockView.reset();
2015         runTestOnUiThread(new Runnable() {
2016             public void run() {
2017                 getActivity().setVisible(true);
2018             }
2019         });
2020         getInstrumentation().waitForIdleSync();
2021         assertTrue(mockView.hasCalledDispatchWindowVisibilityChanged());
2022         assertTrue(mockView.hasCalledOnWindowVisibilityChanged());
2023 
2024         mockView.reset();
2025         runTestOnUiThread(new Runnable() {
2026             public void run() {
2027                 viewGroup.removeView(mockView);
2028             }
2029         });
2030         getInstrumentation().waitForIdleSync();
2031         assertTrue(mockView.hasCalledOnWindowVisibilityChanged());
2032     }
2033 
testGetLocalVisibleRect()2034     public void testGetLocalVisibleRect() throws Throwable {
2035         final View view = mActivity.findViewById(R.id.mock_view);
2036         Rect rect = new Rect();
2037 
2038         assertTrue(view.getLocalVisibleRect(rect));
2039         assertEquals(0, rect.left);
2040         assertEquals(0, rect.top);
2041         assertEquals(100, rect.right);
2042         assertEquals(200, rect.bottom);
2043 
2044         final LinearLayout.LayoutParams layoutParams1 = new LinearLayout.LayoutParams(0, 300);
2045         runTestOnUiThread(new Runnable() {
2046             public void run() {
2047                 view.setLayoutParams(layoutParams1);
2048             }
2049         });
2050         getInstrumentation().waitForIdleSync();
2051         assertFalse(view.getLocalVisibleRect(rect));
2052 
2053         final LinearLayout.LayoutParams layoutParams2 = new LinearLayout.LayoutParams(200, -10);
2054         runTestOnUiThread(new Runnable() {
2055             public void run() {
2056                 view.setLayoutParams(layoutParams2);
2057             }
2058         });
2059         getInstrumentation().waitForIdleSync();
2060         assertFalse(view.getLocalVisibleRect(rect));
2061 
2062         Display display = getActivity().getWindowManager().getDefaultDisplay();
2063         int halfWidth = display.getWidth() / 2;
2064         int halfHeight = display.getHeight() /2;
2065 
2066         final LinearLayout.LayoutParams layoutParams3 =
2067                 new LinearLayout.LayoutParams(halfWidth, halfHeight);
2068         runTestOnUiThread(new Runnable() {
2069             public void run() {
2070                 view.setLayoutParams(layoutParams3);
2071                 view.scrollTo(20, -30);
2072             }
2073         });
2074         getInstrumentation().waitForIdleSync();
2075         assertTrue(view.getLocalVisibleRect(rect));
2076         assertEquals(20, rect.left);
2077         assertEquals(-30, rect.top);
2078         assertEquals(halfWidth + 20, rect.right);
2079         assertEquals(halfHeight - 30, rect.bottom);
2080 
2081         try {
2082             view.getLocalVisibleRect(null);
2083             fail("should throw NullPointerException");
2084         } catch (NullPointerException e) {
2085         }
2086     }
2087 
testMergeDrawableStates()2088     public void testMergeDrawableStates() {
2089         MockView view = new MockView(mActivity);
2090 
2091         int[] states = view.mergeDrawableStatesWrapper(new int[] { 0, 1, 2, 0, 0 },
2092                 new int[] { 3 });
2093         assertNotNull(states);
2094         assertEquals(5, states.length);
2095         assertEquals(0, states[0]);
2096         assertEquals(1, states[1]);
2097         assertEquals(2, states[2]);
2098         assertEquals(3, states[3]);
2099         assertEquals(0, states[4]);
2100 
2101         try {
2102             view.mergeDrawableStatesWrapper(new int[] { 1, 2 }, new int[] { 3 });
2103             fail("should throw IndexOutOfBoundsException");
2104         } catch (IndexOutOfBoundsException e) {
2105         }
2106 
2107         try {
2108             view.mergeDrawableStatesWrapper(null, new int[] { 0 });
2109             fail("should throw NullPointerException");
2110         } catch (NullPointerException e) {
2111         }
2112 
2113         try {
2114             view.mergeDrawableStatesWrapper(new int [] { 0 }, null);
2115             fail("should throw NullPointerException");
2116         } catch (NullPointerException e) {
2117         }
2118     }
2119 
testOnSaveAndRestoreInstanceState()2120     public void testOnSaveAndRestoreInstanceState() {
2121         // it is hard to simulate operation to make callback be called.
2122     }
2123 
testSaveAndRestoreHierarchyState()2124     public void testSaveAndRestoreHierarchyState() {
2125         int viewId = R.id.mock_view;
2126         MockView view = (MockView) mActivity.findViewById(viewId);
2127         SparseArray<Parcelable> container = new SparseArray<Parcelable>();
2128         view.saveHierarchyState(container);
2129         assertTrue(view.hasCalledDispatchSaveInstanceState());
2130         assertTrue(view.hasCalledOnSaveInstanceState());
2131         assertEquals(viewId, container.keyAt(0));
2132 
2133         view.reset();
2134         container.put(R.id.mock_view, BaseSavedState.EMPTY_STATE);
2135         view.restoreHierarchyState(container);
2136         assertTrue(view.hasCalledDispatchRestoreInstanceState());
2137         assertTrue(view.hasCalledOnRestoreInstanceState());
2138         container.clear();
2139         view.saveHierarchyState(container);
2140         assertTrue(view.hasCalledDispatchSaveInstanceState());
2141         assertTrue(view.hasCalledOnSaveInstanceState());
2142         assertEquals(viewId, container.keyAt(0));
2143 
2144         container.clear();
2145         container.put(viewId, new android.graphics.Rect());
2146         try {
2147             view.restoreHierarchyState(container);
2148             fail("Parcelable state must be an AbsSaveState, should throw IllegalArgumentException");
2149         } catch (IllegalArgumentException e) {
2150             // expected
2151         }
2152 
2153         try {
2154             view.restoreHierarchyState(null);
2155             fail("Cannot pass null to restoreHierarchyState(), should throw NullPointerException");
2156         } catch (NullPointerException e) {
2157             // expected
2158         }
2159 
2160         try {
2161             view.saveHierarchyState(null);
2162             fail("Cannot pass null to saveHierarchyState(), should throw NullPointerException");
2163         } catch (NullPointerException e) {
2164             // expected
2165         }
2166     }
2167 
testOnKeyDownOrUp()2168     public void testOnKeyDownOrUp() throws Throwable {
2169         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
2170         runTestOnUiThread(new Runnable() {
2171             public void run() {
2172                 view.setFocusable(true);
2173                 view.requestFocus();
2174             }
2175         });
2176         getInstrumentation().waitForIdleSync();
2177         assertTrue(view.isFocused());
2178 
2179         KeyEvent event = new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_0);
2180         getInstrumentation().sendKeySync(event);
2181         assertTrue(view.hasCalledOnKeyDown());
2182 
2183         event = new KeyEvent(KeyEvent.ACTION_UP, KeyEvent.KEYCODE_0);
2184         getInstrumentation().sendKeySync(event);
2185         assertTrue(view.hasCalledOnKeyUp());
2186 
2187         view.reset();
2188         assertTrue(view.isEnabled());
2189         assertFalse(view.isClickable());
2190         assertFalse(view.isPressed());
2191         event = new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_ENTER);
2192         getInstrumentation().sendKeySync(event);
2193         assertFalse(view.isPressed());
2194         assertTrue(view.hasCalledOnKeyDown());
2195 
2196         runTestOnUiThread(new Runnable() {
2197             public void run() {
2198                 view.setEnabled(true);
2199                 view.setClickable(true);
2200             }
2201         });
2202         view.reset();
2203         OnClickListenerImpl listener = new OnClickListenerImpl();
2204         view.setOnClickListener(listener);
2205 
2206         assertFalse(view.isPressed());
2207         event = new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_ENTER);
2208         getInstrumentation().sendKeySync(event);
2209         assertTrue(view.isPressed());
2210         assertTrue(view.hasCalledOnKeyDown());
2211         event = new KeyEvent(KeyEvent.ACTION_UP, KeyEvent.KEYCODE_ENTER);
2212         getInstrumentation().sendKeySync(event);
2213         assertFalse(view.isPressed());
2214         assertTrue(view.hasCalledOnKeyUp());
2215         assertTrue(listener.hasOnClick());
2216 
2217         view.setPressed(false);
2218         listener.reset();
2219         view.reset();
2220 
2221         assertFalse(view.isPressed());
2222         event = new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_DPAD_CENTER);
2223         getInstrumentation().sendKeySync(event);
2224         assertTrue(view.isPressed());
2225         assertTrue(view.hasCalledOnKeyDown());
2226         event = new KeyEvent(KeyEvent.ACTION_UP, KeyEvent.KEYCODE_DPAD_CENTER);
2227         getInstrumentation().sendKeySync(event);
2228         assertFalse(view.isPressed());
2229         assertTrue(view.hasCalledOnKeyUp());
2230         assertTrue(listener.hasOnClick());
2231     }
2232 
2233     @UiThreadTest
testDispatchKeyEvent()2234     public void testDispatchKeyEvent() {
2235         MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
2236         MockView mockView1 = new MockView(mActivity);
2237         MockView mockView2 = new MockView(mActivity);
2238         ViewGroup viewGroup = (ViewGroup) mActivity.findViewById(R.id.viewlayout_root);
2239         viewGroup.addView(mockView1);
2240         viewGroup.addView(mockView2);
2241         view.setFocusable(true);
2242         mockView1.setFocusable(true);
2243         mockView2.setFocusable(true);
2244 
2245         assertFalse(view.hasCalledOnKeyDown());
2246         assertFalse(mockView1.hasCalledOnKeyDown());
2247         assertFalse(mockView2.hasCalledOnKeyDown());
2248         KeyEvent event = new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_0);
2249         assertFalse(view.dispatchKeyEvent(event));
2250         assertTrue(view.hasCalledOnKeyDown());
2251         assertFalse(mockView1.hasCalledOnKeyDown());
2252         assertFalse(mockView2.hasCalledOnKeyDown());
2253 
2254         view.reset();
2255         mockView1.reset();
2256         mockView2.reset();
2257         assertFalse(view.hasCalledOnKeyDown());
2258         assertFalse(mockView1.hasCalledOnKeyDown());
2259         assertFalse(mockView2.hasCalledOnKeyDown());
2260         event = new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_0);
2261         assertFalse(mockView1.dispatchKeyEvent(event));
2262         assertFalse(view.hasCalledOnKeyDown());
2263         // issue 1695243
2264         // When the view has NOT focus, it dispatches to itself, which disobey the javadoc.
2265         assertTrue(mockView1.hasCalledOnKeyDown());
2266         assertFalse(mockView2.hasCalledOnKeyDown());
2267 
2268         assertFalse(view.hasCalledOnKeyUp());
2269         event = new KeyEvent(KeyEvent.ACTION_UP, KeyEvent.KEYCODE_0);
2270         assertFalse(view.dispatchKeyEvent(event));
2271         assertTrue(view.hasCalledOnKeyUp());
2272 
2273         assertFalse(view.hasCalledOnKeyMultiple());
2274         event = new KeyEvent(1, 2, KeyEvent.ACTION_MULTIPLE, KeyEvent.KEYCODE_0, 2);
2275         assertFalse(view.dispatchKeyEvent(event));
2276         assertTrue(view.hasCalledOnKeyMultiple());
2277 
2278         try {
2279             view.dispatchKeyEvent(null);
2280             fail("should throw NullPointerException");
2281         } catch (NullPointerException e) {
2282             // expected
2283         }
2284 
2285         view.reset();
2286         event = new KeyEvent(KeyEvent.ACTION_UP, KeyEvent.KEYCODE_0);
2287         OnKeyListenerImpl listener = new OnKeyListenerImpl();
2288         view.setOnKeyListener(listener);
2289         assertFalse(listener.hasOnKey());
2290         assertTrue(view.dispatchKeyEvent(event));
2291         assertTrue(listener.hasOnKey());
2292         assertFalse(view.hasCalledOnKeyUp());
2293     }
2294 
2295     @UiThreadTest
testDispatchTouchEvent()2296     public void testDispatchTouchEvent() {
2297         ViewGroup viewGroup = (ViewGroup) mActivity.findViewById(R.id.viewlayout_root);
2298         MockView mockView1 = new MockView(mActivity);
2299         MockView mockView2 = new MockView(mActivity);
2300         viewGroup.addView(mockView1);
2301         viewGroup.addView(mockView2);
2302 
2303         int[] xy = new int[2];
2304         mockView1.getLocationOnScreen(xy);
2305 
2306         final int viewWidth = mockView1.getWidth();
2307         final int viewHeight = mockView1.getHeight();
2308         final float x = xy[0] + viewWidth / 2.0f;
2309         final float y = xy[1] + viewHeight / 2.0f;
2310 
2311         long downTime = SystemClock.uptimeMillis();
2312         long eventTime = SystemClock.uptimeMillis();
2313         MotionEvent event = MotionEvent.obtain(downTime, eventTime, MotionEvent.ACTION_MOVE,
2314                 x, y, 0);
2315 
2316         assertFalse(mockView1.hasCalledOnTouchEvent());
2317         assertFalse(mockView1.dispatchTouchEvent(event));
2318         assertTrue(mockView1.hasCalledOnTouchEvent());
2319 
2320         assertFalse(mockView2.hasCalledOnTouchEvent());
2321         assertFalse(mockView2.dispatchTouchEvent(event));
2322         // issue 1695243
2323         // it passes the touch screen motion event down to itself even if it is not the target view.
2324         assertTrue(mockView2.hasCalledOnTouchEvent());
2325 
2326         mockView1.reset();
2327         OnTouchListenerImpl listener = new OnTouchListenerImpl();
2328         mockView1.setOnTouchListener(listener);
2329         assertFalse(listener.hasOnTouch());
2330         assertTrue(mockView1.dispatchTouchEvent(event));
2331         assertTrue(listener.hasOnTouch());
2332         assertFalse(mockView1.hasCalledOnTouchEvent());
2333     }
2334 
testInvalidate1()2335     public void testInvalidate1() throws Throwable {
2336         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
2337         assertTrue(view.hasCalledOnDraw());
2338 
2339         view.reset();
2340         runTestOnUiThread(new Runnable() {
2341             public void run() {
2342                 view.invalidate();
2343             }
2344         });
2345         getInstrumentation().waitForIdleSync();
2346         new PollingCheck() {
2347             @Override
2348             protected boolean check() {
2349                 return view.hasCalledOnDraw();
2350             }
2351         }.run();
2352 
2353         view.reset();
2354         runTestOnUiThread(new Runnable() {
2355             public void run() {
2356                 view.setVisibility(View.INVISIBLE);
2357                 view.invalidate();
2358             }
2359         });
2360         getInstrumentation().waitForIdleSync();
2361         assertFalse(view.hasCalledOnDraw());
2362     }
2363 
testInvalidate2()2364     public void testInvalidate2() throws Throwable {
2365         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
2366         assertTrue(view.hasCalledOnDraw());
2367 
2368         try {
2369             view.invalidate(null);
2370             fail("should throw NullPointerException");
2371         } catch (NullPointerException e) {
2372         }
2373 
2374         view.reset();
2375         final Rect dirty = new Rect(view.getLeft() + 1, view.getTop() + 1,
2376                 view.getLeft() + view.getWidth() / 2, view.getTop() + view.getHeight() / 2);
2377         runTestOnUiThread(new Runnable() {
2378             public void run() {
2379                 view.invalidate(dirty);
2380             }
2381         });
2382         getInstrumentation().waitForIdleSync();
2383         new PollingCheck() {
2384             @Override
2385             protected boolean check() {
2386                 return view.hasCalledOnDraw();
2387             }
2388         }.run();
2389 
2390         view.reset();
2391         runTestOnUiThread(new Runnable() {
2392             public void run() {
2393                 view.setVisibility(View.INVISIBLE);
2394                 view.invalidate(dirty);
2395             }
2396         });
2397         getInstrumentation().waitForIdleSync();
2398         assertFalse(view.hasCalledOnDraw());
2399     }
2400 
testInvalidate3()2401     public void testInvalidate3() throws Throwable {
2402         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
2403         assertTrue(view.hasCalledOnDraw());
2404 
2405         view.reset();
2406         final Rect dirty = new Rect(view.getLeft() + 1, view.getTop() + 1,
2407                 view.getLeft() + view.getWidth() / 2, view.getTop() + view.getHeight() / 2);
2408         runTestOnUiThread(new Runnable() {
2409             public void run() {
2410                 view.invalidate(dirty.left, dirty.top, dirty.right, dirty.bottom);
2411             }
2412         });
2413         getInstrumentation().waitForIdleSync();
2414         new PollingCheck() {
2415             @Override
2416             protected boolean check() {
2417                 return view.hasCalledOnDraw();
2418             }
2419         }.run();
2420 
2421         view.reset();
2422         runTestOnUiThread(new Runnable() {
2423             public void run() {
2424                 view.setVisibility(View.INVISIBLE);
2425                 view.invalidate(dirty.left, dirty.top, dirty.right, dirty.bottom);
2426             }
2427         });
2428         getInstrumentation().waitForIdleSync();
2429         assertFalse(view.hasCalledOnDraw());
2430     }
2431 
testInvalidateDrawable()2432     public void testInvalidateDrawable() throws Throwable {
2433         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
2434         final Drawable d1 = mResources.getDrawable(R.drawable.scenery);
2435         final Drawable d2 = mResources.getDrawable(R.drawable.pass);
2436 
2437         view.reset();
2438         runTestOnUiThread(new Runnable() {
2439             public void run() {
2440                 view.setBackgroundDrawable(d1);
2441                 view.invalidateDrawable(d1);
2442             }
2443         });
2444         getInstrumentation().waitForIdleSync();
2445         new PollingCheck() {
2446             @Override
2447             protected boolean check() {
2448                 return view.hasCalledOnDraw();
2449             }
2450         }.run();
2451 
2452         view.reset();
2453         runTestOnUiThread(new Runnable() {
2454             public void run() {
2455                 view.invalidateDrawable(d2);
2456             }
2457         });
2458         getInstrumentation().waitForIdleSync();
2459         assertFalse(view.hasCalledOnDraw());
2460 
2461         MockView viewTestNull = new MockView(mActivity);
2462         try {
2463             viewTestNull.invalidateDrawable(null);
2464             fail("should throw NullPointerException");
2465         } catch (NullPointerException e) {
2466         }
2467     }
2468 
2469     @UiThreadTest
testOnFocusChanged()2470     public void testOnFocusChanged() {
2471         MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
2472 
2473         mActivity.findViewById(R.id.fit_windows).setFocusable(true);
2474         view.setFocusable(true);
2475         assertFalse(view.hasCalledOnFocusChanged());
2476 
2477         view.requestFocus();
2478         assertTrue(view.hasCalledOnFocusChanged());
2479 
2480         view.reset();
2481         view.clearFocus();
2482         assertTrue(view.hasCalledOnFocusChanged());
2483     }
2484 
testDrawableState()2485     public void testDrawableState() {
2486         MockView view = new MockView(mActivity);
2487         view.setParent(mMockParent);
2488 
2489         assertFalse(view.hasCalledOnCreateDrawableState());
2490         assertTrue(Arrays.equals(MockView.getEnabledStateSet(), view.getDrawableState()));
2491         assertTrue(view.hasCalledOnCreateDrawableState());
2492 
2493         view.reset();
2494         assertFalse(view.hasCalledOnCreateDrawableState());
2495         assertTrue(Arrays.equals(MockView.getEnabledStateSet(), view.getDrawableState()));
2496         assertFalse(view.hasCalledOnCreateDrawableState());
2497 
2498         view.reset();
2499         assertFalse(view.hasCalledDrawableStateChanged());
2500         view.setPressed(true);
2501         assertTrue(view.hasCalledDrawableStateChanged());
2502         assertTrue(Arrays.equals(MockView.getPressedEnabledStateSet(), view.getDrawableState()));
2503         assertTrue(view.hasCalledOnCreateDrawableState());
2504 
2505         view.reset();
2506         mMockParent.reset();
2507         assertFalse(view.hasCalledDrawableStateChanged());
2508         assertFalse(mMockParent.hasChildDrawableStateChanged());
2509         view.refreshDrawableState();
2510         assertTrue(view.hasCalledDrawableStateChanged());
2511         assertTrue(mMockParent.hasChildDrawableStateChanged());
2512         assertTrue(Arrays.equals(MockView.getPressedEnabledStateSet(), view.getDrawableState()));
2513         assertTrue(view.hasCalledOnCreateDrawableState());
2514     }
2515 
testWindowFocusChanged()2516     public void testWindowFocusChanged() {
2517         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
2518 
2519         // Wait until the window has been focused.
2520         new PollingCheck(TIMEOUT_DELTA) {
2521             @Override
2522             protected boolean check() {
2523                 return view.hasWindowFocus();
2524             }
2525         }.run();
2526 
2527         new PollingCheck() {
2528             protected boolean check() {
2529                 return view.hasCalledOnWindowFocusChanged();
2530             }
2531         }.run();
2532 
2533         assertTrue(view.hasCalledOnWindowFocusChanged());
2534         assertTrue(view.hasCalledDispatchWindowFocusChanged());
2535 
2536         view.reset();
2537         assertFalse(view.hasCalledOnWindowFocusChanged());
2538         assertFalse(view.hasCalledDispatchWindowFocusChanged());
2539 
2540         CtsActivity activity = launchActivity("com.android.cts.view", CtsActivity.class, null);
2541 
2542         // Wait until the window lost focus.
2543         new PollingCheck(TIMEOUT_DELTA) {
2544             @Override
2545             protected boolean check() {
2546                 return !view.hasWindowFocus();
2547             }
2548         }.run();
2549 
2550         assertTrue(view.hasCalledOnWindowFocusChanged());
2551         assertTrue(view.hasCalledDispatchWindowFocusChanged());
2552 
2553         activity.finish();
2554     }
2555 
testDraw()2556     public void testDraw() throws Throwable {
2557         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
2558         runTestOnUiThread(new Runnable() {
2559             public void run() {
2560                 view.requestLayout();
2561             }
2562         });
2563         getInstrumentation().waitForIdleSync();
2564 
2565         assertTrue(view.hasCalledOnDraw());
2566         assertTrue(view.hasCalledDispatchDraw());
2567     }
2568 
testRequestFocusFromTouch()2569     public void testRequestFocusFromTouch() {
2570         View view = new View(mActivity);
2571         view.setFocusable(true);
2572         assertFalse(view.isFocused());
2573 
2574         view.requestFocusFromTouch();
2575         assertTrue(view.isFocused());
2576 
2577         view.requestFocusFromTouch();
2578         assertTrue(view.isFocused());
2579     }
2580 
testRequestRectangleOnScreen1()2581     public void testRequestRectangleOnScreen1() {
2582         MockView view = new MockView(mActivity);
2583         Rect rectangle = new Rect(10, 10, 20, 30);
2584         MockViewGroupParent parent = new MockViewGroupParent(mActivity);
2585 
2586         // parent is null
2587         assertFalse(view.requestRectangleOnScreen(rectangle, true));
2588         assertFalse(view.requestRectangleOnScreen(rectangle, false));
2589         assertFalse(view.requestRectangleOnScreen(null, true));
2590 
2591         view.setParent(parent);
2592         view.scrollTo(1, 2);
2593         assertFalse(parent.hasRequestChildRectangleOnScreen());
2594 
2595         assertFalse(view.requestRectangleOnScreen(rectangle, true));
2596         assertTrue(parent.hasRequestChildRectangleOnScreen());
2597 
2598         parent.reset();
2599         view.scrollTo(11, 22);
2600         assertFalse(parent.hasRequestChildRectangleOnScreen());
2601 
2602         assertFalse(view.requestRectangleOnScreen(rectangle, true));
2603         assertTrue(parent.hasRequestChildRectangleOnScreen());
2604 
2605         try {
2606             view.requestRectangleOnScreen(null, true);
2607             fail("should throw NullPointerException");
2608         } catch (NullPointerException e) {
2609         }
2610     }
2611 
testRequestRectangleOnScreen2()2612     public void testRequestRectangleOnScreen2() {
2613         MockView view = new MockView(mActivity);
2614         Rect rectangle = new Rect();
2615         MockViewGroupParent parent = new MockViewGroupParent(mActivity);
2616 
2617         final Rect requestedRect = new Rect();
2618         MockViewGroupParent grandparent = new MockViewGroupParent(mActivity) {
2619             @Override
2620             public boolean requestChildRectangleOnScreen(View child, Rect rectangle,
2621                     boolean immediate) {
2622                 requestedRect.set(rectangle);
2623                 return super.requestChildRectangleOnScreen(child, rectangle, immediate);
2624             }
2625         };
2626 
2627         // parent is null
2628         assertFalse(view.requestRectangleOnScreen(rectangle));
2629         assertFalse(view.requestRectangleOnScreen(null));
2630         assertEquals(0, rectangle.left);
2631         assertEquals(0, rectangle.top);
2632         assertEquals(0, rectangle.right);
2633         assertEquals(0, rectangle.bottom);
2634 
2635         parent.addView(view);
2636         parent.scrollTo(1, 2);
2637         grandparent.addView(parent);
2638 
2639         assertFalse(parent.hasRequestChildRectangleOnScreen());
2640         assertFalse(grandparent.hasRequestChildRectangleOnScreen());
2641 
2642         assertFalse(view.requestRectangleOnScreen(rectangle));
2643 
2644         assertTrue(parent.hasRequestChildRectangleOnScreen());
2645         assertTrue(grandparent.hasRequestChildRectangleOnScreen());
2646 
2647         assertEquals(-1, requestedRect.left);
2648         assertEquals(-2, requestedRect.top);
2649         assertEquals(-1, requestedRect.right);
2650         assertEquals(-2, requestedRect.bottom);
2651 
2652         try {
2653             view.requestRectangleOnScreen(null);
2654             fail("should throw NullPointerException");
2655         } catch (NullPointerException e) {
2656         }
2657     }
2658 
2659     /**
2660      * For the duration of the tap timeout we are in a 'prepressed' state
2661      * to differentiate between taps and touch scrolls.
2662      * Wait at least this long before testing if the view is pressed
2663      * by calling this function.
2664      */
waitPrepressedTimeout()2665     private void waitPrepressedTimeout() {
2666         try {
2667             Thread.sleep(ViewConfiguration.getTapTimeout() + 10);
2668         } catch (InterruptedException e) {
2669             Log.e(LOG_TAG, "waitPrepressedTimeout() interrupted! Test may fail!", e);
2670         }
2671         getInstrumentation().waitForIdleSync();
2672     }
2673 
testOnTouchEvent()2674     public void testOnTouchEvent() throws Throwable {
2675         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
2676 
2677         assertTrue(view.isEnabled());
2678         assertFalse(view.isClickable());
2679         assertFalse(view.isLongClickable());
2680 
2681         TouchUtils.clickView(this, view);
2682         assertTrue(view.hasCalledOnTouchEvent());
2683 
2684         runTestOnUiThread(new Runnable() {
2685             public void run() {
2686                 view.setEnabled(true);
2687                 view.setClickable(true);
2688                 view.setLongClickable(true);
2689             }
2690         });
2691         getInstrumentation().waitForIdleSync();
2692         assertTrue(view.isEnabled());
2693         assertTrue(view.isClickable());
2694         assertTrue(view.isLongClickable());
2695 
2696         // MotionEvent.ACTION_DOWN
2697         int[] xy = new int[2];
2698         view.getLocationOnScreen(xy);
2699 
2700         final int viewWidth = view.getWidth();
2701         final int viewHeight = view.getHeight();
2702         float x = xy[0] + viewWidth / 2.0f;
2703         float y = xy[1] + viewHeight / 2.0f;
2704 
2705         long downTime = SystemClock.uptimeMillis();
2706         long eventTime = SystemClock.uptimeMillis();
2707         MotionEvent event = MotionEvent.obtain(downTime, eventTime, MotionEvent.ACTION_DOWN,
2708                 x, y, 0);
2709         assertFalse(view.isPressed());
2710         getInstrumentation().sendPointerSync(event);
2711         waitPrepressedTimeout();
2712         assertTrue(view.hasCalledOnTouchEvent());
2713         assertTrue(view.isPressed());
2714 
2715         // MotionEvent.ACTION_MOVE
2716         // move out of the bound.
2717         view.reset();
2718         downTime = SystemClock.uptimeMillis();
2719         eventTime = SystemClock.uptimeMillis();
2720         int slop = ViewConfiguration.get(mActivity).getScaledTouchSlop();
2721         x = xy[0] + viewWidth + slop;
2722         y = xy[1] + viewHeight + slop;
2723         event = MotionEvent.obtain(downTime, eventTime, MotionEvent.ACTION_MOVE, x, y, 0);
2724         getInstrumentation().sendPointerSync(event);
2725         assertTrue(view.hasCalledOnTouchEvent());
2726         assertFalse(view.isPressed());
2727 
2728         // move into view
2729         view.reset();
2730         downTime = SystemClock.uptimeMillis();
2731         eventTime = SystemClock.uptimeMillis();
2732         x = xy[0] + viewWidth - 1;
2733         y = xy[1] + viewHeight - 1;
2734         event = MotionEvent.obtain(downTime, eventTime, MotionEvent.ACTION_MOVE, x, y, 0);
2735         getInstrumentation().sendPointerSync(event);
2736         waitPrepressedTimeout();
2737         assertTrue(view.hasCalledOnTouchEvent());
2738         assertFalse(view.isPressed());
2739 
2740         // MotionEvent.ACTION_UP
2741         OnClickListenerImpl listener = new OnClickListenerImpl();
2742         view.setOnClickListener(listener);
2743         view.reset();
2744         downTime = SystemClock.uptimeMillis();
2745         eventTime = SystemClock.uptimeMillis();
2746         event = MotionEvent.obtain(downTime, eventTime, MotionEvent.ACTION_UP, x, y, 0);
2747         getInstrumentation().sendPointerSync(event);
2748         assertTrue(view.hasCalledOnTouchEvent());
2749         assertFalse(listener.hasOnClick());
2750 
2751         view.reset();
2752         x = xy[0] + viewWidth / 2.0f;
2753         y = xy[1] + viewHeight / 2.0f;
2754         downTime = SystemClock.uptimeMillis();
2755         eventTime = SystemClock.uptimeMillis();
2756         event = MotionEvent.obtain(downTime, eventTime, MotionEvent.ACTION_DOWN, x, y, 0);
2757         getInstrumentation().sendPointerSync(event);
2758         assertTrue(view.hasCalledOnTouchEvent());
2759 
2760         // MotionEvent.ACTION_CANCEL
2761         view.reset();
2762         listener.reset();
2763         downTime = SystemClock.uptimeMillis();
2764         eventTime = SystemClock.uptimeMillis();
2765         event = MotionEvent.obtain(downTime, eventTime, MotionEvent.ACTION_CANCEL, x, y, 0);
2766         getInstrumentation().sendPointerSync(event);
2767         assertTrue(view.hasCalledOnTouchEvent());
2768         assertFalse(view.isPressed());
2769         assertFalse(listener.hasOnClick());
2770     }
2771 
testBringToFront()2772     public void testBringToFront() {
2773         MockView view = new MockView(mActivity);
2774         view.setParent(mMockParent);
2775 
2776         assertFalse(mMockParent.hasBroughtChildToFront());
2777         view.bringToFront();
2778         assertTrue(mMockParent.hasBroughtChildToFront());
2779     }
2780 
testGetApplicationWindowToken()2781     public void testGetApplicationWindowToken() {
2782         View view = new View(mActivity);
2783         // mAttachInfo is null
2784         assertNull(view.getApplicationWindowToken());
2785 
2786         // mAttachInfo is not null
2787         view = mActivity.findViewById(R.id.fit_windows);
2788         assertNotNull(view.getApplicationWindowToken());
2789     }
2790 
testGetBottomPaddingOffset()2791     public void testGetBottomPaddingOffset() {
2792         MockView view = new MockView(mActivity);
2793         assertEquals(0, view.getBottomPaddingOffset());
2794     }
2795 
testGetLeftPaddingOffset()2796     public void testGetLeftPaddingOffset() {
2797         MockView view = new MockView(mActivity);
2798         assertEquals(0, view.getLeftPaddingOffset());
2799     }
2800 
testGetRightPaddingOffset()2801     public void testGetRightPaddingOffset() {
2802         MockView view = new MockView(mActivity);
2803         assertEquals(0, view.getRightPaddingOffset());
2804     }
2805 
testGetTopPaddingOffset()2806     public void testGetTopPaddingOffset() {
2807         MockView view = new MockView(mActivity);
2808         assertEquals(0, view.getTopPaddingOffset());
2809     }
2810 
testIsPaddingOffsetRequired()2811     public void testIsPaddingOffsetRequired() {
2812         MockView view = new MockView(mActivity);
2813         assertFalse(view.isPaddingOffsetRequired());
2814     }
2815 
2816     @UiThreadTest
testPadding()2817     public void testPadding() {
2818         MockView view = (MockView) mActivity.findViewById(R.id.mock_view_padding_full);
2819         Drawable background = view.getBackground();
2820         Rect backgroundPadding = new Rect();
2821         background.getPadding(backgroundPadding);
2822 
2823         // There is some background with a non null padding
2824         assertNotNull(background);
2825         assertTrue(backgroundPadding.left != 0);
2826         assertTrue(backgroundPadding.right != 0);
2827         assertTrue(backgroundPadding.top != 0);
2828         assertTrue(backgroundPadding.bottom != 0);
2829 
2830         // The XML defines android:padding="0dp" and that should be the resulting padding
2831         assertEquals(0, view.getPaddingLeft());
2832         assertEquals(0, view.getPaddingTop());
2833         assertEquals(0, view.getPaddingRight());
2834         assertEquals(0, view.getPaddingBottom());
2835 
2836         // LEFT case
2837         view = (MockView) mActivity.findViewById(R.id.mock_view_padding_left);
2838         background = view.getBackground();
2839         backgroundPadding = new Rect();
2840         background.getPadding(backgroundPadding);
2841 
2842         // There is some background with a non null padding
2843         assertNotNull(background);
2844         assertTrue(backgroundPadding.left != 0);
2845         assertTrue(backgroundPadding.right != 0);
2846         assertTrue(backgroundPadding.top != 0);
2847         assertTrue(backgroundPadding.bottom != 0);
2848 
2849         // The XML defines android:paddingLeft="0dp" and that should be the resulting padding
2850         assertEquals(0, view.getPaddingLeft());
2851         assertEquals(backgroundPadding.top, view.getPaddingTop());
2852         assertEquals(backgroundPadding.right, view.getPaddingRight());
2853         assertEquals(backgroundPadding.bottom, view.getPaddingBottom());
2854 
2855         // RIGHT case
2856         view = (MockView) mActivity.findViewById(R.id.mock_view_padding_right);
2857         background = view.getBackground();
2858         backgroundPadding = new Rect();
2859         background.getPadding(backgroundPadding);
2860 
2861         // There is some background with a non null padding
2862         assertNotNull(background);
2863         assertTrue(backgroundPadding.left != 0);
2864         assertTrue(backgroundPadding.right != 0);
2865         assertTrue(backgroundPadding.top != 0);
2866         assertTrue(backgroundPadding.bottom != 0);
2867 
2868         // The XML defines android:paddingRight="0dp" and that should be the resulting padding
2869         assertEquals(backgroundPadding.left, view.getPaddingLeft());
2870         assertEquals(backgroundPadding.top, view.getPaddingTop());
2871         assertEquals(0, view.getPaddingRight());
2872         assertEquals(backgroundPadding.bottom, view.getPaddingBottom());
2873 
2874         // TOP case
2875         view = (MockView) mActivity.findViewById(R.id.mock_view_padding_top);
2876         background = view.getBackground();
2877         backgroundPadding = new Rect();
2878         background.getPadding(backgroundPadding);
2879 
2880         // There is some background with a non null padding
2881         assertNotNull(background);
2882         assertTrue(backgroundPadding.left != 0);
2883         assertTrue(backgroundPadding.right != 0);
2884         assertTrue(backgroundPadding.top != 0);
2885         assertTrue(backgroundPadding.bottom != 0);
2886 
2887         // The XML defines android:paddingTop="0dp" and that should be the resulting padding
2888         assertEquals(backgroundPadding.left, view.getPaddingLeft());
2889         assertEquals(0, view.getPaddingTop());
2890         assertEquals(backgroundPadding.right, view.getPaddingRight());
2891         assertEquals(backgroundPadding.bottom, view.getPaddingBottom());
2892 
2893         // BOTTOM case
2894         view = (MockView) mActivity.findViewById(R.id.mock_view_padding_bottom);
2895         background = view.getBackground();
2896         backgroundPadding = new Rect();
2897         background.getPadding(backgroundPadding);
2898 
2899         // There is some background with a non null padding
2900         assertNotNull(background);
2901         assertTrue(backgroundPadding.left != 0);
2902         assertTrue(backgroundPadding.right != 0);
2903         assertTrue(backgroundPadding.top != 0);
2904         assertTrue(backgroundPadding.bottom != 0);
2905 
2906         // The XML defines android:paddingBottom="0dp" and that should be the resulting padding
2907         assertEquals(backgroundPadding.left, view.getPaddingLeft());
2908         assertEquals(backgroundPadding.top, view.getPaddingTop());
2909         assertEquals(backgroundPadding.right, view.getPaddingRight());
2910         assertEquals(0, view.getPaddingBottom());
2911 
2912         // Case for interleaved background/padding changes
2913         view = (MockView) mActivity.findViewById(R.id.mock_view_padding_runtime_updated);
2914         background = view.getBackground();
2915         backgroundPadding = new Rect();
2916         background.getPadding(backgroundPadding);
2917 
2918         // There is some background with a null padding
2919         assertNotNull(background);
2920         assertTrue(backgroundPadding.left == 0);
2921         assertTrue(backgroundPadding.right == 0);
2922         assertTrue(backgroundPadding.top == 0);
2923         assertTrue(backgroundPadding.bottom == 0);
2924 
2925         final int paddingLeft = view.getPaddingLeft();
2926         final int paddingRight = view.getPaddingRight();
2927         final int paddingTop = view.getPaddingTop();
2928         final int paddingBottom = view.getPaddingBottom();
2929         assertEquals(8, paddingLeft);
2930         assertEquals(0, paddingTop);
2931         assertEquals(8, paddingRight);
2932         assertEquals(0, paddingBottom);
2933 
2934         // Manipulate background and padding
2935         background.setState(view.getDrawableState());
2936         background.jumpToCurrentState();
2937         view.setBackground(background);
2938         view.setPadding(paddingLeft, paddingTop, paddingRight, paddingBottom);
2939 
2940         assertEquals(8, view.getPaddingLeft());
2941         assertEquals(0, view.getPaddingTop());
2942         assertEquals(8, view.getPaddingRight());
2943         assertEquals(0, view.getPaddingBottom());
2944     }
2945 
testGetWindowVisibleDisplayFrame()2946     public void testGetWindowVisibleDisplayFrame() {
2947         Rect outRect = new Rect();
2948         View view = new View(mActivity);
2949         // mAttachInfo is null
2950         WindowManager wm = (WindowManager)mActivity.getSystemService(Context.WINDOW_SERVICE);
2951         Display d = wm.getDefaultDisplay();
2952         view.getWindowVisibleDisplayFrame(outRect);
2953         assertEquals(0, outRect.left);
2954         assertEquals(0, outRect.top);
2955         assertEquals(d.getWidth(), outRect.right);
2956         assertEquals(d.getHeight(), outRect.bottom);
2957 
2958         // mAttachInfo is not null
2959         outRect = new Rect();
2960         view = mActivity.findViewById(R.id.fit_windows);
2961         // it's implementation detail
2962         view.getWindowVisibleDisplayFrame(outRect);
2963     }
2964 
testSetScrollContainer()2965     public void testSetScrollContainer() throws Throwable {
2966         final MockView mockView = (MockView) mActivity.findViewById(R.id.mock_view);
2967         final MockView scrollView = (MockView) mActivity.findViewById(R.id.scroll_view);
2968         Bitmap bitmap = Bitmap.createBitmap(200, 300, Bitmap.Config.RGB_565);
2969         final BitmapDrawable d = new BitmapDrawable(bitmap);
2970         final InputMethodManager imm = (InputMethodManager)getActivity().getSystemService(
2971                 Context.INPUT_METHOD_SERVICE);
2972         final LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(300, 500);
2973         runTestOnUiThread(new Runnable() {
2974             public void run() {
2975                 mockView.setBackgroundDrawable(d);
2976                 mockView.setHorizontalFadingEdgeEnabled(true);
2977                 mockView.setVerticalFadingEdgeEnabled(true);
2978                 mockView.setLayoutParams(layoutParams);
2979                 scrollView.setLayoutParams(layoutParams);
2980 
2981                 mockView.setFocusable(true);
2982                 mockView.requestFocus();
2983                 mockView.setScrollContainer(true);
2984                 scrollView.setScrollContainer(false);
2985                 imm.showSoftInput(mockView, 0);
2986             }
2987         });
2988         getInstrumentation().waitForIdleSync();
2989 
2990         // FIXME: why the size of view doesn't change?
2991 
2992         runTestOnUiThread(new Runnable() {
2993             public void run() {
2994                 imm.hideSoftInputFromInputMethod(mockView.getWindowToken(), 0);
2995             }
2996         });
2997         getInstrumentation().waitForIdleSync();
2998     }
2999 
testTouchMode()3000     public void testTouchMode() throws Throwable {
3001         final MockView mockView = (MockView) mActivity.findViewById(R.id.mock_view);
3002         final View fitWindowsView = mActivity.findViewById(R.id.fit_windows);
3003         runTestOnUiThread(new Runnable() {
3004             public void run() {
3005                 mockView.setFocusableInTouchMode(true);
3006                 fitWindowsView.setFocusable(true);
3007                 fitWindowsView.requestFocus();
3008             }
3009         });
3010         getInstrumentation().waitForIdleSync();
3011         assertTrue(mockView.isFocusableInTouchMode());
3012         assertFalse(fitWindowsView.isFocusableInTouchMode());
3013         assertTrue(mockView.isFocusable());
3014         assertTrue(fitWindowsView.isFocusable());
3015         assertFalse(mockView.isFocused());
3016         assertTrue(fitWindowsView.isFocused());
3017         assertFalse(mockView.isInTouchMode());
3018         assertFalse(fitWindowsView.isInTouchMode());
3019 
3020         TouchUtils.tapView(this, mockView);
3021         assertFalse(fitWindowsView.isFocused());
3022         assertFalse(mockView.isFocused());
3023         runTestOnUiThread(new Runnable() {
3024             public void run() {
3025                 mockView.requestFocus();
3026             }
3027         });
3028         getInstrumentation().waitForIdleSync();
3029         assertTrue(mockView.isFocused());
3030         runTestOnUiThread(new Runnable() {
3031             public void run() {
3032                 fitWindowsView.requestFocus();
3033             }
3034         });
3035         getInstrumentation().waitForIdleSync();
3036         assertFalse(fitWindowsView.isFocused());
3037         assertTrue(mockView.isInTouchMode());
3038         assertTrue(fitWindowsView.isInTouchMode());
3039 
3040         KeyEvent keyEvent = new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_0);
3041         getInstrumentation().sendKeySync(keyEvent);
3042         assertTrue(mockView.isFocused());
3043         assertFalse(fitWindowsView.isFocused());
3044         runTestOnUiThread(new Runnable() {
3045             public void run() {
3046                 fitWindowsView.requestFocus();
3047             }
3048         });
3049         getInstrumentation().waitForIdleSync();
3050         assertFalse(mockView.isFocused());
3051         assertTrue(fitWindowsView.isFocused());
3052         assertFalse(mockView.isInTouchMode());
3053         assertFalse(fitWindowsView.isInTouchMode());
3054     }
3055 
3056     @UiThreadTest
testScrollbarStyle()3057     public void testScrollbarStyle() {
3058         MockView view = (MockView) mActivity.findViewById(R.id.scroll_view);
3059         Bitmap bitmap = Bitmap.createBitmap(200, 300, Bitmap.Config.RGB_565);
3060         BitmapDrawable d = new BitmapDrawable(bitmap);
3061         view.setBackgroundDrawable(d);
3062         view.setHorizontalFadingEdgeEnabled(true);
3063         view.setVerticalFadingEdgeEnabled(true);
3064 
3065         assertTrue(view.isHorizontalScrollBarEnabled());
3066         assertTrue(view.isVerticalScrollBarEnabled());
3067         int verticalScrollBarWidth = view.getVerticalScrollbarWidth();
3068         int horizontalScrollBarHeight = view.getHorizontalScrollbarHeight();
3069         assertTrue(verticalScrollBarWidth > 0);
3070         assertTrue(horizontalScrollBarHeight > 0);
3071         assertEquals(0, view.getPaddingRight());
3072         assertEquals(0, view.getPaddingBottom());
3073 
3074         view.setScrollBarStyle(View.SCROLLBARS_INSIDE_INSET);
3075         assertEquals(View.SCROLLBARS_INSIDE_INSET, view.getScrollBarStyle());
3076         assertEquals(verticalScrollBarWidth, view.getPaddingRight());
3077         assertEquals(horizontalScrollBarHeight, view.getPaddingBottom());
3078 
3079         view.setScrollBarStyle(View.SCROLLBARS_OUTSIDE_OVERLAY);
3080         assertEquals(View.SCROLLBARS_OUTSIDE_OVERLAY, view.getScrollBarStyle());
3081         assertEquals(0, view.getPaddingRight());
3082         assertEquals(0, view.getPaddingBottom());
3083 
3084         view.setScrollBarStyle(View.SCROLLBARS_OUTSIDE_INSET);
3085         assertEquals(View.SCROLLBARS_OUTSIDE_INSET, view.getScrollBarStyle());
3086         assertEquals(verticalScrollBarWidth, view.getPaddingRight());
3087         assertEquals(horizontalScrollBarHeight, view.getPaddingBottom());
3088 
3089         // TODO: how to get the position of the Scrollbar to assert it is inside or outside.
3090     }
3091 
3092     @UiThreadTest
testScrollFading()3093     public void testScrollFading() {
3094         MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
3095         Bitmap bitmap = Bitmap.createBitmap(200, 300, Bitmap.Config.RGB_565);
3096         BitmapDrawable d = new BitmapDrawable(bitmap);
3097         view.setBackgroundDrawable(d);
3098 
3099         assertFalse(view.isHorizontalFadingEdgeEnabled());
3100         assertFalse(view.isVerticalFadingEdgeEnabled());
3101         assertEquals(0, view.getHorizontalFadingEdgeLength());
3102         assertEquals(0, view.getVerticalFadingEdgeLength());
3103 
3104         view.setHorizontalFadingEdgeEnabled(true);
3105         view.setVerticalFadingEdgeEnabled(true);
3106         assertTrue(view.isHorizontalFadingEdgeEnabled());
3107         assertTrue(view.isVerticalFadingEdgeEnabled());
3108         assertTrue(view.getHorizontalFadingEdgeLength() > 0);
3109         assertTrue(view.getVerticalFadingEdgeLength() > 0);
3110 
3111         final int fadingLength = 20;
3112         view.setFadingEdgeLength(fadingLength);
3113         assertEquals(fadingLength, view.getHorizontalFadingEdgeLength());
3114         assertEquals(fadingLength, view.getVerticalFadingEdgeLength());
3115     }
3116 
3117     @UiThreadTest
testScrolling()3118     public void testScrolling() {
3119         MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
3120         view.reset();
3121         assertEquals(0, view.getScrollX());
3122         assertEquals(0, view.getScrollY());
3123         assertFalse(view.hasCalledOnScrollChanged());
3124 
3125         view.scrollTo(0, 0);
3126         assertEquals(0, view.getScrollX());
3127         assertEquals(0, view.getScrollY());
3128         assertFalse(view.hasCalledOnScrollChanged());
3129 
3130         view.scrollBy(0, 0);
3131         assertEquals(0, view.getScrollX());
3132         assertEquals(0, view.getScrollY());
3133         assertFalse(view.hasCalledOnScrollChanged());
3134 
3135         view.scrollTo(10, 100);
3136         assertEquals(10, view.getScrollX());
3137         assertEquals(100, view.getScrollY());
3138         assertTrue(view.hasCalledOnScrollChanged());
3139 
3140         view.reset();
3141         assertFalse(view.hasCalledOnScrollChanged());
3142         view.scrollBy(-10, -100);
3143         assertEquals(0, view.getScrollX());
3144         assertEquals(0, view.getScrollY());
3145         assertTrue(view.hasCalledOnScrollChanged());
3146 
3147         view.reset();
3148         assertFalse(view.hasCalledOnScrollChanged());
3149         view.scrollTo(-1, -2);
3150         assertEquals(-1, view.getScrollX());
3151         assertEquals(-2, view.getScrollY());
3152         assertTrue(view.hasCalledOnScrollChanged());
3153     }
3154 
testInitializeScrollbarsAndFadingEdge()3155     public void testInitializeScrollbarsAndFadingEdge() {
3156         MockView view = (MockView) mActivity.findViewById(R.id.scroll_view);
3157 
3158         assertTrue(view.isHorizontalScrollBarEnabled());
3159         assertTrue(view.isVerticalScrollBarEnabled());
3160         assertFalse(view.isHorizontalFadingEdgeEnabled());
3161         assertFalse(view.isVerticalFadingEdgeEnabled());
3162 
3163         view = (MockView) mActivity.findViewById(R.id.scroll_view_2);
3164         final int fadingEdgeLength = 20;
3165 
3166         assertTrue(view.isHorizontalScrollBarEnabled());
3167         assertTrue(view.isVerticalScrollBarEnabled());
3168         assertTrue(view.isHorizontalFadingEdgeEnabled());
3169         assertTrue(view.isVerticalFadingEdgeEnabled());
3170         assertEquals(fadingEdgeLength, view.getHorizontalFadingEdgeLength());
3171         assertEquals(fadingEdgeLength, view.getVerticalFadingEdgeLength());
3172     }
3173 
3174     @UiThreadTest
testScrollIndicators()3175     public void testScrollIndicators() {
3176         MockView view = (MockView) mActivity.findViewById(R.id.scroll_view);
3177 
3178         assertEquals("Set indicators match those specified in XML",
3179                 View.SCROLL_INDICATOR_TOP | View.SCROLL_INDICATOR_BOTTOM,
3180                 view.getScrollIndicators());
3181 
3182         view.setScrollIndicators(0);
3183         assertEquals("Cleared indicators", 0, view.getScrollIndicators());
3184 
3185         view.setScrollIndicators(View.SCROLL_INDICATOR_START | View.SCROLL_INDICATOR_RIGHT);
3186         assertEquals("Set start and right indicators",
3187                 View.SCROLL_INDICATOR_START | View.SCROLL_INDICATOR_RIGHT,
3188                 view.getScrollIndicators());
3189 
3190     }
3191 
testOnStartAndFinishTemporaryDetach()3192     public void testOnStartAndFinishTemporaryDetach() throws Throwable {
3193         final MockListView listView = new MockListView(mActivity);
3194         List<String> items = new ArrayList<>();
3195         items.add("1");
3196         items.add("2");
3197         items.add("3");
3198         final Adapter<String> adapter = new Adapter<String>(mActivity, 0, items);
3199 
3200         runTestOnUiThread(new Runnable() {
3201             public void run() {
3202                 mActivity.setContentView(listView);
3203                 listView.setAdapter(adapter);
3204             }
3205         });
3206         getInstrumentation().waitForIdleSync();
3207         final MockView focusChild = (MockView) listView.getChildAt(0);
3208 
3209         runTestOnUiThread(new Runnable() {
3210             public void run() {
3211                 focusChild.requestFocus();
3212             }
3213         });
3214         getInstrumentation().waitForIdleSync();
3215         assertTrue(listView.getChildAt(0).isFocused());
3216 
3217         runTestOnUiThread(new Runnable() {
3218             public void run() {
3219                 listView.detachViewFromParent(focusChild);
3220             }
3221         });
3222         getInstrumentation().waitForIdleSync();
3223         assertFalse(listView.hasCalledOnStartTemporaryDetach());
3224         assertFalse(listView.hasCalledOnFinishTemporaryDetach());
3225     }
3226 
3227     private static class MockListView extends ListView {
3228         private boolean mCalledOnStartTemporaryDetach = false;
3229         private boolean mCalledOnFinishTemporaryDetach = false;
3230 
MockListView(Context context)3231         public MockListView(Context context) {
3232             super(context);
3233         }
3234 
3235         @Override
detachViewFromParent(View child)3236         protected void detachViewFromParent(View child) {
3237             super.detachViewFromParent(child);
3238         }
3239 
3240         @Override
onFinishTemporaryDetach()3241         public void onFinishTemporaryDetach() {
3242             super.onFinishTemporaryDetach();
3243             mCalledOnFinishTemporaryDetach = true;
3244         }
3245 
hasCalledOnFinishTemporaryDetach()3246         public boolean hasCalledOnFinishTemporaryDetach() {
3247             return mCalledOnFinishTemporaryDetach;
3248         }
3249 
3250         @Override
onStartTemporaryDetach()3251         public void onStartTemporaryDetach() {
3252             super.onStartTemporaryDetach();
3253             mCalledOnStartTemporaryDetach = true;
3254         }
3255 
hasCalledOnStartTemporaryDetach()3256         public boolean hasCalledOnStartTemporaryDetach() {
3257             return mCalledOnStartTemporaryDetach;
3258         }
3259 
reset()3260         public void reset() {
3261             mCalledOnStartTemporaryDetach = false;
3262             mCalledOnFinishTemporaryDetach = false;
3263         }
3264     }
3265 
3266     private static class Adapter<T> extends ArrayAdapter<T> {
3267         ArrayList<MockView> views = new ArrayList<MockView>();
3268 
Adapter(Context context, int textViewResourceId, List<T> objects)3269         public Adapter(Context context, int textViewResourceId, List<T> objects) {
3270             super(context, textViewResourceId, objects);
3271             for (int i = 0; i < objects.size(); i++) {
3272                 views.add(new MockView(context));
3273                 views.get(i).setFocusable(true);
3274             }
3275         }
3276 
3277         @Override
getCount()3278         public int getCount() {
3279             return views.size();
3280         }
3281 
3282         @Override
getItemId(int position)3283         public long getItemId(int position) {
3284             return position;
3285         }
3286 
3287         @Override
getView(int position, View convertView, ViewGroup parent)3288         public View getView(int position, View convertView, ViewGroup parent) {
3289             return views.get(position);
3290         }
3291     }
3292 
testKeyPreIme()3293     public void testKeyPreIme() throws Throwable {
3294         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
3295 
3296         runTestOnUiThread(new Runnable() {
3297             public void run() {
3298                 view.setFocusable(true);
3299                 view.requestFocus();
3300             }
3301         });
3302         getInstrumentation().waitForIdleSync();
3303 
3304         getInstrumentation().sendKeySync(new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_BACK));
3305         assertTrue(view.hasCalledDispatchKeyEventPreIme());
3306         assertTrue(view.hasCalledOnKeyPreIme());
3307     }
3308 
testHapticFeedback()3309     public void testHapticFeedback() {
3310         Vibrator vib = (Vibrator) mActivity.getSystemService(Context.VIBRATOR_SERVICE);
3311         boolean hasVibrator = vib.hasVibrator();
3312 
3313         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
3314         final int LONG_PRESS = HapticFeedbackConstants.LONG_PRESS;
3315         final int FLAG_IGNORE_VIEW_SETTING = HapticFeedbackConstants.FLAG_IGNORE_VIEW_SETTING;
3316         final int FLAG_IGNORE_GLOBAL_SETTING = HapticFeedbackConstants.FLAG_IGNORE_GLOBAL_SETTING;
3317         final int ALWAYS = FLAG_IGNORE_VIEW_SETTING | FLAG_IGNORE_GLOBAL_SETTING;
3318 
3319         view.setHapticFeedbackEnabled(false);
3320         assertFalse(view.isHapticFeedbackEnabled());
3321         assertFalse(view.performHapticFeedback(LONG_PRESS));
3322         assertFalse(view.performHapticFeedback(LONG_PRESS, FLAG_IGNORE_GLOBAL_SETTING));
3323         assertEquals(hasVibrator, view.performHapticFeedback(LONG_PRESS, ALWAYS));
3324 
3325         view.setHapticFeedbackEnabled(true);
3326         assertTrue(view.isHapticFeedbackEnabled());
3327         assertEquals(hasVibrator, view.performHapticFeedback(LONG_PRESS, FLAG_IGNORE_GLOBAL_SETTING));
3328     }
3329 
testInputConnection()3330     public void testInputConnection() throws Throwable {
3331         final InputMethodManager imm = (InputMethodManager)getActivity().getSystemService(
3332                 Context.INPUT_METHOD_SERVICE);
3333         final MockView view = (MockView) mActivity.findViewById(R.id.mock_view);
3334         final ViewGroup viewGroup = (ViewGroup) mActivity.findViewById(R.id.viewlayout_root);
3335         final MockEditText editText = new MockEditText(mActivity);
3336 
3337         runTestOnUiThread(new Runnable() {
3338             @Override
3339             public void run() {
3340                 viewGroup.addView(editText);
3341                 editText.requestFocus();
3342             }
3343         });
3344         getInstrumentation().waitForIdleSync();
3345         assertTrue(editText.isFocused());
3346 
3347         runTestOnUiThread(new Runnable() {
3348             @Override
3349             public void run() {
3350                 imm.showSoftInput(editText, 0);
3351             }
3352         });
3353         getInstrumentation().waitForIdleSync();
3354 
3355         new PollingCheck(TIMEOUT_DELTA) {
3356             @Override
3357             protected boolean check() {
3358                 return editText.hasCalledOnCreateInputConnection();
3359             }
3360         }.run();
3361 
3362         assertTrue(editText.hasCalledOnCheckIsTextEditor());
3363 
3364         runTestOnUiThread(new Runnable() {
3365             @Override
3366             public void run() {
3367                 assertTrue(imm.isActive(editText));
3368                 assertFalse(editText.hasCalledCheckInputConnectionProxy());
3369                 imm.isActive(view);
3370                 assertTrue(editText.hasCalledCheckInputConnectionProxy());
3371             }
3372         });
3373     }
3374 
testFilterTouchesWhenObscured()3375     public void testFilterTouchesWhenObscured() throws Throwable {
3376         OnTouchListenerImpl touchListener = new OnTouchListenerImpl();
3377         View view = new View(mActivity);
3378         view.setOnTouchListener(touchListener);
3379 
3380         MotionEvent.PointerProperties[] props = new MotionEvent.PointerProperties[] {
3381                 new MotionEvent.PointerProperties()
3382         };
3383         MotionEvent.PointerCoords[] coords = new MotionEvent.PointerCoords[] {
3384                 new MotionEvent.PointerCoords()
3385         };
3386         MotionEvent obscuredTouch = MotionEvent.obtain(0, 0, MotionEvent.ACTION_DOWN,
3387                 1, props, coords, 0, 0, 0, 0, -1, 0, InputDevice.SOURCE_TOUCHSCREEN,
3388                 MotionEvent.FLAG_WINDOW_IS_OBSCURED);
3389         MotionEvent unobscuredTouch = MotionEvent.obtain(0, 0, MotionEvent.ACTION_DOWN,
3390                 1, props, coords, 0, 0, 0, 0, -1, 0, InputDevice.SOURCE_TOUCHSCREEN,
3391                 0);
3392 
3393         // Initially filter touches is false so all touches are dispatched.
3394         assertFalse(view.getFilterTouchesWhenObscured());
3395 
3396         view.dispatchTouchEvent(unobscuredTouch);
3397         assertTrue(touchListener.hasOnTouch());
3398         touchListener.reset();
3399         view.dispatchTouchEvent(obscuredTouch);
3400         assertTrue(touchListener.hasOnTouch());
3401         touchListener.reset();
3402 
3403         // Set filter touches to true so only unobscured touches are dispatched.
3404         view.setFilterTouchesWhenObscured(true);
3405         assertTrue(view.getFilterTouchesWhenObscured());
3406 
3407         view.dispatchTouchEvent(unobscuredTouch);
3408         assertTrue(touchListener.hasOnTouch());
3409         touchListener.reset();
3410         view.dispatchTouchEvent(obscuredTouch);
3411         assertFalse(touchListener.hasOnTouch());
3412         touchListener.reset();
3413 
3414         // Set filter touches to false so all touches are dispatched.
3415         view.setFilterTouchesWhenObscured(false);
3416         assertFalse(view.getFilterTouchesWhenObscured());
3417 
3418         view.dispatchTouchEvent(unobscuredTouch);
3419         assertTrue(touchListener.hasOnTouch());
3420         touchListener.reset();
3421         view.dispatchTouchEvent(obscuredTouch);
3422         assertTrue(touchListener.hasOnTouch());
3423         touchListener.reset();
3424     }
3425 
testBackgroundTint()3426     public void testBackgroundTint() {
3427         View inflatedView = mActivity.findViewById(R.id.background_tint);
3428 
3429         assertEquals("Background tint inflated correctly",
3430                 Color.WHITE, inflatedView.getBackgroundTintList().getDefaultColor());
3431         assertEquals("Background tint mode inflated correctly",
3432                 PorterDuff.Mode.SRC_OVER, inflatedView.getBackgroundTintMode());
3433 
3434         MockDrawable bg = new MockDrawable();
3435         View view = new View(mActivity);
3436 
3437         view.setBackground(bg);
3438         assertFalse("No background tint applied by default", bg.hasCalledSetTint());
3439 
3440         view.setBackgroundTintList(ColorStateList.valueOf(Color.WHITE));
3441         assertTrue("Background tint applied when setBackgroundTints() called after setBackground()",
3442                 bg.hasCalledSetTint());
3443 
3444         bg.reset();
3445         view.setBackground(null);
3446         view.setBackground(bg);
3447         assertTrue("Background tint applied when setBackgroundTints() called before setBackground()",
3448                 bg.hasCalledSetTint());
3449     }
3450 
testStartActionModeWithParent()3451     public void testStartActionModeWithParent() {
3452         View view = new View(mActivity);
3453         MockViewGroup parent = new MockViewGroup(mActivity);
3454         parent.addView(view);
3455 
3456         ActionMode mode = view.startActionMode(null);
3457 
3458         assertNotNull(mode);
3459         assertEquals(NO_OP_ACTION_MODE, mode);
3460         assertTrue(parent.isStartActionModeForChildCalled);
3461         assertEquals(ActionMode.TYPE_PRIMARY, parent.startActionModeForChildType);
3462     }
3463 
testStartActionModeWithoutParent()3464     public void testStartActionModeWithoutParent() {
3465         View view = new View(mActivity);
3466 
3467         ActionMode mode = view.startActionMode(null);
3468 
3469         assertNull(mode);
3470     }
3471 
testStartActionModeTypedWithParent()3472     public void testStartActionModeTypedWithParent() {
3473         View view = new View(mActivity);
3474         MockViewGroup parent = new MockViewGroup(mActivity);
3475         parent.addView(view);
3476 
3477         ActionMode mode = view.startActionMode(null, ActionMode.TYPE_FLOATING);
3478 
3479         assertNotNull(mode);
3480         assertEquals(NO_OP_ACTION_MODE, mode);
3481         assertTrue(parent.isStartActionModeForChildCalled);
3482         assertEquals(ActionMode.TYPE_FLOATING, parent.startActionModeForChildType);
3483     }
3484 
testStartActionModeTypedWithoutParent()3485     public void testStartActionModeTypedWithoutParent() {
3486         View view = new View(mActivity);
3487 
3488         ActionMode mode = view.startActionMode(null, ActionMode.TYPE_FLOATING);
3489 
3490         assertNull(mode);
3491     }
3492 
3493     private static class MockViewGroup extends ViewGroup {
3494         boolean isStartActionModeForChildCalled = false;
3495         int startActionModeForChildType = ActionMode.TYPE_PRIMARY;
3496 
MockViewGroup(Context context)3497         public MockViewGroup(Context context) {
3498             super(context);
3499         }
3500 
3501         @Override
startActionModeForChild(View originalView, ActionMode.Callback callback)3502         public ActionMode startActionModeForChild(View originalView, ActionMode.Callback callback) {
3503             isStartActionModeForChildCalled = true;
3504             startActionModeForChildType = ActionMode.TYPE_PRIMARY;
3505             return NO_OP_ACTION_MODE;
3506         }
3507 
3508         @Override
startActionModeForChild( View originalView, ActionMode.Callback callback, int type)3509         public ActionMode startActionModeForChild(
3510                 View originalView, ActionMode.Callback callback, int type) {
3511             isStartActionModeForChildCalled = true;
3512             startActionModeForChildType = type;
3513             return NO_OP_ACTION_MODE;
3514         }
3515 
3516         @Override
onLayout(boolean changed, int l, int t, int r, int b)3517         protected void onLayout(boolean changed, int l, int t, int r, int b) {
3518             // no-op
3519         }
3520     }
3521 
3522     private static final ActionMode NO_OP_ACTION_MODE =
3523             new ActionMode() {
3524                 @Override
3525                 public void setTitle(CharSequence title) {}
3526 
3527                 @Override
3528                 public void setTitle(int resId) {}
3529 
3530                 @Override
3531                 public void setSubtitle(CharSequence subtitle) {}
3532 
3533                 @Override
3534                 public void setSubtitle(int resId) {}
3535 
3536                 @Override
3537                 public void setCustomView(View view) {}
3538 
3539                 @Override
3540                 public void invalidate() {}
3541 
3542                 @Override
3543                 public void finish() {}
3544 
3545                 @Override
3546                 public Menu getMenu() {
3547                     return null;
3548                 }
3549 
3550                 @Override
3551                 public CharSequence getTitle() {
3552                     return null;
3553                 }
3554 
3555                 @Override
3556                 public CharSequence getSubtitle() {
3557                     return null;
3558                 }
3559 
3560                 @Override
3561                 public View getCustomView() {
3562                     return null;
3563                 }
3564 
3565                 @Override
3566                 public MenuInflater getMenuInflater() {
3567                     return null;
3568                 }
3569             };
3570 
testTranslationSetter()3571     public void testTranslationSetter() {
3572         View view = new View(mActivity);
3573         float offset = 10.0f;
3574         view.setTranslationX(offset);
3575         view.setTranslationY(offset);
3576         view.setTranslationZ(offset);
3577         view.setElevation(offset);
3578 
3579         assertEquals("Incorrect translationX", offset, view.getTranslationX());
3580         assertEquals("Incorrect translationY", offset, view.getTranslationY());
3581         assertEquals("Incorrect translationZ", offset, view.getTranslationZ());
3582         assertEquals("Incorrect elevation", offset, view.getElevation());
3583     }
3584 
testXYZ()3585     public void testXYZ() {
3586         View view = new View(mActivity);
3587         float offset = 10.0f;
3588         float start = 15.0f;
3589         view.setTranslationX(offset);
3590         view.setLeft((int) start);
3591         view.setTranslationY(offset);
3592         view.setTop((int) start);
3593         view.setTranslationZ(offset);
3594         view.setElevation(start);
3595 
3596         assertEquals("Incorrect X value", offset + start, view.getX());
3597         assertEquals("Incorrect Y value", offset + start, view.getY());
3598         assertEquals("Incorrect Z value", offset + start, view.getZ());
3599     }
3600 
3601     private static class MockDrawable extends Drawable {
3602         private boolean mCalledSetTint = false;
3603 
3604         @Override
draw(Canvas canvas)3605         public void draw(Canvas canvas) {}
3606 
3607         @Override
setAlpha(int alpha)3608         public void setAlpha(int alpha) {}
3609 
3610         @Override
setColorFilter(ColorFilter cf)3611         public void setColorFilter(ColorFilter cf) {}
3612 
3613         @Override
getOpacity()3614         public int getOpacity() {
3615             return 0;
3616         }
3617 
3618         @Override
setTintList(ColorStateList tint)3619         public void setTintList(ColorStateList tint) {
3620             super.setTintList(tint);
3621             mCalledSetTint = true;
3622         }
3623 
hasCalledSetTint()3624         public boolean hasCalledSetTint() {
3625             return mCalledSetTint;
3626         }
3627 
reset()3628         public void reset() {
3629             mCalledSetTint = false;
3630         }
3631     }
3632 
3633     private static class MockEditText extends EditText {
3634         private boolean mCalledCheckInputConnectionProxy = false;
3635         private boolean mCalledOnCreateInputConnection = false;
3636         private boolean mCalledOnCheckIsTextEditor = false;
3637 
MockEditText(Context context)3638         public MockEditText(Context context) {
3639             super(context);
3640         }
3641 
3642         @Override
checkInputConnectionProxy(View view)3643         public boolean checkInputConnectionProxy(View view) {
3644             mCalledCheckInputConnectionProxy = true;
3645             return super.checkInputConnectionProxy(view);
3646         }
3647 
hasCalledCheckInputConnectionProxy()3648         public boolean hasCalledCheckInputConnectionProxy() {
3649             return mCalledCheckInputConnectionProxy;
3650         }
3651 
3652         @Override
onCreateInputConnection(EditorInfo outAttrs)3653         public InputConnection onCreateInputConnection(EditorInfo outAttrs) {
3654             mCalledOnCreateInputConnection = true;
3655             return super.onCreateInputConnection(outAttrs);
3656         }
3657 
hasCalledOnCreateInputConnection()3658         public boolean hasCalledOnCreateInputConnection() {
3659             return mCalledOnCreateInputConnection;
3660         }
3661 
3662         @Override
onCheckIsTextEditor()3663         public boolean onCheckIsTextEditor() {
3664             mCalledOnCheckIsTextEditor = true;
3665             return super.onCheckIsTextEditor();
3666         }
3667 
hasCalledOnCheckIsTextEditor()3668         public boolean hasCalledOnCheckIsTextEditor() {
3669             return mCalledOnCheckIsTextEditor;
3670         }
3671 
reset()3672         public void reset() {
3673             mCalledCheckInputConnectionProxy = false;
3674             mCalledOnCreateInputConnection = false;
3675             mCalledOnCheckIsTextEditor = false;
3676         }
3677     }
3678 
3679     private final static class MockViewParent extends ViewGroup {
3680         private boolean mHasClearChildFocus = false;
3681         private boolean mHasRequestLayout = false;
3682         private boolean mHasCreateContextMenu = false;
3683         private boolean mHasShowContextMenuForChild = false;
3684         private boolean mHasGetChildVisibleRect = false;
3685         private boolean mHasInvalidateChild = false;
3686         private boolean mHasOnCreateDrawableState = false;
3687         private boolean mHasChildDrawableStateChanged = false;
3688         private boolean mHasBroughtChildToFront = false;
3689         private Rect mTempRect;
3690 
3691         private final static int[] DEFAULT_PARENT_STATE_SET = new int[] { 789 };
3692 
requestChildRectangleOnScreen(View child, Rect rectangle, boolean immediate)3693         public boolean requestChildRectangleOnScreen(View child, Rect rectangle,
3694                 boolean immediate) {
3695             return false;
3696         }
3697 
MockViewParent(Context context)3698         public MockViewParent(Context context) {
3699             super(context);
3700         }
3701 
bringChildToFront(View child)3702         public void bringChildToFront(View child) {
3703             mHasBroughtChildToFront = true;
3704         }
3705 
hasBroughtChildToFront()3706         public boolean hasBroughtChildToFront() {
3707             return mHasBroughtChildToFront;
3708         }
3709 
childDrawableStateChanged(View child)3710         public void childDrawableStateChanged(View child) {
3711             mHasChildDrawableStateChanged = true;
3712         }
3713 
hasChildDrawableStateChanged()3714         public boolean hasChildDrawableStateChanged() {
3715             return mHasChildDrawableStateChanged;
3716         }
3717 
3718         @Override
dispatchSetPressed(boolean pressed)3719         public void dispatchSetPressed(boolean pressed) {
3720             super.dispatchSetPressed(pressed);
3721         }
3722 
3723         @Override
dispatchSetSelected(boolean selected)3724         public void dispatchSetSelected(boolean selected) {
3725             super.dispatchSetSelected(selected);
3726         }
3727 
clearChildFocus(View child)3728         public void clearChildFocus(View child) {
3729             mHasClearChildFocus = true;
3730         }
3731 
hasClearChildFocus()3732         public boolean hasClearChildFocus() {
3733             return mHasClearChildFocus;
3734         }
3735 
createContextMenu(ContextMenu menu)3736         public void createContextMenu(ContextMenu menu) {
3737             mHasCreateContextMenu = true;
3738         }
3739 
hasCreateContextMenu()3740         public boolean hasCreateContextMenu() {
3741             return mHasCreateContextMenu;
3742         }
3743 
focusSearch(View v, int direction)3744         public View focusSearch(View v, int direction) {
3745             return v;
3746         }
3747 
focusableViewAvailable(View v)3748         public void focusableViewAvailable(View v) {
3749 
3750         }
3751 
getChildVisibleRect(View child, Rect r, Point offset)3752         public boolean getChildVisibleRect(View child, Rect r, Point offset) {
3753             mHasGetChildVisibleRect = true;
3754             return false;
3755         }
3756 
3757         @Override
onLayout(boolean changed, int l, int t, int r, int b)3758         protected void onLayout(boolean changed, int l, int t, int r, int b) {
3759 
3760         }
3761 
hasGetChildVisibleRect()3762         public boolean hasGetChildVisibleRect() {
3763             return mHasGetChildVisibleRect;
3764         }
3765 
invalidateChildInParent(int[] location, Rect r)3766         public ViewParent invalidateChildInParent(int[] location, Rect r) {
3767             return null;
3768         }
3769 
isLayoutRequested()3770         public boolean isLayoutRequested() {
3771             return false;
3772         }
3773 
recomputeViewAttributes(View child)3774         public void recomputeViewAttributes(View child) {
3775 
3776         }
3777 
requestChildFocus(View child, View focused)3778         public void requestChildFocus(View child, View focused) {
3779 
3780         }
3781 
requestDisallowInterceptTouchEvent(boolean disallowIntercept)3782         public void requestDisallowInterceptTouchEvent(boolean disallowIntercept) {
3783 
3784         }
3785 
3786         @Override
requestLayout()3787         public void requestLayout() {
3788             mHasRequestLayout = true;
3789         }
3790 
hasRequestLayout()3791         public boolean hasRequestLayout() {
3792             return mHasRequestLayout;
3793         }
3794 
requestTransparentRegion(View child)3795         public void requestTransparentRegion(View child) {
3796 
3797         }
3798 
showContextMenuForChild(View originalView)3799         public boolean showContextMenuForChild(View originalView) {
3800             mHasShowContextMenuForChild = true;
3801             return false;
3802         }
3803 
startActionModeForChild(View originalView, ActionMode.Callback callback)3804         public ActionMode startActionModeForChild(View originalView,
3805                 ActionMode.Callback callback) {
3806             return null;
3807         }
3808 
startActionModeForChild(View originalView, ActionMode.Callback callback, int type)3809         public ActionMode startActionModeForChild(View originalView,
3810                 ActionMode.Callback callback, int type) {
3811             return null;
3812         }
3813 
hasShowContextMenuForChild()3814         public boolean hasShowContextMenuForChild() {
3815             return mHasShowContextMenuForChild;
3816         }
3817 
3818         @Override
onCreateDrawableState(int extraSpace)3819         protected int[] onCreateDrawableState(int extraSpace) {
3820             mHasOnCreateDrawableState = true;
3821             return DEFAULT_PARENT_STATE_SET;
3822         }
3823 
requestSendAccessibilityEvent(View child, AccessibilityEvent event)3824         public boolean requestSendAccessibilityEvent(View child, AccessibilityEvent event) {
3825             return false;
3826         }
3827 
getDefaultParentStateSet()3828         public static int[] getDefaultParentStateSet() {
3829             return DEFAULT_PARENT_STATE_SET;
3830         }
3831 
hasOnCreateDrawableState()3832         public boolean hasOnCreateDrawableState() {
3833             return mHasOnCreateDrawableState;
3834         }
3835 
reset()3836         public void reset() {
3837             mHasClearChildFocus = false;
3838             mHasRequestLayout = false;
3839             mHasCreateContextMenu = false;
3840             mHasShowContextMenuForChild = false;
3841             mHasGetChildVisibleRect = false;
3842             mHasInvalidateChild = false;
3843             mHasOnCreateDrawableState = false;
3844             mHasChildDrawableStateChanged = false;
3845             mHasBroughtChildToFront = false;
3846         }
3847 
childOverlayStateChanged(View child)3848         public void childOverlayStateChanged(View child) {
3849 
3850         }
3851 
3852         @Override
childHasTransientStateChanged(View child, boolean hasTransientState)3853         public void childHasTransientStateChanged(View child, boolean hasTransientState) {
3854 
3855         }
3856 
3857         @Override
getParentForAccessibility()3858         public ViewParent getParentForAccessibility() {
3859             return null;
3860         }
3861 
3862         @Override
notifySubtreeAccessibilityStateChanged(View child, View source, int changeType)3863         public void notifySubtreeAccessibilityStateChanged(View child,
3864             View source, int changeType) {
3865 
3866         }
3867 
3868         @Override
onStartNestedScroll(View child, View target, int nestedScrollAxes)3869         public boolean onStartNestedScroll(View child, View target, int nestedScrollAxes) {
3870             return false;
3871         }
3872 
3873         @Override
onNestedScrollAccepted(View child, View target, int nestedScrollAxes)3874         public void onNestedScrollAccepted(View child, View target, int nestedScrollAxes) {
3875         }
3876 
3877         @Override
onStopNestedScroll(View target)3878         public void onStopNestedScroll(View target) {
3879         }
3880 
3881         @Override
onNestedScroll(View target, int dxConsumed, int dyConsumed, int dxUnconsumed, int dyUnconsumed)3882         public void onNestedScroll(View target, int dxConsumed, int dyConsumed,
3883                                    int dxUnconsumed, int dyUnconsumed) {
3884         }
3885 
3886         @Override
onNestedPreScroll(View target, int dx, int dy, int[] consumed)3887         public void onNestedPreScroll(View target, int dx, int dy, int[] consumed) {
3888         }
3889 
3890         @Override
onNestedFling(View target, float velocityX, float velocityY, boolean consumed)3891         public boolean onNestedFling(View target, float velocityX, float velocityY,
3892                 boolean consumed) {
3893             return false;
3894         }
3895 
3896         @Override
onNestedPreFling(View target, float velocityX, float velocityY)3897         public boolean onNestedPreFling(View target, float velocityX, float velocityY) {
3898             return false;
3899         }
3900 
3901         @Override
onNestedPrePerformAccessibilityAction(View target, int action, Bundle args)3902         public boolean onNestedPrePerformAccessibilityAction(View target, int action, Bundle args) {
3903             return false;
3904         }
3905     }
3906 
3907     private final class OnCreateContextMenuListenerImpl implements OnCreateContextMenuListener {
3908         private boolean mHasOnCreateContextMenu = false;
3909 
onCreateContextMenu(ContextMenu menu, View v, ContextMenuInfo menuInfo)3910         public void onCreateContextMenu(ContextMenu menu, View v, ContextMenuInfo menuInfo) {
3911             mHasOnCreateContextMenu = true;
3912         }
3913 
hasOnCreateContextMenu()3914         public boolean hasOnCreateContextMenu() {
3915             return mHasOnCreateContextMenu;
3916         }
3917 
reset()3918         public void reset() {
3919             mHasOnCreateContextMenu = false;
3920         }
3921     }
3922 
3923     private static class MockViewGroupParent extends ViewGroup implements ViewParent {
3924         private boolean mHasRequestChildRectangleOnScreen = false;
3925 
MockViewGroupParent(Context context)3926         public MockViewGroupParent(Context context) {
3927             super(context);
3928         }
3929 
3930         @Override
onLayout(boolean changed, int l, int t, int r, int b)3931         protected void onLayout(boolean changed, int l, int t, int r, int b) {
3932 
3933         }
3934 
3935         @Override
requestChildRectangleOnScreen(View child, Rect rectangle, boolean immediate)3936         public boolean requestChildRectangleOnScreen(View child,
3937                 Rect rectangle, boolean immediate) {
3938             mHasRequestChildRectangleOnScreen = true;
3939             return super.requestChildRectangleOnScreen(child, rectangle, immediate);
3940         }
3941 
hasRequestChildRectangleOnScreen()3942         public boolean hasRequestChildRectangleOnScreen() {
3943             return mHasRequestChildRectangleOnScreen;
3944         }
3945 
3946         @Override
detachViewFromParent(View child)3947         protected void detachViewFromParent(View child) {
3948             super.detachViewFromParent(child);
3949         }
3950 
reset()3951         public void reset() {
3952             mHasRequestChildRectangleOnScreen = false;
3953         }
3954     }
3955 
3956     private static final class OnClickListenerImpl implements OnClickListener {
3957         private boolean mHasOnClick = false;
3958 
onClick(View v)3959         public void onClick(View v) {
3960             mHasOnClick = true;
3961         }
3962 
hasOnClick()3963         public boolean hasOnClick() {
3964             return mHasOnClick;
3965         }
3966 
reset()3967         public void reset() {
3968             mHasOnClick = false;
3969         }
3970     }
3971 
3972     private static final class OnLongClickListenerImpl implements OnLongClickListener {
3973         private boolean mHasOnLongClick = false;
3974 
hasOnLongClick()3975         public boolean hasOnLongClick() {
3976             return mHasOnLongClick;
3977         }
3978 
reset()3979         public void reset() {
3980             mHasOnLongClick = false;
3981         }
3982 
onLongClick(View v)3983         public boolean onLongClick(View v) {
3984             mHasOnLongClick = true;
3985             return true;
3986         }
3987     }
3988 
3989     private static final class OnContextClickListenerImpl implements OnContextClickListener {
3990         private boolean mHasContextClick = false;
3991         private View mLastViewContextClicked;
3992 
hasOnContextClick()3993         public boolean hasOnContextClick() {
3994             return mHasContextClick;
3995         }
3996 
reset()3997         public void reset() {
3998             mHasContextClick = false;
3999             mLastViewContextClicked = null;
4000         }
4001 
onContextClick(View v)4002         public boolean onContextClick(View v) {
4003             mHasContextClick = true;
4004             mLastViewContextClicked = v;
4005             return true;
4006         }
4007 
getLastViewContextClicked()4008         public View getLastViewContextClicked() {
4009             return mLastViewContextClicked;
4010         }
4011     }
4012 
4013     private static final class OnFocusChangeListenerImpl implements OnFocusChangeListener {
4014         private boolean mHasOnFocusChange = false;
4015 
onFocusChange(View v, boolean hasFocus)4016         public void onFocusChange(View v, boolean hasFocus) {
4017             mHasOnFocusChange = true;
4018         }
4019 
hasOnFocusChange()4020         public boolean hasOnFocusChange() {
4021             return mHasOnFocusChange;
4022         }
4023 
reset()4024         public void reset() {
4025             mHasOnFocusChange = false;
4026         }
4027     }
4028 
4029     private static final class OnKeyListenerImpl implements OnKeyListener {
4030         private boolean mHasOnKey = false;
4031 
onKey(View v, int keyCode, KeyEvent event)4032         public boolean onKey(View v, int keyCode, KeyEvent event) {
4033             mHasOnKey = true;
4034             return true;
4035         }
4036 
reset()4037         public void reset() {
4038             mHasOnKey = false;
4039         }
4040 
hasOnKey()4041         public boolean hasOnKey() {
4042             return mHasOnKey;
4043         }
4044     }
4045 
4046     private static final class OnTouchListenerImpl implements OnTouchListener {
4047         private boolean mHasOnTouch = false;
4048 
onTouch(View v, MotionEvent event)4049         public boolean onTouch(View v, MotionEvent event) {
4050             mHasOnTouch = true;
4051             return true;
4052         }
4053 
reset()4054         public void reset() {
4055             mHasOnTouch = false;
4056         }
4057 
hasOnTouch()4058         public boolean hasOnTouch() {
4059             return mHasOnTouch;
4060         }
4061     }
4062 
4063     private static final class MockTouchDelegate extends TouchDelegate {
MockTouchDelegate(Rect bounds, View delegateView)4064         public MockTouchDelegate(Rect bounds, View delegateView) {
4065             super(bounds, delegateView);
4066         }
4067 
4068         private boolean mCalledOnTouchEvent = false;
4069 
4070         @Override
onTouchEvent(MotionEvent event)4071         public boolean onTouchEvent(MotionEvent event) {
4072             mCalledOnTouchEvent = true;
4073             return super.onTouchEvent(event);
4074         }
4075 
hasCalledOnTouchEvent()4076         public boolean hasCalledOnTouchEvent() {
4077             return mCalledOnTouchEvent;
4078         }
4079 
reset()4080         public void reset() {
4081             mCalledOnTouchEvent = false;
4082         }
4083     };
4084 
4085     private static final class ViewData {
4086         public int childCount;
4087         public String tag;
4088         public View firstChild;
4089     }
4090 
4091     private static final class MockRunnable implements Runnable {
4092         public boolean hasRun = false;
4093 
run()4094         public void run() {
4095             hasRun = true;
4096         }
4097     }
4098 }
4099