Commit a59243b8 authored by weinig@apple.com's avatar weinig@apple.com

AlternativeTextController should hold onto Frame as a reference

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

Reviewed by Andreas Kling.

While in the area I also:
  - Reference-ified Editor::killRing().
  - Const-ified Editor::m_killRing, Editor::m_spellChecker, and Editor::m_alternativeTextController.

* editing/AlternativeTextController.cpp:
(WebCore::AlternativeTextController::AlternativeTextController):
(WebCore::AlternativeTextController::stopPendingCorrection):
(WebCore::AlternativeTextController::isSpellingMarkerAllowed):
(WebCore::AlternativeTextController::applyAlternativeTextToRange):
(WebCore::AlternativeTextController::applyAutocorrectionBeforeTypingIfAppropriate):
(WebCore::AlternativeTextController::respondToUnappliedSpellCorrection):
(WebCore::AlternativeTextController::timerFired):
(WebCore::AlternativeTextController::handleAlternativeTextUIResult):
(WebCore::AlternativeTextController::rootViewRectForRange):
(WebCore::AlternativeTextController::respondToChangedSelection):
(WebCore::AlternativeTextController::respondToAppliedEditing):
(WebCore::AlternativeTextController::respondToUnappliedEditing):
(WebCore::AlternativeTextController::alternativeTextClient):
(WebCore::AlternativeTextController::editorClient):
(WebCore::AlternativeTextController::markPrecedingWhitespaceForDeletedAutocorrectionAfterCommand):
(WebCore::AlternativeTextController::processMarkersOnTextToBeReplacedByResult):
(WebCore::AlternativeTextController::respondToMarkerAtEndOfWord):
(WebCore::AlternativeTextController::insertDictatedText):
(WebCore::AlternativeTextController::applyDictationAlternative):
* editing/AlternativeTextController.h:
(WebCore::AlternativeTextController::UNLESS_ENABLED):
* editing/Editor.cpp:
(WebCore::Editor::Editor):
(WebCore::Editor::addToKillRing):
* editing/Editor.h:
(WebCore::Editor::killRing):
* editing/EditorCommand.cpp:
(WebCore::executeYank):
(WebCore::executeYankAndSelect):


