On Linux, should be able to get spelling suggestions without selecting the misspelled word

https://bugs.webkit.org/show_bug.cgi?id=103520

Reviewed by Ryosuke Niwa.

Source/WebCore:

Allow to get/insert spelling suggestions without selecting the misspelled word for
Linux WebKit ports. WebCore assumes that the misspelled word has to be selected
to get its suggestions.

In compliance with native application behaviour a new editing policy is introduced,
to do not highlight the misspelled word to just get its guesses.

No new tests, covered by context-menu-suggestions.html.

* WebCore.exp.in:
Remove _ZN7WebCore6Editor21isSelectionMisspelledEv symbol as Mac port doesn't
need it any longer.

* editing/EditingBehavior.h:
(EditingBehavior):
(WebCore::EditingBehavior::shouldAllowSpellingSuggestionsWithoutSelection):
Add a new behavior for Linux, to allow spelling suggestions without selecting
the misspelled word.

* editing/Editor.cpp:
(WebCore::Editor::isContinuousSpellCheckingEnabled):
Add missing const modifier, to use this method in 'misspelledWordAtCaretOrRange() const'.

(WebCore::Editor::misspelledWordAtCaretOrRange):
Allow to check spelling under the caret or selected word.
Does nothing for selection made on the multiple words.

(WebCore::Editor::misspelledSelectionString):
Return the misspelled selection.

(WebCore::Editor::guessesForMisspelledWord):
Remove 'Selection' from method name as it may return guesses without selection.

(WebCore::Editor::guessesForMisspelledOrUngrammatical):
Ditto.

* page/ContextMenuController.cpp:
(WebCore::ContextMenuController::contextMenuItemSelected):
Select the word under caret to meet the conditions from misspelledWordAtCaretOrRange.

(WebCore::ContextMenuController::populate):
Update guessesForMisspelledOrUngrammatical call.

LayoutTests:

* platform/efl/TestExpectations:
Unskip context-menu-suggestions.html for WebKit-EFL as it passes now.

* platform/gtk/TestExpectations:
Update failing reason.


