summaryrefslogtreecommitdiff
path: root/chromium/third_party/blink/renderer/core/editing/commands
diff options
context:
space:
mode:
Diffstat (limited to 'chromium/third_party/blink/renderer/core/editing/commands')
-rw-r--r--chromium/third_party/blink/renderer/core/editing/commands/apply_style_command.cc64
-rw-r--r--chromium/third_party/blink/renderer/core/editing/commands/clipboard_commands.h2
-rw-r--r--chromium/third_party/blink/renderer/core/editing/commands/composite_edit_command.cc13
-rw-r--r--chromium/third_party/blink/renderer/core/editing/commands/delete_selection_options.h2
-rw-r--r--chromium/third_party/blink/renderer/core/editing/commands/document_exec_command.cc4
-rw-r--r--chromium/third_party/blink/renderer/core/editing/commands/editing_command_test.cc65
-rw-r--r--chromium/third_party/blink/renderer/core/editing/commands/editing_commands_utilities.cc16
-rw-r--r--chromium/third_party/blink/renderer/core/editing/commands/editing_state.h2
-rw-r--r--chromium/third_party/blink/renderer/core/editing/commands/editor_command.cc138
-rw-r--r--chromium/third_party/blink/renderer/core/editing/commands/format_block_command.cc7
-rw-r--r--chromium/third_party/blink/renderer/core/editing/commands/indent_outdent_command.cc2
-rw-r--r--chromium/third_party/blink/renderer/core/editing/commands/insert_commands.h2
-rw-r--r--chromium/third_party/blink/renderer/core/editing/commands/insert_list_command.cc2
-rw-r--r--chromium/third_party/blink/renderer/core/editing/commands/move_commands.cc201
-rw-r--r--chromium/third_party/blink/renderer/core/editing/commands/move_commands.h27
-rw-r--r--chromium/third_party/blink/renderer/core/editing/commands/move_commands_test.cc327
-rw-r--r--chromium/third_party/blink/renderer/core/editing/commands/replace_selection_command.cc4
-rw-r--r--chromium/third_party/blink/renderer/core/editing/commands/split_text_node_containing_element_command.cc6
-rw-r--r--chromium/third_party/blink/renderer/core/editing/commands/style_commands.cc16
-rw-r--r--chromium/third_party/blink/renderer/core/editing/commands/style_commands.h2
20 files changed, 703 insertions, 199 deletions
diff --git a/chromium/third_party/blink/renderer/core/editing/commands/apply_style_command.cc b/chromium/third_party/blink/renderer/core/editing/commands/apply_style_command.cc
index 33898e3e187..d4d67a3a60b 100644
--- a/chromium/third_party/blink/renderer/core/editing/commands/apply_style_command.cc
+++ b/chromium/third_party/blink/renderer/core/editing/commands/apply_style_command.cc
@@ -26,6 +26,7 @@
#include "third_party/blink/renderer/core/editing/commands/apply_style_command.h"
#include "third_party/blink/renderer/core/css/css_computed_style_declaration.h"
+#include "third_party/blink/renderer/core/css/css_numeric_literal_value.h"
#include "third_party/blink/renderer/core/css/css_primitive_value.h"
#include "third_party/blink/renderer/core/css/css_property_names.h"
#include "third_party/blink/renderer/core/css/css_property_value_set.h"
@@ -48,7 +49,6 @@
#include "third_party/blink/renderer/core/editing/visible_selection.h"
#include "third_party/blink/renderer/core/editing/visible_units.h"
#include "third_party/blink/renderer/core/editing/writing_direction.h"
-#include "third_party/blink/renderer/core/frame/use_counter.h"
#include "third_party/blink/renderer/core/html/html_font_element.h"
#include "third_party/blink/renderer/core/html/html_span_element.h"
#include "third_party/blink/renderer/core/html_names.h"
@@ -56,6 +56,7 @@
#include "third_party/blink/renderer/core/layout/layout_text.h"
#include "third_party/blink/renderer/platform/heap/handle.h"
#include "third_party/blink/renderer/platform/heap/heap.h"
+#include "third_party/blink/renderer/platform/instrumentation/use_counter.h"
#include "third_party/blink/renderer/platform/wtf/std_lib_extras.h"
#include "third_party/blink/renderer/platform/wtf/text/string_builder.h"
@@ -510,8 +511,8 @@ void ApplyStyleCommand::ApplyRelativeFontStyleChange(
if (current_font_size != desired_font_size) {
inline_style->SetProperty(
CSSPropertyID::kFontSize,
- *CSSPrimitiveValue::Create(desired_font_size,
- CSSPrimitiveValue::UnitType::kPixels),
+ *CSSNumericLiteralValue::Create(desired_font_size,
+ CSSPrimitiveValue::UnitType::kPixels),
false);
SetNodeAttribute(element, kStyleAttr,
AtomicString(inline_style->AsText()));
@@ -532,11 +533,14 @@ void ApplyStyleCommand::ApplyRelativeFontStyleChange(
}
static ContainerNode* DummySpanAncestorForNode(const Node* node) {
- while (node && (!node->IsElementNode() ||
- !IsStyleSpanOrSpanWithOnlyStyleAttribute(ToElement(node))))
- node = node->parentNode();
+ if (!node)
+ return nullptr;
- return node ? node->parentNode() : nullptr;
+ for (Node& current : NodeTraversal::InclusiveAncestorsOf(*node)) {
+ if (IsStyleSpanOrSpanWithOnlyStyleAttribute(DynamicTo<Element>(current)))
+ return current.parentNode();
+ }
+ return nullptr;
}
void ApplyStyleCommand::CleanupUnstyledAppleStyleSpans(
@@ -615,7 +619,7 @@ HTMLElement* ApplyStyleCommand::SplitAncestorsWithUnicodeBidi(
// Split every ancestor through highest ancestor with embedding.
Node* current_node = node;
while (current_node) {
- Element* parent = ToElement(current_node->parentNode());
+ auto* parent = To<Element>(current_node->parentNode());
if (before ? current_node->previousSibling() : current_node->nextSibling())
SplitElement(parent, before ? current_node : current_node->nextSibling());
if (parent == highest_ancestor_with_unicode_bidi)
@@ -639,7 +643,7 @@ void ApplyStyleCommand::RemoveEmbeddingUpToEnclosingBlock(
if (!runner.IsStyledElement())
continue;
- Element* element = ToElement(&runner);
+ auto* element = To<Element>(&runner);
CSSValueID unicode_bidi = GetIdentifierValue(
MakeGarbageCollected<CSSComputedStyleDeclaration>(element),
CSSPropertyID::kUnicodeBidi);
@@ -1283,7 +1287,7 @@ static Element* UnsplittableElementForPosition(const Position& p) {
// Since enclosingNodeOfType won't search beyond the highest root editable
// node, this code works even if the closest table cell was outside of the
// root editable node.
- Element* enclosing_cell = ToElement(EnclosingNodeOfType(p, &IsTableCell));
+ auto* enclosing_cell = To<Element>(EnclosingNodeOfType(p, &IsTableCell));
if (enclosing_cell)
return enclosing_cell;
@@ -1376,8 +1380,8 @@ void ApplyStyleCommand::PushDownInlineStyleAroundNode(
GetChildNodes(To<ContainerNode>(*current), current_children);
Element* styled_element = nullptr;
if (current->IsStyledElement() &&
- IsStyledInlineElementToRemove(ToElement(current))) {
- styled_element = ToElement(current);
+ IsStyledInlineElementToRemove(To<Element>(current))) {
+ styled_element = To<Element>(current);
elements_to_push_down.push_back(styled_element);
}
@@ -1699,8 +1703,8 @@ bool ApplyStyleCommand::MergeStartWithPreviousIfIdentical(
if (previous_sibling &&
AreIdenticalElements(*start_node, *previous_sibling)) {
- Element* previous_element = ToElement(previous_sibling);
- Element* element = ToElement(start_node);
+ auto* previous_element = To<Element>(previous_sibling);
+ auto* element = To<Element>(start_node);
Node* start_child = element->firstChild();
DCHECK(start_child);
MergeIdenticalElements(previous_element, element, editing_state);
@@ -1742,8 +1746,8 @@ bool ApplyStyleCommand::MergeEndWithNextIfIdentical(
Node* next_sibling = end_node->nextSibling();
if (next_sibling && AreIdenticalElements(*end_node, *next_sibling)) {
- Element* next_element = ToElement(next_sibling);
- Element* element = ToElement(end_node);
+ auto* next_element = To<Element>(next_sibling);
+ auto* element = To<Element>(end_node);
Node* next_child = next_element->firstChild();
MergeIdenticalElements(element, next_element, editing_state);
@@ -1797,22 +1801,22 @@ void ApplyStyleCommand::SurroundNodeRangeWithElement(
Node* next_sibling = element->nextSibling();
Node* previous_sibling = element->previousSibling();
- if (next_sibling && next_sibling->IsElementNode() &&
- HasEditableStyle(*next_sibling) &&
- AreIdenticalElements(*element, ToElement(*next_sibling))) {
- MergeIdenticalElements(element, ToElement(next_sibling), editing_state);
+ auto* next_sibling_element = DynamicTo<Element>(next_sibling);
+ if (next_sibling_element && HasEditableStyle(*next_sibling) &&
+ AreIdenticalElements(*element, *next_sibling_element)) {
+ MergeIdenticalElements(element, next_sibling_element, editing_state);
if (editing_state->IsAborted())
return;
}
- if (previous_sibling && previous_sibling->IsElementNode() &&
- HasEditableStyle(*previous_sibling)) {
- Node* merged_element = previous_sibling->nextSibling();
- if (merged_element->IsElementNode() && HasEditableStyle(*merged_element) &&
- AreIdenticalElements(ToElement(*previous_sibling),
- ToElement(*merged_element))) {
- MergeIdenticalElements(ToElement(previous_sibling),
- ToElement(merged_element), editing_state);
+ auto* previous_sibling_element = DynamicTo<Element>(previous_sibling);
+ if (previous_sibling_element && HasEditableStyle(*previous_sibling)) {
+ auto* merged_element = DynamicTo<Element>(previous_sibling->nextSibling());
+ if (merged_element &&
+ HasEditableStyle(*(previous_sibling->nextSibling())) &&
+ AreIdenticalElements(*previous_sibling_element, *merged_element)) {
+ MergeIdenticalElements(previous_sibling_element, merged_element,
+ editing_state);
if (editing_state->IsAborted())
return;
}
@@ -2041,12 +2045,12 @@ float ApplyStyleCommand::ComputedFontSize(Node* node) {
return 0;
const auto* value = To<CSSPrimitiveValue>(
- style->GetPropertyCSSValue(GetCSSPropertyFontSize()));
+ style->GetPropertyCSSValue(CSSPropertyID::kFontSize));
if (!value)
return 0;
// TODO(yosin): We should have printer for |CSSPrimitiveValue::UnitType|.
- DCHECK(value->TypeWithCalcResolved() == CSSPrimitiveValue::UnitType::kPixels);
+ DCHECK(value->IsPx());
return value->GetFloatValue();
}
diff --git a/chromium/third_party/blink/renderer/core/editing/commands/clipboard_commands.h b/chromium/third_party/blink/renderer/core/editing/commands/clipboard_commands.h
index 4aa6f80477d..6e0f5518437 100644
--- a/chromium/third_party/blink/renderer/core/editing/commands/clipboard_commands.h
+++ b/chromium/third_party/blink/renderer/core/editing/commands/clipboard_commands.h
@@ -33,7 +33,7 @@
#define THIRD_PARTY_BLINK_RENDERER_CORE_EDITING_COMMANDS_CLIPBOARD_COMMANDS_H_
#include "third_party/blink/renderer/core/editing/forward.h"
-#include "third_party/blink/renderer/platform/wtf/allocator.h"
+#include "third_party/blink/renderer/platform/wtf/allocator/allocator.h"
#include "third_party/blink/renderer/platform/wtf/text/wtf_string.h"
namespace blink {
diff --git a/chromium/third_party/blink/renderer/core/editing/commands/composite_edit_command.cc b/chromium/third_party/blink/renderer/core/editing/commands/composite_edit_command.cc
index b8f011b43a7..8d641404bc9 100644
--- a/chromium/third_party/blink/renderer/core/editing/commands/composite_edit_command.cc
+++ b/chromium/third_party/blink/renderer/core/editing/commands/composite_edit_command.cc
@@ -365,9 +365,10 @@ void CompositeEditCommand::AppendNode(Node* node,
// TODO(yosin): We should get rid of |canHaveChildrenForEditing()|, since
// |cloneParagraphUnderNewElement()| attempt to clone non-well-formed HTML,
// produced by JavaScript.
- ABORT_EDITING_COMMAND_IF(!CanHaveChildrenForEditing(parent) &&
- !(parent->IsElementNode() &&
- ToElement(parent)->TagQName() == kObjectTag));
+ auto* parent_element = DynamicTo<Element>(parent);
+ ABORT_EDITING_COMMAND_IF(
+ !CanHaveChildrenForEditing(parent) &&
+ !(parent_element && parent_element->TagQName() == kObjectTag));
ABORT_EDITING_COMMAND_IF(!HasEditableStyle(*parent) &&
parent->InActiveDocument());
ApplyCommandToComposite(MakeGarbageCollected<AppendNodeCommand>(parent, node),
@@ -1192,7 +1193,7 @@ void CompositeEditCommand::CloneParagraphUnderNewElement(
for (wtf_size_t i = ancestors.size(); i != 0; --i) {
Node* item = ancestors[i - 1].Get();
Node* child = item->cloneNode(IsDisplayInsideTable(item));
- AppendNode(child, ToElement(last_node), editing_state);
+ AppendNode(child, To<Element>(last_node), editing_state);
if (editing_state->IsAborted())
return;
last_node = child;
@@ -1686,7 +1687,7 @@ bool CompositeEditCommand::BreakOutOfEmptyListItem(
// should become
// <ul><li> <div><br></div> hello</li></ul>
// at the end
- SplitElement(ToElement(block_enclosing_list), list_node);
+ SplitElement(To<Element>(block_enclosing_list), list_node);
RemoveNodePreservingChildren(list_node->parentNode(), editing_state);
if (editing_state->IsAborted())
return false;
@@ -1713,7 +1714,7 @@ bool CompositeEditCommand::BreakOutOfEmptyListItem(
// If emptyListItem follows another list item or nested list, split the list
// node.
if (IsListItem(previous_list_node) || IsHTMLListElement(previous_list_node))
- SplitElement(ToElement(list_node), empty_list_item);
+ SplitElement(To<Element>(list_node), empty_list_item);
// If emptyListItem is followed by other list item or nested list, then
// insert newBlock before the list node. Because we have splitted the
diff --git a/chromium/third_party/blink/renderer/core/editing/commands/delete_selection_options.h b/chromium/third_party/blink/renderer/core/editing/commands/delete_selection_options.h
index ef1038c5904..92377355d1c 100644
--- a/chromium/third_party/blink/renderer/core/editing/commands/delete_selection_options.h
+++ b/chromium/third_party/blink/renderer/core/editing/commands/delete_selection_options.h
@@ -7,7 +7,7 @@
#include "base/macros.h"
#include "third_party/blink/renderer/core/core_export.h"
-#include "third_party/blink/renderer/platform/wtf/allocator.h"
+#include "third_party/blink/renderer/platform/wtf/allocator/allocator.h"
namespace blink {
diff --git a/chromium/third_party/blink/renderer/core/editing/commands/document_exec_command.cc b/chromium/third_party/blink/renderer/core/editing/commands/document_exec_command.cc
index abf10cdfc54..c8fe153b384 100644
--- a/chromium/third_party/blink/renderer/core/editing/commands/document_exec_command.cc
+++ b/chromium/third_party/blink/renderer/core/editing/commands/document_exec_command.cc
@@ -36,10 +36,10 @@
#include "third_party/blink/renderer/core/editing/editing_tri_state.h"
#include "third_party/blink/renderer/core/editing/editor.h"
#include "third_party/blink/renderer/core/frame/local_frame.h"
-#include "third_party/blink/renderer/core/frame/use_counter.h"
#include "third_party/blink/renderer/core/html/forms/text_control_element.h"
#include "third_party/blink/renderer/core/inspector/console_message.h"
-#include "third_party/blink/renderer/platform/histogram.h"
+#include "third_party/blink/renderer/platform/instrumentation/histogram.h"
+#include "third_party/blink/renderer/platform/instrumentation/use_counter.h"
#include "third_party/blink/renderer/platform/wtf/std_lib_extras.h"
namespace blink {
diff --git a/chromium/third_party/blink/renderer/core/editing/commands/editing_command_test.cc b/chromium/third_party/blink/renderer/core/editing/commands/editing_command_test.cc
index c24e8917608..e1bfe875c48 100644
--- a/chromium/third_party/blink/renderer/core/editing/commands/editing_command_test.cc
+++ b/chromium/third_party/blink/renderer/core/editing/commands/editing_command_test.cc
@@ -7,8 +7,11 @@
#include "third_party/blink/renderer/core/editing/commands/editor_command.h"
#include "third_party/blink/renderer/core/editing/commands/editor_command_names.h"
#include "third_party/blink/renderer/core/editing/editor.h"
+#include "third_party/blink/renderer/core/editing/frame_selection.h"
+#include "third_party/blink/renderer/core/editing/selection_template.h"
#include "third_party/blink/renderer/core/editing/testing/editing_test_base.h"
#include "third_party/blink/renderer/core/frame/local_frame.h"
+#include "third_party/blink/renderer/core/frame/settings.h"
#include "third_party/blink/renderer/platform/wtf/text/wtf_string.h"
namespace blink {
@@ -38,7 +41,7 @@ class EditingCommandTest : public EditingTestBase {};
TEST_F(EditingCommandTest, EditorCommandOrder) {
for (size_t i = 1; i < base::size(kCommandNameEntries); ++i) {
EXPECT_GT(0,
- WTF::CodePointCompareIgnoringASCIICase(
+ WTF::CodeUnitCompareIgnoringASCIICase(
kCommandNameEntries[i - 1].name, kCommandNameEntries[i].name))
<< "EDITOR_COMMAND_MAP must be case-folding ordered. Incorrect index:"
<< i;
@@ -79,4 +82,64 @@ TEST_F(EditingCommandTest, CreateCommandFromInvalidString) {
}
}
+TEST_F(EditingCommandTest, EnabledVisibleSelection) {
+ Editor& editor = GetDocument().GetFrame()->GetEditor();
+ const EditorCommand command =
+ editor.CreateCommand("MoveRightAndModifySelection");
+ Selection().SetSelection(
+ SetSelectionTextToBody("<div contenteditable>a|b<div>"),
+ SetSelectionOptions());
+ Element* div = GetDocument().QuerySelector("div");
+ GetDocument().SetFocusedElement(
+ div,
+ FocusParams(SelectionBehaviorOnFocus::kNone, kWebFocusTypeNone, nullptr));
+ EXPECT_TRUE(command.IsEnabled());
+ div->removeAttribute("contenteditable");
+ EXPECT_FALSE(command.IsEnabled());
+ GetDocument().GetFrame()->GetSettings()->SetCaretBrowsingEnabled(true);
+ EXPECT_TRUE(command.IsEnabled());
+}
+
+TEST_F(EditingCommandTest, EnabledVisibleSelectionAndMark) {
+ Editor& editor = GetDocument().GetFrame()->GetEditor();
+ const EditorCommand command = editor.CreateCommand("SelectToMark");
+ Selection().SetSelection(
+ SetSelectionTextToBody("<div contenteditable>a|b<div>"),
+ SetSelectionOptions());
+ Element* div = GetDocument().QuerySelector("div");
+ GetDocument().SetFocusedElement(
+ div,
+ FocusParams(SelectionBehaviorOnFocus::kNone, kWebFocusTypeNone, nullptr));
+ EXPECT_FALSE(command.IsEnabled());
+ editor.SetMark();
+ EXPECT_TRUE(command.IsEnabled());
+ div->removeAttribute("contenteditable");
+ EXPECT_FALSE(command.IsEnabled());
+ GetDocument().GetFrame()->GetSettings()->SetCaretBrowsingEnabled(true);
+ EXPECT_TRUE(command.IsEnabled());
+}
+
+TEST_F(EditingCommandTest, EnabledInEditableTextOrCaretBrowsing) {
+ Editor& editor = GetDocument().GetFrame()->GetEditor();
+ const EditorCommand command = editor.CreateCommand("MoveRight");
+
+ SetBodyContent("<div>abc</div>");
+ GetDocument().GetFrame()->GetSettings()->SetCaretBrowsingEnabled(false);
+ EXPECT_FALSE(command.IsEnabled());
+ GetDocument().GetFrame()->GetSettings()->SetCaretBrowsingEnabled(true);
+ EXPECT_TRUE(command.IsEnabled());
+
+ GetDocument().GetFrame()->GetSettings()->SetCaretBrowsingEnabled(false);
+ Selection().SetSelection(
+ SetSelectionTextToBody("<div contenteditable>a|b<div>"),
+ SetSelectionOptions());
+ Element* div = GetDocument().QuerySelector("div");
+ GetDocument().SetFocusedElement(
+ div,
+ FocusParams(SelectionBehaviorOnFocus::kNone, kWebFocusTypeNone, nullptr));
+ EXPECT_TRUE(command.IsEnabled());
+ div->removeAttribute("contenteditable");
+ EXPECT_FALSE(command.IsEnabled());
+}
+
} // namespace blink
diff --git a/chromium/third_party/blink/renderer/core/editing/commands/editing_commands_utilities.cc b/chromium/third_party/blink/renderer/core/editing/commands/editing_commands_utilities.cc
index 332305aba57..e00a5c11d4d 100644
--- a/chromium/third_party/blink/renderer/core/editing/commands/editing_commands_utilities.cc
+++ b/chromium/third_party/blink/renderer/core/editing/commands/editing_commands_utilities.cc
@@ -39,7 +39,6 @@
#include "third_party/blink/renderer/core/editing/visible_position.h"
#include "third_party/blink/renderer/core/editing/visible_selection.h"
#include "third_party/blink/renderer/core/frame/local_frame_client.h"
-#include "third_party/blink/renderer/core/frame/use_counter.h"
#include "third_party/blink/renderer/core/frame/web_feature_forward.h"
#include "third_party/blink/renderer/core/html/html_body_element.h"
#include "third_party/blink/renderer/core/html/html_html_element.h"
@@ -47,6 +46,7 @@
#include "third_party/blink/renderer/core/layout/layout_object.h"
#include "third_party/blink/renderer/core/layout/layout_text.h"
#include "third_party/blink/renderer/platform/heap/heap.h"
+#include "third_party/blink/renderer/platform/instrumentation/use_counter.h"
namespace blink {
@@ -80,7 +80,7 @@ Node* HighestNodeToRemoveInPruning(Node* node, const Node* exclude_node) {
}
Element* EnclosingTableCell(const Position& p) {
- return ToElement(EnclosingNodeOfType(p, IsTableCell));
+ return To<Element>(EnclosingNodeOfType(p, IsTableCell));
}
bool IsTableStructureNode(const Node* node) {
@@ -132,18 +132,18 @@ Node* EnclosingEmptyListItem(const VisiblePosition& visible_pos) {
}
bool AreIdenticalElements(const Node& first, const Node& second) {
- if (!first.IsElementNode() || !second.IsElementNode())
+ const auto* first_element = DynamicTo<Element>(first);
+ const auto* second_element = DynamicTo<Element>(second);
+ if (!first_element || !second_element)
return false;
- const Element& first_element = ToElement(first);
- const Element& second_element = ToElement(second);
- if (!first_element.HasTagName(second_element.TagQName()))
+ if (!first_element->HasTagName(second_element->TagQName()))
return false;
- if (!first_element.HasEquivalentAttributes(second_element))
+ if (!first_element->HasEquivalentAttributes(*second_element))
return false;
- return HasEditableStyle(first_element) && HasEditableStyle(second_element);
+ return HasEditableStyle(*first_element) && HasEditableStyle(*second_element);
}
// FIXME: need to dump this
diff --git a/chromium/third_party/blink/renderer/core/editing/commands/editing_state.h b/chromium/third_party/blink/renderer/core/editing/commands/editing_state.h
index e1840d17c0d..f5b63acbfe8 100644
--- a/chromium/third_party/blink/renderer/core/editing/commands/editing_state.h
+++ b/chromium/third_party/blink/renderer/core/editing/commands/editing_state.h
@@ -7,7 +7,7 @@
#include "base/macros.h"
#include "third_party/blink/renderer/core/core_export.h"
-#include "third_party/blink/renderer/platform/wtf/allocator.h"
+#include "third_party/blink/renderer/platform/wtf/allocator/allocator.h"
#include "third_party/blink/renderer/platform/wtf/assertions.h"
namespace blink {
diff --git a/chromium/third_party/blink/renderer/core/editing/commands/editor_command.cc b/chromium/third_party/blink/renderer/core/editing/commands/editor_command.cc
index 43530091ebe..4476c4673d6 100644
--- a/chromium/third_party/blink/renderer/core/editing/commands/editor_command.cc
+++ b/chromium/third_party/blink/renderer/core/editing/commands/editor_command.cc
@@ -60,6 +60,7 @@
#include "third_party/blink/renderer/core/editing/visible_position.h"
#include "third_party/blink/renderer/core/frame/local_frame.h"
#include "third_party/blink/renderer/core/frame/local_frame_view.h"
+#include "third_party/blink/renderer/core/frame/settings.h"
#include "third_party/blink/renderer/core/html/html_br_element.h"
#include "third_party/blink/renderer/core/html_names.h"
#include "third_party/blink/renderer/core/input/event_handler.h"
@@ -68,8 +69,8 @@
#include "third_party/blink/renderer/core/scroll/scrollbar.h"
#include "third_party/blink/renderer/platform/bindings/exception_state.h"
#include "third_party/blink/renderer/platform/heap/heap.h"
-#include "third_party/blink/renderer/platform/histogram.h"
-#include "third_party/blink/renderer/platform/wtf/allocator.h"
+#include "third_party/blink/renderer/platform/instrumentation/histogram.h"
+#include "third_party/blink/renderer/platform/wtf/allocator/allocator.h"
#include "third_party/blink/renderer/platform/wtf/text/atomic_string.h"
#include <iterator>
@@ -101,10 +102,10 @@ WebEditingCommandType WebEditingCommandTypeFromCommandName(
const CommandNameEntry* result = std::lower_bound(
std::begin(kCommandNameEntries), std::end(kCommandNameEntries),
command_name, [](const CommandNameEntry& entry, const String& needle) {
- return CodePointCompareIgnoringASCIICase(needle, entry.name) > 0;
+ return CodeUnitCompareIgnoringASCIICase(needle, entry.name) > 0;
});
if (result != std::end(kCommandNameEntries) &&
- CodePointCompareIgnoringASCIICase(command_name, result->name) == 0)
+ CodeUnitCompareIgnoringASCIICase(command_name, result->name) == 0)
return result->type;
return WebEditingCommandType::kInvalid;
}
@@ -1046,11 +1047,13 @@ static bool EnabledVisibleSelection(LocalFrame& frame,
!frame.Selection().SelectionHasFocus())
return false;
- // The term "visible" here includes a caret in editable text or a range in any
- // text.
+ // The term "visible" here includes a caret in editable text, a range in any
+ // text, or a caret in non-editable text when caret browsing is enabled.
const VisibleSelection& selection =
CreateVisibleSelection(frame.GetEditor().SelectionForCommand(event));
- return (selection.IsCaret() && selection.IsContentEditable()) ||
+ return (selection.IsCaret() &&
+ (selection.IsContentEditable() ||
+ frame.GetSettings()->GetCaretBrowsingEnabled())) ||
selection.IsRange();
}
@@ -1065,7 +1068,9 @@ static bool EnabledVisibleSelectionAndMark(LocalFrame& frame,
const VisibleSelection& selection =
CreateVisibleSelection(frame.GetEditor().SelectionForCommand(event));
- return ((selection.IsCaret() && selection.IsContentEditable()) ||
+ return ((selection.IsCaret() &&
+ (selection.IsContentEditable() ||
+ frame.GetSettings()->GetCaretBrowsingEnabled())) ||
selection.IsRange()) &&
!frame.GetEditor().Mark().IsNone();
}
@@ -1096,6 +1101,13 @@ static bool EnabledInEditableText(LocalFrame& frame,
CreateVisiblePosition(selection.Base()).DeepEquivalent());
}
+static bool EnabledInEditableTextOrCaretBrowsing(LocalFrame& frame,
+ Event* event,
+ EditorCommandSource source) {
+ return frame.GetSettings()->GetCaretBrowsingEnabled() ||
+ EnabledInEditableText(frame, event, source);
+}
+
static bool EnabledDelete(LocalFrame& frame,
Event* event,
EditorCommandSource source) {
@@ -1480,184 +1492,198 @@ static const EditorInternalCommand* InternalCommand(
StyleCommands::StateTextWritingDirectionRightToLeft, ValueStateOrNull,
kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveBackward, MoveCommands::ExecuteMoveBackward,
- SupportedFromMenuOrKeyBinding, EnabledInEditableText, StateNone,
- ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
+ SupportedFromMenuOrKeyBinding, EnabledInEditableTextOrCaretBrowsing,
+ StateNone, ValueStateOrNull, kNotTextInsertion,
+ CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveBackwardAndModifySelection,
MoveCommands::ExecuteMoveBackwardAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveDown, MoveCommands::ExecuteMoveDown,
- SupportedFromMenuOrKeyBinding, EnabledInEditableText, StateNone,
- ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
+ SupportedFromMenuOrKeyBinding, EnabledInEditableTextOrCaretBrowsing,
+ StateNone, ValueStateOrNull, kNotTextInsertion,
+ CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveDownAndModifySelection,
MoveCommands::ExecuteMoveDownAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveForward, MoveCommands::ExecuteMoveForward,
- SupportedFromMenuOrKeyBinding, EnabledInEditableText, StateNone,
- ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
+ SupportedFromMenuOrKeyBinding, EnabledInEditableTextOrCaretBrowsing,
+ StateNone, ValueStateOrNull, kNotTextInsertion,
+ CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveForwardAndModifySelection,
MoveCommands::ExecuteMoveForwardAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveLeft, MoveCommands::ExecuteMoveLeft,
- SupportedFromMenuOrKeyBinding, EnabledInEditableText, StateNone,
- ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
+ SupportedFromMenuOrKeyBinding, EnabledInEditableTextOrCaretBrowsing,
+ StateNone, ValueStateOrNull, kNotTextInsertion,
+ CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveLeftAndModifySelection,
MoveCommands::ExecuteMoveLeftAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMovePageDown, MoveCommands::ExecuteMovePageDown,
- SupportedFromMenuOrKeyBinding, EnabledInEditableText, StateNone,
- ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
+ SupportedFromMenuOrKeyBinding, EnabledInEditableTextOrCaretBrowsing,
+ StateNone, ValueStateOrNull, kNotTextInsertion,
+ CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMovePageDownAndModifySelection,
MoveCommands::ExecuteMovePageDownAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMovePageUp, MoveCommands::ExecuteMovePageUp,
- SupportedFromMenuOrKeyBinding, EnabledInEditableText, StateNone,
- ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
+ SupportedFromMenuOrKeyBinding, EnabledInEditableTextOrCaretBrowsing,
+ StateNone, ValueStateOrNull, kNotTextInsertion,
+ CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMovePageUpAndModifySelection,
MoveCommands::ExecuteMovePageUpAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveParagraphBackward,
MoveCommands::ExecuteMoveParagraphBackward,
- SupportedFromMenuOrKeyBinding, EnabledInEditableText, StateNone,
- ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
+ SupportedFromMenuOrKeyBinding, EnabledInEditableTextOrCaretBrowsing,
+ StateNone, ValueStateOrNull, kNotTextInsertion,
+ CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveParagraphBackwardAndModifySelection,
MoveCommands::ExecuteMoveParagraphBackwardAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveParagraphForward,
MoveCommands::ExecuteMoveParagraphForward, SupportedFromMenuOrKeyBinding,
- EnabledInEditableText, StateNone, ValueStateOrNull, kNotTextInsertion,
- CanNotExecuteWhenDisabled},
+ EnabledInEditableTextOrCaretBrowsing, StateNone, ValueStateOrNull,
+ kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveParagraphForwardAndModifySelection,
MoveCommands::ExecuteMoveParagraphForwardAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveRight, MoveCommands::ExecuteMoveRight,
- SupportedFromMenuOrKeyBinding, EnabledInEditableText, StateNone,
- ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
+ SupportedFromMenuOrKeyBinding, EnabledInEditableTextOrCaretBrowsing,
+ StateNone, ValueStateOrNull, kNotTextInsertion,
+ CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveRightAndModifySelection,
MoveCommands::ExecuteMoveRightAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveToBeginningOfDocument,
MoveCommands::ExecuteMoveToBeginningOfDocument,
- SupportedFromMenuOrKeyBinding, EnabledInEditableText, StateNone,
- ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
+ SupportedFromMenuOrKeyBinding, EnabledInEditableTextOrCaretBrowsing,
+ StateNone, ValueStateOrNull, kNotTextInsertion,
+ CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveToBeginningOfDocumentAndModifySelection,
MoveCommands::ExecuteMoveToBeginningOfDocumentAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveToBeginningOfLine,
MoveCommands::ExecuteMoveToBeginningOfLine,
- SupportedFromMenuOrKeyBinding, EnabledInEditableText, StateNone,
- ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
+ SupportedFromMenuOrKeyBinding, EnabledInEditableTextOrCaretBrowsing,
+ StateNone, ValueStateOrNull, kNotTextInsertion,
+ CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveToBeginningOfLineAndModifySelection,
MoveCommands::ExecuteMoveToBeginningOfLineAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveToBeginningOfParagraph,
MoveCommands::ExecuteMoveToBeginningOfParagraph,
- SupportedFromMenuOrKeyBinding, EnabledInEditableText, StateNone,
- ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
+ SupportedFromMenuOrKeyBinding, EnabledInEditableTextOrCaretBrowsing,
+ StateNone, ValueStateOrNull, kNotTextInsertion,
+ CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveToBeginningOfParagraphAndModifySelection,
MoveCommands::ExecuteMoveToBeginningOfParagraphAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveToBeginningOfSentence,
MoveCommands::ExecuteMoveToBeginningOfSentence,
- SupportedFromMenuOrKeyBinding, EnabledInEditableText, StateNone,
- ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
+ SupportedFromMenuOrKeyBinding, EnabledInEditableTextOrCaretBrowsing,
+ StateNone, ValueStateOrNull, kNotTextInsertion,
+ CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveToBeginningOfSentenceAndModifySelection,
MoveCommands::ExecuteMoveToBeginningOfSentenceAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveToEndOfDocument,
MoveCommands::ExecuteMoveToEndOfDocument, SupportedFromMenuOrKeyBinding,
- EnabledInEditableText, StateNone, ValueStateOrNull, kNotTextInsertion,
- CanNotExecuteWhenDisabled},
+ EnabledInEditableTextOrCaretBrowsing, StateNone, ValueStateOrNull,
+ kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveToEndOfDocumentAndModifySelection,
MoveCommands::ExecuteMoveToEndOfDocumentAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveToEndOfLine,
MoveCommands::ExecuteMoveToEndOfLine, SupportedFromMenuOrKeyBinding,
- EnabledInEditableText, StateNone, ValueStateOrNull, kNotTextInsertion,
- CanNotExecuteWhenDisabled},
+ EnabledInEditableTextOrCaretBrowsing, StateNone, ValueStateOrNull,
+ kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveToEndOfLineAndModifySelection,
MoveCommands::ExecuteMoveToEndOfLineAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveToEndOfParagraph,
MoveCommands::ExecuteMoveToEndOfParagraph, SupportedFromMenuOrKeyBinding,
- EnabledInEditableText, StateNone, ValueStateOrNull, kNotTextInsertion,
- CanNotExecuteWhenDisabled},
+ EnabledInEditableTextOrCaretBrowsing, StateNone, ValueStateOrNull,
+ kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveToEndOfParagraphAndModifySelection,
MoveCommands::ExecuteMoveToEndOfParagraphAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveToEndOfSentence,
MoveCommands::ExecuteMoveToEndOfSentence, SupportedFromMenuOrKeyBinding,
- EnabledInEditableText, StateNone, ValueStateOrNull, kNotTextInsertion,
- CanNotExecuteWhenDisabled},
+ EnabledInEditableTextOrCaretBrowsing, StateNone, ValueStateOrNull,
+ kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveToEndOfSentenceAndModifySelection,
MoveCommands::ExecuteMoveToEndOfSentenceAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveToLeftEndOfLine,
MoveCommands::ExecuteMoveToLeftEndOfLine, SupportedFromMenuOrKeyBinding,
- EnabledInEditableText, StateNone, ValueStateOrNull, kNotTextInsertion,
- CanNotExecuteWhenDisabled},
+ EnabledInEditableTextOrCaretBrowsing, StateNone, ValueStateOrNull,
+ kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveToLeftEndOfLineAndModifySelection,
MoveCommands::ExecuteMoveToLeftEndOfLineAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledInEditableText, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveToRightEndOfLine,
MoveCommands::ExecuteMoveToRightEndOfLine, SupportedFromMenuOrKeyBinding,
- EnabledInEditableText, StateNone, ValueStateOrNull, kNotTextInsertion,
- CanNotExecuteWhenDisabled},
+ EnabledInEditableTextOrCaretBrowsing, StateNone, ValueStateOrNull,
+ kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveToRightEndOfLineAndModifySelection,
MoveCommands::ExecuteMoveToRightEndOfLineAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledInEditableText, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveUp, MoveCommands::ExecuteMoveUp,
- SupportedFromMenuOrKeyBinding, EnabledInEditableText, StateNone,
- ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
+ SupportedFromMenuOrKeyBinding, EnabledInEditableTextOrCaretBrowsing,
+ StateNone, ValueStateOrNull, kNotTextInsertion,
+ CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveUpAndModifySelection,
MoveCommands::ExecuteMoveUpAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveWordBackward,
MoveCommands::ExecuteMoveWordBackward, SupportedFromMenuOrKeyBinding,
- EnabledInEditableText, StateNone, ValueStateOrNull, kNotTextInsertion,
- CanNotExecuteWhenDisabled},
+ EnabledInEditableTextOrCaretBrowsing, StateNone, ValueStateOrNull,
+ kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveWordBackwardAndModifySelection,
MoveCommands::ExecuteMoveWordBackwardAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveWordForward,
MoveCommands::ExecuteMoveWordForward, SupportedFromMenuOrKeyBinding,
- EnabledInEditableText, StateNone, ValueStateOrNull, kNotTextInsertion,
- CanNotExecuteWhenDisabled},
+ EnabledInEditableTextOrCaretBrowsing, StateNone, ValueStateOrNull,
+ kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveWordForwardAndModifySelection,
MoveCommands::ExecuteMoveWordForwardAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveWordLeft, MoveCommands::ExecuteMoveWordLeft,
- SupportedFromMenuOrKeyBinding, EnabledInEditableText, StateNone,
- ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
+ SupportedFromMenuOrKeyBinding, EnabledInEditableTextOrCaretBrowsing,
+ StateNone, ValueStateOrNull, kNotTextInsertion,
+ CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveWordLeftAndModifySelection,
MoveCommands::ExecuteMoveWordLeftAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
ValueStateOrNull, kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveWordRight,
MoveCommands::ExecuteMoveWordRight, SupportedFromMenuOrKeyBinding,
- EnabledInEditableText, StateNone, ValueStateOrNull, kNotTextInsertion,
- CanNotExecuteWhenDisabled},
+ EnabledInEditableTextOrCaretBrowsing, StateNone, ValueStateOrNull,
+ kNotTextInsertion, CanNotExecuteWhenDisabled},
{WebEditingCommandType::kMoveWordRightAndModifySelection,
MoveCommands::ExecuteMoveWordRightAndModifySelection,
SupportedFromMenuOrKeyBinding, EnabledVisibleSelection, StateNone,
diff --git a/chromium/third_party/blink/renderer/core/editing/commands/format_block_command.cc b/chromium/third_party/blink/renderer/core/editing/commands/format_block_command.cc
index d4670e1891e..8f6215d8715 100644
--- a/chromium/third_party/blink/renderer/core/editing/commands/format_block_command.cc
+++ b/chromium/third_party/blink/renderer/core/editing/commands/format_block_command.cc
@@ -45,8 +45,8 @@ using namespace html_names;
static Node* EnclosingBlockToSplitTreeTo(Node* start_node);
static bool IsElementForFormatBlock(const QualifiedName& tag_name);
static inline bool IsElementForFormatBlock(Node* node) {
- return node->IsElementNode() &&
- IsElementForFormatBlock(ToElement(node)->TagQName());
+ auto* element = DynamicTo<Element>(node);
+ return element && IsElementForFormatBlock(element->TagQName());
}
static Element* EnclosingBlockFlowElement(
@@ -170,8 +170,7 @@ Element* FormatBlockCommand::ElementForFormatBlockCommand(
if (!element || common_ancestor->contains(element))
return nullptr;
- return common_ancestor->IsElementNode() ? ToElement(common_ancestor)
- : nullptr;
+ return DynamicTo<Element>(common_ancestor);
}
bool IsElementForFormatBlock(const QualifiedName& tag_name) {
diff --git a/chromium/third_party/blink/renderer/core/editing/commands/indent_outdent_command.cc b/chromium/third_party/blink/renderer/core/editing/commands/indent_outdent_command.cc
index e0c550f0bb0..ab283d72b39 100644
--- a/chromium/third_party/blink/renderer/core/editing/commands/indent_outdent_command.cc
+++ b/chromium/third_party/blink/renderer/core/editing/commands/indent_outdent_command.cc
@@ -158,7 +158,7 @@ void IndentOutdentCommand::IndentIntoBlockquote(const Position& start,
const Position& end,
HTMLElement*& target_blockquote,
EditingState* editing_state) {
- Element* enclosing_cell = ToElement(EnclosingNodeOfType(start, &IsTableCell));
+ auto* enclosing_cell = To<Element>(EnclosingNodeOfType(start, &IsTableCell));
Element* element_to_split_to;
if (enclosing_cell)
element_to_split_to = enclosing_cell;
diff --git a/chromium/third_party/blink/renderer/core/editing/commands/insert_commands.h b/chromium/third_party/blink/renderer/core/editing/commands/insert_commands.h
index 19a633e0a66..0ac3d424ebc 100644
--- a/chromium/third_party/blink/renderer/core/editing/commands/insert_commands.h
+++ b/chromium/third_party/blink/renderer/core/editing/commands/insert_commands.h
@@ -32,7 +32,7 @@
#ifndef THIRD_PARTY_BLINK_RENDERER_CORE_EDITING_COMMANDS_INSERT_COMMANDS_H_
#define THIRD_PARTY_BLINK_RENDERER_CORE_EDITING_COMMANDS_INSERT_COMMANDS_H_
-#include "third_party/blink/renderer/platform/wtf/allocator.h"
+#include "third_party/blink/renderer/platform/wtf/allocator/allocator.h"
#include "third_party/blink/renderer/platform/wtf/forward.h"
namespace blink {
diff --git a/chromium/third_party/blink/renderer/core/editing/commands/insert_list_command.cc b/chromium/third_party/blink/renderer/core/editing/commands/insert_list_command.cc
index ddf9e35d81a..c7fcbbbedd2 100644
--- a/chromium/third_party/blink/renderer/core/editing/commands/insert_list_command.cc
+++ b/chromium/third_party/blink/renderer/core/editing/commands/insert_list_command.cc
@@ -402,7 +402,7 @@ bool InsertListCommand::DoApplyForSingleParagraph(
list_element);
Element* outer_block =
first_child_in_list && IsBlockFlowElement(*first_child_in_list)
- ? ToElement(first_child_in_list)
+ ? To<Element>(first_child_in_list)
: list_element;
MoveParagraphWithClones(
diff --git a/chromium/third_party/blink/renderer/core/editing/commands/move_commands.cc b/chromium/third_party/blink/renderer/core/editing/commands/move_commands.cc
index c9c11f8f260..b84a47076e3 100644
--- a/chromium/third_party/blink/renderer/core/editing/commands/move_commands.cc
+++ b/chromium/third_party/blink/renderer/core/editing/commands/move_commands.cc
@@ -31,21 +31,29 @@
#include "third_party/blink/renderer/core/editing/commands/move_commands.h"
+#include "third_party/blink/renderer/core/dom/node_computed_style.h"
#include "third_party/blink/renderer/core/editing/editing_behavior.h"
#include "third_party/blink/renderer/core/editing/editing_utilities.h"
#include "third_party/blink/renderer/core/editing/editor.h"
#include "third_party/blink/renderer/core/editing/frame_selection.h"
#include "third_party/blink/renderer/core/editing/selection_modifier.h"
#include "third_party/blink/renderer/core/frame/local_frame.h"
+#include "third_party/blink/renderer/core/frame/settings.h"
#include "third_party/blink/renderer/core/layout/layout_box.h"
#include "third_party/blink/renderer/core/paint/paint_layer_scrollable_area.h"
namespace blink {
unsigned MoveCommands::VerticalScrollDistance(LocalFrame& frame) {
- const Element* const focused_element = frame.GetDocument()->FocusedElement();
- if (!focused_element)
- return 0;
+ const Element* focused_element = frame.GetDocument()->FocusedElement();
+ if (!focused_element) {
+ if (frame.GetSettings()->GetCaretBrowsingEnabled()) {
+ focused_element = frame.GetDocument()->ActiveElement();
+ }
+
+ if (!focused_element)
+ return 0;
+ }
LayoutObject* const layout_object = focused_element->GetLayoutObject();
if (!layout_object || !layout_object->IsBox())
return 0;
@@ -55,7 +63,8 @@ unsigned MoveCommands::VerticalScrollDistance(LocalFrame& frame) {
return 0;
if (!(style->OverflowY() == EOverflow::kScroll ||
style->OverflowY() == EOverflow::kAuto ||
- HasEditableStyle(*focused_element)))
+ HasEditableStyle(*focused_element) ||
+ frame.GetSettings()->GetCaretBrowsingEnabled()))
return 0;
const ScrollableArea& scrollable_area = *frame.View()->LayoutViewport();
const int height = std::min<int>(layout_box.ClientHeight().ToInt(),
@@ -71,6 +80,9 @@ bool MoveCommands::ModifySelectionWithPageGranularity(
SelectionModifyAlteration alter,
unsigned vertical_distance,
SelectionModifyVerticalDirection direction) {
+ if (alter == SelectionModifyAlteration::kMove)
+ UpdateSelectionForCaretBrowsing(frame);
+
SelectionModifier selection_modifier(
frame, frame.Selection().GetSelectionInDOMTree());
selection_modifier.SetSelectionIsDirectional(
@@ -94,16 +106,87 @@ bool MoveCommands::ModifySelectionWithPageGranularity(
.Behavior()
.ShouldConsiderSelectionAsDirectional())
.Build());
+
+ UpdateFocusForCaretBrowsing(frame);
+
return true;
}
+bool MoveCommands::MoveSelection(LocalFrame& frame,
+ SelectionModifyDirection direction,
+ TextGranularity granularity) {
+ UpdateSelectionForCaretBrowsing(frame);
+ const bool modified =
+ frame.Selection().Modify(SelectionModifyAlteration::kMove, direction,
+ granularity, SetSelectionBy::kUser);
+ if (modified)
+ UpdateFocusForCaretBrowsing(frame);
+
+ return modified;
+}
+
+void MoveCommands::UpdateFocusForCaretBrowsing(LocalFrame& frame) {
+ if (!frame.GetSettings()->GetCaretBrowsingEnabled())
+ return;
+
+ SelectionInDOMTree selection = frame.Selection().GetSelectionInDOMTree();
+ if (!selection.IsCaret())
+ return;
+
+ Node* node = selection.Extent().ComputeContainerNode();
+ if (!node)
+ return;
+
+ const ComputedStyle* style = node->GetComputedStyle();
+ if (!style || style->UserModify() != EUserModify::kReadOnly)
+ return;
+
+ Element* new_focused_element = nullptr;
+
+ while (node) {
+ if (node->IsElementNode() && ToElement(node)->IsFocusable()) {
+ new_focused_element = ToElement(node);
+ break;
+ }
+ node = node->ParentOrShadowHostNode();
+ }
+
+ if (new_focused_element == frame.GetDocument()->FocusedElement())
+ return;
+
+ frame.GetDocument()->SetFocusedElement(
+ new_focused_element,
+ FocusParams(SelectionBehaviorOnFocus::kNone, kWebFocusTypeNone, nullptr));
+}
+
+void MoveCommands::UpdateSelectionForCaretBrowsing(LocalFrame& frame) {
+ if (!frame.GetSettings()->GetCaretBrowsingEnabled())
+ return;
+
+ if (frame.Selection().SelectionHasFocus())
+ return;
+
+ Element* activeElement = frame.GetDocument()->ActiveElement();
+ if (!activeElement)
+ return;
+
+ frame.Selection().SetSelection(
+ SelectionInDOMTree::Builder()
+ .Collapse(Position::FirstPositionInOrBeforeNode(*activeElement))
+ .Build(),
+ SetSelectionOptions::Builder()
+ .SetShouldCloseTyping(true)
+ .SetShouldClearTypingStyle(true)
+ .SetDoNotSetFocus(true)
+ .Build());
+}
+
bool MoveCommands::ExecuteMoveBackward(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- frame.Selection().Modify(SelectionModifyAlteration::kMove,
- SelectionModifyDirection::kBackward,
- TextGranularity::kCharacter, SetSelectionBy::kUser);
+ MoveSelection(frame, SelectionModifyDirection::kBackward,
+ TextGranularity::kCharacter);
return true;
}
@@ -121,9 +204,8 @@ bool MoveCommands::ExecuteMoveDown(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- return frame.Selection().Modify(
- SelectionModifyAlteration::kMove, SelectionModifyDirection::kForward,
- TextGranularity::kLine, SetSelectionBy::kUser);
+ return MoveSelection(frame, SelectionModifyDirection::kForward,
+ TextGranularity::kLine);
}
bool MoveCommands::ExecuteMoveDownAndModifySelection(LocalFrame& frame,
@@ -140,9 +222,8 @@ bool MoveCommands::ExecuteMoveForward(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- frame.Selection().Modify(SelectionModifyAlteration::kMove,
- SelectionModifyDirection::kForward,
- TextGranularity::kCharacter, SetSelectionBy::kUser);
+ MoveSelection(frame, SelectionModifyDirection::kForward,
+ TextGranularity::kCharacter);
return true;
}
@@ -160,9 +241,8 @@ bool MoveCommands::ExecuteMoveLeft(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- return frame.Selection().Modify(
- SelectionModifyAlteration::kMove, SelectionModifyDirection::kLeft,
- TextGranularity::kCharacter, SetSelectionBy::kUser);
+ return MoveSelection(frame, SelectionModifyDirection::kLeft,
+ TextGranularity::kCharacter);
}
bool MoveCommands::ExecuteMoveLeftAndModifySelection(LocalFrame& frame,
@@ -227,9 +307,8 @@ bool MoveCommands::ExecuteMoveParagraphBackward(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- frame.Selection().Modify(SelectionModifyAlteration::kMove,
- SelectionModifyDirection::kBackward,
- TextGranularity::kParagraph, SetSelectionBy::kUser);
+ MoveSelection(frame, SelectionModifyDirection::kBackward,
+ TextGranularity::kParagraph);
return true;
}
@@ -248,9 +327,8 @@ bool MoveCommands::ExecuteMoveParagraphForward(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- frame.Selection().Modify(SelectionModifyAlteration::kMove,
- SelectionModifyDirection::kForward,
- TextGranularity::kParagraph, SetSelectionBy::kUser);
+ MoveSelection(frame, SelectionModifyDirection::kForward,
+ TextGranularity::kParagraph);
return true;
}
@@ -269,9 +347,8 @@ bool MoveCommands::ExecuteMoveRight(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- return frame.Selection().Modify(
- SelectionModifyAlteration::kMove, SelectionModifyDirection::kRight,
- TextGranularity::kCharacter, SetSelectionBy::kUser);
+ return MoveSelection(frame, SelectionModifyDirection::kRight,
+ TextGranularity::kCharacter);
}
bool MoveCommands::ExecuteMoveRightAndModifySelection(LocalFrame& frame,
@@ -288,9 +365,8 @@ bool MoveCommands::ExecuteMoveToBeginningOfDocument(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- frame.Selection().Modify(
- SelectionModifyAlteration::kMove, SelectionModifyDirection::kBackward,
- TextGranularity::kDocumentBoundary, SetSelectionBy::kUser);
+ MoveSelection(frame, SelectionModifyDirection::kBackward,
+ TextGranularity::kDocumentBoundary);
return true;
}
@@ -309,9 +385,8 @@ bool MoveCommands::ExecuteMoveToBeginningOfLine(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- frame.Selection().Modify(
- SelectionModifyAlteration::kMove, SelectionModifyDirection::kBackward,
- TextGranularity::kLineBoundary, SetSelectionBy::kUser);
+ MoveSelection(frame, SelectionModifyDirection::kBackward,
+ TextGranularity::kLineBoundary);
return true;
}
@@ -330,9 +405,8 @@ bool MoveCommands::ExecuteMoveToBeginningOfParagraph(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- frame.Selection().Modify(
- SelectionModifyAlteration::kMove, SelectionModifyDirection::kBackward,
- TextGranularity::kParagraphBoundary, SetSelectionBy::kUser);
+ MoveSelection(frame, SelectionModifyDirection::kBackward,
+ TextGranularity::kParagraphBoundary);
return true;
}
@@ -351,9 +425,8 @@ bool MoveCommands::ExecuteMoveToBeginningOfSentence(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- frame.Selection().Modify(
- SelectionModifyAlteration::kMove, SelectionModifyDirection::kBackward,
- TextGranularity::kSentenceBoundary, SetSelectionBy::kUser);
+ MoveSelection(frame, SelectionModifyDirection::kBackward,
+ TextGranularity::kSentenceBoundary);
return true;
}
@@ -372,9 +445,8 @@ bool MoveCommands::ExecuteMoveToEndOfDocument(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- frame.Selection().Modify(
- SelectionModifyAlteration::kMove, SelectionModifyDirection::kForward,
- TextGranularity::kDocumentBoundary, SetSelectionBy::kUser);
+ MoveSelection(frame, SelectionModifyDirection::kForward,
+ TextGranularity::kDocumentBoundary);
return true;
}
@@ -393,9 +465,8 @@ bool MoveCommands::ExecuteMoveToEndOfLine(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- frame.Selection().Modify(
- SelectionModifyAlteration::kMove, SelectionModifyDirection::kForward,
- TextGranularity::kLineBoundary, SetSelectionBy::kUser);
+ MoveSelection(frame, SelectionModifyDirection::kForward,
+ TextGranularity::kLineBoundary);
return true;
}
@@ -413,9 +484,8 @@ bool MoveCommands::ExecuteMoveToEndOfParagraph(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- frame.Selection().Modify(
- SelectionModifyAlteration::kMove, SelectionModifyDirection::kForward,
- TextGranularity::kParagraphBoundary, SetSelectionBy::kUser);
+ MoveSelection(frame, SelectionModifyDirection::kForward,
+ TextGranularity::kParagraphBoundary);
return true;
}
@@ -434,9 +504,8 @@ bool MoveCommands::ExecuteMoveToEndOfSentence(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- frame.Selection().Modify(
- SelectionModifyAlteration::kMove, SelectionModifyDirection::kForward,
- TextGranularity::kSentenceBoundary, SetSelectionBy::kUser);
+ MoveSelection(frame, SelectionModifyDirection::kForward,
+ TextGranularity::kSentenceBoundary);
return true;
}
@@ -455,9 +524,8 @@ bool MoveCommands::ExecuteMoveToLeftEndOfLine(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- frame.Selection().Modify(
- SelectionModifyAlteration::kMove, SelectionModifyDirection::kLeft,
- TextGranularity::kLineBoundary, SetSelectionBy::kUser);
+ MoveSelection(frame, SelectionModifyDirection::kLeft,
+ TextGranularity::kLineBoundary);
return true;
}
@@ -476,9 +544,8 @@ bool MoveCommands::ExecuteMoveToRightEndOfLine(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- frame.Selection().Modify(
- SelectionModifyAlteration::kMove, SelectionModifyDirection::kRight,
- TextGranularity::kLineBoundary, SetSelectionBy::kUser);
+ MoveSelection(frame, SelectionModifyDirection::kRight,
+ TextGranularity::kLineBoundary);
return true;
}
@@ -497,9 +564,8 @@ bool MoveCommands::ExecuteMoveUp(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- return frame.Selection().Modify(
- SelectionModifyAlteration::kMove, SelectionModifyDirection::kBackward,
- TextGranularity::kLine, SetSelectionBy::kUser);
+ return MoveSelection(frame, SelectionModifyDirection::kBackward,
+ TextGranularity::kLine);
}
bool MoveCommands::ExecuteMoveUpAndModifySelection(LocalFrame& frame,
@@ -516,9 +582,8 @@ bool MoveCommands::ExecuteMoveWordBackward(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- frame.Selection().Modify(SelectionModifyAlteration::kMove,
- SelectionModifyDirection::kBackward,
- TextGranularity::kWord, SetSelectionBy::kUser);
+ MoveSelection(frame, SelectionModifyDirection::kBackward,
+ TextGranularity::kWord);
return true;
}
@@ -537,9 +602,8 @@ bool MoveCommands::ExecuteMoveWordForward(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- frame.Selection().Modify(SelectionModifyAlteration::kMove,
- SelectionModifyDirection::kForward,
- TextGranularity::kWord, SetSelectionBy::kUser);
+ MoveSelection(frame, SelectionModifyDirection::kForward,
+ TextGranularity::kWord);
return true;
}
@@ -557,9 +621,7 @@ bool MoveCommands::ExecuteMoveWordLeft(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- frame.Selection().Modify(SelectionModifyAlteration::kMove,
- SelectionModifyDirection::kLeft,
- TextGranularity::kWord, SetSelectionBy::kUser);
+ MoveSelection(frame, SelectionModifyDirection::kLeft, TextGranularity::kWord);
return true;
}
@@ -577,9 +639,8 @@ bool MoveCommands::ExecuteMoveWordRight(LocalFrame& frame,
Event*,
EditorCommandSource,
const String&) {
- frame.Selection().Modify(SelectionModifyAlteration::kMove,
- SelectionModifyDirection::kRight,
- TextGranularity::kWord, SetSelectionBy::kUser);
+ MoveSelection(frame, SelectionModifyDirection::kRight,
+ TextGranularity::kWord);
return true;
}
diff --git a/chromium/third_party/blink/renderer/core/editing/commands/move_commands.h b/chromium/third_party/blink/renderer/core/editing/commands/move_commands.h
index 4eaf2cc9868..062c6416e4f 100644
--- a/chromium/third_party/blink/renderer/core/editing/commands/move_commands.h
+++ b/chromium/third_party/blink/renderer/core/editing/commands/move_commands.h
@@ -32,7 +32,8 @@
#ifndef THIRD_PARTY_BLINK_RENDERER_CORE_EDITING_COMMANDS_MOVE_COMMANDS_H_
#define THIRD_PARTY_BLINK_RENDERER_CORE_EDITING_COMMANDS_MOVE_COMMANDS_H_
-#include "third_party/blink/renderer/platform/wtf/allocator.h"
+#include "third_party/blink/renderer/core/core_export.h"
+#include "third_party/blink/renderer/platform/wtf/allocator/allocator.h"
#include "third_party/blink/renderer/platform/wtf/forward.h"
namespace blink {
@@ -42,10 +43,12 @@ class LocalFrame;
enum class EditorCommandSource;
enum class SelectionModifyAlteration;
+enum class SelectionModifyDirection;
enum class SelectionModifyVerticalDirection;
+enum class TextGranularity;
// This class provides static functions about commands related to move.
-class MoveCommands {
+class CORE_EXPORT MoveCommands {
STATIC_ONLY(MoveCommands);
public:
@@ -257,6 +260,26 @@ class MoveCommands {
SelectionModifyAlteration,
unsigned,
SelectionModifyVerticalDirection);
+
+ // Wraps FrameSelection::Modify for case where the selection is moved by the
+ // user. Returns false if the "selectstart" event is dispatched and canceled,
+ // otherwise returns true (return value does not indicate whether the
+ // selection was modified).
+ static bool MoveSelection(LocalFrame&,
+ SelectionModifyDirection,
+ TextGranularity);
+
+ // If caret browsing is enabled and the caret is in a non-editable region then
+ // UpdateFocusForCaretBrowsing moves focus to the nearest focusable ancestor
+ // of the caret, if there is one. This will, for example, move focus to anchor
+ // elements when the caret enters an anchor. If there is no focusable ancestor
+ // then focus will move to the body.
+ static void UpdateFocusForCaretBrowsing(LocalFrame&);
+
+ // If caret browsing is enabled and the caret/selection is not in focus then
+ // UpdateSelectionForCaretBrowsing moves the caret to the first position in
+ // the active element.
+ static void UpdateSelectionForCaretBrowsing(LocalFrame&);
};
} // namespace blink
diff --git a/chromium/third_party/blink/renderer/core/editing/commands/move_commands_test.cc b/chromium/third_party/blink/renderer/core/editing/commands/move_commands_test.cc
new file mode 100644
index 00000000000..7de107b8210
--- /dev/null
+++ b/chromium/third_party/blink/renderer/core/editing/commands/move_commands_test.cc
@@ -0,0 +1,327 @@
+// Copyright 2019 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include <string>
+
+#include "build/build_config.h"
+#include "third_party/blink/renderer/core/dom/element.h"
+#include "third_party/blink/renderer/core/editing/commands/move_commands.h"
+#include "third_party/blink/renderer/core/editing/editor.h"
+#include "third_party/blink/renderer/core/editing/frame_selection.h"
+#include "third_party/blink/renderer/core/editing/selection_template.h"
+#include "third_party/blink/renderer/core/editing/testing/editing_test_base.h"
+#include "third_party/blink/renderer/core/frame/settings.h"
+
+namespace blink {
+
+class MoveCommandsTest : public EditingTestBase {
+ protected:
+ void VerifyCaretBrowsingPositionAndFocusUpdate(
+ const std::string& initial_selection_text,
+ const AtomicString& initial_focus_element,
+ bool (*execute)(LocalFrame&, Event*, EditorCommandSource, const String&),
+ const std::string& final_selection_text,
+ const AtomicString& final_focus_element) {
+ Selection().SetSelection(SetSelectionTextToBody(initial_selection_text),
+ SetSelectionOptions());
+ GetDocument().SetFocusedElement(
+ GetDocument().QuerySelector(initial_focus_element),
+ FocusParams(SelectionBehaviorOnFocus::kNone, kWebFocusTypeNone,
+ nullptr));
+ GetDocument().GetFrame()->GetSettings()->SetCaretBrowsingEnabled(true);
+ execute(*GetDocument().GetFrame(), nullptr,
+ EditorCommandSource::kMenuOrKeyBinding, String());
+ EXPECT_EQ(final_selection_text, GetSelectionTextFromBody());
+ EXPECT_EQ(GetDocument().QuerySelector(final_focus_element),
+ GetDocument().ActiveElement());
+ }
+};
+
+// The following CaretBrowsingPositionAndFocusUpdate_Move* tests verify that the
+// move commands are using UpdateFocusForCaretBrowsing to adjust caret position
+// and focus while caret browsing.
+
+TEST_F(MoveCommandsTest, CaretBrowsingPositionAndFocusUpdate_MoveBackward) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div><a href=\"foo\">a</a>|b</div>", "body",
+ MoveCommands::ExecuteMoveBackward, "<div><a href=\"foo\">|a</a>b</div>",
+ "a");
+}
+
+TEST_F(MoveCommandsTest, CaretBrowsingPositionAndFocusUpdate_MoveDown) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div>a|b</div><div><a href=\"foo\">cd</a></div>", "body",
+ MoveCommands::ExecuteMoveDown,
+#if !defined(OS_MACOSX)
+ "<div>ab</div><div><a href=\"foo\">c|d</a></div>", "a");
+#else // defined(OS_MACOSX)
+ // MoveDown navigates visually, placing caret at different position for
+ // macOS.
+ "<div>ab</div><div><a href=\"foo\">|cd</a></div>", "a");
+#endif // !defined(OS_MACOSX)
+}
+
+TEST_F(MoveCommandsTest, CaretBrowsingPositionAndFocusUpdate_MoveForward) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div>a|<a href=\"foo\">b</a></div>", "body",
+ MoveCommands::ExecuteMoveForward, "<div>a<a href=\"foo\">b|</a></div>",
+ "a");
+}
+
+TEST_F(MoveCommandsTest, CaretBrowsingPositionAndFocusUpdate_MoveLeft) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div><a href=\"foo\">a</a>|b</div>", "body",
+ MoveCommands::ExecuteMoveLeft, "<div><a href=\"foo\">|a</a>b</div>", "a");
+}
+
+TEST_F(MoveCommandsTest,
+ CaretBrowsingPositionAndFocusUpdate_MoveParagraphBackward) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div><a href=\"foo\">a</a>|b</div>", "body",
+ MoveCommands::ExecuteMoveParagraphBackward,
+ "<div><a href=\"foo\">|a</a>b</div>", "a");
+}
+
+TEST_F(MoveCommandsTest,
+ CaretBrowsingPositionAndFocusUpdate_MoveParagraphForward) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div>a|<a href=\"foo\">b</a></div>", "body",
+ MoveCommands::ExecuteMoveParagraphForward,
+ "<div>a<a href=\"foo\">b|</a></div>", "a");
+}
+
+TEST_F(MoveCommandsTest, CaretBrowsingPositionAndFocusUpdate_MoveRight) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div>a|<a href=\"foo\">b</a></div>", "body",
+ MoveCommands::ExecuteMoveRight, "<div>a<a href=\"foo\">b|</a></div>",
+ "a");
+}
+
+TEST_F(MoveCommandsTest,
+ CaretBrowsingPositionAndFocusUpdate_MoveToBeginningOfDocument) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div><a href=\"foo\">a</a>|b</div>", "body",
+ MoveCommands::ExecuteMoveToBeginningOfDocument,
+ "<div><a href=\"foo\">|a</a>b</div>", "a");
+}
+
+TEST_F(MoveCommandsTest,
+ CaretBrowsingPositionAndFocusUpdate_MoveToBeginningOfLine) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div><a href=\"foo\">a</a>|b</div>", "body",
+ MoveCommands::ExecuteMoveToBeginningOfLine,
+ "<div><a href=\"foo\">|a</a>b</div>", "a");
+}
+
+TEST_F(MoveCommandsTest,
+ CaretBrowsingPositionAndFocusUpdate_MoveToBeginningOfParagraph) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div><a href=\"foo\">a</a>|b</div>", "body",
+ MoveCommands::ExecuteMoveToBeginningOfParagraph,
+ "<div><a href=\"foo\">|a</a>b</div>", "a");
+}
+
+TEST_F(MoveCommandsTest,
+ CaretBrowsingPositionAndFocusUpdate_MoveToBeginningOfSentence) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div><a href=\"foo\">a</a>|b</div>", "body",
+ MoveCommands::ExecuteMoveToBeginningOfSentence,
+ "<div><a href=\"foo\">|a</a>b</div>", "a");
+}
+
+TEST_F(MoveCommandsTest,
+ CaretBrowsingPositionAndFocusUpdate_MoveToEndOfDocument) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div>a|<a href=\"foo\">b</a></div>", "body",
+ MoveCommands::ExecuteMoveToEndOfDocument,
+ "<div>a<a href=\"foo\">b|</a></div>", "a");
+}
+
+TEST_F(MoveCommandsTest, CaretBrowsingPositionAndFocusUpdate_MoveToEndOfLine) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div>a|<a href=\"foo\">b</a></div>", "body",
+ MoveCommands::ExecuteMoveToEndOfLine,
+ "<div>a<a href=\"foo\">b|</a></div>", "a");
+}
+
+TEST_F(MoveCommandsTest,
+ CaretBrowsingPositionAndFocusUpdate_MoveToEndOfParagraph) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div>a|<a href=\"foo\">b</a></div>", "body",
+ MoveCommands::ExecuteMoveToEndOfParagraph,
+ "<div>a<a href=\"foo\">b|</a></div>", "a");
+}
+
+TEST_F(MoveCommandsTest,
+ CaretBrowsingPositionAndFocusUpdate_MoveToEndOfSentence) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div>a|<a href=\"foo\">b</a></div>", "body",
+ MoveCommands::ExecuteMoveToEndOfSentence,
+ "<div>a<a href=\"foo\">b|</a></div>", "a");
+}
+
+TEST_F(MoveCommandsTest,
+ CaretBrowsingPositionAndFocusUpdate_MoveToLeftEndOfLine) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div><a href=\"foo\">a</a>|b</div>", "body",
+ MoveCommands::ExecuteMoveToLeftEndOfLine,
+ "<div><a href=\"foo\">|a</a>b</div>", "a");
+}
+
+TEST_F(MoveCommandsTest,
+ CaretBrowsingPositionAndFocusUpdate_MoveToRightEndOfLine) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div>a|<a href=\"foo\">b</a></div>", "body",
+ MoveCommands::ExecuteMoveToRightEndOfLine,
+ "<div>a<a href=\"foo\">b|</a></div>", "a");
+}
+
+TEST_F(MoveCommandsTest, CaretBrowsingPositionAndFocusUpdate_MoveUp) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div><a href=\"foo\">ab</a></div><div>c|d</div>", "body",
+ MoveCommands::ExecuteMoveUp,
+#if !defined(OS_MACOSX)
+ "<div><a href=\"foo\">a|b</a></div><div>cd</div>", "a");
+#else // defined(OS_MACOSX)
+ // MoveUp navigates visually, placing caret at different position for
+ // macOS.
+ "<div><a href=\"foo\">|ab</a></div><div>cd</div>", "a");
+#endif // !defined(OS_MACOSX)
+}
+
+TEST_F(MoveCommandsTest, CaretBrowsingPositionAndFocusUpdate_MoveWordBackward) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div><a href=\"foo\">a</a>|b</div>", "body",
+ MoveCommands::ExecuteMoveWordBackward,
+ "<div><a href=\"foo\">|a</a>b</div>", "a");
+}
+
+TEST_F(MoveCommandsTest, CaretBrowsingPositionAndFocusUpdate_MoveWordForward) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div>a|<a href=\"foo\">b</a></div>", "body",
+ MoveCommands::ExecuteMoveWordForward,
+ "<div>a<a href=\"foo\">b|</a></div>", "a");
+}
+
+TEST_F(MoveCommandsTest, CaretBrowsingPositionAndFocusUpdate_MoveWordLeft) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div><a href=\"foo\">a</a>|b</div>", "body",
+ MoveCommands::ExecuteMoveWordLeft, "<div><a href=\"foo\">|a</a>b</div>",
+ "a");
+}
+
+TEST_F(MoveCommandsTest, CaretBrowsingPositionAndFocusUpdate_MoveWordRight) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div>a|<a href=\"foo\"> b</a></div>", "body",
+ MoveCommands::ExecuteMoveWordRight, "<div>a<a href=\"foo\"> b|</a></div>",
+ "a");
+}
+
+// This test verifies that focus returns to the body after browsing out of a
+// focusable element.
+TEST_F(MoveCommandsTest,
+ CaretBrowsingPositionAndFocusUpdate_ExitingFocusableElement) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div><a href=\"foo\">a|</a>b</div>", "a", MoveCommands::ExecuteMoveRight,
+ "<div><a href=\"foo\">a</a>b|</div>", "body");
+}
+
+// This test verifies that caret browsing into a focusable element does not
+// move focus if inside an editable region.
+TEST_F(MoveCommandsTest, CaretBrowsingPositionAndFocusUpdate_EditableElements) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div contenteditable>a|<a href=\"foo\">b</a>c</div>", "div",
+ MoveCommands::ExecuteMoveRight,
+ "<div contenteditable>a<a href=\"foo\">b|</a>c</div>", "div");
+}
+
+// This test verifies that another focusable element (the button element) can be
+// moved into while caret browsing and gains focus, just like an anchor
+// element.
+TEST_F(MoveCommandsTest,
+ CaretBrowsingPositionAndFocusUpdate_MoveRightButtonElement) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div>Some text to the left of the button|<button>Click "
+ "Me!</button></div>",
+ "body", MoveCommands::ExecuteMoveRight,
+ "<div>Some text to the left of the button<button>C|lick "
+ "Me!</button></div>",
+ "button");
+}
+
+// This test verifies that an element with tabindex set can be moved
+// into while caret browsing and gains focus, just like an anchor element.
+TEST_F(MoveCommandsTest,
+ CaretBrowsingPositionAndFocusUpdate_MoveRightElementWithTabIndex) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div>Some text to the left of the span|<span tabindex=\"0\">Span with "
+ "tabindex set</span></div>",
+ "body", MoveCommands::ExecuteMoveRight,
+ "<div>Some text to the left of the span<span tabindex=\"0\">S|pan with "
+ "tabindex set</span></div>",
+ "span");
+}
+
+// This test verifies that an input element will be skipped when caret browsing
+// and not gain focus.
+TEST_F(MoveCommandsTest,
+ CaretBrowsingPositionAndFocusUpdate_MoveRightInputElement) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div>Some text to the left of the input element|<input type=\"text\" "
+ "value=\"This is some initial text\">Some text to the right of the input "
+ "element</div>",
+ "body", MoveCommands::ExecuteMoveRight,
+ "<div>Some text to the left of the input element<input type=\"text\" "
+ "value=\"This is some initial text\">|Some text to the right of the "
+ "input element</div>",
+ "body");
+}
+
+// This test verifies that a contentEditable element will be skipped when caret
+// browsing and not gain focus.
+TEST_F(MoveCommandsTest,
+ CaretBrowsingPositionAndFocusUpdate_MoveRightContentEditableElement) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div>Some text to the left of the contentEditable element|<span "
+ "contentEditable=\"true\">I am content editable</span>Some text to the "
+ "right of the contentEditable element</div>",
+ "body", MoveCommands::ExecuteMoveRight,
+ "<div>Some text to the left of the contentEditable element<span "
+ "contenteditable=\"true\">I am content editable</span>|Some text to the "
+ "right of the contentEditable element</div>",
+ "body");
+}
+
+// This test verifies that a textarea element will be skipped when caret
+// browsing and not gain focus.
+TEST_F(MoveCommandsTest,
+ CaretBrowsingPositionAndFocusUpdate_MoveRightTextAreaElement) {
+ VerifyCaretBrowsingPositionAndFocusUpdate(
+ "<div>Some text to the left of the textarea element|<textarea>I am in a "
+ "textarea</textarea>Some text to the "
+ "right of the textarea element</div>",
+ "body", MoveCommands::ExecuteMoveRight,
+ "<div>Some text to the left of the textarea element<textarea>I am in a "
+ "textarea</textarea>|Some text to the "
+ "right of the textarea element</div>",
+ "body");
+}
+
+// This test verifies that while caret browsing if you try to move the caret
+// when it is not in focus then it jumps to the active element before moving.
+TEST_F(MoveCommandsTest, CaretBrowsingSelectionUpdate) {
+ Selection().SetSelection(
+ SetSelectionTextToBody("<div>|a<a href=\"foo\">b</a></div>"),
+ SetSelectionOptions());
+ GetDocument().SetFocusedElement(
+ GetDocument().QuerySelector("a"),
+ FocusParams(SelectionBehaviorOnFocus::kNone, kWebFocusTypeNone, nullptr));
+ GetDocument().GetFrame()->GetSettings()->SetCaretBrowsingEnabled(true);
+ MoveCommands::ExecuteMoveRight(*GetDocument().GetFrame(), nullptr,
+ EditorCommandSource::kMenuOrKeyBinding,
+ String());
+ EXPECT_EQ("<div>a<a href=\"foo\">b|</a></div>", GetSelectionTextFromBody());
+}
+
+} // namespace blink
diff --git a/chromium/third_party/blink/renderer/core/editing/commands/replace_selection_command.cc b/chromium/third_party/blink/renderer/core/editing/commands/replace_selection_command.cc
index 16890313a8f..3e9be2f1704 100644
--- a/chromium/third_party/blink/renderer/core/editing/commands/replace_selection_command.cc
+++ b/chromium/third_party/blink/renderer/core/editing/commands/replace_selection_command.cc
@@ -52,7 +52,6 @@
#include "third_party/blink/renderer/core/editing/visible_units.h"
#include "third_party/blink/renderer/core/events/before_text_inserted_event.h"
#include "third_party/blink/renderer/core/frame/local_frame.h"
-#include "third_party/blink/renderer/core/frame/use_counter.h"
#include "third_party/blink/renderer/core/html/forms/html_input_element.h"
#include "third_party/blink/renderer/core/html/forms/html_select_element.h"
#include "third_party/blink/renderer/core/html/html_br_element.h"
@@ -67,6 +66,7 @@
#include "third_party/blink/renderer/platform/bindings/exception_state.h"
#include "third_party/blink/renderer/platform/heap/heap.h"
#include "third_party/blink/renderer/platform/instrumentation/tracing/trace_event.h"
+#include "third_party/blink/renderer/platform/instrumentation/use_counter.h"
#include "third_party/blink/renderer/platform/wtf/std_lib_extras.h"
#include "third_party/blink/renderer/platform/wtf/vector.h"
@@ -556,7 +556,7 @@ void ReplaceSelectionCommand::RemoveRedundantStylesAndKeepStyleSpanInline(
if (!node->IsStyledElement())
continue;
- Element* element = ToElement(node);
+ auto* element = To<Element>(node);
const CSSPropertyValueSet* inline_style = element->InlineStyle();
EditingStyle* new_inline_style =
diff --git a/chromium/third_party/blink/renderer/core/editing/commands/split_text_node_containing_element_command.cc b/chromium/third_party/blink/renderer/core/editing/commands/split_text_node_containing_element_command.cc
index 4fb767ba315..77a2d6368ac 100644
--- a/chromium/third_party/blink/renderer/core/editing/commands/split_text_node_containing_element_command.cc
+++ b/chromium/third_party/blink/renderer/core/editing/commands/split_text_node_containing_element_command.cc
@@ -55,10 +55,10 @@ void SplitTextNodeContainingElementCommand::DoApply(EditingState*) {
LayoutObject* parent_layout_object = parent->GetLayoutObject();
if (!parent_layout_object || !parent_layout_object->IsInline()) {
WrapContentsInDummySpan(parent);
- Node* first_child = parent->firstChild();
- if (!first_child || !first_child->IsElementNode())
+ auto* first_child_element = DynamicTo<Element>(parent->firstChild());
+ if (!first_child_element)
return;
- parent = ToElement(first_child);
+ parent = first_child_element;
}
SplitElement(parent, text_.Get());
diff --git a/chromium/third_party/blink/renderer/core/editing/commands/style_commands.cc b/chromium/third_party/blink/renderer/core/editing/commands/style_commands.cc
index 46a362991dd..00eef3d1f00 100644
--- a/chromium/third_party/blink/renderer/core/editing/commands/style_commands.cc
+++ b/chromium/third_party/blink/renderer/core/editing/commands/style_commands.cc
@@ -85,7 +85,7 @@ bool StyleCommands::ApplyCommandToFrame(LocalFrame& frame,
EditorCommandSource source,
InputEvent::InputType input_type,
CSSPropertyValueSet* style) {
- // TODO(editnig-dev): We don't call shouldApplyStyle when the source is DOM;
+ // TODO(editing-dev): We don't call shouldApplyStyle when the source is DOM;
// is there a good reason for that?
switch (source) {
case EditorCommandSource::kMenuOrKeyBinding:
@@ -315,7 +315,7 @@ bool StyleCommands::ExecuteToggleStyleInList(LocalFrame& frame,
const String new_style =
ComputeToggleStyleInList(*selection_style, property_id, value);
- // TODO(editnig-dev): We shouldn't be having to convert new style into text.
+ // TODO(editing-dev): We shouldn't be having to convert new style into text.
// We should have setPropertyCSSValue.
auto* const new_mutable_style =
MakeGarbageCollected<MutableCSSPropertyValueSet>(kHTMLQuirksMode);
@@ -444,7 +444,7 @@ WritingDirection StyleCommands::TextDirectionForSelection(
const CSSComputedStyleDeclaration& style =
*MakeGarbageCollected<CSSComputedStyleDeclaration>(&node);
const CSSValue* unicode_bidi =
- style.GetPropertyCSSValue(GetCSSPropertyUnicodeBidi());
+ style.GetPropertyCSSValue(CSSPropertyID::kUnicodeBidi);
auto* unicode_bidi_identifier_value =
DynamicTo<CSSIdentifierValue>(unicode_bidi);
if (!unicode_bidi_identifier_value)
@@ -478,11 +478,11 @@ WritingDirection StyleCommands::TextDirectionForSelection(
if (!runner.IsStyledElement())
continue;
- Element* element = &ToElement(runner);
+ auto* element = To<Element>(&runner);
const CSSComputedStyleDeclaration& style =
*MakeGarbageCollected<CSSComputedStyleDeclaration>(element);
const CSSValue* unicode_bidi =
- style.GetPropertyCSSValue(GetCSSPropertyUnicodeBidi());
+ style.GetPropertyCSSValue(CSSPropertyID::kUnicodeBidi);
auto* unicode_bidi_identifier_value =
DynamicTo<CSSIdentifierValue>(unicode_bidi);
if (!unicode_bidi_identifier_value)
@@ -499,7 +499,7 @@ WritingDirection StyleCommands::TextDirectionForSelection(
DCHECK(EditingStyleUtilities::IsEmbedOrIsolate(unicode_bidi_value))
<< static_cast<int>(unicode_bidi_value);
const CSSValue* direction =
- style.GetPropertyCSSValue(GetCSSPropertyDirection());
+ style.GetPropertyCSSValue(CSSPropertyID::kDirection);
auto* direction_identifier_value = DynamicTo<CSSIdentifierValue>(direction);
if (!direction_identifier_value)
continue;
@@ -534,7 +534,7 @@ EditingTriState StyleCommands::StateTextWritingDirection(
WritingDirection selection_direction = TextDirectionForSelection(
frame.Selection().ComputeVisibleSelectionInDOMTreeDeprecated(),
frame.GetEditor().TypingStyle(), has_nested_or_multiple_embeddings);
- // TODO(editnig-dev): We should be returning MixedTriState when
+ // TODO(editing-dev): We should be returning MixedTriState when
// selectionDirection == direction && hasNestedOrMultipleEmbeddings
return (selection_direction == direction &&
!has_nested_or_multiple_embeddings)
@@ -584,7 +584,7 @@ String StyleCommands::SelectionStartCSSPropertyValue(
String StyleCommands::ValueStyle(LocalFrame& frame, CSSPropertyID property_id) {
frame.GetDocument()->UpdateStyleAndLayout();
- // TODO(editnig-dev): Rather than retrieving the style at the start of the
+ // TODO(editing-dev): Rather than retrieving the style at the start of the
// current selection, we should retrieve the style present throughout the
// selection for non-Mac platforms.
return SelectionStartCSSPropertyValue(frame, property_id);
diff --git a/chromium/third_party/blink/renderer/core/editing/commands/style_commands.h b/chromium/third_party/blink/renderer/core/editing/commands/style_commands.h
index cece1e2a9c7..0400ca28394 100644
--- a/chromium/third_party/blink/renderer/core/editing/commands/style_commands.h
+++ b/chromium/third_party/blink/renderer/core/editing/commands/style_commands.h
@@ -33,7 +33,7 @@
#define THIRD_PARTY_BLINK_RENDERER_CORE_EDITING_COMMANDS_STYLE_COMMANDS_H_
#include "third_party/blink/renderer/core/events/input_event.h"
-#include "third_party/blink/renderer/platform/wtf/allocator.h"
+#include "third_party/blink/renderer/platform/wtf/allocator/allocator.h"
#include "third_party/blink/renderer/platform/wtf/forward.h"
namespace blink {