OLD | NEW |
1 /* | 1 /* |
2 * Copyright (C) 2011, 2012 Google Inc. All rights reserved. | 2 * Copyright (C) 2011, 2012 Google Inc. All rights reserved. |
3 * | 3 * |
4 * Redistribution and use in source and binary forms, with or without | 4 * Redistribution and use in source and binary forms, with or without |
5 * modification, are permitted provided that the following conditions are | 5 * modification, are permitted provided that the following conditions are |
6 * met: | 6 * met: |
7 * | 7 * |
8 * * Redistributions of source code must retain the above copyright | 8 * * 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 * * Redistributions in binary form must reproduce the above | 10 * * Redistributions in binary form must reproduce the above |
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
53 #include "core/frame/VisualViewport.h" | 53 #include "core/frame/VisualViewport.h" |
54 #include "core/frame/WebLocalFrameBase.h" | 54 #include "core/frame/WebLocalFrameBase.h" |
55 #include "core/html/HTMLIFrameElement.h" | 55 #include "core/html/HTMLIFrameElement.h" |
56 #include "core/html/HTMLInputElement.h" | 56 #include "core/html/HTMLInputElement.h" |
57 #include "core/html/HTMLTextAreaElement.h" | 57 #include "core/html/HTMLTextAreaElement.h" |
58 #include "core/inspector/DevToolsEmulator.h" | 58 #include "core/inspector/DevToolsEmulator.h" |
59 #include "core/layout/api/LayoutViewItem.h" | 59 #include "core/layout/api/LayoutViewItem.h" |
60 #include "core/loader/DocumentLoader.h" | 60 #include "core/loader/DocumentLoader.h" |
61 #include "core/loader/FrameLoadRequest.h" | 61 #include "core/loader/FrameLoadRequest.h" |
62 #include "core/page/ChromeClient.h" | 62 #include "core/page/ChromeClient.h" |
| 63 #include "core/page/FocusController.h" |
63 #include "core/page/Page.h" | 64 #include "core/page/Page.h" |
64 #include "core/page/PrintContext.h" | 65 #include "core/page/PrintContext.h" |
65 #include "core/page/ScopedPageSuspender.h" | 66 #include "core/page/ScopedPageSuspender.h" |
66 #include "core/paint/PaintLayer.h" | 67 #include "core/paint/PaintLayer.h" |
67 #include "core/paint/PaintLayerPainter.h" | 68 #include "core/paint/PaintLayerPainter.h" |
68 #include "core/timing/DOMWindowPerformance.h" | 69 #include "core/timing/DOMWindowPerformance.h" |
69 #include "core/timing/Performance.h" | 70 #include "core/timing/Performance.h" |
70 #include "platform/KeyboardCodes.h" | 71 #include "platform/KeyboardCodes.h" |
71 #include "platform/geometry/IntRect.h" | 72 #include "platform/geometry/IntRect.h" |
72 #include "platform/geometry/IntSize.h" | 73 #include "platform/geometry/IntSize.h" |
(...skipping 1552 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1625 web_view->SetInitialFocus(false); | 1626 web_view->SetInitialFocus(false); |
1626 frame->SetEditableSelectionOffsets(4, 10); | 1627 frame->SetEditableSelectionOffsets(4, 10); |
1627 EXPECT_TRUE(web_view->IsSelectionAnchorFirst()); | 1628 EXPECT_TRUE(web_view->IsSelectionAnchorFirst()); |
1628 WebRect anchor; | 1629 WebRect anchor; |
1629 WebRect focus; | 1630 WebRect focus; |
1630 web_view->SelectionBounds(anchor, focus); | 1631 web_view->SelectionBounds(anchor, focus); |
1631 frame->SelectRange(WebPoint(focus.x, focus.y), WebPoint(anchor.x, anchor.y)); | 1632 frame->SelectRange(WebPoint(focus.x, focus.y), WebPoint(anchor.x, anchor.y)); |
1632 EXPECT_FALSE(web_view->IsSelectionAnchorFirst()); | 1633 EXPECT_FALSE(web_view->IsSelectionAnchorFirst()); |
1633 } | 1634 } |
1634 | 1635 |
| 1636 TEST_P( |
| 1637 WebViewTest, |
| 1638 MoveFocusToNextFocusableElementInFormWithKeyEventListenersAndNonEditableElem
ents) { |
| 1639 const std::string test_file = |
| 1640 "advance_focus_in_form_with_key_event_listeners.html"; |
| 1641 RegisterMockedHttpURLLoad(test_file); |
| 1642 WebViewBase* web_view = |
| 1643 web_view_helper_.InitializeAndLoad(base_url_ + test_file); |
| 1644 web_view->SetInitialFocus(false); |
| 1645 Document* document = web_view->MainFrameImpl()->GetFrame()->GetDocument(); |
| 1646 WebInputMethodController* active_input_method_controller = |
| 1647 web_view->MainFrameImpl() |
| 1648 ->FrameWidget() |
| 1649 ->GetActiveWebInputMethodController(); |
| 1650 const int default_text_input_flags = kWebTextInputFlagAutocapitalizeSentences; |
| 1651 |
| 1652 struct FocusedElement { |
| 1653 AtomicString element_id; |
| 1654 int text_input_flags; |
| 1655 } focused_elements[] = { |
| 1656 {"input1", |
| 1657 default_text_input_flags | kWebTextInputFlagHaveNextFocusableElement}, |
| 1658 {"contenteditable1", kWebTextInputFlagHaveNextFocusableElement | |
| 1659 kWebTextInputFlagHavePreviousFocusableElement}, |
| 1660 {"input2", default_text_input_flags | |
| 1661 kWebTextInputFlagHaveNextFocusableElement | |
| 1662 kWebTextInputFlagHavePreviousFocusableElement}, |
| 1663 {"textarea1", default_text_input_flags | |
| 1664 kWebTextInputFlagHaveNextFocusableElement | |
| 1665 kWebTextInputFlagHavePreviousFocusableElement}, |
| 1666 {"input3", default_text_input_flags | |
| 1667 kWebTextInputFlagHaveNextFocusableElement | |
| 1668 kWebTextInputFlagHavePreviousFocusableElement}, |
| 1669 {"textarea2", default_text_input_flags | |
| 1670 kWebTextInputFlagHavePreviousFocusableElement}, |
| 1671 }; |
| 1672 |
| 1673 // Forward Navigation in form1 with NEXT |
| 1674 Element* input1 = document->getElementById("input1"); |
| 1675 input1->focus(); |
| 1676 Element* current_focus = nullptr; |
| 1677 Element* next_focus = nullptr; |
| 1678 WebTextInputInfo text_input_info; |
| 1679 for (size_t i = 0; i < WTF_ARRAY_LENGTH(focused_elements); ++i) { |
| 1680 current_focus = document->getElementById(focused_elements[i].element_id); |
| 1681 EXPECT_EQ(current_focus, document->FocusedElement()); |
| 1682 text_input_info = active_input_method_controller->TextInputInfo(); |
| 1683 EXPECT_EQ(focused_elements[i].text_input_flags, text_input_info.flags); |
| 1684 next_focus = |
| 1685 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 1686 current_focus, kWebFocusTypeForward); |
| 1687 if (next_focus) { |
| 1688 EXPECT_EQ(next_focus->GetIdAttribute(), |
| 1689 focused_elements[i + 1].element_id); |
| 1690 } |
| 1691 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeForward); |
| 1692 } |
| 1693 // Now focus will stay on previous focus itself, because it has no next |
| 1694 // element. |
| 1695 EXPECT_EQ(current_focus, document->FocusedElement()); |
| 1696 |
| 1697 // Backward Navigation in form1 with PREVIOUS |
| 1698 for (size_t i = WTF_ARRAY_LENGTH(focused_elements); i-- > 0;) { |
| 1699 current_focus = document->getElementById(focused_elements[i].element_id); |
| 1700 EXPECT_EQ(current_focus, document->FocusedElement()); |
| 1701 text_input_info = active_input_method_controller->TextInputInfo(); |
| 1702 EXPECT_EQ(focused_elements[i].text_input_flags, text_input_info.flags); |
| 1703 next_focus = |
| 1704 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 1705 current_focus, kWebFocusTypeBackward); |
| 1706 if (next_focus) { |
| 1707 EXPECT_EQ(next_focus->GetIdAttribute(), |
| 1708 focused_elements[i - 1].element_id); |
| 1709 } |
| 1710 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeBackward); |
| 1711 } |
| 1712 // Now focus will stay on previous focus itself, because it has no previous |
| 1713 // element. |
| 1714 EXPECT_EQ(current_focus, document->FocusedElement()); |
| 1715 |
| 1716 // Setting a non editable element as focus in form1, and ensuring editable |
| 1717 // navigation is fine in forward and backward. |
| 1718 Element* button1 = document->getElementById("button1"); |
| 1719 button1->focus(); |
| 1720 text_input_info = active_input_method_controller->TextInputInfo(); |
| 1721 EXPECT_EQ(kWebTextInputFlagHaveNextFocusableElement | |
| 1722 kWebTextInputFlagHavePreviousFocusableElement, |
| 1723 text_input_info.flags); |
| 1724 next_focus = |
| 1725 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 1726 button1, kWebFocusTypeForward); |
| 1727 EXPECT_EQ(next_focus->GetIdAttribute(), "contenteditable1"); |
| 1728 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeForward); |
| 1729 Element* content_editable1 = document->getElementById("contenteditable1"); |
| 1730 EXPECT_EQ(content_editable1, document->FocusedElement()); |
| 1731 button1->focus(); |
| 1732 next_focus = |
| 1733 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 1734 button1, kWebFocusTypeBackward); |
| 1735 EXPECT_EQ(next_focus->GetIdAttribute(), "input1"); |
| 1736 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeBackward); |
| 1737 EXPECT_EQ(input1, document->FocusedElement()); |
| 1738 |
| 1739 Element* anchor1 = document->getElementById("anchor1"); |
| 1740 anchor1->focus(); |
| 1741 text_input_info = active_input_method_controller->TextInputInfo(); |
| 1742 // No Next/Previous element for elements outside form. |
| 1743 EXPECT_EQ(0, text_input_info.flags); |
| 1744 next_focus = |
| 1745 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 1746 anchor1, kWebFocusTypeForward); |
| 1747 EXPECT_EQ(next_focus, nullptr); |
| 1748 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeForward); |
| 1749 // Since anchor is not a form control element, next/previous element will |
| 1750 // be null, hence focus will stay same as it is. |
| 1751 EXPECT_EQ(anchor1, document->FocusedElement()); |
| 1752 |
| 1753 next_focus = |
| 1754 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 1755 anchor1, kWebFocusTypeBackward); |
| 1756 EXPECT_EQ(next_focus, nullptr); |
| 1757 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeBackward); |
| 1758 EXPECT_EQ(anchor1, document->FocusedElement()); |
| 1759 |
| 1760 // Navigation of elements which is not part of any forms. |
| 1761 Element* text_area3 = document->getElementById("textarea3"); |
| 1762 text_area3->focus(); |
| 1763 text_input_info = active_input_method_controller->TextInputInfo(); |
| 1764 // No Next/Previous element for elements outside form. |
| 1765 EXPECT_EQ(default_text_input_flags, text_input_info.flags); |
| 1766 next_focus = |
| 1767 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 1768 text_area3, kWebFocusTypeForward); |
| 1769 EXPECT_EQ(next_focus, nullptr); |
| 1770 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeForward); |
| 1771 // No Next/Previous element to this element because it's not part of any |
| 1772 // form. Hence focus won't change wrt NEXT/PREVIOUS. |
| 1773 EXPECT_EQ(text_area3, document->FocusedElement()); |
| 1774 next_focus = |
| 1775 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 1776 text_area3, kWebFocusTypeBackward); |
| 1777 EXPECT_EQ(next_focus, nullptr); |
| 1778 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeBackward); |
| 1779 EXPECT_EQ(text_area3, document->FocusedElement()); |
| 1780 |
| 1781 // Navigation from an element which is part of a form but not an editable |
| 1782 // element. |
| 1783 Element* button2 = document->getElementById("button2"); |
| 1784 button2->focus(); |
| 1785 text_input_info = active_input_method_controller->TextInputInfo(); |
| 1786 // No Next element for this element, due to last element outside the form. |
| 1787 EXPECT_EQ(kWebTextInputFlagHavePreviousFocusableElement, |
| 1788 text_input_info.flags); |
| 1789 next_focus = |
| 1790 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 1791 button2, kWebFocusTypeForward); |
| 1792 EXPECT_EQ(next_focus, nullptr); |
| 1793 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeForward); |
| 1794 // No Next element to this element because it's not part of any form. |
| 1795 // Hence focus won't change wrt NEXT. |
| 1796 EXPECT_EQ(button2, document->FocusedElement()); |
| 1797 Element* text_area2 = document->getElementById("textarea2"); |
| 1798 next_focus = |
| 1799 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 1800 button2, kWebFocusTypeBackward); |
| 1801 EXPECT_EQ(next_focus, text_area2); |
| 1802 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeBackward); |
| 1803 // Since button is a form control element from form1, ensuring focus is set |
| 1804 // at correct position. |
| 1805 EXPECT_EQ(text_area2, document->FocusedElement()); |
| 1806 |
| 1807 Element* content_editable2 = document->getElementById("contenteditable2"); |
| 1808 document->SetFocusedElement( |
| 1809 content_editable2, |
| 1810 FocusParams(SelectionBehaviorOnFocus::kNone, kWebFocusTypeNone, nullptr)); |
| 1811 text_input_info = active_input_method_controller->TextInputInfo(); |
| 1812 // No Next/Previous element for elements outside form. |
| 1813 EXPECT_EQ(0, text_input_info.flags); |
| 1814 next_focus = |
| 1815 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 1816 content_editable2, kWebFocusTypeForward); |
| 1817 EXPECT_EQ(next_focus, nullptr); |
| 1818 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeForward); |
| 1819 // No Next/Previous element to this element because it's not part of any |
| 1820 // form. Hence focus won't change wrt NEXT/PREVIOUS. |
| 1821 EXPECT_EQ(content_editable2, document->FocusedElement()); |
| 1822 next_focus = |
| 1823 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 1824 content_editable2, kWebFocusTypeBackward); |
| 1825 EXPECT_EQ(next_focus, nullptr); |
| 1826 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeBackward); |
| 1827 EXPECT_EQ(content_editable2, document->FocusedElement()); |
| 1828 |
| 1829 // Navigation of elements which is having invalid form attribute and hence |
| 1830 // not part of any forms. |
| 1831 Element* text_area4 = document->getElementById("textarea4"); |
| 1832 text_area4->focus(); |
| 1833 text_input_info = active_input_method_controller->TextInputInfo(); |
| 1834 // No Next/Previous element for elements which is having invalid form |
| 1835 // attribute. |
| 1836 EXPECT_EQ(default_text_input_flags, text_input_info.flags); |
| 1837 next_focus = |
| 1838 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 1839 text_area4, kWebFocusTypeForward); |
| 1840 EXPECT_EQ(next_focus, nullptr); |
| 1841 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeForward); |
| 1842 // No Next/Previous element to this element because it's not part of any |
| 1843 // form. Hence focus won't change wrt NEXT/PREVIOUS. |
| 1844 EXPECT_EQ(text_area4, document->FocusedElement()); |
| 1845 next_focus = |
| 1846 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 1847 text_area4, kWebFocusTypeBackward); |
| 1848 EXPECT_EQ(next_focus, nullptr); |
| 1849 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeBackward); |
| 1850 EXPECT_EQ(text_area4, document->FocusedElement()); |
| 1851 |
| 1852 web_view_helper_.Reset(); |
| 1853 } |
| 1854 |
| 1855 TEST_P( |
| 1856 WebViewTest, |
| 1857 MoveFocusToNextFocusableElementInFormWithNonEditableNonFormControlElements)
{ |
| 1858 const std::string test_file = |
| 1859 "advance_focus_in_form_with_key_event_listeners.html"; |
| 1860 RegisterMockedHttpURLLoad(test_file); |
| 1861 WebViewBase* web_view = |
| 1862 web_view_helper_.InitializeAndLoad(base_url_ + test_file); |
| 1863 web_view->SetInitialFocus(false); |
| 1864 Document* document = web_view->MainFrameImpl()->GetFrame()->GetDocument(); |
| 1865 WebInputMethodController* active_input_method_controller = |
| 1866 web_view->MainFrameImpl() |
| 1867 ->FrameWidget() |
| 1868 ->GetActiveWebInputMethodController(); |
| 1869 const int default_text_input_flags = kWebTextInputFlagAutocapitalizeSentences; |
| 1870 |
| 1871 struct FocusedElement { |
| 1872 const char* element_id; |
| 1873 int text_input_flags; |
| 1874 } focused_elements[] = { |
| 1875 {"textarea5", |
| 1876 default_text_input_flags | kWebTextInputFlagHaveNextFocusableElement}, |
| 1877 {"input4", default_text_input_flags | |
| 1878 kWebTextInputFlagHaveNextFocusableElement | |
| 1879 kWebTextInputFlagHavePreviousFocusableElement}, |
| 1880 {"contenteditable3", kWebTextInputFlagHaveNextFocusableElement | |
| 1881 kWebTextInputFlagHavePreviousFocusableElement}, |
| 1882 {"input5", kWebTextInputFlagHavePreviousFocusableElement}, |
| 1883 }; |
| 1884 |
| 1885 // Forward Navigation in form2 with NEXT |
| 1886 Element* text_area5 = document->getElementById("textarea5"); |
| 1887 text_area5->focus(); |
| 1888 Element* current_focus = nullptr; |
| 1889 Element* next_focus = nullptr; |
| 1890 WebTextInputInfo text_input_info; |
| 1891 for (size_t i = 0; i < WTF_ARRAY_LENGTH(focused_elements); ++i) { |
| 1892 current_focus = document->getElementById(focused_elements[i].element_id); |
| 1893 EXPECT_EQ(current_focus, document->FocusedElement()); |
| 1894 text_input_info = active_input_method_controller->TextInputInfo(); |
| 1895 EXPECT_EQ(focused_elements[i].text_input_flags, text_input_info.flags); |
| 1896 next_focus = |
| 1897 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 1898 current_focus, kWebFocusTypeForward); |
| 1899 if (next_focus) { |
| 1900 EXPECT_EQ(next_focus->GetIdAttribute(), |
| 1901 focused_elements[i + 1].element_id); |
| 1902 } |
| 1903 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeForward); |
| 1904 } |
| 1905 // Now focus will stay on previous focus itself, because it has no next |
| 1906 // element. |
| 1907 EXPECT_EQ(current_focus, document->FocusedElement()); |
| 1908 |
| 1909 // Backward Navigation in form1 with PREVIOUS |
| 1910 for (size_t i = WTF_ARRAY_LENGTH(focused_elements); i-- > 0;) { |
| 1911 current_focus = document->getElementById(focused_elements[i].element_id); |
| 1912 EXPECT_EQ(current_focus, document->FocusedElement()); |
| 1913 text_input_info = active_input_method_controller->TextInputInfo(); |
| 1914 EXPECT_EQ(focused_elements[i].text_input_flags, text_input_info.flags); |
| 1915 next_focus = |
| 1916 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 1917 current_focus, kWebFocusTypeBackward); |
| 1918 if (next_focus) { |
| 1919 EXPECT_EQ(next_focus->GetIdAttribute(), |
| 1920 focused_elements[i - 1].element_id); |
| 1921 } |
| 1922 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeBackward); |
| 1923 } |
| 1924 // Now focus will stay on previous focus itself, because it has no previous |
| 1925 // element. |
| 1926 EXPECT_EQ(current_focus, document->FocusedElement()); |
| 1927 |
| 1928 // Setting a non editable element as focus in form1, and ensuring editable |
| 1929 // navigation is fine in forward and backward. |
| 1930 Element* anchor2 = document->getElementById("anchor2"); |
| 1931 anchor2->focus(); |
| 1932 text_input_info = active_input_method_controller->TextInputInfo(); |
| 1933 // No Next/Previous element for non-form control elements inside form. |
| 1934 EXPECT_EQ(0, text_input_info.flags); |
| 1935 next_focus = |
| 1936 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 1937 anchor2, kWebFocusTypeForward); |
| 1938 EXPECT_EQ(next_focus, nullptr); |
| 1939 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeForward); |
| 1940 // Since anchor is not a form control element, next/previous element will |
| 1941 // be null, hence focus will stay same as it is. |
| 1942 EXPECT_EQ(anchor2, document->FocusedElement()); |
| 1943 next_focus = |
| 1944 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 1945 anchor2, kWebFocusTypeBackward); |
| 1946 EXPECT_EQ(next_focus, nullptr); |
| 1947 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeBackward); |
| 1948 EXPECT_EQ(anchor2, document->FocusedElement()); |
| 1949 |
| 1950 web_view_helper_.Reset(); |
| 1951 } |
| 1952 |
| 1953 TEST_P(WebViewTest, MoveFocusToNextFocusableElementInFormWithTabIndexElements) { |
| 1954 const std::string test_file = |
| 1955 "advance_focus_in_form_with_tabindex_elements.html"; |
| 1956 RegisterMockedHttpURLLoad(test_file); |
| 1957 WebViewBase* web_view = |
| 1958 web_view_helper_.InitializeAndLoad(base_url_ + test_file); |
| 1959 web_view->SetInitialFocus(false); |
| 1960 Document* document = web_view->MainFrameImpl()->GetFrame()->GetDocument(); |
| 1961 WebInputMethodController* active_input_method_controller = |
| 1962 web_view->MainFrameImpl() |
| 1963 ->FrameWidget() |
| 1964 ->GetActiveWebInputMethodController(); |
| 1965 const int default_text_input_flags = kWebTextInputFlagAutocapitalizeSentences; |
| 1966 |
| 1967 struct FocusedElement { |
| 1968 const char* element_id; |
| 1969 int text_input_flags; |
| 1970 } focused_elements[] = { |
| 1971 {"textarea6", |
| 1972 default_text_input_flags | kWebTextInputFlagHaveNextFocusableElement}, |
| 1973 {"input5", default_text_input_flags | |
| 1974 kWebTextInputFlagHaveNextFocusableElement | |
| 1975 kWebTextInputFlagHavePreviousFocusableElement}, |
| 1976 {"contenteditable4", kWebTextInputFlagHaveNextFocusableElement | |
| 1977 kWebTextInputFlagHavePreviousFocusableElement}, |
| 1978 {"input6", default_text_input_flags | |
| 1979 kWebTextInputFlagHavePreviousFocusableElement}, |
| 1980 }; |
| 1981 |
| 1982 // Forward Navigation in form with NEXT which has tabindex attribute |
| 1983 // which differs visual order. |
| 1984 Element* text_area6 = document->getElementById("textarea6"); |
| 1985 text_area6->focus(); |
| 1986 Element* current_focus = nullptr; |
| 1987 Element* next_focus = nullptr; |
| 1988 WebTextInputInfo text_input_info; |
| 1989 for (size_t i = 0; i < WTF_ARRAY_LENGTH(focused_elements); ++i) { |
| 1990 current_focus = document->getElementById(focused_elements[i].element_id); |
| 1991 EXPECT_EQ(current_focus, document->FocusedElement()); |
| 1992 text_input_info = active_input_method_controller->TextInputInfo(); |
| 1993 EXPECT_EQ(focused_elements[i].text_input_flags, text_input_info.flags); |
| 1994 next_focus = |
| 1995 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 1996 current_focus, kWebFocusTypeForward); |
| 1997 if (next_focus) { |
| 1998 EXPECT_EQ(next_focus->GetIdAttribute(), |
| 1999 focused_elements[i + 1].element_id); |
| 2000 } |
| 2001 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeForward); |
| 2002 } |
| 2003 // No next editable element which is focusable with proper tab index, hence |
| 2004 // staying on previous focus. |
| 2005 EXPECT_EQ(current_focus, document->FocusedElement()); |
| 2006 |
| 2007 // Backward Navigation in form with PREVIOUS which has tabindex attribute |
| 2008 // which differs visual order. |
| 2009 for (size_t i = WTF_ARRAY_LENGTH(focused_elements); i-- > 0;) { |
| 2010 current_focus = document->getElementById(focused_elements[i].element_id); |
| 2011 EXPECT_EQ(current_focus, document->FocusedElement()); |
| 2012 text_input_info = active_input_method_controller->TextInputInfo(); |
| 2013 EXPECT_EQ(focused_elements[i].text_input_flags, text_input_info.flags); |
| 2014 next_focus = |
| 2015 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 2016 current_focus, kWebFocusTypeBackward); |
| 2017 if (next_focus) { |
| 2018 EXPECT_EQ(next_focus->GetIdAttribute(), |
| 2019 focused_elements[i - 1].element_id); |
| 2020 } |
| 2021 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeBackward); |
| 2022 } |
| 2023 // Now focus will stay on previous focus itself, because it has no previous |
| 2024 // element. |
| 2025 EXPECT_EQ(current_focus, document->FocusedElement()); |
| 2026 |
| 2027 // Setting an element which has invalid tabindex and ensuring it is not |
| 2028 // modifying further navigation. |
| 2029 Element* content_editable5 = document->getElementById("contenteditable5"); |
| 2030 content_editable5->focus(); |
| 2031 Element* input6 = document->getElementById("input6"); |
| 2032 next_focus = |
| 2033 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 2034 content_editable5, kWebFocusTypeForward); |
| 2035 EXPECT_EQ(next_focus, input6); |
| 2036 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeForward); |
| 2037 EXPECT_EQ(input6, document->FocusedElement()); |
| 2038 content_editable5->focus(); |
| 2039 next_focus = |
| 2040 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 2041 content_editable5, kWebFocusTypeBackward); |
| 2042 EXPECT_EQ(next_focus, text_area6); |
| 2043 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeBackward); |
| 2044 EXPECT_EQ(text_area6, document->FocusedElement()); |
| 2045 |
| 2046 web_view_helper_.Reset(); |
| 2047 } |
| 2048 |
| 2049 TEST_P(WebViewTest, |
| 2050 MoveFocusToNextFocusableElementInFormWithDisabledAndReadonlyElements) { |
| 2051 const std::string test_file = |
| 2052 "advance_focus_in_form_with_disabled_and_readonly_elements.html"; |
| 2053 RegisterMockedHttpURLLoad(test_file); |
| 2054 WebViewBase* web_view = |
| 2055 web_view_helper_.InitializeAndLoad(base_url_ + test_file); |
| 2056 web_view->SetInitialFocus(false); |
| 2057 Document* document = web_view->MainFrameImpl()->GetFrame()->GetDocument(); |
| 2058 WebInputMethodController* active_input_method_controller = |
| 2059 web_view->MainFrameImpl() |
| 2060 ->FrameWidget() |
| 2061 ->GetActiveWebInputMethodController(); |
| 2062 |
| 2063 struct FocusedElement { |
| 2064 const char* element_id; |
| 2065 int text_input_flags; |
| 2066 } focused_elements[] = { |
| 2067 {"contenteditable6", kWebTextInputFlagHaveNextFocusableElement}, |
| 2068 {"contenteditable7", kWebTextInputFlagHavePreviousFocusableElement}, |
| 2069 }; |
| 2070 // Forward Navigation in form with NEXT which has has disabled/enabled |
| 2071 // elements which will gets skipped during navigation. |
| 2072 Element* content_editable6 = document->getElementById("contenteditable6"); |
| 2073 content_editable6->focus(); |
| 2074 Element* current_focus = nullptr; |
| 2075 Element* next_focus = nullptr; |
| 2076 WebTextInputInfo text_input_info; |
| 2077 for (size_t i = 0; i < WTF_ARRAY_LENGTH(focused_elements); ++i) { |
| 2078 current_focus = document->getElementById(focused_elements[i].element_id); |
| 2079 EXPECT_EQ(current_focus, document->FocusedElement()); |
| 2080 text_input_info = active_input_method_controller->TextInputInfo(); |
| 2081 EXPECT_EQ(focused_elements[i].text_input_flags, text_input_info.flags); |
| 2082 next_focus = |
| 2083 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 2084 current_focus, kWebFocusTypeForward); |
| 2085 if (next_focus) { |
| 2086 EXPECT_EQ(next_focus->GetIdAttribute(), |
| 2087 focused_elements[i + 1].element_id); |
| 2088 } |
| 2089 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeForward); |
| 2090 } |
| 2091 // No next editable element which is focusable, hence staying on previous |
| 2092 // focus. |
| 2093 EXPECT_EQ(current_focus, document->FocusedElement()); |
| 2094 |
| 2095 // Backward Navigation in form with PREVIOUS which has has |
| 2096 // disabled/enabled elements which will gets skipped during navigation. |
| 2097 for (size_t i = WTF_ARRAY_LENGTH(focused_elements); i-- > 0;) { |
| 2098 current_focus = document->getElementById(focused_elements[i].element_id); |
| 2099 EXPECT_EQ(current_focus, document->FocusedElement()); |
| 2100 text_input_info = active_input_method_controller->TextInputInfo(); |
| 2101 EXPECT_EQ(focused_elements[i].text_input_flags, text_input_info.flags); |
| 2102 next_focus = |
| 2103 document->GetPage()->GetFocusController().NextFocusableElementInForm( |
| 2104 current_focus, kWebFocusTypeBackward); |
| 2105 if (next_focus) { |
| 2106 EXPECT_EQ(next_focus->GetIdAttribute(), |
| 2107 focused_elements[i - 1].element_id); |
| 2108 } |
| 2109 web_view->MainFrameImpl()->AdvanceFocusInForm(kWebFocusTypeBackward); |
| 2110 } |
| 2111 // Now focus will stay on previous focus itself, because it has no previous |
| 2112 // element. |
| 2113 EXPECT_EQ(current_focus, document->FocusedElement()); |
| 2114 |
| 2115 web_view_helper_.Reset(); |
| 2116 } |
| 2117 |
1635 TEST_P(WebViewTest, ExitingDeviceEmulationResetsPageScale) { | 2118 TEST_P(WebViewTest, ExitingDeviceEmulationResetsPageScale) { |
1636 RegisterMockedHttpURLLoad("200-by-300.html"); | 2119 RegisterMockedHttpURLLoad("200-by-300.html"); |
1637 WebViewBase* web_view_impl = | 2120 WebViewBase* web_view_impl = |
1638 web_view_helper_.InitializeAndLoad(base_url_ + "200-by-300.html"); | 2121 web_view_helper_.InitializeAndLoad(base_url_ + "200-by-300.html"); |
1639 web_view_impl->Resize(WebSize(200, 300)); | 2122 web_view_impl->Resize(WebSize(200, 300)); |
1640 | 2123 |
1641 float page_scale_expected = web_view_impl->PageScaleFactor(); | 2124 float page_scale_expected = web_view_impl->PageScaleFactor(); |
1642 | 2125 |
1643 WebDeviceEmulationParams params; | 2126 WebDeviceEmulationParams params; |
1644 params.screen_position = WebDeviceEmulationParams::kDesktop; | 2127 params.screen_position = WebDeviceEmulationParams::kDesktop; |
(...skipping 2752 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4397 EXPECT_FALSE(frame_view->VisualViewportSuppliesScrollbars()); | 4880 EXPECT_FALSE(frame_view->VisualViewportSuppliesScrollbars()); |
4398 if (RuntimeEnabledFeatures::RootLayerScrollingEnabled()) { | 4881 if (RuntimeEnabledFeatures::RootLayerScrollingEnabled()) { |
4399 EXPECT_NE(nullptr, | 4882 EXPECT_NE(nullptr, |
4400 frame_view->LayoutViewportScrollableArea()->VerticalScrollbar()); | 4883 frame_view->LayoutViewportScrollableArea()->VerticalScrollbar()); |
4401 } else { | 4884 } else { |
4402 EXPECT_NE(nullptr, frame_view->VerticalScrollbar()); | 4885 EXPECT_NE(nullptr, frame_view->VerticalScrollbar()); |
4403 } | 4886 } |
4404 } | 4887 } |
4405 | 4888 |
4406 } // namespace blink | 4889 } // namespace blink |
OLD | NEW |