Changeset 164401 in webkit


Ignore:
Timestamp:
Feb 19, 2014 4:12:59 PM (10 years ago)
Author:
rniwa@webkit.org
Message:

Changing selection shouldn't synchronously update editor UI components
https://bugs.webkit.org/show_bug.cgi?id=129024

Reviewed by Brent Fulgham.

Source/WebCore:

Make updates to spellchecker, alternative text controller (correction pane), and delete button controller
asynchronous for programmatically triggered selection changes.

We continue to update their states synchronously immediately after we have applied, unapplied, or reapplied
editing commands to keep states in spell checker and alternative text controller consistent. We should be
able to make them asynchronous as well in the future but that should be done in a separate patch.

  • WebCore.exp.in:
  • editing/AlternativeTextController.cpp:

(WebCore::AlternativeTextController::respondToChangedSelection): This function used to enumerate all document
makers and call respondToMarkerAtEndOfWord on each one of them only to exit early when SetSelectionOptions
had DictationTriggered. This condition is now checked in Editor::respondToChangedSelection to avoid all the
unnecessary work and remove the dependency on SetSelectionOptions.
(WebCore::AlternativeTextController::respondToMarkerAtEndOfWord): Ditto.

  • editing/AlternativeTextController.h:
  • editing/Editor.cpp:

(WebCore::Editor::appliedEditing): Calls updateEditorUINowIfScheduled before calling respondToAppliedEditing
on the alternative text controller.
(WebCore::Editor::unappliedEditing): Ditto.
(WebCore::Editor::reappliedEditing): Ditto.
(WebCore::Editor::Editor): Initializes newly added booleans.
(WebCore::Editor::respondToChangedSelection): Continue to call respondToChangedSelection (for API consistency)
and setStartNewKillRingSequence but defer the "editor UI updates" to spellchecker, alternative text controller
and delete button controller by firing a newly added one shot timer.
(WebCore::Editor::updateEditorUINowIfScheduled): Synchronously update the pending editor UI updates.
(WebCore::Editor::editorUIUpdateTimerFired): Extracted from respondToChangedSelection.

  • editing/Editor.h:
  • testing/Internals.cpp:

(WebCore::Internals::markerCountForNode): Calls updateEditorUINowIfScheduled() to update document markers.
(WebCore::Internals::markerAt): Ditto.
(WebCore::Internals::updateEditorUINowIfScheduled): Added.
(WebCore::Internals::findEditingDeleteButton): Added. Updates delete button controller synchronously.
(WebCore::Internals::hasSpellingMarker): Calls updateEditorUINowIfScheduled() to update document markers.
(WebCore::Internals::hasAutocorrectedMarker): Ditto.

  • testing/Internals.h:
  • testing/Internals.idl:

Source/WebKit:

Added symbols for internals.

  • WebKit.vcxproj/WebKitExportGenerator/WebKitExports.def.in:

LayoutTests:

Many tests now calls internals.updateEditorUINowIfScheduled() to update the spellchecker states, and uses
setTimeout() to make things testable in the browser.

  • editing/spelling/script-tests/spelling-backspace-between-lines.js:

(testTwoLinesMisspellings): Uses updateEditorUINowIfScheduled and setTimeout to make spellchecker recognize
two selection changes. This is okay since the user never moves selection multiple times in a single task.

  • editing/spelling/spellcheck-attribute.html: Ditto.
  • platform/mac/editing/deleting/deletionUI-click-on-delete-button.html: Use intenals.findEditingDeleteButton

which updates delete button controller states synchronously instead of getElementById which doesn't do that.

  • platform/mac/editing/deleting/id-in-deletebutton-expected.txt:
  • platform/mac/editing/deleting/id-in-deletebutton.html: Ditto. Also did some cleanups.
  • platform/mac/editing/deleting/resources/deletionUI-helpers.js:

