diff options
Diffstat (limited to 'chromium/content')
13 files changed, 98 insertions, 55 deletions
diff --git a/chromium/content/browser/renderer_host/render_frame_host_impl.cc b/chromium/content/browser/renderer_host/render_frame_host_impl.cc index c48863fc9c2..ed441caa5f3 100644 --- a/chromium/content/browser/renderer_host/render_frame_host_impl.cc +++ b/chromium/content/browser/renderer_host/render_frame_host_impl.cc @@ -5359,9 +5359,10 @@ void RenderFrameHostImpl::FocusedElementChanged( void RenderFrameHostImpl::TextSelectionChanged(const std::u16string& text, uint32_t offset, - const gfx::Range& range) { + const gfx::Range& range, + bool user_initiated) { has_selection_ = !text.empty(); - GetRenderWidgetHost()->SelectionChanged(text, offset, range); + GetRenderWidgetHost()->SelectionChanged(text, offset, range, user_initiated); } void RenderFrameHostImpl::DidReceiveUserActivation() { diff --git a/chromium/content/browser/renderer_host/render_frame_host_impl.h b/chromium/content/browser/renderer_host/render_frame_host_impl.h index 3456986091a..760ccc5c757 100644 --- a/chromium/content/browser/renderer_host/render_frame_host_impl.h +++ b/chromium/content/browser/renderer_host/render_frame_host_impl.h @@ -1861,7 +1861,8 @@ class CONTENT_EXPORT RenderFrameHostImpl blink::mojom::FocusType focus_type) override; void TextSelectionChanged(const std::u16string& text, uint32_t offset, - const gfx::Range& range) override; + const gfx::Range& range, + bool user_initiated) override; void ShowPopupMenu( mojo::PendingRemote<blink::mojom::PopupMenuClient> popup_client, const gfx::Rect& bounds, diff --git a/chromium/content/browser/renderer_host/render_widget_host_impl.cc b/chromium/content/browser/renderer_host/render_widget_host_impl.cc index 6a784277073..7b576ab127d 100644 --- a/chromium/content/browser/renderer_host/render_widget_host_impl.cc +++ b/chromium/content/browser/renderer_host/render_widget_host_impl.cc @@ -2139,9 +2139,12 @@ void RenderWidgetHostImpl::GetSnapshotFromBrowser( void RenderWidgetHostImpl::SelectionChanged(const std::u16string& text, uint32_t offset, - const gfx::Range& range) { - if (view_) - view_->SelectionChanged(text, static_cast<size_t>(offset), range); + const gfx::Range& range, + bool user_initiated) { + if (view_) { + view_->SelectionChanged(text, static_cast<size_t>(offset), range, + user_initiated); + } } void RenderWidgetHostImpl::SelectionBoundsChanged( diff --git a/chromium/content/browser/renderer_host/render_widget_host_impl.h b/chromium/content/browser/renderer_host/render_widget_host_impl.h index bc4800b72f8..2c1a07c6daa 100644 --- a/chromium/content/browser/renderer_host/render_widget_host_impl.h +++ b/chromium/content/browser/renderer_host/render_widget_host_impl.h @@ -696,7 +696,8 @@ class CONTENT_EXPORT RenderWidgetHostImpl // Called from a RenderFrameHost when the text selection has changed. void SelectionChanged(const std::u16string& text, uint32_t offset, - const gfx::Range& range); + const gfx::Range& range, + bool user_initiated); size_t in_flight_event_count() const { return in_flight_event_count_; } diff --git a/chromium/content/browser/renderer_host/render_widget_host_view_aura.cc b/chromium/content/browser/renderer_host/render_widget_host_view_aura.cc index b8ae3c5d06c..1cfec9cf5f1 100644 --- a/chromium/content/browser/renderer_host/render_widget_host_view_aura.cc +++ b/chromium/content/browser/renderer_host/render_widget_host_view_aura.cc @@ -2576,7 +2576,9 @@ void RenderWidgetHostViewAura::OnTextSelectionChanged( ui::ClipboardBuffer::kSelection)) { const TextInputManager::TextSelection* selection = GetTextInputManager()->GetTextSelection(focused_view); - if (selection->selected_text().length()) { + if (selection->selected_text().length() + && selection->user_initiated() + ) { // Set the ClipboardBuffer::kSelection to the ui::Clipboard. ui::ScopedClipboardWriter clipboard_writer( ui::ClipboardBuffer::kSelection); diff --git a/chromium/content/browser/renderer_host/render_widget_host_view_base.cc b/chromium/content/browser/renderer_host/render_widget_host_view_base.cc index ec0d6b0acbc..b67a546bd65 100644 --- a/chromium/content/browser/renderer_host/render_widget_host_view_base.cc +++ b/chromium/content/browser/renderer_host/render_widget_host_view_base.cc @@ -176,9 +176,11 @@ RenderWidgetHostViewBase* RenderWidgetHostViewBase::GetRootView() { void RenderWidgetHostViewBase::SelectionChanged(const std::u16string& text, size_t offset, - const gfx::Range& range) { + const gfx::Range& range, + bool user_initiated) { if (GetTextInputManager()) - GetTextInputManager()->SelectionChanged(this, text, offset, range); + GetTextInputManager()->SelectionChanged(this, text, offset, range, + user_initiated); } gfx::Size RenderWidgetHostViewBase::GetRequestedRendererSize() { diff --git a/chromium/content/browser/renderer_host/render_widget_host_view_base.h b/chromium/content/browser/renderer_host/render_widget_host_view_base.h index 8cc591cfc75..f1739d6f84c 100644 --- a/chromium/content/browser/renderer_host/render_widget_host_view_base.h +++ b/chromium/content/browser/renderer_host/render_widget_host_view_base.h @@ -211,7 +211,8 @@ class CONTENT_EXPORT RenderWidgetHostViewBase : public RenderWidgetHostView { // Notifies the View that the renderer text selection has changed. virtual void SelectionChanged(const std::u16string& text, size_t offset, - const gfx::Range& range); + const gfx::Range& range, + bool user_initiated); // The requested size of the renderer. May differ from GetViewBounds().size() // when the view requires additional throttling. diff --git a/chromium/content/browser/renderer_host/text_input_manager.cc b/chromium/content/browser/renderer_host/text_input_manager.cc index 707d5d7348f..b8eab6b746f 100644 --- a/chromium/content/browser/renderer_host/text_input_manager.cc +++ b/chromium/content/browser/renderer_host/text_input_manager.cc @@ -340,9 +340,10 @@ void TextInputManager::ImeCompositionRangeChanged( void TextInputManager::SelectionChanged(RenderWidgetHostViewBase* view, const std::u16string& text, size_t offset, - const gfx::Range& range) { + const gfx::Range& range, + bool user_initiated) { DCHECK(IsRegistered(view)); - text_selection_map_[view].SetSelection(text, offset, range); + text_selection_map_[view].SetSelection(text, offset, range, user_initiated); for (auto& observer : observer_list_) observer.OnTextSelectionChanged(this, view); } @@ -431,11 +432,13 @@ TextInputManager::TextSelection::~TextSelection() {} void TextInputManager::TextSelection::SetSelection(const std::u16string& text, size_t offset, - const gfx::Range& range) { + const gfx::Range& range, + bool user_initiated) { text_ = text; range_.set_start(range.start()); range_.set_end(range.end()); offset_ = offset; + user_initiated_ = user_initiated; // Update the selected text. selected_text_.clear(); diff --git a/chromium/content/browser/renderer_host/text_input_manager.h b/chromium/content/browser/renderer_host/text_input_manager.h index f1cc5560c1a..d7d887e8aef 100644 --- a/chromium/content/browser/renderer_host/text_input_manager.h +++ b/chromium/content/browser/renderer_host/text_input_manager.h @@ -108,12 +108,14 @@ class CONTENT_EXPORT TextInputManager { void SetSelection(const std::u16string& text, size_t offset, - const gfx::Range& range); + const gfx::Range& range, + bool user_initiated); const std::u16string& selected_text() const { return selected_text_; } size_t offset() const { return offset_; } const gfx::Range& range() const { return range_; } const std::u16string& text() const { return text_; } + bool user_initiated() const { return user_initiated_; } private: // The offset of the text stored in |text| relative to the start of the web @@ -132,6 +134,9 @@ class CONTENT_EXPORT TextInputManager { // Part of the text on the page which includes the highlighted text plus // possibly several characters before and after it. std::u16string text_; + + // True if text selection is triggered by user input. + bool user_initiated_ = false; }; explicit TextInputManager(bool should_do_learning); @@ -215,7 +220,8 @@ class CONTENT_EXPORT TextInputManager { void SelectionChanged(RenderWidgetHostViewBase* view, const std::u16string& text, size_t offset, - const gfx::Range& range); + const gfx::Range& range, + bool user_initiated); // Registers the given |view| for tracking its TextInputState. This is called // by any view which has updates in its TextInputState (whether tab's RWHV or diff --git a/chromium/content/public/renderer/render_frame.h b/chromium/content/public/renderer/render_frame.h index 577f42d52e0..4a5fcfca191 100644 --- a/chromium/content/public/renderer/render_frame.h +++ b/chromium/content/public/renderer/render_frame.h @@ -215,7 +215,8 @@ class CONTENT_EXPORT RenderFrame : public IPC::Listener, // Notifies the browser of text selection changes made. virtual void SetSelectedText(const std::u16string& selection_text, size_t offset, - const gfx::Range& range) = 0; + const gfx::Range& range, + bool user_initiated) = 0; // Adds |message| to the DevTools console. virtual void AddMessageToConsole(blink::mojom::ConsoleMessageLevel level, diff --git a/chromium/content/renderer/pepper/pepper_plugin_instance_impl.cc b/chromium/content/renderer/pepper/pepper_plugin_instance_impl.cc index b43d23fce76..7b47dafa6d5 100644 --- a/chromium/content/renderer/pepper/pepper_plugin_instance_impl.cc +++ b/chromium/content/renderer/pepper/pepper_plugin_instance_impl.cc @@ -1294,7 +1294,7 @@ void PepperPluginInstanceImpl::SetSelectedText( selected_text_ = selected_text; gfx::Range range(0, selected_text.length()); - render_frame_->SetSelectedText(selected_text, 0, range); + render_frame_->SetSelectedText(selected_text, 0, range, true); } void PepperPluginInstanceImpl::SetLinkUnderCursor(const std::string& url) { diff --git a/chromium/content/renderer/render_frame_impl.cc b/chromium/content/renderer/render_frame_impl.cc index 09cf0bc111e..12d0e63945e 100644 --- a/chromium/content/renderer/render_frame_impl.cc +++ b/chromium/content/renderer/render_frame_impl.cc @@ -1970,7 +1970,7 @@ void RenderFrameImpl::PepperSelectionChanged( // We have no reason to believe the locally cached last synced selection is // invalid so we do not need to force the update if it matches our last synced // value. - SyncSelectionIfRequired(blink::SyncCondition::kNotForced); + SyncSelectionIfRequired(blink::SyncCondition::kNotForced, true /* user_initiated */); } #endif // BUILDFLAG(ENABLE_PLUGINS) @@ -2357,9 +2357,11 @@ bool RenderFrameImpl::IsFTPDirectoryListing() { void RenderFrameImpl::SetSelectedText(const std::u16string& selection_text, size_t offset, - const gfx::Range& range) { + const gfx::Range& range, + bool user_initiated) { GetWebFrame()->TextSelectionChanged(WebString::FromUTF16(selection_text), - static_cast<uint32_t>(offset), range); + static_cast<uint32_t>(offset), range, + user_initiated); } void RenderFrameImpl::AddMessageToConsole( @@ -3967,20 +3969,32 @@ void RenderFrameImpl::AbortClientNavigation() { void RenderFrameImpl::DidChangeSelection(bool is_empty_selection, blink::SyncCondition force_sync) { - if (!GetLocalRootWebFrameWidget()->HandlingInputEvent() && - !GetLocalRootWebFrameWidget()->HandlingSelectRange()) - return; + bool user_initiated = + GetLocalRootWebFrameWidget()->HandlingInputEvent() || + GetLocalRootWebFrameWidget()->HandlingSelectRange(); if (is_empty_selection) selection_text_.clear(); + if (!user_initiated) { + // Do not update text input state unnecessarily when text selection remains + // empty. + if (selection_text_.empty()) + return; + + + // Ignore selection change of text replacement triggered by IME composition. + if (GetLocalRootWebFrameWidget()->ImeCompositionReplacement()) + return; + } + // UpdateTextInputState should be called before SyncSelectionIfRequired. // UpdateTextInputState may send TextInputStateChanged to notify the focus // was changed, and SyncSelectionIfRequired may send SelectionChanged // to notify the selection was changed. Focus change should be notified // before selection change. GetLocalRootWebFrameWidget()->UpdateTextInputState(); - SyncSelectionIfRequired(force_sync); + SyncSelectionIfRequired(force_sync, user_initiated); } void RenderFrameImpl::OnMainFrameIntersectionChanged( @@ -5297,10 +5311,11 @@ void RenderFrameImpl::UpdateEncoding(WebFrame* frame, GetFrameHost()->UpdateEncoding(encoding_name); } -void RenderFrameImpl::SyncSelectionIfRequired(blink::SyncCondition force_sync) { +void RenderFrameImpl::SyncSelectionIfRequired(blink::SyncCondition force_sync, + bool user_initiated) { std::u16string text; - size_t offset; - gfx::Range range; + size_t offset = 0; + gfx::Range range = gfx::Range::InvalidRange(); #if BUILDFLAG(ENABLE_PLUGINS) if (focused_pepper_plugin_) { focused_pepper_plugin_->GetSurroundingText(&text, &range); @@ -5311,31 +5326,37 @@ void RenderFrameImpl::SyncSelectionIfRequired(blink::SyncCondition force_sync) { { WebRange selection = frame_->GetInputMethodController()->GetSelectionOffsets(); - if (selection.IsNull()) - return; - - range = gfx::Range(selection.StartOffset(), selection.EndOffset()); - if (frame_->GetInputMethodController()->TextInputType() != - blink::kWebTextInputTypeNone) { - // If current focused element is editable, we will send 100 more chars - // before and after selection. It is for input method surrounding text - // feature. - if (selection.StartOffset() > kExtraCharsBeforeAndAfterSelection) - offset = selection.StartOffset() - kExtraCharsBeforeAndAfterSelection; - else - offset = 0; - size_t length = - selection.EndOffset() - offset + kExtraCharsBeforeAndAfterSelection; - text = frame_->RangeAsText(WebRange(offset, length)).Utf16(); - } else { - offset = selection.StartOffset(); - text = frame_->SelectionAsText().Utf16(); - // http://crbug.com/101435 - // In some case, frame->selectionAsText() returned text's length is not - // equal to the length returned from frame_->GetSelectionOffsets(). So we - // have to set the range according to text.length(). - range.set_end(range.start() + text.length()); + // When clearing text selection from JavaScript the selection range + // might be null but the selected text still have to be updated. + // Do not cancel sync selection if the clear was not user initiated. + if (!selection.IsNull()) { + range = gfx::Range(selection.StartOffset(), selection.EndOffset()); + + if (frame_->GetInputMethodController()->TextInputType() != + blink::kWebTextInputTypeNone) { + // If current focused element is editable, we will send 100 more chars + // before and after selection. It is for input method surrounding text + // feature. + if (selection.StartOffset() > kExtraCharsBeforeAndAfterSelection) + offset = selection.StartOffset() - kExtraCharsBeforeAndAfterSelection; + else + offset = 0; + size_t length = + selection.EndOffset() - offset + kExtraCharsBeforeAndAfterSelection; + text = frame_->RangeAsText(WebRange(offset, length)).Utf16(); + } else { + offset = selection.StartOffset(); + text = frame_->SelectionAsText().Utf16(); + // http://crbug.com/101435 + // In some case, frame->selectionAsText() returned text's length is not + // equal to the length returned from + // GetWebWidget()->caretOrSelectionRange(). + // So we have to set the range according to text.length(). + range.set_end(range.start() + text.length()); + } + } else if (user_initiated) { + return; } } @@ -5351,7 +5372,7 @@ void RenderFrameImpl::SyncSelectionIfRequired(blink::SyncCondition force_sync) { selection_text_ = text; selection_text_offset_ = offset; selection_range_ = range; - SetSelectedText(text, offset, range); + SetSelectedText(text, offset, range, user_initiated); } GetLocalRootWebFrameWidget()->UpdateSelectionBounds(); } diff --git a/chromium/content/renderer/render_frame_impl.h b/chromium/content/renderer/render_frame_impl.h index f659ea4833f..c5328328e6b 100644 --- a/chromium/content/renderer/render_frame_impl.h +++ b/chromium/content/renderer/render_frame_impl.h @@ -359,7 +359,8 @@ class CONTENT_EXPORT RenderFrameImpl bool IsFTPDirectoryListing() override; void SetSelectedText(const std::u16string& selection_text, size_t offset, - const gfx::Range& range) override; + const gfx::Range& range, + bool user_initiated) override; void AddMessageToConsole(blink::mojom::ConsoleMessageLevel level, const std::string& message) override; blink::PreviewsState GetPreviewsState() override; @@ -610,7 +611,7 @@ class CONTENT_EXPORT RenderFrameImpl // it has changed or if the forced flag is passed. The forced flag is used // when the browser selection may be out of sync with the renderer due to // incorrect prediction. - void SyncSelectionIfRequired(blink::SyncCondition force_sync) override; + void SyncSelectionIfRequired(blink::SyncCondition force_sync, bool user_initiated) override; void CreateAudioInputStream( blink::CrossVariantMojoRemote< blink::mojom::RendererAudioInputStreamFactoryClientInterfaceBase> |