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

Side by Side Diff: Source/core/page/FocusController.cpp

Issue 852083002: Propagate focus type to plugins (Closed) Base URL: svn://svn.chromium.org/blink/trunk
Patch Set: Moved Created 5 years, 11 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 | Annotate | Revision Log
« no previous file with comments | « Source/core/page/FocusController.h ('k') | Source/core/page/FocusType.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /* 1 /*
2 * Copyright (C) 2006, 2007 Apple Inc. All rights reserved. 2 * Copyright (C) 2006, 2007 Apple Inc. All rights reserved.
3 * Copyright (C) 2008 Nuanti Ltd. 3 * Copyright (C) 2008 Nuanti Ltd.
4 * 4 *
5 * Redistribution and use in source and binary forms, with or without 5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions 6 * modification, are permitted provided that the following conditions
7 * are met: 7 * are met:
8 * 1. Redistributions of source code must retain the above copyright 8 * 1. Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer. 9 * notice, this list of conditions and the following disclaimer.
10 * 2. Redistributions in binary form must reproduce the above copyright 10 * 2. Redistributions in binary form must reproduce the above copyright
(...skipping 157 matching lines...) Expand 10 before | Expand all | Expand 10 after
168 if (focusedElement == document->focusedElement()) 168 if (focusedElement == document->focusedElement())
169 focusedElement->dispatchFocusOutEvent(EventTypeNames::DOMFocusOu t, nullptr); 169 focusedElement->dispatchFocusOutEvent(EventTypeNames::DOMFocusOu t, nullptr);
170 } 170 }
171 } 171 }
172 172
173 if (LocalDOMWindow* window = document->domWindow()) 173 if (LocalDOMWindow* window = document->domWindow())
174 window->dispatchEvent(Event::create(focused ? EventTypeNames::focus : Ev entTypeNames::blur)); 174 window->dispatchEvent(Event::create(focused ? EventTypeNames::focus : Ev entTypeNames::blur));
175 if (focused && document->focusedElement()) { 175 if (focused && document->focusedElement()) {
176 RefPtrWillBeRawPtr<Element> focusedElement(document->focusedElement()); 176 RefPtrWillBeRawPtr<Element> focusedElement(document->focusedElement());
177 focusedElement->setFocus(true); 177 focusedElement->setFocus(true);
178 focusedElement->dispatchFocusEvent(0, FocusTypePage); 178 focusedElement->dispatchFocusEvent(0, WebFocusTypePage);
179 if (focusedElement == document->focusedElement()) { 179 if (focusedElement == document->focusedElement()) {
180 document->focusedElement()->dispatchFocusInEvent(EventTypeNames::foc usin, nullptr, FocusTypePage); 180 document->focusedElement()->dispatchFocusInEvent(EventTypeNames::foc usin, nullptr, WebFocusTypePage);
181 if (focusedElement == document->focusedElement()) 181 if (focusedElement == document->focusedElement())
182 document->focusedElement()->dispatchFocusInEvent(EventTypeNames: :DOMFocusIn, nullptr, FocusTypePage); 182 document->focusedElement()->dispatchFocusInEvent(EventTypeNames: :DOMFocusIn, nullptr, WebFocusTypePage);
183 } 183 }
184 } 184 }
185 } 185 }
186 186
187 static inline bool hasCustomFocusLogic(const Element& element) 187 static inline bool hasCustomFocusLogic(const Element& element)
188 { 188 {
189 return element.isHTMLElement() && toHTMLElement(element).hasCustomFocusLogic (); 189 return element.isHTMLElement() && toHTMLElement(element).hasCustomFocusLogic ();
190 } 190 }
191 191
192 #if ENABLE(ASSERT) 192 #if ENABLE(ASSERT)
(...skipping 98 matching lines...) Expand 10 before | Expand all | Expand 10 after
291 focusedElement->dispatchFocusOutEvent(EventTypeNames::DOMFoc usOut, nullptr); 291 focusedElement->dispatchFocusOutEvent(EventTypeNames::DOMFoc usOut, nullptr);
292 } 292 }
293 } 293 }
294 } 294 }
295 295
296 RefPtrWillBeRawPtr<LocalFrame> newFocusedFrame = (frame && frame->isLocalFra me()) ? toLocalFrame(frame.get()) : nullptr; 296 RefPtrWillBeRawPtr<LocalFrame> newFocusedFrame = (frame && frame->isLocalFra me()) ? toLocalFrame(frame.get()) : nullptr;
297 if (newFocusedFrame && newFocusedFrame->view()) { 297 if (newFocusedFrame && newFocusedFrame->view()) {
298 RefPtrWillBeRawPtr<Document> document = newFocusedFrame->document(); 298 RefPtrWillBeRawPtr<Document> document = newFocusedFrame->document();
299 Element* focusedElement = document ? document->focusedElement() : nullpt r; 299 Element* focusedElement = document ? document->focusedElement() : nullpt r;
300 if (focusedElement) { 300 if (focusedElement) {
301 focusedElement->dispatchFocusEvent(0, FocusTypePage); 301 focusedElement->dispatchFocusEvent(0, WebFocusTypePage);
302 if (focusedElement == document->focusedElement()) { 302 if (focusedElement == document->focusedElement()) {
303 document->focusedElement()->dispatchFocusInEvent(EventTypeNames: :focusin, nullptr, FocusTypePage); 303 document->focusedElement()->dispatchFocusInEvent(EventTypeNames: :focusin, nullptr, WebFocusTypePage);
304 if (focusedElement == document->focusedElement()) 304 if (focusedElement == document->focusedElement())
305 document->focusedElement()->dispatchFocusInEvent(EventTypeNa mes::DOMFocusIn, nullptr, FocusTypePage); 305 document->focusedElement()->dispatchFocusInEvent(EventTypeNa mes::DOMFocusIn, nullptr, WebFocusTypePage);
306 } 306 }
307 } 307 }
308 } 308 }
309 309
310 setFocusedFrame(frame); 310 setFocusedFrame(frame);
311 } 311 }
312 312
313 Frame* FocusController::focusedOrMainFrame() const 313 Frame* FocusController::focusedOrMainFrame() const
314 { 314 {
315 if (Frame* frame = focusedFrame()) 315 if (Frame* frame = focusedFrame())
(...skipping 23 matching lines...) Expand all
339 setFocusedFrame(m_page->mainFrame()); 339 setFocusedFrame(m_page->mainFrame());
340 340
341 // setFocusedFrame above might reject to update m_focusedFrame, or 341 // setFocusedFrame above might reject to update m_focusedFrame, or
342 // m_focusedFrame might be changed by blur/focus event handlers. 342 // m_focusedFrame might be changed by blur/focus event handlers.
343 if (m_focusedFrame && m_focusedFrame->isLocalFrame() && toLocalFrame(m_focus edFrame.get())->view()) { 343 if (m_focusedFrame && m_focusedFrame->isLocalFrame() && toLocalFrame(m_focus edFrame.get())->view()) {
344 toLocalFrame(m_focusedFrame.get())->selection().setFocused(focused); 344 toLocalFrame(m_focusedFrame.get())->selection().setFocused(focused);
345 dispatchEventsOnWindowAndFocusedNode(toLocalFrame(m_focusedFrame.get())- >document(), focused); 345 dispatchEventsOnWindowAndFocusedNode(toLocalFrame(m_focusedFrame.get())- >document(), focused);
346 } 346 }
347 } 347 }
348 348
349 Node* FocusController::findFocusableNodeDecendingDownIntoFrameDocument(FocusType type, Node* node) 349 Node* FocusController::findFocusableNodeDecendingDownIntoFrameDocument(WebFocusT ype type, Node* node)
350 { 350 {
351 // The node we found might be a HTMLFrameOwnerElement, so descend down the t ree until we find either: 351 // The node we found might be a HTMLFrameOwnerElement, so descend down the t ree until we find either:
352 // 1) a focusable node, or 352 // 1) a focusable node, or
353 // 2) the deepest-nested HTMLFrameOwnerElement. 353 // 2) the deepest-nested HTMLFrameOwnerElement.
354 while (node && node->isFrameOwnerElement()) { 354 while (node && node->isFrameOwnerElement()) {
355 HTMLFrameOwnerElement& owner = toHTMLFrameOwnerElement(*node); 355 HTMLFrameOwnerElement& owner = toHTMLFrameOwnerElement(*node);
356 if (!owner.contentFrame() || !owner.contentFrame()->isLocalFrame()) 356 if (!owner.contentFrame() || !owner.contentFrame()->isLocalFrame())
357 break; 357 break;
358 toLocalFrame(owner.contentFrame())->document()->updateLayoutIgnorePendin gStylesheets(); 358 toLocalFrame(owner.contentFrame())->document()->updateLayoutIgnorePendin gStylesheets();
359 Node* foundNode = findFocusableNode(type, FocusNavigationScope::ownedByI Frame(owner), nullptr); 359 Node* foundNode = findFocusableNode(type, FocusNavigationScope::ownedByI Frame(owner), nullptr);
360 if (!foundNode) 360 if (!foundNode)
361 break; 361 break;
362 ASSERT(node != foundNode); 362 ASSERT(node != foundNode);
363 node = foundNode; 363 node = foundNode;
364 } 364 }
365 return node; 365 return node;
366 } 366 }
367 367
368 bool FocusController::setInitialFocus(FocusType type) 368 bool FocusController::setInitialFocus(WebFocusType type)
369 { 369 {
370 bool didAdvanceFocus = advanceFocus(type, true); 370 bool didAdvanceFocus = advanceFocus(type, true);
371 371
372 // If focus is being set initially, accessibility needs to be informed that system focus has moved 372 // If focus is being set initially, accessibility needs to be informed that system focus has moved
373 // into the web area again, even if focus did not change within WebCore. Pos tNotification is called instead 373 // into the web area again, even if focus did not change within WebCore. Pos tNotification is called instead
374 // of handleFocusedUIElementChanged, because this will send the notification even if the element is the same. 374 // of handleFocusedUIElementChanged, because this will send the notification even if the element is the same.
375 if (focusedOrMainFrame()->isLocalFrame()) { 375 if (focusedOrMainFrame()->isLocalFrame()) {
376 Document* document = toLocalFrame(focusedOrMainFrame())->document(); 376 Document* document = toLocalFrame(focusedOrMainFrame())->document();
377 if (AXObjectCache* cache = document->existingAXObjectCache()) 377 if (AXObjectCache* cache = document->existingAXObjectCache())
378 cache->handleInitialFocus(); 378 cache->handleInitialFocus();
379 } 379 }
380 380
381 return didAdvanceFocus; 381 return didAdvanceFocus;
382 } 382 }
383 383
384 bool FocusController::advanceFocus(FocusType type, bool initialFocus) 384 bool FocusController::advanceFocus(WebFocusType type, bool initialFocus)
385 { 385 {
386 switch (type) { 386 switch (type) {
387 case FocusTypeForward: 387 case WebFocusTypeForward:
388 case FocusTypeBackward: 388 case WebFocusTypeBackward:
389 return advanceFocusInDocumentOrder(type, initialFocus); 389 return advanceFocusInDocumentOrder(type, initialFocus);
390 case FocusTypeLeft: 390 case WebFocusTypeLeft:
391 case FocusTypeRight: 391 case WebFocusTypeRight:
392 case FocusTypeUp: 392 case WebFocusTypeUp:
393 case FocusTypeDown: 393 case WebFocusTypeDown:
394 return advanceFocusDirectionally(type); 394 return advanceFocusDirectionally(type);
395 default: 395 default:
396 ASSERT_NOT_REACHED(); 396 ASSERT_NOT_REACHED();
397 } 397 }
398 398
399 return false; 399 return false;
400 } 400 }
401 401
402 bool FocusController::advanceFocusInDocumentOrder(FocusType type, bool initialFo cus) 402 bool FocusController::advanceFocusInDocumentOrder(WebFocusType type, bool initia lFocus)
403 { 403 {
404 // FIXME: Focus advancement won't work with externally rendered frames until after 404 // FIXME: Focus advancement won't work with externally rendered frames until after
405 // inter-frame focus control is moved out of Blink. 405 // inter-frame focus control is moved out of Blink.
406 if (!focusedOrMainFrame()->isLocalFrame()) 406 if (!focusedOrMainFrame()->isLocalFrame())
407 return false; 407 return false;
408 LocalFrame* frame = toLocalFrame(focusedOrMainFrame()); 408 LocalFrame* frame = toLocalFrame(focusedOrMainFrame());
409 ASSERT(frame); 409 ASSERT(frame);
410 Document* document = frame->document(); 410 Document* document = frame->document();
411 411
412 Node* currentNode = document->focusedElement(); 412 Node* currentNode = document->focusedElement();
(...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after
477 if (caretBrowsing) { 477 if (caretBrowsing) {
478 Position position = firstPositionInOrBeforeNode(element); 478 Position position = firstPositionInOrBeforeNode(element);
479 VisibleSelection newSelection(position, position, DOWNSTREAM); 479 VisibleSelection newSelection(position, position, DOWNSTREAM);
480 frame->selection().setSelection(newSelection); 480 frame->selection().setSelection(newSelection);
481 } 481 }
482 482
483 element->focus(false, type); 483 element->focus(false, type);
484 return true; 484 return true;
485 } 485 }
486 486
487 Node* FocusController::findFocusableNodeAcrossFocusScope(FocusType type, const F ocusNavigationScope& scope, Node* currentNode) 487 Node* FocusController::findFocusableNodeAcrossFocusScope(WebFocusType type, cons t FocusNavigationScope& scope, Node* currentNode)
488 { 488 {
489 ASSERT(!currentNode || !isNonFocusableShadowHost(*currentNode)); 489 ASSERT(!currentNode || !isNonFocusableShadowHost(*currentNode));
490 Node* found; 490 Node* found;
491 if (currentNode && type == FocusTypeForward && isKeyboardFocusableShadowHost (*currentNode)) { 491 if (currentNode && type == WebFocusTypeForward && isKeyboardFocusableShadowH ost(*currentNode)) {
492 Node* foundInInnerFocusScope = findFocusableNodeRecursively(type, FocusN avigationScope::ownedByShadowHost(*currentNode), nullptr); 492 Node* foundInInnerFocusScope = findFocusableNodeRecursively(type, FocusN avigationScope::ownedByShadowHost(*currentNode), nullptr);
493 found = foundInInnerFocusScope ? foundInInnerFocusScope : findFocusableN odeRecursively(type, scope, currentNode); 493 found = foundInInnerFocusScope ? foundInInnerFocusScope : findFocusableN odeRecursively(type, scope, currentNode);
494 } else { 494 } else {
495 found = findFocusableNodeRecursively(type, scope, currentNode); 495 found = findFocusableNodeRecursively(type, scope, currentNode);
496 } 496 }
497 497
498 // If there's no focusable node to advance to, move up the focus scopes unti l we find one. 498 // If there's no focusable node to advance to, move up the focus scopes unti l we find one.
499 FocusNavigationScope currentScope = scope; 499 FocusNavigationScope currentScope = scope;
500 while (!found) { 500 while (!found) {
501 Node* owner = currentScope.owner(); 501 Node* owner = currentScope.owner();
502 if (!owner) 502 if (!owner)
503 break; 503 break;
504 currentScope = FocusNavigationScope::focusNavigationScopeOf(*owner); 504 currentScope = FocusNavigationScope::focusNavigationScopeOf(*owner);
505 if (type == FocusTypeBackward && isKeyboardFocusableShadowHost(*owner)) { 505 if (type == WebFocusTypeBackward && isKeyboardFocusableShadowHost(*owner )) {
506 found = owner; 506 found = owner;
507 break; 507 break;
508 } 508 }
509 found = findFocusableNodeRecursively(type, currentScope, owner); 509 found = findFocusableNodeRecursively(type, currentScope, owner);
510 } 510 }
511 found = findFocusableNodeDecendingDownIntoFrameDocument(type, found); 511 found = findFocusableNodeDecendingDownIntoFrameDocument(type, found);
512 return found; 512 return found;
513 } 513 }
514 514
515 Node* FocusController::findFocusableNodeRecursively(FocusType type, const FocusN avigationScope& scope, Node* start) 515 Node* FocusController::findFocusableNodeRecursively(WebFocusType type, const Foc usNavigationScope& scope, Node* start)
516 { 516 {
517 // Starting node is exclusive. 517 // Starting node is exclusive.
518 Node* foundOrNull = findFocusableNode(type, scope, start); 518 Node* foundOrNull = findFocusableNode(type, scope, start);
519 if (!foundOrNull) 519 if (!foundOrNull)
520 return nullptr; 520 return nullptr;
521 Node& found = *foundOrNull; 521 Node& found = *foundOrNull;
522 if (type == FocusTypeForward) { 522 if (type == WebFocusTypeForward) {
523 if (!isNonFocusableFocusScopeOwner(found)) 523 if (!isNonFocusableFocusScopeOwner(found))
524 return &found; 524 return &found;
525 Node* foundInInnerFocusScope = findFocusableNodeRecursively(type, FocusN avigationScope::ownedByNonFocusableFocusScopeOwner(found), nullptr); 525 Node* foundInInnerFocusScope = findFocusableNodeRecursively(type, FocusN avigationScope::ownedByNonFocusableFocusScopeOwner(found), nullptr);
526 return foundInInnerFocusScope ? foundInInnerFocusScope : findFocusableNo deRecursively(type, scope, &found); 526 return foundInInnerFocusScope ? foundInInnerFocusScope : findFocusableNo deRecursively(type, scope, &found);
527 } 527 }
528 ASSERT(type == FocusTypeBackward); 528 ASSERT(type == WebFocusTypeBackward);
529 if (isKeyboardFocusableShadowHost(found)) { 529 if (isKeyboardFocusableShadowHost(found)) {
530 Node* foundInInnerFocusScope = findFocusableNodeRecursively(type, FocusN avigationScope::ownedByShadowHost(found), nullptr); 530 Node* foundInInnerFocusScope = findFocusableNodeRecursively(type, FocusN avigationScope::ownedByShadowHost(found), nullptr);
531 return foundInInnerFocusScope ? foundInInnerFocusScope : &found; 531 return foundInInnerFocusScope ? foundInInnerFocusScope : &found;
532 } 532 }
533 if (isNonFocusableFocusScopeOwner(found)) { 533 if (isNonFocusableFocusScopeOwner(found)) {
534 Node* foundInInnerFocusScope = findFocusableNodeRecursively(type, FocusN avigationScope::ownedByNonFocusableFocusScopeOwner(found), nullptr); 534 Node* foundInInnerFocusScope = findFocusableNodeRecursively(type, FocusN avigationScope::ownedByNonFocusableFocusScopeOwner(found), nullptr);
535 return foundInInnerFocusScope ? foundInInnerFocusScope :findFocusableNod eRecursively(type, scope, &found); 535 return foundInInnerFocusScope ? foundInInnerFocusScope :findFocusableNod eRecursively(type, scope, &found);
536 } 536 }
537 return &found; 537 return &found;
538 } 538 }
539 539
540 Node* FocusController::findFocusableNode(FocusType type, const FocusNavigationSc ope& scope, Node* node) 540 Node* FocusController::findFocusableNode(WebFocusType type, const FocusNavigatio nScope& scope, Node* node)
541 { 541 {
542 return type == FocusTypeForward ? nextFocusableNode(scope, node) : previousF ocusableNode(scope, node); 542 return type == WebFocusTypeForward ? nextFocusableNode(scope, node) : previo usFocusableNode(scope, node);
543 } 543 }
544 544
545 Node* FocusController::findNodeWithExactTabIndex(Node* start, int tabIndex, Focu sType type) 545 Node* FocusController::findNodeWithExactTabIndex(Node* start, int tabIndex, WebF ocusType type)
546 { 546 {
547 // Search is inclusive of start 547 // Search is inclusive of start
548 for (Node* node = start; node; node = type == FocusTypeForward ? NodeTravers al::next(*node) : NodeTraversal::previous(*node)) { 548 for (Node* node = start; node; node = type == WebFocusTypeForward ? NodeTrav ersal::next(*node) : NodeTraversal::previous(*node)) {
549 if (shouldVisit(*node) && adjustedTabIndex(*node) == tabIndex) 549 if (shouldVisit(*node) && adjustedTabIndex(*node) == tabIndex)
550 return node; 550 return node;
551 } 551 }
552 return nullptr; 552 return nullptr;
553 } 553 }
554 554
555 static Node* nextNodeWithGreaterTabIndex(Node* start, int tabIndex) 555 static Node* nextNodeWithGreaterTabIndex(Node* start, int tabIndex)
556 { 556 {
557 // Search is inclusive of start 557 // Search is inclusive of start
558 int winningTabIndex = std::numeric_limits<short>::max() + 1; 558 int winningTabIndex = std::numeric_limits<short>::max() + 1;
(...skipping 29 matching lines...) Expand all
588 if (start) { 588 if (start) {
589 int tabIndex = adjustedTabIndex(*start); 589 int tabIndex = adjustedTabIndex(*start);
590 // If a node is excluded from the normal tabbing cycle, the next focusab le node is determined by tree order 590 // If a node is excluded from the normal tabbing cycle, the next focusab le node is determined by tree order
591 if (tabIndex < 0) { 591 if (tabIndex < 0) {
592 for (Node& node : NodeTraversal::startsAfter(*start)) { 592 for (Node& node : NodeTraversal::startsAfter(*start)) {
593 if (shouldVisit(node) && adjustedTabIndex(node) >= 0) 593 if (shouldVisit(node) && adjustedTabIndex(node) >= 0)
594 return &node; 594 return &node;
595 } 595 }
596 } else { 596 } else {
597 // First try to find a node with the same tabindex as start that com es after start in the scope. 597 // First try to find a node with the same tabindex as start that com es after start in the scope.
598 if (Node* winner = findNodeWithExactTabIndex(NodeTraversal::next(*st art), tabIndex, FocusTypeForward)) 598 if (Node* winner = findNodeWithExactTabIndex(NodeTraversal::next(*st art), tabIndex, WebFocusTypeForward))
599 return winner; 599 return winner;
600 } 600 }
601 if (!tabIndex) { 601 if (!tabIndex) {
602 // We've reached the last node in the document with a tabindex of 0. This is the end of the tabbing order. 602 // We've reached the last node in the document with a tabindex of 0. This is the end of the tabbing order.
603 return nullptr; 603 return nullptr;
604 } 604 }
605 } 605 }
606 606
607 // Look for the first node in the scope that: 607 // Look for the first node in the scope that:
608 // 1) has the lowest tabindex that is higher than start's tabindex (or 0, if start is null), and 608 // 1) has the lowest tabindex that is higher than start's tabindex (or 0, if start is null), and
609 // 2) comes first in the scope, if there's a tie. 609 // 2) comes first in the scope, if there's a tie.
610 if (Node* winner = nextNodeWithGreaterTabIndex(scope.rootNode(), start ? adj ustedTabIndex(*start) : 0)) 610 if (Node* winner = nextNodeWithGreaterTabIndex(scope.rootNode(), start ? adj ustedTabIndex(*start) : 0))
611 return winner; 611 return winner;
612 612
613 // There are no nodes with a tabindex greater than start's tabindex, 613 // There are no nodes with a tabindex greater than start's tabindex,
614 // so find the first node with a tabindex of 0. 614 // so find the first node with a tabindex of 0.
615 return findNodeWithExactTabIndex(scope.rootNode(), 0, FocusTypeForward); 615 return findNodeWithExactTabIndex(scope.rootNode(), 0, WebFocusTypeForward);
616 } 616 }
617 617
618 Node* FocusController::previousFocusableNode(const FocusNavigationScope& scope, Node* start) 618 Node* FocusController::previousFocusableNode(const FocusNavigationScope& scope, Node* start)
619 { 619 {
620 Node* last = nullptr; 620 Node* last = nullptr;
621 for (Node* node = scope.rootNode(); node; node = node->lastChild()) 621 for (Node* node = scope.rootNode(); node; node = node->lastChild())
622 last = node; 622 last = node;
623 ASSERT(last); 623 ASSERT(last);
624 624
625 // First try to find the last node in the scope that comes before start and has the same tabindex as start. 625 // First try to find the last node in the scope that comes before start and has the same tabindex as start.
626 // If start is null, find the last node in the scope with a tabindex of 0. 626 // If start is null, find the last node in the scope with a tabindex of 0.
627 Node* startingNode; 627 Node* startingNode;
628 int startingTabIndex; 628 int startingTabIndex;
629 if (start) { 629 if (start) {
630 startingNode = NodeTraversal::previous(*start); 630 startingNode = NodeTraversal::previous(*start);
631 startingTabIndex = adjustedTabIndex(*start); 631 startingTabIndex = adjustedTabIndex(*start);
632 } else { 632 } else {
633 startingNode = last; 633 startingNode = last;
634 startingTabIndex = 0; 634 startingTabIndex = 0;
635 } 635 }
636 636
637 // However, if a node is excluded from the normal tabbing cycle, the previou s focusable node is determined by tree order 637 // However, if a node is excluded from the normal tabbing cycle, the previou s focusable node is determined by tree order
638 if (startingTabIndex < 0) { 638 if (startingTabIndex < 0) {
639 for (Node* node = startingNode; node; node = NodeTraversal::previous(*no de)) { 639 for (Node* node = startingNode; node; node = NodeTraversal::previous(*no de)) {
640 if (shouldVisit(*node) && adjustedTabIndex(*node) >= 0) 640 if (shouldVisit(*node) && adjustedTabIndex(*node) >= 0)
641 return node; 641 return node;
642 } 642 }
643 } else { 643 } else {
644 if (Node* winner = findNodeWithExactTabIndex(startingNode, startingTabIn dex, FocusTypeBackward)) 644 if (Node* winner = findNodeWithExactTabIndex(startingNode, startingTabIn dex, WebFocusTypeBackward))
645 return winner; 645 return winner;
646 } 646 }
647 647
648 // There are no nodes before start with the same tabindex as start, so look for a node that: 648 // There are no nodes before start with the same tabindex as start, so look for a node that:
649 // 1) has the highest non-zero tabindex (that is less than start's tabindex) , and 649 // 1) has the highest non-zero tabindex (that is less than start's tabindex) , and
650 // 2) comes last in the scope, if there's a tie. 650 // 2) comes last in the scope, if there's a tie.
651 startingTabIndex = (start && startingTabIndex) ? startingTabIndex : std::num eric_limits<short>::max(); 651 startingTabIndex = (start && startingTabIndex) ? startingTabIndex : std::num eric_limits<short>::max();
652 return previousNodeWithLowerTabIndex(last, startingTabIndex); 652 return previousNodeWithLowerTabIndex(last, startingTabIndex);
653 } 653 }
654 654
(...skipping 25 matching lines...) Expand all
680 680
681 if (!enclosingTextFormControl(selectionStartNode)) 681 if (!enclosingTextFormControl(selectionStartNode))
682 return; 682 return;
683 683
684 if (selectionStartNode->isInShadowTree() && selectionStartNode->shadowHost() == newFocusedNode) 684 if (selectionStartNode->isInShadowTree() && selectionStartNode->shadowHost() == newFocusedNode)
685 return; 685 return;
686 686
687 selection.clear(); 687 selection.clear();
688 } 688 }
689 689
690 bool FocusController::setFocusedElement(Element* element, PassRefPtrWillBeRawPtr <Frame> newFocusedFrame, FocusType type) 690 bool FocusController::setFocusedElement(Element* element, PassRefPtrWillBeRawPtr <Frame> newFocusedFrame, WebFocusType type)
691 { 691 {
692 RefPtrWillBeRawPtr<LocalFrame> oldFocusedFrame = toLocalFrame(focusedFrame() ); 692 RefPtrWillBeRawPtr<LocalFrame> oldFocusedFrame = toLocalFrame(focusedFrame() );
693 RefPtrWillBeRawPtr<Document> oldDocument = oldFocusedFrame ? oldFocusedFrame ->document() : nullptr; 693 RefPtrWillBeRawPtr<Document> oldDocument = oldFocusedFrame ? oldFocusedFrame ->document() : nullptr;
694 694
695 Element* oldFocusedElement = oldDocument ? oldDocument->focusedElement() : n ullptr; 695 Element* oldFocusedElement = oldDocument ? oldDocument->focusedElement() : n ullptr;
696 if (element && oldFocusedElement == element) 696 if (element && oldFocusedElement == element)
697 return true; 697 return true;
698 698
699 // FIXME: Might want to disable this check for caretBrowsing 699 // FIXME: Might want to disable this check for caretBrowsing
700 if (oldFocusedElement && oldFocusedElement->isRootEditableElement() && !reli nquishesEditingFocus(*oldFocusedElement)) 700 if (oldFocusedElement && oldFocusedElement->isRootEditableElement() && !reli nquishesEditingFocus(*oldFocusedElement))
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after
745 if (frame->isLocalFrame()) { 745 if (frame->isLocalFrame()) {
746 // Invalidate all custom scrollbars because they support the CSS 746 // Invalidate all custom scrollbars because they support the CSS
747 // window-active attribute. This should be applied to the entire page so 747 // window-active attribute. This should be applied to the entire page so
748 // we invalidate from the root FrameView instead of just the focused. 748 // we invalidate from the root FrameView instead of just the focused.
749 if (FrameView* view = toLocalFrame(frame)->localFrameRoot()->document()- >view()) 749 if (FrameView* view = toLocalFrame(frame)->localFrameRoot()->document()- >view())
750 view->invalidateAllCustomScrollbarsOnActiveChanged(); 750 view->invalidateAllCustomScrollbarsOnActiveChanged();
751 toLocalFrame(frame)->selection().pageActivationChanged(); 751 toLocalFrame(frame)->selection().pageActivationChanged();
752 } 752 }
753 } 753 }
754 754
755 static void updateFocusCandidateIfNeeded(FocusType type, const FocusCandidate& c urrent, FocusCandidate& candidate, FocusCandidate& closest) 755 static void updateFocusCandidateIfNeeded(WebFocusType type, const FocusCandidate & current, FocusCandidate& candidate, FocusCandidate& closest)
756 { 756 {
757 ASSERT(candidate.visibleNode->isElementNode()); 757 ASSERT(candidate.visibleNode->isElementNode());
758 ASSERT(candidate.visibleNode->renderer()); 758 ASSERT(candidate.visibleNode->renderer());
759 759
760 // Ignore iframes that don't have a src attribute 760 // Ignore iframes that don't have a src attribute
761 if (frameOwnerElement(candidate) && (!frameOwnerElement(candidate)->contentF rame() || candidate.rect.isEmpty())) 761 if (frameOwnerElement(candidate) && (!frameOwnerElement(candidate)->contentF rame() || candidate.rect.isEmpty()))
762 return; 762 return;
763 763
764 // Ignore off screen child nodes of containers that do not scroll (overflow: hidden) 764 // Ignore off screen child nodes of containers that do not scroll (overflow: hidden)
765 if (candidate.isOffscreen && !canBeScrolledIntoView(type, candidate)) 765 if (candidate.isOffscreen && !canBeScrolledIntoView(type, candidate))
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after
797 if (candidate.alignment == closest.alignment) { 797 if (candidate.alignment == closest.alignment) {
798 if (candidate.distance < closest.distance) 798 if (candidate.distance < closest.distance)
799 closest = candidate; 799 closest = candidate;
800 return; 800 return;
801 } 801 }
802 802
803 if (candidate.alignment > closest.alignment) 803 if (candidate.alignment > closest.alignment)
804 closest = candidate; 804 closest = candidate;
805 } 805 }
806 806
807 void FocusController::findFocusCandidateInContainer(Node& container, const Layou tRect& startingRect, FocusType type, FocusCandidate& closest) 807 void FocusController::findFocusCandidateInContainer(Node& container, const Layou tRect& startingRect, WebFocusType type, FocusCandidate& closest)
808 { 808 {
809 Element* focusedElement = (focusedFrame() && toLocalFrame(focusedFrame())->d ocument()) ? toLocalFrame(focusedFrame())->document()->focusedElement() : nullpt r; 809 Element* focusedElement = (focusedFrame() && toLocalFrame(focusedFrame())->d ocument()) ? toLocalFrame(focusedFrame())->document()->focusedElement() : nullpt r;
810 810
811 Element* element = ElementTraversal::firstWithin(container); 811 Element* element = ElementTraversal::firstWithin(container);
812 FocusCandidate current; 812 FocusCandidate current;
813 current.rect = startingRect; 813 current.rect = startingRect;
814 current.focusableNode = focusedElement; 814 current.focusableNode = focusedElement;
815 current.visibleNode = focusedElement; 815 current.visibleNode = focusedElement;
816 816
817 for (; element; element = (element->isFrameOwnerElement() || canScrollInDire ction(element, type)) 817 for (; element; element = (element->isFrameOwnerElement() || canScrollInDire ction(element, type))
818 ? ElementTraversal::nextSkippingChildren(*element, &container) 818 ? ElementTraversal::nextSkippingChildren(*element, &container)
819 : ElementTraversal::next(*element, &container)) { 819 : ElementTraversal::next(*element, &container)) {
820 if (element == focusedElement) 820 if (element == focusedElement)
821 continue; 821 continue;
822 822
823 if (!element->isKeyboardFocusable() && !element->isFrameOwnerElement() & & !canScrollInDirection(element, type)) 823 if (!element->isKeyboardFocusable() && !element->isFrameOwnerElement() & & !canScrollInDirection(element, type))
824 continue; 824 continue;
825 825
826 FocusCandidate candidate = FocusCandidate(element, type); 826 FocusCandidate candidate = FocusCandidate(element, type);
827 if (candidate.isNull()) 827 if (candidate.isNull())
828 continue; 828 continue;
829 829
830 candidate.enclosingScrollableBox = &container; 830 candidate.enclosingScrollableBox = &container;
831 updateFocusCandidateIfNeeded(type, current, candidate, closest); 831 updateFocusCandidateIfNeeded(type, current, candidate, closest);
832 } 832 }
833 } 833 }
834 834
835 bool FocusController::advanceFocusDirectionallyInContainer(Node* container, cons t LayoutRect& startingRect, FocusType type) 835 bool FocusController::advanceFocusDirectionallyInContainer(Node* container, cons t LayoutRect& startingRect, WebFocusType type)
836 { 836 {
837 if (!container) 837 if (!container)
838 return false; 838 return false;
839 839
840 LayoutRect newStartingRect = startingRect; 840 LayoutRect newStartingRect = startingRect;
841 841
842 if (startingRect.isEmpty()) 842 if (startingRect.isEmpty())
843 newStartingRect = virtualRectForDirection(type, nodeRectInAbsoluteCoordi nates(container)); 843 newStartingRect = virtualRectForDirection(type, nodeRectInAbsoluteCoordi nates(container));
844 844
845 // Find the closest node within current container in the direction of the na vigation. 845 // Find the closest node within current container in the direction of the na vigation.
(...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after
895 } 895 }
896 896
897 // We found a new focus node, navigate to it. 897 // We found a new focus node, navigate to it.
898 Element* element = toElement(focusCandidate.focusableNode); 898 Element* element = toElement(focusCandidate.focusableNode);
899 ASSERT(element); 899 ASSERT(element);
900 900
901 element->focus(false, type); 901 element->focus(false, type);
902 return true; 902 return true;
903 } 903 }
904 904
905 bool FocusController::advanceFocusDirectionally(FocusType type) 905 bool FocusController::advanceFocusDirectionally(WebFocusType type)
906 { 906 {
907 // FIXME: Directional focus changes don't yet work with RemoteFrames. 907 // FIXME: Directional focus changes don't yet work with RemoteFrames.
908 if (!focusedOrMainFrame()->isLocalFrame()) 908 if (!focusedOrMainFrame()->isLocalFrame())
909 return false; 909 return false;
910 LocalFrame* curFrame = toLocalFrame(focusedOrMainFrame()); 910 LocalFrame* curFrame = toLocalFrame(focusedOrMainFrame());
911 ASSERT(curFrame); 911 ASSERT(curFrame);
912 912
913 Document* focusedDocument = curFrame->document(); 913 Document* focusedDocument = curFrame->document();
914 if (!focusedDocument) 914 if (!focusedDocument)
915 return false; 915 return false;
(...skipping 29 matching lines...) Expand all
945 return consumed; 945 return consumed;
946 } 946 }
947 947
948 void FocusController::trace(Visitor* visitor) 948 void FocusController::trace(Visitor* visitor)
949 { 949 {
950 visitor->trace(m_page); 950 visitor->trace(m_page);
951 visitor->trace(m_focusedFrame); 951 visitor->trace(m_focusedFrame);
952 } 952 }
953 953
954 } // namespace blink 954 } // namespace blink
OLDNEW
« no previous file with comments | « Source/core/page/FocusController.h ('k') | Source/core/page/FocusType.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698