(deletionUIDeleteButtonForElement): Ditto.

  • platform/mac/editing/spelling/editing-word-with-marker-1.html: Again, we must notify the spellchecker

synchronously here because we're expecting spellchecker to use the old selection set by setSelectionRange
in Editor::editorUIUpdateTimerFired triggered by the pasting command. This is, again, not a problem in
practice since user never pastes content synchronously after changing selection like this in a single task.

Location:
trunk
Files:
19 edited

Legend:

Unmodified
Added
Removed
  • trunk/LayoutTests/ChangeLog

    r164394 r164401  
     12014-02-18  Ryosuke Niwa  <rniwa@webkit.org>
     2
     3        Changing selection shouldn't synchronously update editor UI components
     4        https://bugs.webkit.org/show_bug.cgi?id=129024
     5
     6        Reviewed by Brent Fulgham.
     7
     8        Many tests now calls internals.updateEditorUINowIfScheduled() to update the spellchecker states, and uses
     9        setTimeout() to make things testable in the browser.
     10
     11        * editing/spelling/script-tests/spelling-backspace-between-lines.js:
     12        (testTwoLinesMisspellings): Uses updateEditorUINowIfScheduled and setTimeout to make spellchecker recognize
     13        two selection changes. This is okay since the user never moves selection multiple times in a single task.
     14        * editing/spelling/spellcheck-attribute.html: Ditto.
     15
     16        * platform/mac/editing/deleting/deletionUI-click-on-delete-button.html: Use intenals.findEditingDeleteButton
     17        which updates delete button controller states synchronously instead of getElementById which doesn't do that.
     18        * platform/mac/editing/deleting/id-in-deletebutton-expected.txt:
     19        * platform/mac/editing/deleting/id-in-deletebutton.html: Ditto. Also did some cleanups.
     20        * platform/mac/editing/deleting/resources/deletionUI-helpers.js:
     21        (deletionUIDeleteButtonForElement): Ditto.
     22
     23        * platform/mac/editing/spelling/editing-word-with-marker-1.html: Again, we must notify the spellchecker
     24        synchronously here because we're expecting spellchecker to use the old selection set by setSelectionRange
     25        in Editor::editorUIUpdateTimerFired triggered by the pasting command. This is, again, not a problem in
     26        practice since user never pastes content synchronously after changing selection like this in a single task.
     27
    1282014-02-19  Brent Fulgham  <bfulgham@apple.com>
    229
  • trunk/LayoutTests/editing/spelling/script-tests/spelling-backspace-between-lines.js

    r163615 r164401  
    3434
    3535    sel.modify("move", "forward", "line"); // ^OK zz OK
    36     for (var i = 0; i < 3; i++)
    37         sel.modify("move", "forward", "word");
     36    if (window.internals)
     37        internals.updateEditorUINowIfScheduled();
     38    setTimeout(function () {
     39        for (var i = 0; i < 3; i++)
     40            sel.modify("move", "forward", "word");
    3841
    39     shouldBeEqualToString("firstLineText('target1')", "OK");
    40     shouldBeEqualToString("sel.anchorNode.data", "OK zz OK");
    41     if (window.internals)
    42         shouldBecomeEqual("internals.hasSpellingMarker(3, 2)", "true", done);
    43     else
    44         done();
     42        shouldBeEqualToString("firstLineText('target1')", "OK");
     43        shouldBeEqualToString("sel.anchorNode.data", "OK zz OK");
     44        if (window.internals)
     45            shouldBecomeEqual("internals.hasSpellingMarker(3, 2)", "true", done);
     46        else
     47            done();
     48    }, 100);
    4549}
    4650
  • trunk/LayoutTests/editing/spelling/spellcheck-attribute.html

    r163432 r164401  
    4949    input.focus();
    5050    // Activate spellchecking.
    51     moveSelectionForwardByWordCommand();
     51    if (window.internals)
     52        internals.updateEditorUINowIfScheduled();
     53    setTimeout(function () {
     54        moveSelectionForwardByWordCommand();
    5255
    53     logMarkup(id, spellcheck, true);
     56        logMarkup(id, spellcheck, true);
    5457
    55     if (window.internals)
    56         shouldBecomeEqual('internals.hasSpellingMarker(0, 2)', shouldBeMisspelled ? 'true' : 'false', done);
    57     else
    58         done();
     58        if (window.internals)
     59            shouldBecomeEqual('internals.hasSpellingMarker(0, 2)', shouldBeMisspelled ? 'true' : 'false', done);
     60        else
     61            done();
     62    }, 10);
    5963}
    6064
  • trunk/LayoutTests/platform/mac/editing/deleting/deletionUI-click-on-delete-button.html

    r142559 r164401  
    1515
    1616if (window.testRunner) {
    17     deleteButton = document.getElementById("WebKit-Editing-Delete-Button");
     17    deleteButton = internals.findEditingDeleteButton();
    1818    x = deleteButton.offsetParent.offsetLeft + deleteButton.offsetParent.offsetParent.offsetLeft + deleteButton.offsetLeft + deleteButton.offsetWidth / 2;
    1919    y = deleteButton.offsetParent.offsetTop + deleteButton.offsetParent.offsetParent.offsetTop + deleteButton.offsetTop + deleteButton.offsetHeight / 2;
     
    2121    eventSender.mouseDown();
    2222    eventSender.mouseUp();
    23     deleteButton = document.getElementById("WebKit-Editing-Delete-Button");
     23    deleteButton = internals.findEditingDeleteButton();
    2424    testContainer = document.getElementById("test");
    2525    Markup.description("There should be no visible content in the markup below. This test is for a bug where the delete button wouldn't work because it had -webkit-user-select:none instead of -webkit-user-select:ignore.");
  • trunk/LayoutTests/platform/mac/editing/deleting/id-in-deletebutton-expected.txt

    r142599 r164401  
    44
    55
    6 PASS deleteButton is non-null.
     6PASS internals.findEditingDeleteButton(); document.getElementById("WebKit-Editing-Delete-Button") is non-null.
    77PASS successfullyParsed is true
    88
  • trunk/LayoutTests/platform/mac/editing/deleting/id-in-deletebutton.html

    r155282 r164401  
    11<html>
    2 <head>
    3 <script src="../../../../resources/js-test-pre.js"></script>
    4 </head>
    52<body>
    6 
    73<div contenteditable="true">
    84<ul class="needsDeletionUI"><li>1</li><li id="li">2</li></ul>
    9 
     5<script src="../../../../resources/js-test-pre.js"></script>
    106<script>
    117description('Test document.getElementById("WebKit-Editing-Delete-Button")');
     
    1511sel.setPosition(li, 0);
    1612
    17 if (window.testRunner) {
    18     deleteButton = document.getElementById("WebKit-Editing-Delete-Button");
    19     shouldBeNonNull('deleteButton');
    20 }
     13if (window.testRunner)
     14    shouldBeNonNull('internals.findEditingDeleteButton(); document.getElementById("WebKit-Editing-Delete-Button")');
     15
     16var successfullyParsed = true;
     17
    2118</script>
    2219<script src="../../../../resources/js-test-post.js"></script>
  • trunk/LayoutTests/platform/mac/editing/deleting/resources/deletionUI-helpers.js

    r120173 r164401  
    1111function deletionUIDeleteButtonForElement(id)
    1212{
     13    if (!window.internals)
     14        return null;
    1315    var sel = window.getSelection();
    1416    var selElement = document.getElementById(id);
    1517    sel.setPosition(selElement, 0);
    16     var deleteButton = document.getElementById("WebKit-Editing-Delete-Button");
    17     return deleteButton;
     18    return internals.findEditingDeleteButton();
    1819}
    1920
  • trunk/LayoutTests/platform/mac/editing/spelling/editing-word-with-marker-1.html

    r158113 r164401  
    149149execCopyCommand();
    150150textarea.setSelectionRange(15, 15);
     151if (window.internals)
     152    internals.updateEditorUINowIfScheduled();
    151153execPasteCommand();
    152154if (window.internals && window.internals.hasSpellingMarker) {
  • trunk/Source/WebCore/ChangeLog

    r164391 r164401  
     12014-02-18  Ryosuke Niwa  <rniwa@webkit.org>
     2
     3        Changing selection shouldn't synchronously update editor UI components
     4        https://bugs.webkit.org/show_bug.cgi?id=129024
     5
     6        Reviewed by Brent Fulgham.
     7
     8        Make updates to spellchecker, alternative text controller (correction pane), and delete button controller
     9        asynchronous for programmatically triggered selection changes.
     10
     11        We continue to update their states synchronously immediately after we have applied, unapplied, or reapplied
     12        editing commands to keep states in spell checker and alternative text controller consistent. We should be
     13        able to make them asynchronous as well in the future but that should be done in a separate patch.
     14
     15        * WebCore.exp.in:
     16        * editing/AlternativeTextController.cpp:
     17        (WebCore::AlternativeTextController::respondToChangedSelection): This function used to enumerate all document
     18        makers and call respondToMarkerAtEndOfWord on each one of them only to exit early when SetSelectionOptions
     19        had DictationTriggered. This condition is now checked in Editor::respondToChangedSelection to avoid all the
     20        unnecessary work and remove the dependency on SetSelectionOptions.
     21        (WebCore::AlternativeTextController::respondToMarkerAtEndOfWord): Ditto.
     22        * editing/AlternativeTextController.h:
     23
     24        * editing/Editor.cpp:
     25        (WebCore::Editor::appliedEditing): Calls updateEditorUINowIfScheduled before calling respondToAppliedEditing
     26        on the alternative text controller.
     27        (WebCore::Editor::unappliedEditing): Ditto.
     28        (WebCore::Editor::reappliedEditing): Ditto.
     29        (WebCore::Editor::Editor): Initializes newly added booleans.
     30        (WebCore::Editor::respondToChangedSelection): Continue to call respondToChangedSelection (for API consistency)
     31        and setStartNewKillRingSequence but defer the "editor UI updates" to spellchecker, alternative text controller
     32        and delete button controller by firing a newly added one shot timer.
     33        (WebCore::Editor::updateEditorUINowIfScheduled): Synchronously update the pending editor UI updates.
     34        (WebCore::Editor::editorUIUpdateTimerFired): Extracted from respondToChangedSelection.
     35        * editing/Editor.h:
     36
     37        * testing/Internals.cpp:
     38        (WebCore::Internals::markerCountForNode): Calls updateEditorUINowIfScheduled() to update document markers.
     39        (WebCore::Internals::markerAt): Ditto.
     40        (WebCore::Internals::updateEditorUINowIfScheduled): Added.
     41        (WebCore::Internals::findEditingDeleteButton): Added. Updates delete button controller synchronously.
     42        (WebCore::Internals::hasSpellingMarker): Calls updateEditorUINowIfScheduled() to update document markers.
     43        (WebCore::Internals::hasAutocorrectedMarker): Ditto.
     44        * testing/Internals.h:
     45        * testing/Internals.idl:
     46
    1472014-02-19  Anders Carlsson  <andersca@apple.com>
    248
  • trunk/Source/WebCore/WebCore.exp.in

    r164364 r164401  
    11171117__ZN7WebCore6Editor26writeSelectionToPasteboardERNS_10PasteboardE
    11181118__ZN7WebCore6Editor28replaceSelectionWithFragmentEN3WTF10PassRefPtrINS_16DocumentFragmentEEEbbb
     1119__ZN7WebCore6Editor28updateEditorUINowIfScheduledEv
    11191120__ZN7WebCore6Editor29canDecreaseSelectionListLevelEv
    11201121__ZN7WebCore6Editor29canIncreaseSelectionListLevelEv
  • trunk/Source/WebCore/editing/AlternativeTextController.cpp

    r163721 r164401  
    441441}       
    442442
    443 void AlternativeTextController::respondToChangedSelection(const VisibleSelection& oldSelection, FrameSelection::SetSelectionOptions options)
     443void AlternativeTextController::respondToChangedSelection(const VisibleSelection& oldSelection)
    444444{
    445445    VisibleSelection currentSelection(m_frame.selection().selection());
     
    474474            continue;
    475475
    476         if (respondToMarkerAtEndOfWord(*marker, position, options))
     476        if (respondToMarkerAtEndOfWord(*marker, position))
    477477            break;
    478478    }
     
    626626}
    627627
    628 bool AlternativeTextController::respondToMarkerAtEndOfWord(const DocumentMarker& marker, const Position& endOfWordPosition, FrameSelection::SetSelectionOptions options)
    629 {
    630     if (options & FrameSelection::DictationTriggered)
    631         return false;
     628bool AlternativeTextController::respondToMarkerAtEndOfWord(const DocumentMarker& marker, const Position& endOfWordPosition)
     629{
    632630    if (!shouldStartTimerFor(marker, endOfWordPosition.offsetInContainerNode()))
    633631        return false;
  • trunk/Source/WebCore/editing/AlternativeTextController.h

    r161768 r164401  
    109109    void respondToAppliedEditing(CompositeEditCommand*) UNLESS_ENABLED({ })
    110110    void respondToUnappliedEditing(EditCommandComposition*) UNLESS_ENABLED({ })
    111     void respondToChangedSelection(const VisibleSelection& oldSelection, FrameSelection::SetSelectionOptions) UNLESS_ENABLED({ UNUSED_PARAM(oldSelection); })
     111    void respondToChangedSelection(const VisibleSelection& oldSelection) UNLESS_ENABLED({ UNUSED_PARAM(oldSelection); })
    112112
    113113    void stopPendingCorrection(const VisibleSelection& oldSelection) UNLESS_ENABLED({ UNUSED_PARAM(oldSelection); })
     
    145145
    146146    bool shouldStartTimerFor(const DocumentMarker&, int endOffset) const;
    147     bool respondToMarkerAtEndOfWord(const DocumentMarker&, const Position& endOfWordPosition, FrameSelection::SetSelectionOptions);
     147    bool respondToMarkerAtEndOfWord(const DocumentMarker&, const Position& endOfWordPosition);
    148148
    149149    AlternativeTextClient* alternativeTextClient();
  • trunk/Source/WebCore/editing/Editor.cpp

    r164358 r164401  
    10671067    VisibleSelection newSelection(cmd->endingSelection());
    10681068
    1069     m_alternativeTextController->respondToAppliedEditing(cmd.get());
    1070 
    10711069    notifyTextFromControls(composition->startingRootEditableElement(), composition->endingRootEditableElement());
    10721070
     
    10751073    changeSelectionAfterCommand(newSelection, options);
    10761074    dispatchEditableContentChangedEvents(composition->startingRootEditableElement(), composition->endingRootEditableElement());
     1075
     1076    updateEditorUINowIfScheduled();
     1077   
     1078    m_alternativeTextController->respondToAppliedEditing(cmd.get());
    10771079
    10781080    if (!cmd->preservesTypingStyle())
     
    11031105    dispatchEditableContentChangedEvents(cmd->startingRootEditableElement(), cmd->endingRootEditableElement());
    11041106
     1107    updateEditorUINowIfScheduled();
     1108
    11051109    m_alternativeTextController->respondToUnappliedEditing(cmd.get());
    11061110
     
    11201124    changeSelectionAfterCommand(newSelection, FrameSelection::defaultSetSelectionOptions());
    11211125    dispatchEditableContentChangedEvents(cmd->startingRootEditableElement(), cmd->endingRootEditableElement());
     1126   
     1127    updateEditorUINowIfScheduled();
    11221128
    11231129    m_lastEditCommand = 0;
     
    11421148    , m_defaultParagraphSeparator(EditorParagraphSeparatorIsDiv)
    11431149    , m_overwriteModeEnabled(false)
     1150    , m_editorUIUpdateTimer(this, &Editor::editorUIUpdateTimerFired)
     1151    , m_editorUIUpdateTimerShouldCheckSpellingAndGrammar(false)
     1152    , m_editorUIUpdateTimerWasTriggeredByDictation(false)
    11441153{
    11451154}
     
    32953304}
    32963305
    3297 void Editor::respondToChangedSelection(const VisibleSelection& oldSelection, FrameSelection::SetSelectionOptions options)
     3306void Editor::respondToChangedSelection(const VisibleSelection&, FrameSelection::SetSelectionOptions options)
    32983307{
    32993308#if PLATFORM(IOS)
     
    33033312#endif
    33043313
     3314    if (client())
     3315        client()->respondToChangedSelection(&m_frame);
     3316    setStartNewKillRingSequence(true);
     3317
     3318    if (m_editorUIUpdateTimer.isActive())
     3319        return;
     3320
     3321    // Don't check spelling and grammar if the change of selection is triggered by spelling correction itself.
     3322    m_editorUIUpdateTimerShouldCheckSpellingAndGrammar = options & FrameSelection::CloseTyping
     3323        && !(options & FrameSelection::SpellCorrectionTriggered);
     3324    m_editorUIUpdateTimerWasTriggeredByDictation = options & FrameSelection::DictationTriggered;
     3325    m_editorUIUpdateTimer.startOneShot(0);
     3326}
     3327
     3328void Editor::updateEditorUINowIfScheduled()
     3329{
     3330    if (!m_editorUIUpdateTimer.isActive())
     3331        return;
     3332    m_editorUIUpdateTimer.stop();
     3333    editorUIUpdateTimerFired(m_editorUIUpdateTimer);
     3334}
     3335
     3336void Editor::editorUIUpdateTimerFired(Timer<Editor>&)
     3337{
     3338    VisibleSelection oldSelection = m_oldSelectionForEditorUIUpdate;
     3339
    33053340    m_alternativeTextController->stopPendingCorrection(oldSelection);
    3306 
    3307     bool closeTyping = options & FrameSelection::CloseTyping;
     3341   
    33083342    bool isContinuousSpellCheckingEnabled = this->isContinuousSpellCheckingEnabled();
    33093343    bool isContinuousGrammarCheckingEnabled = isContinuousSpellCheckingEnabled && isGrammarCheckingEnabled();
     
    33323366        }
    33333367
    3334         // Don't check spelling and grammar if the change of selection is triggered by spelling correction itself.
    3335         bool shouldCheckSpellingAndGrammar = !(options & FrameSelection::SpellCorrectionTriggered);
    3336 
    33373368        // When typing we check spelling elsewhere, so don't redo it here.
    33383369        // If this is a change in selection resulting from a delete operation,
    33393370        // oldSelection may no longer be in the document.
    3340         if (shouldCheckSpellingAndGrammar && closeTyping && oldSelection.isContentEditable() && oldSelection.start().deprecatedNode() && oldSelection.start().anchorNode()->inDocument()) {
     3371        if (m_editorUIUpdateTimerShouldCheckSpellingAndGrammar && oldSelection.isContentEditable() && oldSelection.start().deprecatedNode() && oldSelection.start().anchorNode()->inDocument()) {
    33413372            VisiblePosition oldStart(oldSelection.visibleStart());
    33423373            VisibleSelection oldAdjacentWords = VisibleSelection(startOfWord(oldStart, LeftWordIfOnBoundary), endOfWord(oldStart, RightWordIfOnBoundary));
     
    33663397        document().markers().removeMarkers(DocumentMarker::Grammar);
    33673398
    3368     if (client())
    3369         client()->respondToChangedSelection(&m_frame);
    3370     setStartNewKillRingSequence(true);
    33713399#if ENABLE(DELETION_UI)
    33723400    m_deleteButtonController->respondToChangedSelection(oldSelection);
    33733401#endif
    3374     m_alternativeTextController->respondToChangedSelection(oldSelection, options);
     3402    if (m_editorUIUpdateTimerWasTriggeredByDictation)
     3403        m_alternativeTextController->respondToChangedSelection(oldSelection);
     3404
     3405    m_oldSelectionForEditorUIUpdate = m_frame.selection().selection();
    33753406}
    33763407
  • trunk/Source/WebCore/editing/Editor.h

    r164331 r164401  
    363363
    364364    void respondToChangedSelection(const VisibleSelection& oldSelection, FrameSelection::SetSelectionOptions);
     365    void updateEditorUINowIfScheduled();
    365366    bool shouldChangeSelection(const VisibleSelection& oldSelection, const VisibleSelection& newSelection, EAffinity, bool stillSelecting) const;
    366367    unsigned countMatchesForText(const String&, Range*, FindOptions, unsigned limit, bool markMatches, Vector<RefPtr<Range>>*);
     
    464465
    465466    void changeSelectionAfterCommand(const VisibleSelection& newSelection, FrameSelection::SetSelectionOptions);
     467
     468    void editorUIUpdateTimerFired(Timer<Editor>&);
    466469
    467470    Node* findEventTargetFromSelection() const;
     
    496499    EditorParagraphSeparator m_defaultParagraphSeparator;
    497500    bool m_overwriteModeEnabled;
     501
     502    VisibleSelection m_oldSelectionForEditorUIUpdate;
     503    Timer<Editor> m_editorUIUpdateTimer;
     504    bool m_editorUIUpdateTimerShouldCheckSpellingAndGrammar;
     505    bool m_editorUIUpdateTimerWasTriggeredByDictation;
    498506};
    499507
  • trunk/Source/WebCore/testing/Internals.cpp

    r164251 r164401  
    749749    }
    750750
     751    node->document().frame()->editor().updateEditorUINowIfScheduled();
     752
    751753    return node->document().markers().markersFor(node, markerTypes).size();
    752754}
     
    765767        return 0;
    766768    }
     769
     770    node->document().frame()->editor().updateEditorUINowIfScheduled();
    767771
    768772    Vector<DocumentMarker*> markers = node->document().markers().markersFor(node, markerTypes);
     
    12961300}
    12971301
     1302void Internals::updateEditorUINowIfScheduled()
     1303{
     1304    if (Document* document = contextDocument()) {
     1305        if (Frame* frame = document->frame())
     1306            frame->editor().updateEditorUINowIfScheduled();
     1307    }
     1308}
     1309
     1310Node* Internals::findEditingDeleteButton()
     1311{
     1312    Document* document = contextDocument();
     1313    if (!document || !document->frame())
     1314        return 0;
     1315
     1316    updateEditorUINowIfScheduled();
     1317
     1318    // FIXME: We shouldn't pollute the id namespace with this name.
     1319    return document->getElementById("WebKit-Editing-Delete-Button");
     1320}
     1321
    12981322bool Internals::hasSpellingMarker(int from, int length, ExceptionCode&)
    12991323{
     
    13011325    if (!document || !document->frame())
    13021326        return 0;
     1327
     1328    updateEditorUINowIfScheduled();
    13031329
    13041330    return document->frame()->editor().selectionStartHasMarkerFor(DocumentMarker::Spelling, from, length);
     
    13101336    if (!document || !document->frame())
    13111337        return 0;
    1312    
     1338
     1339    updateEditorUINowIfScheduled();
     1340
    13131341    return document->frame()->editor().selectionStartHasMarkerFor(DocumentMarker::Autocorrected, from, length);
    13141342}
  • trunk/Source/WebCore/testing/Internals.h

    r164131 r164401  
    170170    String parserMetaData(Deprecated::ScriptValue = Deprecated::ScriptValue());
    171171
     172    Node* findEditingDeleteButton();
     173    void updateEditorUINowIfScheduled();
     174
    172175    bool hasSpellingMarker(int from, int length, ExceptionCode&);
    173176    bool hasGrammarMarker(int from, int length, ExceptionCode&);
  • trunk/Source/WebCore/testing/Internals.idl

    r164131 r164401  
    130130    DOMString parserMetaData(optional any func);
    131131
     132    void updateEditorUINowIfScheduled();
     133
     134    Node findEditingDeleteButton();
     135
    132136    [RaisesException] boolean hasSpellingMarker(long from, long length);
    133137    [RaisesException] boolean hasGrammarMarker(long from, long length);
  • trunk/Source/WebKit/ChangeLog

    r164245 r164401  
     12014-02-18  Ryosuke Niwa  <rniwa@webkit.org>
     2
     3        Changing selection shouldn't synchronously update editor UI components
     4        https://bugs.webkit.org/show_bug.cgi?id=129024
     5
     6        Reviewed by Brent Fulgham.
     7
     8        Added symbols for internals.
     9
     10        * WebKit.vcxproj/WebKitExportGenerator/WebKitExports.def.in:
     11
    1122014-02-17  Sergio Correia  <sergio.correia@openbossa.org>
    213
  • trunk/Source/WebKit/WebKit.vcxproj/WebKitExportGenerator/WebKitExports.def.in

    r164245 r164401  
    205205        symbolWithPointer(?getCachedDOMStructure@WebCore@@YAPAVStructure@JSC@@PAVJSDOMGlobalObject@1@PBUClassInfo@3@@Z, ?getCachedDOMStructure@WebCore@@YAPEAVStructure@JSC@@PEAVJSDOMGlobalObject@1@PEBUClassInfo@3@@Z)
    206206        symbolWithPointer(?getData16SlowCase@StringImpl@WTF@@ABEPB_WXZ, ?getData16SlowCase@StringImpl@WTF@@AEBAPEB_WXZ)
     207        symbolWithPointer(?getElementById@TreeScope@WebCore@@QBEPAVElement@2@ABVAtomicString@WTF@@@Z)
    207208        symbolWithPointer(?getLocationAndLengthFromRange@TextIterator@WebCore@@SA_NPAVNode@2@PBVRange@2@AAI2@Z, ?getLocationAndLengthFromRange@TextIterator@WebCore@@SA_NPEAVNode@2@PEBVRange@2@AEA_K2@Z)
    208209        symbolWithPointer(?hitTest@RenderView@WebCore@@QAE_NABVHitTestRequest@2@AAVHitTestResult@2@@Z, ?hitTest@RenderView@WebCore@@QEAA_NAEBVHitTestRequest@2@AEAVHitTestResult@2@@Z)
     
    324325        symbolWithPointer(?toRange@WebCore@@YAPAVRange@1@VJSValue@JSC@@@Z, ?toRange@WebCore@@YAPEAVRange@1@VJSValue@JSC@@@Z)
    325326        symbolWithPointer(?isTreeScope@Node@WebCore@@QBE_NXZ, ?isTreeScope@Node@WebCore@@QEBA_NXZ)
     327        symbolWithPointer(?updateEditorUINowIfScheduled@Editor@WebCore@@QAEXXZ)
    326328        symbolWithPointer(?updateLayoutIgnorePendingStylesheets@Document@WebCore@@QAEXXZ, ?updateLayoutIgnorePendingStylesheets@Document@WebCore@@QEAAXXZ)
    327329        symbolWithPointer(?updateStyleIfNeeded@Document@WebCore@@QAEXXZ, ?updateStyleIfNeeded@Document@WebCore@@QEAAXXZ)
Note: See TracChangeset for help on using the changeset viewer.