SelectionHandleTest.java revision a031efa9dbd9b321781674193e8ac7636d47eb1d
1a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch// Copyright 2013 The Chromium Authors. All rights reserved. 2a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch// Use of this source code is governed by a BSD-style license that can be 3a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch// found in the LICENSE file. 4a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 5a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochpackage org.chromium.content.browser.input; 6a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 7a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport android.graphics.Point; 8a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport android.graphics.Rect; 9a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport android.os.SystemClock; 10a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport android.text.Editable; 11a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport android.text.Selection; 12a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport android.test.suitebuilder.annotation.MediumTest; 13a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport android.view.MotionEvent; 14a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport android.view.View; 15a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport android.view.inputmethod.EditorInfo; 16a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 17a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport java.util.concurrent.Callable; 18a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 19a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport org.chromium.base.test.util.Feature; 20a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport org.chromium.base.test.util.UrlUtils; 21a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport org.chromium.base.ThreadUtils; 22a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport org.chromium.content.browser.ContentView; 23a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport org.chromium.content.browser.RenderCoordinates; 24a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport org.chromium.content.browser.test.util.CriteriaHelper; 25a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport org.chromium.content.browser.test.util.Criteria; 26a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport org.chromium.content.browser.test.util.DOMUtils; 27a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport org.chromium.content.browser.test.util.TestCallbackHelperContainer; 28a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport org.chromium.content.browser.test.util.TestInputMethodManagerWrapper; 29a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport org.chromium.content.browser.test.util.TestTouchUtils; 30a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport org.chromium.content.browser.test.util.TouchCommon; 31a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochimport org.chromium.content_shell_apk.ContentShellTestBase; 32a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 33a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdochpublic class SelectionHandleTest extends ContentShellTestBase { 34a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private static final String META_DISABLE_ZOOM = 35a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "<meta name=\"viewport\" content=\"" + 36a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "height=device-height," + 37a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "width=device-width," + 38a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "initial-scale=1.0," + 39a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "minimum-scale=1.0," + 40a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "maximum-scale=1.0," + 41a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "\" />"; 42a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 43a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch // For these we use a tiny font-size so that we can be more strict on the expected handle 44a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch // positions. 45a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private static final String TEXTAREA_ID = "textarea"; 46a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private static final String TEXTAREA_DATA_URL = UrlUtils.encodeHtmlDataUri( 47a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "<html><head>" + META_DISABLE_ZOOM + "</head><body>" + 48a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "<textarea id=\"" + TEXTAREA_ID + 49a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "\" cols=\"40\" rows=\"20\" style=\"font-size:6px\">" + 50a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "L r m i s m d l r s t a e , c n e t t r a i i i i g e i , s d d e u m d t m o " + 51a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "i c d d n u l b r e d l r m g a l q a U e i a m n m e i m q i n s r d " + 52a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "e e c t t o u l m o a o i n s u a i u p x a o m d c n e u t D i a t " + 53a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "i u e o o i r p e e d r t n o u t t v l t s e i l m o o e u u i t u l " + 54a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "p r a u . x e t u s n o c e a c p d t t o p o d n , u t n u p q i " + 55a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "o f c a e e u t o l t n m d s l b r m." + 56a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "L r m i s m d l r s t a e , c n e t t r a i i i i g e i , s d d e u m d t m o " + 57a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "i c d d n u l b r e d l r m g a l q a U e i a m n m e i m q i n s r d " + 58a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "e e c t t o u l m o a o i n s u a i u p x a o m d c n e u t D i a t " + 59a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "i u e o o i r p e e d r t n o u t t v l t s e i l m o o e u u i t u l " + 60a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "p r a u . x e t u s n o c e a c p d t t o p o d n , u t n u p q i " + 61a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "o f c a e e u t o l t n m d s l b r m." + 62a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "</textarea>" + 63a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "</body></html>"); 64a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 65a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private static final String NONEDITABLE_DIV_ID = "noneditable"; 66a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private static final String NONEDITABLE_DATA_URL = UrlUtils.encodeHtmlDataUri( 67a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "<html><head>" + META_DISABLE_ZOOM + "</head><body>" + 68a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "<div id=\"" + NONEDITABLE_DIV_ID + "\" style=\"width:200; font-size:6px\">" + 69a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "L r m i s m d l r s t a e , c n e t t r a i i i i g e i , s d d e u m d t m o " + 70a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "i c d d n u l b r e d l r m g a l q a U e i a m n m e i m q i n s r d " + 71a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "e e c t t o u l m o a o i n s u a i u p x a o m d c n e u t D i a t " + 72a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "i u e o o i r p e e d r t n o u t t v l t s e i l m o o e u u i t u l " + 73a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "p r a u . x e t u s n o c e a c p d t t o p o d n , u t n u p q i " + 74a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "o f c a e e u t o l t n m d s l b r m." + 75a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "L r m i s m d l r s t a e , c n e t t r a i i i i g e i , s d d e u m d t m o " + 76a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "i c d d n u l b r e d l r m g a l q a U e i a m n m e i m q i n s r d " + 77a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "e e c t t o u l m o a o i n s u a i u p x a o m d c n e u t D i a t " + 78a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "i u e o o i r p e e d r t n o u t t v l t s e i l m o o e u u i t u l " + 79a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "p r a u . x e t u s n o c e a c p d t t o p o d n , u t n u p q i " + 80a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "o f c a e e u t o l t n m d s l b r m." + 81a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "</div>" + 82a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch "</body></html>"); 83a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 84a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch // TODO(cjhopman): These tolerances should be based on the actual width/height of a 85a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch // character/line. 86a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private static final int HANDLE_POSITION_X_TOLERANCE_PIX = 20; 87a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private static final int HANDLE_POSITION_Y_TOLERANCE_PIX = 30; 88a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 89a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private enum TestPageType { 90a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch EDITABLE(TEXTAREA_ID, TEXTAREA_DATA_URL, true), 91a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch NONEDITABLE(NONEDITABLE_DIV_ID, NONEDITABLE_DATA_URL, false); 92a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 93a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch final String nodeId; 94a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch final String dataUrl; 95a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch final boolean selectionShouldBeEditable; 96a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 97a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch TestPageType(String nodeId, String dataUrl, boolean selectionShouldBeEditable) { 98a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch this.nodeId = nodeId; 99a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch this.dataUrl = dataUrl; 100a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch this.selectionShouldBeEditable = selectionShouldBeEditable; 101a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 102a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 103a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 104a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private void launchWithUrl(String url) throws Throwable { 105a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch launchContentShellWithUrl(url); 106a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertTrue("Page failed to load", waitForActiveShellToBeDoneLoading()); 107a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertWaitForPageScaleFactorMatch(1.0f); 108a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 109a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch // The TestInputMethodManagerWrapper intercepts showSoftInput so that a keyboard is never 110a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch // brought up. 111a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch getImeAdapter().setInputMethodManagerWrapper( 112a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch new TestInputMethodManagerWrapper(getContentViewCore())); 113a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 114a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 115a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private void assertWaitForHasSelectionPosition() 116a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch throws Throwable { 117a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertTrue(CriteriaHelper.pollForCriteria(new Criteria() { 118a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch @Override 119a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch public boolean isSatisfied() { 120a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int start = getSelectionStart(); 121a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int end = getSelectionEnd(); 122a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch return start > 0 && start == end; 123a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 124a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch })); 125a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 126a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 127a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch /** 128a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch * Verifies that when a long-press is performed on static page text, 129a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch * selection handles appear and that handles can be dragged to extend the 130a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch * selection. Does not check exact handle position as this will depend on 131a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch * screen size; instead, position is expected to be correct within 132a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch * HANDLE_POSITION_TOLERANCE_PIX. 133a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch */ 134a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch @MediumTest 135a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch @Feature({ "TextSelection", "Main" }) 136a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch public void testNoneditableSelectionHandles() throws Throwable { 137a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch doSelectionHandleTest(TestPageType.NONEDITABLE); 138a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 139a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 140a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch /** 141a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch * Verifies that when a long-press is performed on editable text (within a 142a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch * textarea), selection handles appear and that handles can be dragged to 143a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch * extend the selection. Does not check exact handle position as this will 144a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch * depend on screen size; instead, position is expected to be correct within 145a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch * HANDLE_POSITION_TOLERANCE_PIX. 146a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch */ 147a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch @MediumTest 148a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch @Feature({ "TextSelection" }) 149a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch public void testEditableSelectionHandles() throws Throwable { 150a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch doSelectionHandleTest(TestPageType.EDITABLE); 151a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 152a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 153a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private void doSelectionHandleTest(TestPageType pageType) throws Throwable { 154a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch launchWithUrl(pageType.dataUrl); 155a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 156a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch clickNodeToShowSelectionHandles(pageType.nodeId); 157a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertWaitForSelectionEditableEquals(pageType.selectionShouldBeEditable); 158a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 159a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch HandleView startHandle = getStartHandle(); 160a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch HandleView endHandle = getEndHandle(); 161a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 162a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch Rect nodeWindowBounds = getNodeBoundsPix(pageType.nodeId); 163a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 164a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int leftX = (nodeWindowBounds.left + nodeWindowBounds.centerX()) / 2; 165a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int centerX = nodeWindowBounds.centerX(); 166a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int rightX = (nodeWindowBounds.right + nodeWindowBounds.centerX()) / 2; 167a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 168a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int topY = (nodeWindowBounds.top + nodeWindowBounds.centerY()) / 2; 169a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int centerY = nodeWindowBounds.centerY(); 170a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int bottomY = (nodeWindowBounds.bottom + nodeWindowBounds.centerY()) / 2; 171a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 172a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch // Drag start handle up and to the left. The selection start should decrease. 173a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch dragHandleAndCheckSelectionChange(startHandle, leftX, topY, -1, 0); 174a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch // Drag end handle down and to the right. The selection end should increase. 175a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch dragHandleAndCheckSelectionChange(endHandle, rightX, bottomY, 0, 1); 176a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch // Drag start handle back to the middle. The selection start should increase. 177a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch dragHandleAndCheckSelectionChange(startHandle, centerX, centerY, 1, 0); 178a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch // Drag end handle up and to the left past the start handle. Both selection start and end 179a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch // should decrease. 180a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch dragHandleAndCheckSelectionChange(endHandle, leftX, topY, -1, -1); 181a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch // Drag start handle down and to the right past the end handle. Both selection start and end 182a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch // should increase. 183a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch dragHandleAndCheckSelectionChange(startHandle, rightX, bottomY, 1, 1); 184a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 185a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch clickToDismissHandles(); 186a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 187a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 188a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private void dragHandleAndCheckSelectionChange(HandleView handle, int dragToX, int dragToY, 189a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch final int expectedStartChange, final int expectedEndChange) throws Throwable { 190a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch String initialText = getContentViewCore().getSelectedText(); 191a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch final int initialSelectionEnd = getSelectionEnd(); 192a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch final int initialSelectionStart = getSelectionStart(); 193a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 194a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch dragHandleTo(handle, dragToX, dragToY, 10); 195a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertWaitForEitherHandleNear(dragToX, dragToY); 196a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 197a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch if (getContentViewCore().isSelectionEditable()) { 198a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertTrue(CriteriaHelper.pollForCriteria(new Criteria() { 199a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch @Override 200a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch public boolean isSatisfied() { 201a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int startChange = getSelectionStart() - initialSelectionStart; 202a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch // TODO(cjhopman): Due to http://crbug.com/244633 we can't really assert that 203a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch // there is no change when we expect to be able to. 204a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch if (expectedStartChange != 0) { 205a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch if ((int) Math.signum(startChange) != expectedStartChange) return false; 206a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 207a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 208a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int endChange = getSelectionEnd() - initialSelectionEnd; 209a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch if (expectedEndChange != 0) { 210a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch if ((int) Math.signum(endChange) != expectedEndChange) return false; 211a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 212a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 213a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch return true; 214a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 215a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch })); 216a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 217a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 218a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertWaitForHandleViewStopped(getStartHandle()); 219a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertWaitForHandleViewStopped(getEndHandle()); 220a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 221a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 222a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private void assertWaitForSelectionEditableEquals(final boolean expected) throws Throwable { 223a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertTrue(CriteriaHelper.pollForCriteria(new Criteria() { 224a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch @Override 225a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch public boolean isSatisfied() { 226a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch return getContentViewCore().isSelectionEditable() == expected; 227a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 228a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch })); 229a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 230a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 231a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private void assertWaitForHandleViewStopped(final HandleView handle) throws Throwable { 232a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertTrue(CriteriaHelper.pollForCriteria(new Criteria() { 233a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private Point position = new Point(-1, -1); 234a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch @Override 235a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch public boolean isSatisfied() { 236a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch Point lastPosition = position; 237a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch position = getHandlePosition(handle); 238a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch return !handle.isDragging() && 239a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch position.equals(lastPosition); 240a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 241a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch })); 242a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 243a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 244a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch /** 245a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch * Verifies that when a selection is made within static page text, that the 246a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch * contextual action bar of the correct type is displayed. Also verified 247a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch * that the bar disappears upon deselection. 248a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch */ 249a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch @MediumTest 250a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch @Feature({ "TextSelection" }) 251a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch public void testNoneditableSelectionActionBar() throws Throwable { 252a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch doSelectionActionBarTest(TestPageType.NONEDITABLE); 253a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 254a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 255a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch /** 256a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch * Verifies that when a selection is made within editable text, that the 257a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch * contextual action bar of the correct type is displayed. Also verified 258a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch * that the bar disappears upon deselection. 259a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch */ 260a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch @MediumTest 261a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch @Feature({ "TextSelection" }) 262a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch public void testEditableSelectionActionBar() throws Throwable { 263a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch doSelectionActionBarTest(TestPageType.EDITABLE); 264a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 265a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 266a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private void doSelectionActionBarTest(TestPageType pageType) throws Throwable { 267a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch launchWithUrl(pageType.dataUrl); 268a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertFalse(getContentViewCore().isSelectActionBarShowing()); 269a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch clickNodeToShowSelectionHandles(pageType.nodeId); 270a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertWaitForSelectActionBarShowingEquals(true); 271a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch clickToDismissHandles(); 272a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertWaitForSelectActionBarShowingEquals(false); 273a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 274a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 275a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private static Point getHandlePosition(final HandleView handle) { 276a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch return ThreadUtils.runOnUiThreadBlockingNoException(new Callable<Point>() { 277a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch @Override 278a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch public Point call() { 279a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch return new Point(handle.getAdjustedPositionX(), handle.getAdjustedPositionY()); 280a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 281a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch }); 282a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 283a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 284a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private static boolean isHandleNear(HandleView handle, int x, int y) { 285a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch Point position = getHandlePosition(handle); 286a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch return (Math.abs(position.x - x) < HANDLE_POSITION_X_TOLERANCE_PIX) && 287a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch (Math.abs(position.y - y) < HANDLE_POSITION_Y_TOLERANCE_PIX); 288a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 289a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 290a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private void assertWaitForHandleNear(final HandleView handle, final int x, final int y) 291a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch throws Throwable { 292a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertTrue(CriteriaHelper.pollForCriteria(new Criteria() { 293a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch @Override 294a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch public boolean isSatisfied() { 295a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch return isHandleNear(handle, x, y); 296a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 297a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch })); 298a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 299a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 300a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private void assertWaitForEitherHandleNear(final int x, final int y) throws Throwable { 301a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch final HandleView startHandle = getStartHandle(); 302a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch final HandleView endHandle = getEndHandle(); 303a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertTrue(CriteriaHelper.pollForCriteria(new Criteria() { 304a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch @Override 305a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch public boolean isSatisfied() { 306a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch return isHandleNear(startHandle, x, y) || isHandleNear(endHandle, x, y); 307a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 308a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch })); 309a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 310a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 311a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private void assertWaitForHandlesShowingEquals(final boolean shouldBeShowing) throws Throwable { 312a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertTrue(CriteriaHelper.pollForCriteria(new Criteria() { 313a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch @Override 314a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch public boolean isSatisfied() { 315a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch SelectionHandleController shc = 316a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch getContentViewCore().getSelectionHandleControllerForTest(); 317a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch boolean isShowing = shc != null && shc.isShowing(); 318a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch return shouldBeShowing == isShowing; 319a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 320a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch })); 321a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 322a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 323a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 324a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private void dragHandleTo(final HandleView handle, final int dragToX, final int dragToY, 325a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch final int steps) throws Throwable { 326a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch ContentView view = getContentView(); 327a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertTrue(ThreadUtils.runOnUiThreadBlocking(new Callable<Boolean>() { 328a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch @Override 329a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch public Boolean call() { 330a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int adjustedX = handle.getAdjustedPositionX(); 331a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int adjustedY = handle.getAdjustedPositionY(); 332a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int realX = handle.getPositionX(); 333a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int realY = handle.getPositionY(); 334a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 335a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int realDragToX = dragToX + (realX - adjustedX); 336a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int realDragToY = dragToY + (realY - adjustedY); 337a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 338a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch ContentView view = getContentView(); 339a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int[] fromLocation = TestTouchUtils.getAbsoluteLocationFromRelative( 340a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch view, realX, realY); 341a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int[] toLocation = TestTouchUtils.getAbsoluteLocationFromRelative( 342a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch view, realDragToX, realDragToY); 343a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 344a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch long downTime = SystemClock.uptimeMillis(); 345a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch MotionEvent event = MotionEvent.obtain(downTime, downTime, MotionEvent.ACTION_DOWN, 346a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch fromLocation[0], fromLocation[1], 0); 347a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch handle.dispatchTouchEvent(event); 348a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 349a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch if (!handle.isDragging()) return false; 350a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 351a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch for (int i = 0; i < steps; i++) { 352a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch float scale = (float) (i + 1) / steps; 353a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int x = fromLocation[0] + (int) (scale * (toLocation[0] - fromLocation[0])); 354a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int y = fromLocation[1] + (int) (scale * (toLocation[1] - fromLocation[1])); 355a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch long eventTime = SystemClock.uptimeMillis(); 356a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch event = MotionEvent.obtain(downTime, eventTime, MotionEvent.ACTION_MOVE, 357a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch x, y, 0); 358a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch handle.dispatchTouchEvent(event); 359a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 360a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch long upTime = SystemClock.uptimeMillis(); 361a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch event = MotionEvent.obtain(downTime, upTime, MotionEvent.ACTION_UP, 362a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch toLocation[0], toLocation[1], 0); 363a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch handle.dispatchTouchEvent(event); 364a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 365a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch return !handle.isDragging(); 366a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 367a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch })); 368a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 369a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 370a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private Rect getNodeBoundsPix(String nodeId) throws Throwable { 371a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch Rect nodeBounds = DOMUtils.getNodeBounds(getContentView(), 372a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch new TestCallbackHelperContainer(getContentView()), nodeId); 373a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 374a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch RenderCoordinates renderCoordinates = getContentView().getRenderCoordinates(); 375a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int offsetX = getContentView().getContentViewCore().getViewportSizeOffsetWidthPix(); 376a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int offsetY = getContentView().getContentViewCore().getViewportSizeOffsetHeightPix(); 377a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 378a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int left = (int) renderCoordinates.fromLocalCssToPix(nodeBounds.left) + offsetX; 379a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int right = (int) renderCoordinates.fromLocalCssToPix(nodeBounds.right) + offsetX; 380a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int top = (int) renderCoordinates.fromLocalCssToPix(nodeBounds.top) + offsetY; 381a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int bottom = (int) renderCoordinates.fromLocalCssToPix(nodeBounds.bottom) + offsetY; 382a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 383a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch return new Rect(left, top, right, bottom); 384a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 385a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 386a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private void clickNodeToShowSelectionHandles(String nodeId) throws Throwable { 387a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch Rect nodeWindowBounds = getNodeBoundsPix(nodeId); 388a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 389a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch TouchCommon touchCommon = new TouchCommon(this); 390a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int centerX = nodeWindowBounds.centerX(); 391a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch int centerY = nodeWindowBounds.centerY(); 392a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch touchCommon.longPressView(getContentView(), centerX, centerY); 393a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 394a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertWaitForHandlesShowingEquals(true); 395a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 396a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch // No words wrap in the sample text so handles should be at the same y 397a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch // position. 398a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertEquals(getStartHandle().getPositionY(), getEndHandle().getPositionY()); 399a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 400a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch // In ContentShell, the handles are initially misplaced when they first appear. This is 401a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch // fixed after the first time they are dragged (or the page is scrolled). 402a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch // TODO(cjhopman): Fix this problem in ContentShell: http://crbug.com/243836 403a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch dragHandleTo(getStartHandle(), centerX - 40, centerY - 40, 1); 404a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertWaitForHandleViewStopped(getStartHandle()); 405a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 406a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 407a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private void clickToDismissHandles() throws Throwable { 408a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch TestTouchUtils.sleepForDoubleTapTimeout(getInstrumentation()); 409a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch new TouchCommon(this).singleClickView(getContentView(), 0, 0); 410a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertWaitForHandlesShowingEquals(false); 411a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 412a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 413a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private void assertWaitForSelectActionBarShowingEquals(final boolean shouldBeShowing) 414a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch throws InterruptedException { 415a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch assertTrue(CriteriaHelper.pollForCriteria(new Criteria() { 416a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch @Override 417a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch public boolean isSatisfied() { 418a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch return shouldBeShowing == getContentViewCore().isSelectActionBarShowing(); 419a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 420a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch })); 421a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 422a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 423a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private ImeAdapter getImeAdapter() { 424a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch return getContentViewCore().getImeAdapterForTest(); 425a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 426a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 427a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private int getSelectionStart() { 428a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch return Selection.getSelectionStart(getEditable()); 429a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 430a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 431a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private int getSelectionEnd() { 432a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch return Selection.getSelectionEnd(getEditable()); 433a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 434a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 435a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private Editable getEditable() { 436a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch return getContentViewCore().getEditableForTest(); 437a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 438a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 439a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private HandleView getStartHandle() { 440a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch SelectionHandleController shc = getContentViewCore().getSelectionHandleControllerForTest(); 441a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch return shc.getStartHandleViewForTest(); 442a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 443a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch 444a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch private HandleView getEndHandle() { 445a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch SelectionHandleController shc = getContentViewCore().getSelectionHandleControllerForTest(); 446a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch return shc.getEndHandleViewForTest(); 447a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch } 448a031efa9dbd9b321781674193e8ac7636d47eb1dBen Murdoch} 449