git-svn-id: http://svn.webkit.org/repository/webkit/trunk@139412 268f45cc-cd09-0410-ab3c-d52691b4dbfc
parent ca9dfa44
2013-01-10 Grzegorz Czajkowski <g.czajkowski@samsung.com>
On Linux, should be able to get spelling suggestions without selecting the misspelled word
https://bugs.webkit.org/show_bug.cgi?id=103520
Reviewed by Ryosuke Niwa.
* platform/efl/TestExpectations:
Unskip context-menu-suggestions.html for WebKit-EFL as it passes now.
* platform/gtk/TestExpectations:
Update failing reason.
2013-01-10 John J. Barton <johnjbarton@chromium.org>
Web Inspector: Pass the script url to the script-preprocessor script
......@@ -1684,9 +1684,6 @@ webkit.org/b/101670 media/video-controls-captions-trackmenu-localized.html [ Ski
# Fails until we enable the Resource Timing API.
webkit.org/b/61138 http/tests/w3c/webperf/submission/resource-timing [ Skip ]
# No spellcheck suggestions in context menu
Bug(EFL) editing/spelling/context-menu-suggestions.html [ Failure ]
# No support for exposing in-band text tracks
Bug(EFL) media/track/track-in-band.html [ Skip ]
Bug(EFL) media/track/track-in-band-cues-added-once.html [ Skip ]
......
......@@ -968,7 +968,7 @@ webkit.org/b/73936 inspector/profiler/canvas2d/canvas-has-uninstrumented-canvase
webkit.org/b/37613 webkit.org/b/20011 printing [ Skip ]
webkit.org/b/37613 editing/execCommand/print.html [ Skip ]
# Need to dump context menu items on eventSender.contextClick(true).
# DRT doesn't dispatch an event for the second call eventSender.contextClick().
webkit.org/b/39102 editing/spelling/context-menu-suggestions.html [ Failure ]
# Some input type=range tests fail because of the size
......
2013-01-10 Grzegorz Czajkowski <g.czajkowski@samsung.com>
On Linux, should be able to get spelling suggestions without selecting the misspelled word
https://bugs.webkit.org/show_bug.cgi?id=103520
Reviewed by Ryosuke Niwa.
Allow to get/insert spelling suggestions without selecting the misspelled word for
Linux WebKit ports. WebCore assumes that the misspelled word has to be selected
to get its suggestions.
In compliance with native application behaviour a new editing policy is introduced,
to do not highlight the misspelled word to just get its guesses.
No new tests, covered by context-menu-suggestions.html.
* WebCore.exp.in:
Remove _ZN7WebCore6Editor21isSelectionMisspelledEv symbol as Mac port doesn't
need it any longer.
* editing/EditingBehavior.h:
(EditingBehavior):
(WebCore::EditingBehavior::shouldAllowSpellingSuggestionsWithoutSelection):
Add a new behavior for Linux, to allow spelling suggestions without selecting
the misspelled word.
* editing/Editor.cpp:
(WebCore::Editor::isContinuousSpellCheckingEnabled):
Add missing const modifier, to use this method in 'misspelledWordAtCaretOrRange() const'.
(WebCore::Editor::misspelledWordAtCaretOrRange):
Allow to check spelling under the caret or selected word.
Does nothing for selection made on the multiple words.
(WebCore::Editor::misspelledSelectionString):
Return the misspelled selection.
(WebCore::Editor::guessesForMisspelledWord):
Remove 'Selection' from method name as it may return guesses without selection.
(WebCore::Editor::guessesForMisspelledOrUngrammatical):
Ditto.
* page/ContextMenuController.cpp:
(WebCore::ContextMenuController::contextMenuItemSelected):
Select the word under caret to meet the conditions from misspelledWordAtCaretOrRange.
(WebCore::ContextMenuController::populate):
Update guessesForMisspelledOrUngrammatical call.
2013-01-10 Hajime Morrita <morrita@google.com>
https://bugs.webkit.org/show_bug.cgi?id=106283
......@@ -842,7 +842,6 @@ __ZN7WebCore6Editor19countMatchesForTextERKN3WTF6StringEPNS_5RangeEjjb
__ZN7WebCore6Editor19deleteWithDirectionENS_18SelectionDirectionENS_15TextGranularityEbb
__ZN7WebCore6Editor19insertUnorderedListEv
__ZN7WebCore6Editor21applyStyleToSelectionEPNS_16StylePropertySetENS_10EditActionE
__ZN7WebCore6Editor21isSelectionMisspelledEv
__ZN7WebCore6Editor23setBaseWritingDirectionE16WritingDirection
__ZN7WebCore6Editor24computeAndSetTypingStyleEPNS_16StylePropertySetENS_10EditActionE
__ZN7WebCore6Editor24isSelectionUngrammaticalEv
......
......@@ -59,6 +59,17 @@ public:
// On Mac, when processing a contextual click, the object being clicked upon should be selected.
bool shouldSelectOnContextualMenuClick() const { return m_type == EditingMacBehavior; }
// On Linux, should be able to get and insert spelling suggestions without selecting the misspelled word.
// Skip this policy for Chromium, they require selection for the misspelled word.
bool shouldAllowSpellingSuggestionsWithoutSelection() const
{
#if !PLATFORM(CHROMIUM)
return m_type == EditingUnixBehavior;
#else
return false;
#endif
}
// On Mac and Windows, pressing backspace (when it isn't handled otherwise) should navigate back.
bool shouldNavigateBackOnBackspace() const { return m_type != EditingUnixBehavior; }
......
......@@ -1090,7 +1090,7 @@ void Editor::copyImage(const HitTestResult& result)
Pasteboard::generalPasteboard()->writeImage(result.innerNonSharedNode(), url, result.altDisplayString());
}
bool Editor::isContinuousSpellCheckingEnabled()
bool Editor::isContinuousSpellCheckingEnabled() const
{
return client() && client()->isContinuousSpellCheckingEnabled();
}
......@@ -1681,23 +1681,50 @@ void Editor::advanceToNextMisspelling(bool startBeforeSelection)
}
}
bool Editor::isSelectionMisspelled()
String Editor::misspelledWordAtCaretOrRange(Node* clickedNode) const
{
if (!isContinuousSpellCheckingEnabled() || !clickedNode || !isSpellCheckingEnabledFor(clickedNode))
return String();
VisibleSelection selection = m_frame->selection()->selection();
if (!selection.isContentEditable() || selection.isNone())
return String();
VisibleSelection wordSelection(selection.base());
wordSelection.expandUsingGranularity(WordGranularity);
RefPtr<Range> wordRange = wordSelection.toNormalizedRange();
// In compliance with GTK+ applications, additionally allow to provide suggestions when the current
// selection exactly match the word selection.
if (selection.isRange() && !areRangesEqual(wordRange.get(), selection.toNormalizedRange().get()))
return String();
String word = wordRange->text();
if (word.isEmpty() || !client())
return String();
int wordLength = word.length();
int misspellingLocation = -1;
int misspellingLength = 0;
textChecker()->checkSpellingOfString(word.characters(), wordLength, &misspellingLocation, &misspellingLength);
return misspellingLength == wordLength ? word : String();
}
String Editor::misspelledSelectionString() const
{
String selectedString = selectedText();
int length = selectedString.length();
if (!length)
return false;
if (!length || !client())
return String();
if (!client())
return false;
int misspellingLocation = -1;
int misspellingLength = 0;
textChecker()->checkSpellingOfString(selectedString.characters(), length, &misspellingLocation, &misspellingLength);
// The selection only counts as misspelled if the selected text is exactly one misspelled word
if (misspellingLength != length)
return false;
return String();
// Update the spelling panel to be displaying this error (whether or not the spelling panel is on screen).
// This is necessary to make a subsequent call to [NSSpellChecker ignoreWord:inSpellDocumentWithTag:] work
......@@ -1705,7 +1732,7 @@ bool Editor::isSelectionMisspelled()
// or a grammar error.
client()->updateSpellingUIWithMisspelledWord(selectedString);
return true;
return selectedString;
}
bool Editor::isSelectionUngrammatical()
......@@ -1736,18 +1763,17 @@ Vector<String> Editor::guessesForUngrammaticalSelection()
#endif
}
Vector<String> Editor::guessesForMisspelledSelection()
Vector<String> Editor::guessesForMisspelledWord(const String& word) const
{
String selectedString = selectedText();
ASSERT(selectedString.length());
ASSERT(word.length());
Vector<String> guesses;
if (client())
textChecker()->getGuessesForWord(selectedString, String(), guesses);
textChecker()->getGuessesForWord(word, String(), guesses);
return guesses;
}
Vector<String> Editor::guessesForMisspelledOrUngrammaticalSelection(bool& misspelled, bool& ungrammatical)
Vector<String> Editor::guessesForMisspelledOrUngrammatical(bool& misspelled, bool& ungrammatical)
{
if (unifiedTextCheckerEnabled()) {
RefPtr<Range> range = frame()->selection()->toNormalizedRange();
......@@ -1756,10 +1782,12 @@ Vector<String> Editor::guessesForMisspelledOrUngrammaticalSelection(bool& misspe
return TextCheckingHelper(client(), range).guessesForMisspelledOrUngrammaticalRange(isGrammarCheckingEnabled(), misspelled, ungrammatical);
}
misspelled = isSelectionMisspelled();
String misspelledWord = behavior().shouldAllowSpellingSuggestionsWithoutSelection() ? misspelledWordAtCaretOrRange(m_frame->document()->focusedNode()) : misspelledSelectionString();
misspelled = !misspelledWord.isEmpty();
if (misspelled) {
ungrammatical = false;
return guessesForMisspelledSelection();
return guessesForMisspelledWord(misspelledWord);
}
if (isGrammarCheckingEnabled() && isSelectionUngrammatical()) {
ungrammatical = true;
......
......@@ -213,7 +213,7 @@ public:
bool insertParagraphSeparatorInQuotedContent();
#endif
bool isContinuousSpellCheckingEnabled();
bool isContinuousSpellCheckingEnabled() const;
void toggleContinuousSpellChecking();
bool isGrammarCheckingEnabled();
void toggleGrammarChecking();
......@@ -221,10 +221,11 @@ public:
void learnSpelling();
int spellCheckerDocumentTag();
bool isSelectionUngrammatical();
bool isSelectionMisspelled();
Vector<String> guessesForMisspelledSelection();
String misspelledSelectionString() const;
String misspelledWordAtCaretOrRange(Node* clickedNode) const;
Vector<String> guessesForMisspelledWord(const String&) const;
Vector<String> guessesForUngrammaticalSelection();
Vector<String> guessesForMisspelledOrUngrammaticalSelection(bool& misspelled, bool& ungrammatical);
Vector<String> guessesForMisspelledOrUngrammatical(bool& misspelled, bool& ungrammatical);
bool isSpellCheckingEnabledInFocusedNode() const;
bool isSpellCheckingEnabledFor(Node*) const;
void markMisspellingsAfterTypingToWord(const VisiblePosition &wordStart, const VisibleSelection& selectionAfterTyping, bool doReplacement);
......
......@@ -340,15 +340,28 @@ void ContextMenuController::contextMenuItemSelected(ContextMenuItem* item)
frame->editor()->command("SelectAll").execute();
break;
#endif
case ContextMenuItemTagSpellingGuess:
ASSERT(frame->editor()->selectedText().length());
if (frame->editor()->shouldInsertText(item->title(), frame->selection()->toNormalizedRange().get(), EditorInsertActionPasted)) {
case ContextMenuItemTagSpellingGuess: {
FrameSelection* frameSelection = frame->selection();
if (frame->editor()->shouldInsertText(item->title(), frameSelection->toNormalizedRange().get(), EditorInsertActionPasted)) {
Document* document = frame->document();
RefPtr<ReplaceSelectionCommand> command = ReplaceSelectionCommand::create(document, createFragmentFromMarkup(document, item->title(), ""), ReplaceSelectionCommand::SelectReplacement | ReplaceSelectionCommand::MatchStyle | ReplaceSelectionCommand::PreventNesting);
ReplaceSelectionCommand::CommandOptions replaceOptions = ReplaceSelectionCommand::MatchStyle | ReplaceSelectionCommand::PreventNesting;
if (frame->editor()->behavior().shouldAllowSpellingSuggestionsWithoutSelection()) {
ASSERT(frameSelection->isCaretOrRange());
VisibleSelection wordSelection(frameSelection->base());
wordSelection.expandUsingGranularity(WordGranularity);
frameSelection->setSelection(wordSelection);
} else {
ASSERT(frame->editor()->selectedText().length());
replaceOptions |= ReplaceSelectionCommand::SelectReplacement;
}
RefPtr<ReplaceSelectionCommand> command = ReplaceSelectionCommand::create(document, createFragmentFromMarkup(document, item->title(), ""), replaceOptions);
applyCommand(command);
frame->selection()->revealSelection(ScrollAlignment::alignToEdgeIfNeeded);
frameSelection->revealSelection(ScrollAlignment::alignToEdgeIfNeeded);
}
break;
}
case ContextMenuItemTagIgnoreSpelling:
frame->editor()->ignoreSpelling();
break;
......@@ -914,7 +927,7 @@ void ContextMenuController::populate()
// is never considered a misspelling and bad grammar at the same time)
bool misspelling;
bool badGrammar;
Vector<String> guesses = frame->editor()->guessesForMisspelledOrUngrammaticalSelection(misspelling, badGrammar);
Vector<String> guesses = frame->editor()->guessesForMisspelledOrUngrammatical(misspelling, badGrammar);
if (misspelling || badGrammar) {
size_t size = guesses.size();
if (!size) {
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment