Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(180)

Side by Side Diff: chrome/browser/site_per_process_interactive_browsertest.cc

Issue 2771213003: OOPIF: Add test to for tab and mouse focus changes. (Closed)
Patch Set: Created 3 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « no previous file | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2016 The Chromium Authors. All rights reserved. 1 // Copyright 2016 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "base/command_line.h" 5 #include "base/command_line.h"
6 #include "base/strings/string_number_conversions.h" 6 #include "base/strings/string_number_conversions.h"
7 #include "chrome/browser/renderer_context_menu/render_view_context_menu_browsert est_util.h" 7 #include "chrome/browser/renderer_context_menu/render_view_context_menu_browsert est_util.h"
8 #include "chrome/browser/ui/browser.h" 8 #include "chrome/browser/ui/browser.h"
9 #include "chrome/browser/ui/browser_window.h" 9 #include "chrome/browser/ui/browser_window.h"
10 #include "chrome/browser/ui/exclusive_access/fullscreen_controller_test.h" 10 #include "chrome/browser/ui/exclusive_access/fullscreen_controller_test.h"
11 #include "chrome/browser/ui/tabs/tab_strip_model.h" 11 #include "chrome/browser/ui/tabs/tab_strip_model.h"
12 #include "chrome/test/base/in_process_browser_test.h" 12 #include "chrome/test/base/in_process_browser_test.h"
13 #include "chrome/test/base/interactive_test_utils.h" 13 #include "chrome/test/base/interactive_test_utils.h"
14 #include "chrome/test/base/ui_test_utils.h" 14 #include "chrome/test/base/ui_test_utils.h"
15 #include "components/guest_view/browser/guest_view_manager_delegate.h" 15 #include "components/guest_view/browser/guest_view_manager_delegate.h"
16 #include "components/guest_view/browser/test_guest_view_manager.h" 16 #include "components/guest_view/browser/test_guest_view_manager.h"
17 #include "content/public/browser/navigation_handle.h" 17 #include "content/public/browser/navigation_handle.h"
18 #include "content/public/browser/render_frame_host.h" 18 #include "content/public/browser/render_frame_host.h"
19 #include "content/public/browser/render_widget_host.h" 19 #include "content/public/browser/render_widget_host.h"
20 #include "content/public/browser/render_widget_host_view.h" 20 #include "content/public/browser/render_widget_host_view.h"
21 #include "content/public/browser/web_contents.h" 21 #include "content/public/browser/web_contents.h"
22 #include "content/public/test/browser_test_utils.h" 22 #include "content/public/test/browser_test_utils.h"
23 #include "content/public/test/content_browser_test_utils.h" 23 #include "content/public/test/content_browser_test_utils.h"
24 #include "content/public/test/test_navigation_observer.h" 24 #include "content/public/test/test_navigation_observer.h"
25 #include "content/public/test/test_utils.h" 25 #include "content/public/test/test_utils.h"
26 #include "extensions/browser/api/extensions_api_client.h" 26 #include "extensions/browser/api/extensions_api_client.h"
27 #include "extensions/common/constants.h" 27 #include "extensions/common/constants.h"
28 #include "net/dns/mock_host_resolver.h" 28 #include "net/dns/mock_host_resolver.h"
29 #include "net/test/embedded_test_server/embedded_test_server.h" 29 #include "net/test/embedded_test_server/embedded_test_server.h"
30 #include "ui/base/test/ui_controls.h"
30 #include "ui/display/display.h" 31 #include "ui/display/display.h"
31 #include "ui/display/screen.h" 32 #include "ui/display/screen.h"
32 #include "url/gurl.h" 33 #include "url/gurl.h"
33 34
34 class SitePerProcessInteractiveBrowserTest : public InProcessBrowserTest { 35 class SitePerProcessInteractiveBrowserTest : public InProcessBrowserTest {
35 public: 36 public:
36 SitePerProcessInteractiveBrowserTest() {} 37 SitePerProcessInteractiveBrowserTest() {}
37 ~SitePerProcessInteractiveBrowserTest() override {} 38 ~SitePerProcessInteractiveBrowserTest() override {}
38 39
39 void SetUpCommandLine(base::CommandLine* command_line) override { 40 void SetUpCommandLine(base::CommandLine* command_line) override {
(...skipping 233 matching lines...) Expand 10 before | Expand all | Expand 10 after
273 EXPECT_EQ("\"child2-focused-input2\"", press_tab_and_wait_for_message(true)); 274 EXPECT_EQ("\"child2-focused-input2\"", press_tab_and_wait_for_message(true));
274 EXPECT_EQ(child2, web_contents->GetFocusedFrame()); 275 EXPECT_EQ(child2, web_contents->GetFocusedFrame());
275 EXPECT_EQ("\"child2-focused-input1\"", press_tab_and_wait_for_message(true)); 276 EXPECT_EQ("\"child2-focused-input1\"", press_tab_and_wait_for_message(true));
276 EXPECT_EQ("\"child1-focused-input2\"", press_tab_and_wait_for_message(true)); 277 EXPECT_EQ("\"child1-focused-input2\"", press_tab_and_wait_for_message(true));
277 EXPECT_EQ(child1, web_contents->GetFocusedFrame()); 278 EXPECT_EQ(child1, web_contents->GetFocusedFrame());
278 EXPECT_EQ("\"child1-focused-input1\"", press_tab_and_wait_for_message(true)); 279 EXPECT_EQ("\"child1-focused-input1\"", press_tab_and_wait_for_message(true));
279 EXPECT_EQ("\"root-focused-input1\"", press_tab_and_wait_for_message(true)); 280 EXPECT_EQ("\"root-focused-input1\"", press_tab_and_wait_for_message(true));
280 EXPECT_EQ(main_frame, web_contents->GetFocusedFrame()); 281 EXPECT_EQ(main_frame, web_contents->GetFocusedFrame());
281 } 282 }
282 283
284 // TODO(http://crbug.com/702330): Enable this test.
alexmos 2017/03/24 23:55:39 nit: https
avallee 2017/03/27 19:54:24 Done.
285 // Ensures that renderers know to advance focus to sibling frames and parent
286 // frames in the presence of mouse click initiated focus changes.
287 IN_PROC_BROWSER_TEST_F(SitePerProcessInteractiveBrowserTest,
288 DISABLED_TabAndMouseFocusNavigation) {
289 GURL main_url(embedded_test_server()->GetURL(
290 "a.com", "/cross_site_iframe_factory.html?a(b,c)"));
291 ui_test_utils::NavigateToURL(browser(), main_url);
292
293 content::WebContents* web_contents =
294 browser()->tab_strip_model()->GetActiveWebContents();
295
296 content::RenderFrameHost* main_frame = web_contents->GetMainFrame();
297 content::RenderFrameHost* child1 = ChildFrameAt(main_frame, 0);
298 ASSERT_NE(nullptr, child1);
299 content::RenderFrameHost* child2 = ChildFrameAt(main_frame, 1);
300 ASSERT_NE(nullptr, child2);
301
302 // Assign a name to each frame. This will be sent along in test messages
303 // from focus events.
304 EXPECT_TRUE(ExecuteScript(main_frame, "window.name = 'root';"));
305 EXPECT_TRUE(ExecuteScript(child1, "window.name = 'child1';"));
306 EXPECT_TRUE(ExecuteScript(child2, "window.name = 'child2';"));
307
308 // This script will insert two <input> fields in the document, one at the
309 // beginning and one at the end. For root frame, this means that we will
310 // have an <input>, then two <iframe> elements, then another <input>.
alexmos 2017/03/24 23:55:39 Perhaps also mention what it sends back. It's kin
avallee 2017/03/27 19:54:24 Done.
311 std::string script =
312 "function onFocus(e) {"
313 " console.log(window.name+'-focused-'+ e.target.id);"
314 " domAutomationController.setAutomationId(0);"
315 " domAutomationController.send(window.name + '-focused-' + e.target.id);"
316 "}"
317 ""
318 "function getElementCoords(element) {"
319 " var rect = element.getBoundingClientRect();"
320 " return Math.floor(rect.left + 0.5 * rect.width) +','+"
321 " Math.floor(rect.top + 0.5 * rect.height);"
322 "}"
323 "function getIframeCoords(element) {"
324 " var rect = element.getBoundingClientRect();"
325 " return Math.floor(rect.left) +','+"
326 " Math.floor(rect.top);"
327 "}"
328 ""
329 "document.styleSheets[0].insertRule('input {width:100%;margin:0;}', 1);"
330 "document.styleSheets[0].insertRule('h2 {margin:0;}', 1);"
331 "var input1 = document.createElement('input');"
332 "input1.id = 'input1';"
333 "input1.addEventListener('focus', onFocus, false);"
334 "var input2 = document.createElement('input');"
335 "input2.id = 'input2';"
336 "input2.addEventListener('focus', onFocus, false);"
337 "document.body.insertBefore(input1, document.body.firstChild);"
338 "document.body.appendChild(input2);"
339 ""
340 "var frames = document.querySelectorAll('iframe');"
341 "frames = Array.prototype.map.call(frames, getIframeCoords).join(';');"
342 "var inputCoords = [input1, input2].map(getElementCoords).join(';');"
343 "if (frames) {"
344 " inputCoords = inputCoords + ':' + frames;"
345 "}"
346 "domAutomationController.send(inputCoords);";
347
348 auto parse_points = [](const std::string& input, const gfx::Point& offset) {
349 base::StringPairs pieces;
350 base::SplitStringIntoKeyValuePairs(input, ',', ';', &pieces);
351 std::vector<gfx::Point> points;
352 for (const auto& piece : pieces) {
353 int x, y;
354 EXPECT_TRUE(base::StringToInt(piece.first, &x));
355 EXPECT_TRUE(base::StringToInt(piece.second, &y));
356 points.push_back(gfx::Point(x + offset.x(), y + offset.y()));
357 }
358 return points;
359 };
360 auto parse_points_and_offsets = [parse_points](const std::string& input) {
361 auto pieces = base::SplitString(input, ":", base::TRIM_WHITESPACE,
362 base::SPLIT_WANT_NONEMPTY);
363 gfx::Point origin;
alexmos 2017/03/24 23:55:39 is there a better name? I'm thinking of the docum
avallee 2017/03/27 19:54:24 Well both the input points and the offset points f
alexmos 2017/03/27 23:09:28 Yes, either one of those sounds fine.
364 return make_pair(parse_points(pieces[0], origin),
365 parse_points(pieces[1], origin));
366 };
367
368 // Add two input fields to each of the three frames.
369 std::string result;
370 EXPECT_TRUE(ExecuteScriptAndExtractString(main_frame, script, &result));
371 auto parsed = parse_points_and_offsets(result);
372 auto main_points = parsed.first;
alexmos 2017/03/24 23:55:39 nit: I'd rename to something like main_frame_input
avallee 2017/03/27 19:54:24 Done.
373
374 EXPECT_TRUE(ExecuteScriptAndExtractString(child1, script, &result));
375 auto child1_points = parse_points(result, parsed.second[0]);
376 EXPECT_TRUE(ExecuteScriptAndExtractString(child2, script, &result));
377 auto child2_points = parse_points(result, parsed.second[1]);
378
379 // Helper to simulate a tab press and wait for a focus message.
380 auto press_tab_and_wait_for_message = [web_contents](bool reverse) {
381 content::DOMMessageQueue msg_queue;
382 std::string reply;
383 LOG(ERROR) << "SimulateKeyPress";
alexmos 2017/03/24 23:55:39 Did you want to leave these and the console.log()
avallee 2017/03/27 19:54:25 nope, missed a couple.
384 SimulateKeyPress(web_contents, ui::DomKey::TAB, ui::DomCode::TAB,
385 ui::VKEY_TAB, false, reverse /* shift */, false, false);
386 EXPECT_TRUE(msg_queue.WaitForMessage(&reply));
387 LOG(ERROR) << "the reply is: " << reply;
388 return reply;
389 };
390
391 auto click_element_and_wait_for_message =
392 [web_contents](const gfx::Point& point) {
393 content::DOMMessageQueue msg_queue{web_contents};
alexmos 2017/03/24 23:55:39 Why the {} and not just ()? And do you need it at
avallee 2017/03/27 19:54:24 Gone, this was trying to fix the failure that I di
394
395 auto content_bounds = web_contents->GetContainerBounds();
396 ui_controls::SendMouseMove(point.x() + content_bounds.x(),
397 point.y() + content_bounds.y());
398 ui_controls::SendMouseClick(ui_controls::LEFT);
399
400 std::string reply;
401 EXPECT_TRUE(msg_queue.WaitForMessage(&reply));
402 return reply;
403 };
404
405 // Tab from child1 back to root.
406 EXPECT_EQ("\"root-focused-input1\"",
407 click_element_and_wait_for_message(main_points[0]));
408 EXPECT_EQ(main_frame, web_contents->GetFocusedFrame());
409 EXPECT_EQ("\"child1-focused-input1\"",
410 click_element_and_wait_for_message(child1_points[0]));
411 EXPECT_EQ(child1, web_contents->GetFocusedFrame());
412 EXPECT_EQ("\"root-focused-input1\"", press_tab_and_wait_for_message(true));
413 EXPECT_EQ(main_frame, web_contents->GetFocusedFrame());
414
415 // Tab from child2 forward to root.
416 EXPECT_EQ("\"root-focused-input2\"",
417 click_element_and_wait_for_message(main_points[1]));
418 EXPECT_EQ(main_frame, web_contents->GetFocusedFrame());
419 EXPECT_EQ("\"child2-focused-input2\"",
420 click_element_and_wait_for_message(child2_points[1]));
421 EXPECT_EQ(child2, web_contents->GetFocusedFrame());
422 EXPECT_EQ("\"root-focused-input2\"", press_tab_and_wait_for_message(false));
423 EXPECT_EQ(main_frame, web_contents->GetFocusedFrame());
424
425 // Tab forward from child1 to child2.
426 EXPECT_EQ("\"child2-focused-input1\"",
427 click_element_and_wait_for_message(child2_points[0]));
428 EXPECT_EQ(child2, web_contents->GetFocusedFrame());
429 EXPECT_EQ("\"child1-focused-input2\"",
430 click_element_and_wait_for_message(child1_points[1]));
431 EXPECT_EQ(child1, web_contents->GetFocusedFrame());
432 LOG(ERROR) << "before fail";
alexmos 2017/03/24 23:55:39 remove? (also below)
avallee 2017/03/27 19:54:24 Done.
433 EXPECT_EQ("\"child2-focused-input1\"", press_tab_and_wait_for_message(false));
434 LOG(ERROR) << "after fail";
435 EXPECT_EQ(child2, web_contents->GetFocusedFrame());
436
437 // Tab backward from child2 to child1.
438 EXPECT_EQ("\"child1-focused-input2\"",
439 click_element_and_wait_for_message(child1_points[1]));
440 EXPECT_EQ(child1, web_contents->GetFocusedFrame());
441 EXPECT_EQ("\"child2-focused-input1\"",
442 click_element_and_wait_for_message(child2_points[0]));
443 EXPECT_EQ(child2, web_contents->GetFocusedFrame());
444 EXPECT_EQ("\"child1-focused-input2\"", press_tab_and_wait_for_message(true));
445 EXPECT_EQ(child1, web_contents->GetFocusedFrame());
446
447 // Ensure there are no pending focus events after tabbing.
448 EXPECT_EQ("\"root-focused-input1\"",
449 click_element_and_wait_for_message(main_points[0]))
450 << "Unexpected extra focus events.";
451 }
452
283 namespace { 453 namespace {
284 454
285 // Helper to retrieve the frame's (window.innerWidth, window.innerHeight). 455 // Helper to retrieve the frame's (window.innerWidth, window.innerHeight).
286 gfx::Size GetFrameSize(content::RenderFrameHost* frame) { 456 gfx::Size GetFrameSize(content::RenderFrameHost* frame) {
287 int width = 0; 457 int width = 0;
288 EXPECT_TRUE(ExecuteScriptAndExtractInt( 458 EXPECT_TRUE(ExecuteScriptAndExtractInt(
289 frame, "domAutomationController.send(window.innerWidth);", &width)); 459 frame, "domAutomationController.send(window.innerWidth);", &width));
290 460
291 int height = 0; 461 int height = 0;
292 EXPECT_TRUE(ExecuteScriptAndExtractInt( 462 EXPECT_TRUE(ExecuteScriptAndExtractInt(
(...skipping 624 matching lines...) Expand 10 before | Expand all | Expand 10 after
917 send_right_mouse_event(child_view->GetRenderWidgetHost(), 10, 20, 1087 send_right_mouse_event(child_view->GetRenderWidgetHost(), 10, 20,
918 blink::WebInputEvent::MouseUp); 1088 blink::WebInputEvent::MouseUp);
919 menu_waiter.WaitForMenuOpenAndClose(); 1089 menu_waiter.WaitForMenuOpenAndClose();
920 1090
921 gfx::Point point_in_root_window = 1091 gfx::Point point_in_root_window =
922 child_view->TransformPointToRootCoordSpace(gfx::Point(10, 20)); 1092 child_view->TransformPointToRootCoordSpace(gfx::Point(10, 20));
923 1093
924 EXPECT_EQ(point_in_root_window.x(), menu_waiter.params().x); 1094 EXPECT_EQ(point_in_root_window.x(), menu_waiter.params().x);
925 EXPECT_EQ(point_in_root_window.y(), menu_waiter.params().y); 1095 EXPECT_EQ(point_in_root_window.y(), menu_waiter.params().y);
926 } 1096 }
OLDNEW
« no previous file with comments | « no previous file | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698