Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(585)

Side by Side Diff: third_party/WebKit/Source/core/editing/InputMethodController.cpp

Issue 2650113004: [WIP] Add support for Android SuggestionSpans when editing text (Closed)
Patch Set: Uploading the latest version from my repo so I can reference it Created 3 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 /* 1 /*
2 * Copyright (C) 2006, 2007, 2008, 2011 Apple Inc. All rights reserved. 2 * Copyright (C) 2006, 2007, 2008, 2011 Apple Inc. All rights reserved.
3 * Copyright (C) 2008 Nokia Corporation and/or its subsidiary(-ies) 3 * Copyright (C) 2008 Nokia Corporation and/or its subsidiary(-ies)
4 * 4 *
5 * Redistribution and use in source and binary forms, with or without 5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions 6 * modification, are permitted provided that the following conditions
7 * are met: 7 * are met:
8 * 1. Redistributions of source code must retain the above copyright 8 * 1. Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer. 9 * notice, this list of conditions and the following disclaimer.
10 * 2. Redistributions in binary form must reproduce the above copyright 10 * 2. Redistributions in binary form must reproduce the above copyright
(...skipping 15 matching lines...) Expand all
26 26
27 #include "core/editing/InputMethodController.h" 27 #include "core/editing/InputMethodController.h"
28 28
29 #include "core/InputModeNames.h" 29 #include "core/InputModeNames.h"
30 #include "core/InputTypeNames.h" 30 #include "core/InputTypeNames.h"
31 #include "core/dom/Document.h" 31 #include "core/dom/Document.h"
32 #include "core/dom/Element.h" 32 #include "core/dom/Element.h"
33 #include "core/dom/Text.h" 33 #include "core/dom/Text.h"
34 #include "core/editing/EditingUtilities.h" 34 #include "core/editing/EditingUtilities.h"
35 #include "core/editing/Editor.h" 35 #include "core/editing/Editor.h"
36 #include "core/editing/TextSuggestionController.h"
36 #include "core/editing/commands/TypingCommand.h" 37 #include "core/editing/commands/TypingCommand.h"
37 #include "core/editing/markers/DocumentMarkerController.h" 38 #include "core/editing/markers/DocumentMarkerController.h"
38 #include "core/editing/state_machines/BackwardCodePointStateMachine.h" 39 #include "core/editing/state_machines/BackwardCodePointStateMachine.h"
39 #include "core/editing/state_machines/ForwardCodePointStateMachine.h" 40 #include "core/editing/state_machines/ForwardCodePointStateMachine.h"
40 #include "core/events/CompositionEvent.h" 41 #include "core/events/CompositionEvent.h"
41 #include "core/frame/LocalFrame.h" 42 #include "core/frame/LocalFrame.h"
42 #include "core/html/HTMLInputElement.h" 43 #include "core/html/HTMLInputElement.h"
43 #include "core/html/HTMLTextAreaElement.h" 44 #include "core/html/HTMLTextAreaElement.h"
44 #include "core/input/EventHandler.h" 45 #include "core/input/EventHandler.h"
45 #include "core/layout/LayoutObject.h" 46 #include "core/layout/LayoutObject.h"
(...skipping 18 matching lines...) Expand all
64 Element* target = frame.document()->focusedElement(); 65 Element* target = frame.document()->focusedElement();
65 if (!target) 66 if (!target)
66 return; 67 return;
67 68
68 CompositionEvent* event = CompositionEvent::create( 69 CompositionEvent* event = CompositionEvent::create(
69 EventTypeNames::compositionend, frame.domWindow(), text); 70 EventTypeNames::compositionend, frame.domWindow(), text);
70 target->dispatchEvent(event); 71 target->dispatchEvent(event);
71 } 72 }
72 73
73 bool needsIncrementalInsertion(const LocalFrame& frame, const String& newText) { 74 bool needsIncrementalInsertion(const LocalFrame& frame, const String& newText) {
74 // No need to apply incremental insertion if it doesn't support formated text.
75 if (!frame.editor().canEditRichly())
76 return false;
77
78 // No need to apply incremental insertion if the old text (text to be 75 // No need to apply incremental insertion if the old text (text to be
79 // replaced) or the new text (text to be inserted) is empty. 76 // replaced) or the new text (text to be inserted) is empty.
80 if (frame.selectedText().isEmpty() || newText.isEmpty()) 77 if (frame.selectedText().isEmpty() || newText.isEmpty())
81 return false; 78 return false;
82 79
83 return true; 80 return true;
84 } 81 }
85 82
86 void dispatchBeforeInputFromComposition(EventTarget* target, 83 void dispatchBeforeInputFromComposition(EventTarget* target,
87 InputEvent::InputType inputType, 84 InputEvent::InputType inputType,
(...skipping 348 matching lines...) Expand 10 before | Expand all | Expand 10 after
436 unsigned offsetInPlainChars) { 433 unsigned offsetInPlainChars) {
437 for (const auto& underline : underlines) { 434 for (const auto& underline : underlines) {
438 unsigned underlineStart = offsetInPlainChars + underline.startOffset(); 435 unsigned underlineStart = offsetInPlainChars + underline.startOffset();
439 unsigned underlineEnd = offsetInPlainChars + underline.endOffset(); 436 unsigned underlineEnd = offsetInPlainChars + underline.endOffset();
440 437
441 EphemeralRange ephemeralLineRange = 438 EphemeralRange ephemeralLineRange =
442 PlainTextRange(underlineStart, underlineEnd).createRange(*baseElement); 439 PlainTextRange(underlineStart, underlineEnd).createRange(*baseElement);
443 if (ephemeralLineRange.isNull()) 440 if (ephemeralLineRange.isNull())
444 continue; 441 continue;
445 442
446 document().markers().addCompositionMarker( 443 if (underline.suggestions().isEmpty()) {
447 ephemeralLineRange, underline.color(), underline.thick(), 444 document().markers().addCompositionMarker(
448 underline.backgroundColor()); 445 ephemeralLineRange, underline.color(), underline.thick(),
446 underline.backgroundColor());
447 } else {
448 document().markers().addSuggestionMarker(
449 ephemeralLineRange,
450 underline.color(), underline.thick(), underline.backgroundColor(),
451 underline.suggestions());
452 }
449 } 453 }
450 } 454 }
451 455
452 bool InputMethodController::replaceCompositionAndMoveCaret( 456 bool InputMethodController::replaceCompositionAndMoveCaret(
453 const String& text, 457 const String& text,
454 int relativeCaretPosition, 458 int relativeCaretPosition,
455 const Vector<CompositionUnderline>& underlines) { 459 const Vector<CompositionUnderline>& underlines) {
456 Element* rootEditableElement = 460 Element* rootEditableElement =
457 frame() 461 frame()
458 .selection() 462 .selection()
459 .computeVisibleSelectionInDOMTreeDeprecated() 463 .computeVisibleSelectionInDOMTreeDeprecated()
460 .rootEditableElement(); 464 .rootEditableElement();
461 if (!rootEditableElement) 465 if (!rootEditableElement)
462 return false; 466 return false;
463 DCHECK(hasComposition()); 467 DCHECK(hasComposition());
464 PlainTextRange compositionRange = 468 PlainTextRange compositionRange =
465 PlainTextRange::create(*rootEditableElement, *m_compositionRange); 469 PlainTextRange::create(*rootEditableElement, *m_compositionRange);
466 if (compositionRange.isNull()) 470 if (compositionRange.isNull())
467 return false; 471 return false;
472
468 int textStart = compositionRange.start(); 473 int textStart = compositionRange.start();
469 474
470 if (!replaceComposition(text)) 475 if (!replaceComposition(text))
471 return false; 476 return false;
472 477
473 // TODO(xiaochengh): The use of updateStyleAndLayoutIgnorePendingStylesheets 478 // TODO(xiaochengh): The use of updateStyleAndLayoutIgnorePendingStylesheets
474 // needs to be audited. see http://crbug.com/590369 for more details. 479 // needs to be audited. see http://crbug.com/590369 for more details.
475 document().updateStyleAndLayoutIgnorePendingStylesheets(); 480 document().updateStyleAndLayoutIgnorePendingStylesheets();
476 481
477 addCompositionUnderlines(underlines, rootEditableElement, textStart); 482 addCompositionUnderlines(underlines, rootEditableElement, textStart);
(...skipping 11 matching lines...) Expand all
489 return true; 494 return true;
490 } 495 }
491 496
492 bool InputMethodController::insertTextAndMoveCaret( 497 bool InputMethodController::insertTextAndMoveCaret(
493 const String& text, 498 const String& text,
494 int relativeCaretPosition, 499 int relativeCaretPosition,
495 const Vector<CompositionUnderline>& underlines) { 500 const Vector<CompositionUnderline>& underlines) {
496 PlainTextRange selectionRange = getSelectionOffsets(); 501 PlainTextRange selectionRange = getSelectionOffsets();
497 if (selectionRange.isNull()) 502 if (selectionRange.isNull())
498 return false; 503 return false;
504
499 int textStart = selectionRange.start(); 505 int textStart = selectionRange.start();
500 506
501 if (text.length()) { 507 if (text.length()) {
502 if (!insertText(text)) 508 if (!insertText(text))
503 return false; 509 return false;
504 510
505 Element* rootEditableElement = 511 Element* rootEditableElement =
506 frame() 512 frame()
507 .selection() 513 .selection()
508 .computeVisibleSelectionInDOMTreeDeprecated() 514 .computeVisibleSelectionInDOMTreeDeprecated()
(...skipping 174 matching lines...) Expand 10 before | Expand all | Expand 10 after
683 baseNode->layoutObject()->setShouldDoFullPaintInvalidation(); 689 baseNode->layoutObject()->setShouldDoFullPaintInvalidation();
684 690
685 // TODO(xiaochengh): The use of updateStyleAndLayoutIgnorePendingStylesheets 691 // TODO(xiaochengh): The use of updateStyleAndLayoutIgnorePendingStylesheets
686 // needs to be audited. see http://crbug.com/590369 for more details. 692 // needs to be audited. see http://crbug.com/590369 for more details.
687 document().updateStyleAndLayoutIgnorePendingStylesheets(); 693 document().updateStyleAndLayoutIgnorePendingStylesheets();
688 694
689 // We shouldn't close typing in the middle of setComposition. 695 // We shouldn't close typing in the middle of setComposition.
690 setEditableSelectionOffsets(selectedRange, NotUserTriggered); 696 setEditableSelectionOffsets(selectedRange, NotUserTriggered);
691 697
692 if (underlines.isEmpty()) { 698 if (underlines.isEmpty()) {
699 // Don't add black underline when suggestion menu is open, the suggestion
700 // range already gets an underline
701 if (frame().textSuggestionController().suggestionMenuIsOpen())
702 return;
703
693 document().markers().addCompositionMarker( 704 document().markers().addCompositionMarker(
694 EphemeralRange(m_compositionRange), Color::black, false, 705 EphemeralRange(m_compositionRange), Color::black, false,
695 LayoutTheme::theme().platformDefaultCompositionBackgroundColor()); 706 LayoutTheme::theme().platformDefaultCompositionBackgroundColor());
696 return; 707 return;
697 } 708 }
698 709
699 const PlainTextRange compositionPlainTextRange = 710 const PlainTextRange compositionPlainTextRange =
700 PlainTextRange::create(*baseNode->parentNode(), *m_compositionRange); 711 PlainTextRange::create(*baseNode->parentNode(), *m_compositionRange);
701 addCompositionUnderlines(underlines, baseNode->parentNode(), 712 addCompositionUnderlines(underlines, baseNode->parentNode(),
702 compositionPlainTextRange.start()); 713 compositionPlainTextRange.start());
(...skipping 538 matching lines...) Expand 10 before | Expand all | Expand 10 after
1241 finishComposingText(KeepSelection); 1252 finishComposingText(KeepSelection);
1242 } 1253 }
1243 1254
1244 DEFINE_TRACE(InputMethodController) { 1255 DEFINE_TRACE(InputMethodController) {
1245 visitor->trace(m_frame); 1256 visitor->trace(m_frame);
1246 visitor->trace(m_compositionRange); 1257 visitor->trace(m_compositionRange);
1247 SynchronousMutationObserver::trace(visitor); 1258 SynchronousMutationObserver::trace(visitor);
1248 } 1259 }
1249 1260
1250 } // namespace blink 1261 } // namespace blink
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698