git-svn-id: http://svn.webkit.org/repository/webkit/trunk@154648 268f45cc-cd09-0410-ab3c-d52691b4dbfc
parent a872654a
2013-08-26 Sam Weinig <sam@webkit.org>
AlternativeTextController should hold onto Frame as a reference
https://bugs.webkit.org/show_bug.cgi?id=120327
Reviewed by Andreas Kling.
While in the area I also:
- Reference-ified Editor::killRing().
- Const-ified Editor::m_killRing, Editor::m_spellChecker, and Editor::m_alternativeTextController.
* editing/AlternativeTextController.cpp:
(WebCore::AlternativeTextController::AlternativeTextController):
(WebCore::AlternativeTextController::stopPendingCorrection):
(WebCore::AlternativeTextController::isSpellingMarkerAllowed):
(WebCore::AlternativeTextController::applyAlternativeTextToRange):
(WebCore::AlternativeTextController::applyAutocorrectionBeforeTypingIfAppropriate):
(WebCore::AlternativeTextController::respondToUnappliedSpellCorrection):
(WebCore::AlternativeTextController::timerFired):
(WebCore::AlternativeTextController::handleAlternativeTextUIResult):
(WebCore::AlternativeTextController::rootViewRectForRange):
(WebCore::AlternativeTextController::respondToChangedSelection):
(WebCore::AlternativeTextController::respondToAppliedEditing):
(WebCore::AlternativeTextController::respondToUnappliedEditing):
(WebCore::AlternativeTextController::alternativeTextClient):
(WebCore::AlternativeTextController::editorClient):
(WebCore::AlternativeTextController::markPrecedingWhitespaceForDeletedAutocorrectionAfterCommand):
(WebCore::AlternativeTextController::processMarkersOnTextToBeReplacedByResult):
(WebCore::AlternativeTextController::respondToMarkerAtEndOfWord):
(WebCore::AlternativeTextController::insertDictatedText):
(WebCore::AlternativeTextController::applyDictationAlternative):
* editing/AlternativeTextController.h:
(WebCore::AlternativeTextController::UNLESS_ENABLED):
* editing/Editor.cpp:
(WebCore::Editor::Editor):
(WebCore::Editor::addToKillRing):
* editing/Editor.h:
(WebCore::Editor::killRing):
* editing/EditorCommand.cpp:
(WebCore::executeYank):
(WebCore::executeYankAndSelect):
2013-08-23 Andy Estes <aestes@apple.com>
Fix issues found by the Clang Static Analyzer
......@@ -132,7 +132,7 @@ static bool markersHaveIdenticalDescription(const Vector<DocumentMarker*>& marke
return true;
}
AlternativeTextController::AlternativeTextController(Frame* frame)
AlternativeTextController::AlternativeTextController(Frame& frame)
: m_timer(this, &AlternativeTextController::timerFired)
, m_frame(frame)
{
......@@ -165,7 +165,7 @@ void AlternativeTextController::stopAlternativeTextUITimer()
void AlternativeTextController::stopPendingCorrection(const VisibleSelection& oldSelection)
{
// Make sure there's no pending autocorrection before we call markMisspellingsAndBadGrammar() below.
VisibleSelection currentSelection(m_frame->selection().selection());
VisibleSelection currentSelection(m_frame.selection().selection());
if (currentSelection == oldSelection)
return;
......@@ -197,7 +197,7 @@ bool AlternativeTextController::hasPendingCorrection() const
bool AlternativeTextController::isSpellingMarkerAllowed(PassRefPtr<Range> misspellingRange) const
{
return !m_frame->document()->markers().hasMarkers(misspellingRange.get(), DocumentMarker::SpellCheckingExemption);
return !m_frame.document()->markers().hasMarkers(misspellingRange.get(), DocumentMarker::SpellCheckingExemption);
}
void AlternativeTextController::show(PassRefPtr<Range> rangeToReplace, const String& replacement)
......@@ -276,12 +276,12 @@ void AlternativeTextController::applyAlternativeTextToRange(const Range* range,
// Clone the range, since the caller of this method may want to keep the original range around.
RefPtr<Range> rangeWithAlternative = range->cloneRange(ec);
int paragraphStartIndex = TextIterator::rangeLength(Range::create(m_frame->document(), m_frame->document(), 0, paragraphRangeContainingCorrection.get()->startContainer(), paragraphRangeContainingCorrection.get()->startOffset()).get());
int paragraphStartIndex = TextIterator::rangeLength(Range::create(m_frame.document(), m_frame.document(), 0, paragraphRangeContainingCorrection.get()->startContainer(), paragraphRangeContainingCorrection.get()->startOffset()).get());
applyCommand(SpellingCorrectionCommand::create(rangeWithAlternative, alternative));
// Recalculate pragraphRangeContainingCorrection, since SpellingCorrectionCommand modified the DOM, such that the original paragraphRangeContainingCorrection is no longer valid. Radar: 10305315 Bugzilla: 89526
paragraphRangeContainingCorrection = TextIterator::rangeFromLocationAndLength(m_frame->document(), paragraphStartIndex, correctionStartOffsetInParagraph + alternative.length());
paragraphRangeContainingCorrection = TextIterator::rangeFromLocationAndLength(m_frame.document(), paragraphStartIndex, correctionStartOffsetInParagraph + alternative.length());
setEnd(paragraphRangeContainingCorrection.get(), m_frame->selection().selection().start());
setEnd(paragraphRangeContainingCorrection.get(), m_frame.selection().selection().start());
RefPtr<Range> replacementRange = TextIterator::subrange(paragraphRangeContainingCorrection.get(), correctionStartOffsetInParagraph, alternative.length());
String newText = plainText(replacementRange.get());
......@@ -303,7 +303,7 @@ bool AlternativeTextController::applyAutocorrectionBeforeTypingIfAppropriate()
if (m_alternativeTextInfo.type != AlternativeTextTypeCorrection)
return false;
Position caretPosition = m_frame->selection().selection().start();
Position caretPosition = m_frame.selection().selection().start();
if (m_alternativeTextInfo.rangeWithAlternative->endPosition() == caretPosition) {
handleAlternativeTextUIResult(dismissSoon(ReasonForDismissingAlternativeTextAccepted));
......@@ -320,11 +320,11 @@ void AlternativeTextController::respondToUnappliedSpellCorrection(const VisibleS
{
if (AlternativeTextClient* client = alternativeTextClient())
client->recordAutocorrectionResponse(AutocorrectionReverted, corrected, correction);
m_frame->document()->updateLayout();
m_frame->selection().setSelection(selectionOfCorrected, FrameSelection::CloseTyping | FrameSelection::ClearTypingStyle | FrameSelection::SpellCorrectionTriggered);
RefPtr<Range> range = Range::create(m_frame->document(), m_frame->selection().selection().start(), m_frame->selection().selection().end());
m_frame.document()->updateLayout();
m_frame.selection().setSelection(selectionOfCorrected, FrameSelection::CloseTyping | FrameSelection::ClearTypingStyle | FrameSelection::SpellCorrectionTriggered);
RefPtr<Range> range = Range::create(m_frame.document(), m_frame.selection().selection().start(), m_frame.selection().selection().end());
DocumentMarkerController& markers = m_frame->document()->markers();
DocumentMarkerController& markers = m_frame.document()->markers();
markers.removeMarkers(range.get(), DocumentMarker::Spelling | DocumentMarker::Autocorrected, DocumentMarkerController::RemovePartiallyOverlappingMarker);
markers.addMarker(range.get(), DocumentMarker::Replacement);
markers.addMarker(range.get(), DocumentMarker::SpellCheckingExemption);
......@@ -335,11 +335,11 @@ void AlternativeTextController::timerFired(Timer<AlternativeTextController>*)
m_isDismissedByEditing = false;
switch (m_alternativeTextInfo.type) {
case AlternativeTextTypeCorrection: {
VisibleSelection selection(m_frame->selection().selection());
VisibleSelection selection(m_frame.selection().selection());
VisiblePosition start(selection.start(), selection.affinity());
VisiblePosition p = startOfWord(start, LeftWordIfOnBoundary);
VisibleSelection adjacentWords = VisibleSelection(p, start);
m_frame->editor().markAllMisspellingsAndBadGrammarInRanges(TextCheckingTypeSpelling | TextCheckingTypeReplacement | TextCheckingTypeShowCorrectionPanel, adjacentWords.toNormalizedRange().get(), 0);
m_frame.editor().markAllMisspellingsAndBadGrammarInRanges(TextCheckingTypeSpelling | TextCheckingTypeReplacement | TextCheckingTypeShowCorrectionPanel, adjacentWords.toNormalizedRange().get(), 0);
}
break;
case AlternativeTextTypeReversion: {
......@@ -397,7 +397,7 @@ void AlternativeTextController::timerFired(Timer<AlternativeTextController>*)
void AlternativeTextController::handleAlternativeTextUIResult(const String& result)
{
Range* rangeWithAlternative = m_alternativeTextInfo.rangeWithAlternative.get();
if (!rangeWithAlternative || m_frame->document() != rangeWithAlternative->ownerDocument())
if (!rangeWithAlternative || m_frame.document() != rangeWithAlternative->ownerDocument())
return;
String currentWord = plainText(rangeWithAlternative);
......@@ -435,7 +435,7 @@ bool AlternativeTextController::isAutomaticSpellingCorrectionEnabled()
FloatRect AlternativeTextController::rootViewRectForRange(const Range* range) const
{
FrameView* view = m_frame->view();
FrameView* view = m_frame.view();
if (!view)
return FloatRect();
Vector<FloatQuad> textQuads;
......@@ -449,7 +449,7 @@ FloatRect AlternativeTextController::rootViewRectForRange(const Range* range) co
void AlternativeTextController::respondToChangedSelection(const VisibleSelection& oldSelection, FrameSelection::SetSelectionOptions options)
{
VisibleSelection currentSelection(m_frame->selection().selection());
VisibleSelection currentSelection(m_frame.selection().selection());
// When user moves caret to the end of autocorrected word and pauses, we show the panel
// containing the original pre-correction word so that user can quickly revert the
// undesired autocorrection. Here, we start correction panel timer once we confirm that
......@@ -488,7 +488,7 @@ void AlternativeTextController::respondToChangedSelection(const VisibleSelection
void AlternativeTextController::respondToAppliedEditing(CompositeEditCommand* command)
{
if (command->isTopLevelCommand() && !command->shouldRetainAutocorrectionIndicator())
m_frame->document()->markers().removeMarkers(DocumentMarker::CorrectionIndicator);
m_frame.document()->markers().removeMarkers(DocumentMarker::CorrectionIndicator);
markPrecedingWhitespaceForDeletedAutocorrectionAfterCommand(command);
m_originalStringForLastDeletedAutocorrection = String();
......@@ -498,28 +498,22 @@ void AlternativeTextController::respondToUnappliedEditing(EditCommandComposition
{
if (!command->wasCreateLinkCommand())
return;
RefPtr<Range> range = Range::create(m_frame->document(), command->startingSelection().start(), command->startingSelection().end());
RefPtr<Range> range = Range::create(m_frame.document(), command->startingSelection().start(), command->startingSelection().end());
if (!range)
return;
DocumentMarkerController& markers = m_frame->document()->markers();
DocumentMarkerController& markers = m_frame.document()->markers();
markers.addMarker(range.get(), DocumentMarker::Replacement);
markers.addMarker(range.get(), DocumentMarker::SpellCheckingExemption);
}
AlternativeTextClient* AlternativeTextController::alternativeTextClient()
{
if (!m_frame)
return 0;
return m_frame->page() ? m_frame->page()->alternativeTextClient() : 0;
return m_frame.page() ? m_frame.page()->alternativeTextClient() : 0;
}
EditorClient* AlternativeTextController::editorClient()
{
if (!m_frame)
return 0;
return m_frame->page() ? m_frame->page()->editorClient() : 0;
return m_frame.page() ? m_frame.page()->editorClient() : 0;
}
TextCheckerClient* AlternativeTextController::textChecker()
......@@ -596,7 +590,7 @@ void AlternativeTextController::markPrecedingWhitespaceForDeletedAutocorrectionA
if (endOfSelection == precedingCharacterPosition)
return;
RefPtr<Range> precedingCharacterRange = Range::create(m_frame->document(), precedingCharacterPosition, endOfSelection);
RefPtr<Range> precedingCharacterRange = Range::create(m_frame.document(), precedingCharacterPosition, endOfSelection);
String string = plainText(precedingCharacterRange.get());
if (string.isEmpty() || !isWhitespace(string[string.length() - 1]))
return;
......@@ -604,12 +598,12 @@ void AlternativeTextController::markPrecedingWhitespaceForDeletedAutocorrectionA
// Mark this whitespace to indicate we have deleted an autocorrection following this
// whitespace. So if the user types the same original word again at this position, we
// won't autocorrect it again.
m_frame->document()->markers().addMarker(precedingCharacterRange.get(), DocumentMarker::DeletedAutocorrection, m_originalStringForLastDeletedAutocorrection);
m_frame.document()->markers().addMarker(precedingCharacterRange.get(), DocumentMarker::DeletedAutocorrection, m_originalStringForLastDeletedAutocorrection);
}
bool AlternativeTextController::processMarkersOnTextToBeReplacedByResult(const TextCheckingResult* result, Range* rangeWithAlternative, const String& stringToBeReplaced)
{
DocumentMarkerController& markerController = m_frame->document()->markers();
DocumentMarkerController& markerController = m_frame.document()->markers();
if (markerController.hasMarkers(rangeWithAlternative, DocumentMarker::Replacement)) {
if (result->type == TextCheckingTypeCorrection)
recordSpellcheckerResponseForModifiedCorrection(rangeWithAlternative, stringToBeReplaced, result->replacement);
......@@ -621,7 +615,7 @@ bool AlternativeTextController::processMarkersOnTextToBeReplacedByResult(const T
Position beginningOfRange = rangeWithAlternative->startPosition();
Position precedingCharacterPosition = beginningOfRange.previous();
RefPtr<Range> precedingCharacterRange = Range::create(m_frame->document(), precedingCharacterPosition, beginningOfRange);
RefPtr<Range> precedingCharacterRange = Range::create(m_frame.document(), precedingCharacterPosition, beginningOfRange);
Vector<DocumentMarker*> markers = markerController.markersInRange(precedingCharacterRange.get(), DocumentMarker::DeletedAutocorrection);
......@@ -645,7 +639,7 @@ bool AlternativeTextController::respondToMarkerAtEndOfWord(const DocumentMarker&
if (!shouldStartTimerFor(marker, endOfWordPosition.offsetInContainerNode()))
return false;
Node* node = endOfWordPosition.containerNode();
RefPtr<Range> wordRange = Range::create(m_frame->document(), node, marker.startOffset(), node, marker.endOffset());
RefPtr<Range> wordRange = Range::create(m_frame.document(), node, marker.startOffset(), node, marker.endOffset());
if (!wordRange)
return false;
String currentWord = plainText(wordRange.get());
......@@ -693,20 +687,18 @@ String AlternativeTextController::markerDescriptionForAppliedAlternativeText(Alt
bool AlternativeTextController::insertDictatedText(const String& text, const Vector<DictationAlternative>& dictationAlternatives, Event* triggeringEvent)
{
if (!m_frame)
return false;
EventTarget* target;
if (triggeringEvent)
target = triggeringEvent->target();
else
target = eventTargetNodeForDocument(m_frame->document());
target = eventTargetNodeForDocument(m_frame.document());
if (!target)
return false;
if (FrameView* view = m_frame->view())
if (FrameView* view = m_frame.view())
view->resetDeferredRepaintDelay();
RefPtr<TextEvent> event = TextEvent::createForDictation(m_frame->document()->domWindow(), text, dictationAlternatives);
RefPtr<TextEvent> event = TextEvent::createForDictation(m_frame.document()->domWindow(), text, dictationAlternatives);
event->setUnderlyingEvent(triggeringEvent);
target->dispatchEvent(event, IGNORE_EXCEPTION);
......@@ -742,7 +734,7 @@ Vector<String> AlternativeTextController::dictationAlternativesForMarker(const D
void AlternativeTextController::applyDictationAlternative(const String& alternativeString)
{
#if USE(DICTATION_ALTERNATIVES)
Editor& editor = m_frame->editor();
Editor& editor = m_frame.editor();
RefPtr<Range> selection = editor.selectedRange();
if (!selection || !editor.shouldInsertText(alternativeString, selection.get(), EditorInsertActionPasted))
return;
......
......@@ -93,7 +93,7 @@ class AlternativeTextController {
WTF_MAKE_NONCOPYABLE(AlternativeTextController);
WTF_MAKE_FAST_ALLOCATED;
public:
explicit AlternativeTextController(Frame*) UNLESS_ENABLED({ })
explicit AlternativeTextController(Frame& frame) UNLESS_ENABLED( : m_frame(frame) { })
~AlternativeTextController() UNLESS_ENABLED({ })
void startAlternativeTextUITimer(AlternativeTextType) UNLESS_ENABLED({ })
......@@ -161,7 +161,7 @@ private:
Position m_positionForLastDeletedAutocorrection;
#endif
Frame* m_frame;
Frame& m_frame;
};
#undef UNLESS_ENABLED
......
......@@ -899,7 +899,7 @@ Editor::Editor(Frame& frame)
, m_shouldStyleWithCSS(false)
, m_killRing(adoptPtr(new KillRing))
, m_spellChecker(adoptPtr(new SpellChecker(frame)))
, m_alternativeTextController(adoptPtr(new AlternativeTextController(&frame)))
, m_alternativeTextController(adoptPtr(new AlternativeTextController(frame)))
, m_areMarkedTextMatchesHighlighted(false)
, m_defaultParagraphSeparator(EditorParagraphSeparatorIsDiv)
, m_overwriteModeEnabled(false)
......@@ -2557,13 +2557,13 @@ void Editor::transpose()
void Editor::addToKillRing(Range* range, bool prepend)
{
if (m_shouldStartNewKillRingSequence)
killRing()->startNewSequence();
killRing().startNewSequence();
String text = plainText(range);
if (prepend)
killRing()->prepend(text);
killRing().prepend(text);
else
killRing()->append(text);
killRing().append(text);
m_shouldStartNewKillRingSequence = false;
}
......
......@@ -328,7 +328,7 @@ public:
VisibleSelection selectionForCommand(Event*);
KillRing* killRing() const { return m_killRing.get(); }
KillRing& killRing() const { return *m_killRing.get(); }
SpellChecker& spellChecker() const { return *m_spellChecker.get(); }
EditingBehavior behavior() const;
......@@ -427,9 +427,9 @@ private:
bool m_ignoreCompositionSelectionChange;
bool m_shouldStartNewKillRingSequence;
bool m_shouldStyleWithCSS;
OwnPtr<KillRing> m_killRing;
OwnPtr<SpellChecker> m_spellChecker;
OwnPtr<AlternativeTextController> m_alternativeTextController;
const OwnPtr<KillRing> m_killRing;
const OwnPtr<SpellChecker> m_spellChecker;
const OwnPtr<AlternativeTextController> m_alternativeTextController;
VisibleSelection m_mark;
bool m_areMarkedTextMatchesHighlighted;
EditorParagraphSeparator m_defaultParagraphSeparator;
......
......@@ -1143,15 +1143,15 @@ static bool executeUnselect(Frame* frame, Event*, EditorCommandSource, const Str
static bool executeYank(Frame* frame, Event*, EditorCommandSource, const String&)
{
frame->editor().insertTextWithoutSendingTextEvent(frame->editor().killRing()->yank(), false, 0);
frame->editor().killRing()->setToYankedState();
frame->editor().insertTextWithoutSendingTextEvent(frame->editor().killRing().yank(), false, 0);
frame->editor().killRing().setToYankedState();
return true;
}
static bool executeYankAndSelect(Frame* frame, Event*, EditorCommandSource, const String&)
{
frame->editor().insertTextWithoutSendingTextEvent(frame->editor().killRing()->yank(), true, 0);
frame->editor().killRing()->setToYankedState();
frame->editor().insertTextWithoutSendingTextEvent(frame->editor().killRing().yank(), true, 0);
frame->editor().killRing().setToYankedState();
return true;
}
......
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