1 // Copyright 2013 The Chromium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 package org.chromium.chrome.browser.contextmenu; 6 7 import android.content.ClipData; 8 import android.content.ClipboardManager; 9 import android.content.Context; 10 import android.os.Build; 11 import android.test.FlakyTest; 12 import android.view.ContextMenu; 13 14 import junit.framework.Assert; 15 16 import org.chromium.base.test.util.Feature; 17 import org.chromium.chrome.R; 18 import org.chromium.chrome.browser.Tab; 19 import org.chromium.chrome.shell.ChromeShellTestBase; 20 import org.chromium.chrome.test.util.TabUtils; 21 import org.chromium.chrome.test.util.TabUtils.TestCallbackHelperContainerForTab; 22 import org.chromium.chrome.test.util.TestHttpServerClient; 23 import org.chromium.chrome.test.util.browser.contextmenu.ContextMenuUtils; 24 import org.chromium.content.browser.test.util.Criteria; 25 import org.chromium.content.browser.test.util.CriteriaHelper; 26 import org.chromium.content.browser.test.util.KeyUtils; 27 import org.chromium.content.browser.test.util.TestCallbackHelperContainer.OnPageFinishedHelper; 28 import org.chromium.content.browser.test.util.TestTouchUtils; 29 30 import java.util.concurrent.TimeoutException; 31 import java.util.concurrent.atomic.AtomicReference; 32 33 public class ContextMenuTest extends ChromeShellTestBase { 34 @Override 35 public void setUp() throws Exception { 36 super.setUp(); 37 launchChromeShellWithUrl(TestHttpServerClient.getUrl( 38 "chrome/test/data/android/contextmenu/context_menu_test.html")); 39 assertTrue("Page failed to load", waitForActiveShellToBeDoneLoading()); 40 assertWaitForPageScaleFactorMatch(0.5f); 41 } 42 43 // http://crbug.com/326769 44 @FlakyTest 45 // @LargeTest 46 @Feature({"Browser", "Main"}) 47 public void testCopyLinkURL() throws InterruptedException, TimeoutException { 48 Tab tab = getActivity().getActiveTab(); 49 ContextMenuUtils.selectContextMenuItem(this, tab, 50 TabUtils.getTestCallbackHelperContainer(tab), "testLink", 51 R.id.contextmenu_copy_link_address_text); 52 53 assertStringContains("test_link.html", getClipboardText()); 54 } 55 56 // http://crbug.com/326769 57 @FlakyTest 58 // @LargeTest 59 @Feature({"Browser"}) 60 public void testCopyImageLinkCopiesLinkURL() throws InterruptedException, TimeoutException { 61 Tab tab = getActivity().getActiveTab(); 62 ContextMenuUtils.selectContextMenuItem(this, tab, 63 TabUtils.getTestCallbackHelperContainer(tab), "testImageLink", 64 R.id.contextmenu_copy_link_address_text); 65 66 assertStringContains("test_link.html", getClipboardText()); 67 } 68 69 // http://crbug.com/326769 70 @FlakyTest 71 // @LargeTest 72 @Feature({"Browser"}) 73 public void testCopyLinkTextSimple() throws InterruptedException, TimeoutException { 74 Tab tab = getActivity().getActiveTab(); 75 ContextMenuUtils.selectContextMenuItem(this, tab, 76 TabUtils.getTestCallbackHelperContainer(tab), "testLink", 77 R.id.contextmenu_copy_link_text); 78 79 assertEquals("Clipboard text was not what was expected", "Test Link", 80 getClipboardText()); 81 } 82 83 // http://crbug.com/326769 84 @FlakyTest 85 // @LargeTest 86 @Feature({"Browser"}) 87 public void testCopyLinkTextComplex() throws InterruptedException, TimeoutException { 88 Tab tab = getActivity().getActiveTab(); 89 ContextMenuUtils.selectContextMenuItem(this, tab, 90 TabUtils.getTestCallbackHelperContainer(tab), "copyLinkTextComplex", 91 R.id.contextmenu_copy_link_text); 92 93 assertEquals("Clipboard text was not what was expected", 94 "This is pretty extreme \n(newline). ", getClipboardText()); 95 } 96 97 // http://crbug.com/326769 98 @FlakyTest 99 // @LargeTest 100 @Feature({"Browser"}) 101 public void testCopyImageToClipboard() throws InterruptedException, TimeoutException { 102 if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN) return; 103 104 Tab tab = getActivity().getActiveTab(); 105 ContextMenuUtils.selectContextMenuItem(this, tab, 106 TabUtils.getTestCallbackHelperContainer(tab), "testImage", 107 R.id.contextmenu_copy_image); 108 109 String expectedUrl = TestHttpServerClient.getUrl( 110 "chrome/test/data/android/contextmenu/test_image.png"); 111 112 assertEquals("Clipboard text is not correct", expectedUrl, getClipboardText()); 113 } 114 115 // http://crbug.com/326769 116 @FlakyTest 117 // @LargeTest 118 @Feature({"Browser"}) 119 public void testLongPressOnImage() throws InterruptedException, TimeoutException { 120 final Tab tab = getActivity().getActiveTab(); 121 122 TestCallbackHelperContainerForTab helper = 123 TabUtils.getTestCallbackHelperContainer(tab); 124 125 OnPageFinishedHelper callback = helper.getOnPageFinishedHelper(); 126 int callbackCount = callback.getCallCount(); 127 128 ContextMenuUtils.selectContextMenuItem(this, tab, helper, "testImage", 129 R.id.contextmenu_open_image); 130 131 callback.waitForCallback(callbackCount); 132 133 String expectedUrl = TestHttpServerClient.getUrl( 134 "chrome/test/data/android/contextmenu/test_image.png"); 135 136 final AtomicReference<String> actualUrl = new AtomicReference<String>(); 137 getInstrumentation().runOnMainSync(new Runnable() { 138 @Override 139 public void run() { 140 actualUrl.set(tab.getUrl()); 141 } 142 }); 143 144 assertEquals("Failed to navigate to the image", expectedUrl, actualUrl.get()); 145 } 146 147 // http://crbug.com/326769 148 @FlakyTest 149 // @LargeTest 150 @Feature({"Browser"}) 151 public void testLongPressOnImageLink() throws InterruptedException, TimeoutException { 152 final Tab tab = getActivity().getActiveTab(); 153 154 TestCallbackHelperContainerForTab helper = 155 TabUtils.getTestCallbackHelperContainer(tab); 156 157 OnPageFinishedHelper callback = helper.getOnPageFinishedHelper(); 158 int callbackCount = callback.getCallCount(); 159 160 ContextMenuUtils.selectContextMenuItem(this, tab, helper, "testImage", 161 R.id.contextmenu_open_image); 162 163 callback.waitForCallback(callbackCount); 164 165 final AtomicReference<String> actualTitle = new AtomicReference<String>(); 166 getInstrumentation().runOnMainSync(new Runnable() { 167 @Override 168 public void run() { 169 actualTitle.set(tab.getTitle()); 170 } 171 }); 172 173 assertTrue("Navigated to the wrong page.", actualTitle.get().startsWith("test_image.png")); 174 } 175 176 // http://crbug.com/326769 177 @FlakyTest 178 // @LargeTest 179 @Feature({"Browser"}) 180 public void testDismissContextMenuOnBack() throws InterruptedException, TimeoutException { 181 Tab tab = getActivity().getActiveTab(); 182 ContextMenu menu = ContextMenuUtils.openContextMenu(this, tab, 183 TabUtils.getTestCallbackHelperContainer(tab), "testImage"); 184 assertNotNull("Context menu was not properly created", menu); 185 assertFalse("Context menu did not have window focus", getActivity().hasWindowFocus()); 186 187 KeyUtils.pressBack(getInstrumentation()); 188 189 Assert.assertTrue("Activity did not regain focus.", 190 CriteriaHelper.pollForCriteria(new Criteria() { 191 @Override 192 public boolean isSatisfied() { 193 return getActivity().hasWindowFocus(); 194 } 195 })); 196 } 197 198 // http://crbug.com/326769 199 @FlakyTest 200 // @LargeTest 201 @Feature({"Browser"}) 202 public void testDismissContextMenuOnClick() throws InterruptedException, TimeoutException { 203 Tab tab = getActivity().getActiveTab(); 204 ContextMenu menu = ContextMenuUtils.openContextMenu(this, tab, 205 TabUtils.getTestCallbackHelperContainer(tab), "testImage"); 206 assertNotNull("Context menu was not properly created", menu); 207 assertFalse("Context menu did not have window focus", getActivity().hasWindowFocus()); 208 209 TestTouchUtils.singleClickView(getInstrumentation(), tab.getView(), 0, 0); 210 211 Assert.assertTrue("Activity did not regain focus.", 212 CriteriaHelper.pollForCriteria(new Criteria() { 213 @Override 214 public boolean isSatisfied() { 215 return getActivity().hasWindowFocus(); 216 } 217 })); 218 } 219 220 private String getClipboardText() { 221 ClipboardManager clipMgr = 222 (ClipboardManager) getActivity().getSystemService(Context.CLIPBOARD_SERVICE); 223 ClipData clipData = clipMgr.getPrimaryClip(); 224 assertNotNull("Primary clip is null", clipData); 225 assertTrue("Primary clip contains no items.", clipData.getItemCount() > 0); 226 return clipData.getItemAt(0).getText().toString(); 227 } 228 229 private void assertStringContains(String subString, String superString) { 230 assertTrue("String '" + superString + "' does not contain '" + subString + "'", 231 superString.contains(subString)); 232 } 233 } 234