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

Side by Side Diff: Source/core/editing/FrameSelection.cpp

Issue 988023005: Implementing directional selection strategy in Blink. (Closed) Base URL: https://chromium.googlesource.com/chromium/blink.git@master
Patch Set: Created 5 years, 9 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
« no previous file with comments | « Source/core/editing/FrameSelection.h ('k') | Source/core/editing/FrameSelectionTest.cpp » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /* 1 /*
2 * Copyright (C) 2004, 2008, 2009, 2010 Apple Inc. All rights reserved. 2 * Copyright (C) 2004, 2008, 2009, 2010 Apple Inc. All rights reserved.
3 * 3 *
4 * Redistribution and use in source and binary forms, with or without 4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions 5 * modification, are permitted provided that the following conditions
6 * are met: 6 * are met:
7 * 1. Redistributions of source code must retain the above copyright 7 * 1. Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer. 8 * notice, this list of conditions and the following disclaimer.
9 * 2. Redistributions in binary form must reproduce the above copyright 9 * 2. Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the 10 * notice, this list of conditions and the following disclaimer in the
(...skipping 74 matching lines...) Expand 10 before | Expand all | Expand 10 after
85 static inline LayoutUnit NoXPosForVerticalArrowNavigation() 85 static inline LayoutUnit NoXPosForVerticalArrowNavigation()
86 { 86 {
87 return LayoutUnit::min(); 87 return LayoutUnit::min();
88 } 88 }
89 89
90 static inline bool shouldAlwaysUseDirectionalSelection(LocalFrame* frame) 90 static inline bool shouldAlwaysUseDirectionalSelection(LocalFrame* frame)
91 { 91 {
92 return !frame || frame->editor().behavior().shouldConsiderSelectionAsDirecti onal(); 92 return !frame || frame->editor().behavior().shouldConsiderSelectionAsDirecti onal();
93 } 93 }
94 94
95 class GranularityStrategy {
96 public:
97 virtual ~GranularityStrategy() { };
98 virtual void Clear();
99 // Returns the selection extent based on the strategy.
100 virtual VisiblePosition moveRangeSelectionExtent(const VisiblePosition&, Fra meSelection*);
101 protected:
102 GranularityStrategy() { };
103 };
104
105 class DefaultGranularityStrategy : public GranularityStrategy {
106 public:
107 DefaultGranularityStrategy() { };
108 ~DefaultGranularityStrategy() override { };
109
110 void Clear() override { };
111 VisiblePosition moveRangeSelectionExtent(const VisiblePosition&, FrameSelect ion*) override
112 {
113 return extentPosition;
114 };
115 };
116
117 // Uses word granularity when selection is expanding. Uses character granularity when selection is shrinking.
118 class DirectionGranularityStrategy : public GranularityStrategy {
119 public:
120 DirectionGranularityStrategy();
121 ~DirectionGranularityStrategy() override { };
122
123 void Clear() override;
124 VisiblePosition moveRangeSelectionExtent(const VisiblePosition&, FrameSelect ion*) override;
125 private:
126 // Returns the next word boundary starting from |pos|. |direction| specifies the direction
127 // in which to search for the next bound. nextIfOnBound controls whether |po s| or the next boundary
128 // is returned when |pos| is located exactly on word boundary.
129 VisiblePosition nextWordBound(const VisiblePosition& /*pos*/, int /*directio n*/, bool /*nextIfOnBound*/);
130
131 // Current selection granularity being used
132 TextGranularity m_granularity;
133 // If the selection extent is extended beyond this threshold - the granulari ty will be changed to WordGranularity
134 VisiblePosition m_wordBoundary;
135 // Cached extentPosition passed in moveRangeSelectionExtent
136 VisiblePosition m_extentPosition;
137 };
138
139 DirectionGranularityStrategy::DirectionGranularityStrategy()
140 : m_granularity(CharacterGranularity) { }
141
142 void DirectionGranularityStrategy::Clear()
143 {
144 m_wordBoundary.clear();
145 m_extentPosition.clear();
146 m_granularity = CharacterGranularity;
147 }
148
149 VisiblePosition DirectionGranularityStrategy::nextWordBound(
150 const VisiblePosition& pos,
151 int direction,
152 bool nextIfOnBound)
153 {
154 return direction > 0 ? endOfWord(pos, nextIfOnBound ? RightWordIfOnBoundary : LeftWordIfOnBoundary)
155 : startOfWord(pos, nextIfOnBound ? LeftWordIfOnBoundary : RightWordIfOnB oundary);
156 }
157
158 VisiblePosition DirectionGranularityStrategy::moveRangeSelectionExtent(const Vis iblePosition& extentPosition, FrameSelection* fs)
159 {
160 fprintf(stderr, "DirectionGranularityStrategy::moveRangeSelectionExtent, ext entPosition offset=%d, characterBefore=%c, characterAfter=%c\n",
161 extentPosition.deepEquivalent().offsetInContainerNode(), extentPosition. characterBefore(), extentPosition.characterAfter());
162
163 const VisibleSelection& oldSel = fs->selection();
164 const VisiblePosition& base = oldSel.isBaseFirst() ? oldSel.visibleStart() : oldSel.visibleEnd();
yosin_UTC9 2015/03/10 01:37:03 nit: Just use |visibleBase()|.
165 const VisiblePosition& oldExtent = oldSel.isBaseFirst() ? oldSel.visibleEnd( ) : oldSel.visibleStart();
yosin_UTC9 2015/03/10 01:37:03 nit: Just use |visibleExtent()|.
166
167 int extentBaseOrder = comparePositions(extentPosition, base);
168 int oldExtentBaseOrder = comparePositions(oldExtent, base);
169 ASSERT(extentBaseOrder != 0);
170
171 bool extentBaseOrderChanged = extentBaseOrder * oldExtentBaseOrder < 0;
172
173 if (m_wordBoundary.isNull()) {
174 fprintf(stderr, "m_ThresholdEnd.isNull()\n");
175 ASSERT(m_extentPosition.isNull());
176 ASSERT(m_granularity == CharacterGranularity);
177 m_wordBoundary = nextWordBound(oldExtent, extentBaseOrder, false);
178 m_extentPosition = extentPosition;
179 }
180 if (extentBaseOrderChanged) {
181 fprintf(stderr, "extentBaseOrderSwitched, old m_wordBoundary=%d\n",
182 m_wordBoundary.deepEquivalent().offsetInContainerNode());
183 m_wordBoundary = nextWordBound(base, extentBaseOrder, true);
184 m_granularity = CharacterGranularity;
185 fprintf(stderr, "new m_wordBoundary=%d\n",
186 m_wordBoundary.deepEquivalent().offsetInContainerNode());
187 }
188 bool beyondWordBoundary = extentBaseOrder > 0 ? comparePositions(extentPosit ion, m_wordBoundary) > 0
189 : comparePositions(extentPosition, m_wordBoundary) < 0;
190 fprintf(stderr, "m_wordBoundary=%d, beyondWordBoundary=%d, order=%d\n",
191 m_wordBoundary.deepEquivalent().offsetInContainerNode(), beyondWordBound ary, extentBaseOrder);
192 if (beyondWordBoundary) {
193 if (m_granularity == CharacterGranularity)
194 m_granularity = WordGranularity;
195 // The value passed for |nextIfOnBound| doesn't matter here.
196 m_wordBoundary = nextWordBound(extentPosition, extentBaseOrder, true);
197 } else if (!extentBaseOrderChanged) {
198 // If selection was shrunk - switch to character granularity
199 if (extentBaseOrder * comparePositions(extentPosition, m_extentPosition) < 0) {
200 m_granularity = CharacterGranularity;
201 m_wordBoundary = nextWordBound(extentPosition, extentBaseOrder, true );
202 }
203 }
204 m_extentPosition = extentPosition;
205
206 VisiblePosition visibleExtent = extentPosition;
207 if (m_granularity == WordGranularity) {
208 fprintf(stderr, "m_extendGranularity == WordGranularity\n");
209 visibleExtent = nextWordBound(extentPosition, extentBaseOrder, false);
210 }
211
212 return visibleExtent;
213 }
214
95 FrameSelection::FrameSelection(LocalFrame* frame) 215 FrameSelection::FrameSelection(LocalFrame* frame)
96 : m_frame(frame) 216 : m_frame(frame)
97 , m_xPosForVerticalArrowNavigation(NoXPosForVerticalArrowNavigation()) 217 , m_xPosForVerticalArrowNavigation(NoXPosForVerticalArrowNavigation())
98 , m_observingVisibleSelection(false) 218 , m_observingVisibleSelection(false)
99 , m_granularity(CharacterGranularity) 219 , m_granularity(CharacterGranularity)
100 , m_caretBlinkTimer(this, &FrameSelection::caretBlinkTimerFired) 220 , m_caretBlinkTimer(this, &FrameSelection::caretBlinkTimerFired)
101 , m_caretRectDirty(true) 221 , m_caretRectDirty(true)
102 , m_shouldPaintCaret(true) 222 , m_shouldPaintCaret(true)
103 , m_isCaretBlinkingSuspended(false) 223 , m_isCaretBlinkingSuspended(false)
104 , m_focused(frame && frame->page() && frame->page()->focusController().focus edFrame() == frame) 224 , m_focused(frame && frame->page() && frame->page()->focusController().focus edFrame() == frame)
105 , m_shouldShowBlockCursor(false) 225 , m_shouldShowBlockCursor(false)
106 { 226 {
107 if (shouldAlwaysUseDirectionalSelection(m_frame)) 227 if (shouldAlwaysUseDirectionalSelection(m_frame))
108 m_selection.setIsDirectional(true); 228 m_selection.setIsDirectional(true);
229 m_granularityStrategy = adoptPtr(new DirectionGranularityStrategy());
109 } 230 }
110 231
111 FrameSelection::~FrameSelection() 232 FrameSelection::~FrameSelection()
112 { 233 {
113 #if !ENABLE(OILPAN) 234 #if !ENABLE(OILPAN)
114 // Oilpan: No need to clear out VisibleSelection observer; 235 // Oilpan: No need to clear out VisibleSelection observer;
115 // it is finalized as a part object of FrameSelection. 236 // it is finalized as a part object of FrameSelection.
116 stopObservingVisibleSelectionChangeIfNecessary(); 237 stopObservingVisibleSelectionChangeIfNecessary();
117 #endif 238 #endif
118 } 239 }
119 240
120 Element* FrameSelection::rootEditableElementOrDocumentElement() const 241 Element* FrameSelection::rootEditableElementOrDocumentElement() const
121 { 242 {
122 Element* selectionRoot = m_selection.rootEditableElement(); 243 Element* selectionRoot = m_selection.rootEditableElement();
123 return selectionRoot ? selectionRoot : m_frame->document()->documentElement( ); 244 return selectionRoot ? selectionRoot : m_frame->document()->documentElement( );
124 } 245 }
125 246
126 ContainerNode* FrameSelection::rootEditableElementOrTreeScopeRootNode() const 247 ContainerNode* FrameSelection::rootEditableElementOrTreeScopeRootNode() const
127 { 248 {
128 Element* selectionRoot = m_selection.rootEditableElement(); 249 Element* selectionRoot = m_selection.rootEditableElement();
129 if (selectionRoot) 250 if (selectionRoot)
130 return selectionRoot; 251 return selectionRoot;
131 252
132 Node* node = m_selection.base().containerNode(); 253 Node* node = m_selection.base().containerNode();
133 return node ? &node->treeScope().rootNode() : 0; 254 return node ? &node->treeScope().rootNode() : 0;
134 } 255 }
135 256
136 void FrameSelection::moveTo(const VisiblePosition &pos, EUserTriggered userTrigg ered, CursorAlignOnScroll align) 257 void FrameSelection::moveTo(const VisiblePosition &pos, EUserTriggered userTrigg ered, CursorAlignOnScroll align)
137 { 258 {
259 fprintf(stderr, "FrameSelection::moveTo 1");
138 SetSelectionOptions options = CloseTyping | ClearTypingStyle | userTriggered ; 260 SetSelectionOptions options = CloseTyping | ClearTypingStyle | userTriggered ;
139 setSelection(VisibleSelection(pos.deepEquivalent(), pos.deepEquivalent(), po s.affinity(), m_selection.isDirectional()), options, align); 261 setSelection(VisibleSelection(pos.deepEquivalent(), pos.deepEquivalent(), po s.affinity(), m_selection.isDirectional()), options, align);
140 } 262 }
141 263
142 void FrameSelection::moveTo(const VisiblePosition &base, const VisiblePosition & extent, EUserTriggered userTriggered) 264 void FrameSelection::moveTo(const VisiblePosition &base, const VisiblePosition & extent, EUserTriggered userTriggered)
143 { 265 {
266 fprintf(stderr, "FrameSelection::moveTo 2");
144 const bool selectionHasDirection = true; 267 const bool selectionHasDirection = true;
145 SetSelectionOptions options = CloseTyping | ClearTypingStyle | userTriggered ; 268 SetSelectionOptions options = CloseTyping | ClearTypingStyle | userTriggered ;
146 setSelection(VisibleSelection(base.deepEquivalent(), extent.deepEquivalent() , base.affinity(), selectionHasDirection), options); 269 setSelection(VisibleSelection(base.deepEquivalent(), extent.deepEquivalent() , base.affinity(), selectionHasDirection), options);
147 } 270 }
148 271
149 void FrameSelection::moveTo(const Position &pos, EAffinity affinity, EUserTrigge red userTriggered) 272 void FrameSelection::moveTo(const Position &pos, EAffinity affinity, EUserTrigge red userTriggered)
150 { 273 {
274 fprintf(stderr, "FrameSelection::moveTo 3");
151 SetSelectionOptions options = CloseTyping | ClearTypingStyle | userTriggered ; 275 SetSelectionOptions options = CloseTyping | ClearTypingStyle | userTriggered ;
152 setSelection(VisibleSelection(pos, affinity, m_selection.isDirectional()), o ptions); 276 setSelection(VisibleSelection(pos, affinity, m_selection.isDirectional()), o ptions);
153 } 277 }
154 278
155 static void adjustEndpointsAtBidiBoundary(VisiblePosition& visibleBase, VisibleP osition& visibleExtent) 279 static void adjustEndpointsAtBidiBoundary(VisiblePosition& visibleBase, VisibleP osition& visibleExtent)
156 { 280 {
157 RenderedPosition base(visibleBase); 281 RenderedPosition base(visibleBase);
158 RenderedPosition extent(visibleExtent); 282 RenderedPosition extent(visibleExtent);
159 283
160 if (base.isNull() || extent.isNull() || base.isEquivalent(extent)) 284 if (base.isNull() || extent.isNull() || base.isEquivalent(extent))
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after
209 } else if (m_originalBase.isNotNull()) { 333 } else if (m_originalBase.isNotNull()) {
210 if (m_selection.base() == newSelection.base()) 334 if (m_selection.base() == newSelection.base())
211 newSelection.setBase(m_originalBase); 335 newSelection.setBase(m_originalBase);
212 m_originalBase.clear(); 336 m_originalBase.clear();
213 } 337 }
214 338
215 newSelection.setIsDirectional(isDirectional); // Adjusting base and extent w ill make newSelection always directional 339 newSelection.setIsDirectional(isDirectional); // Adjusting base and extent w ill make newSelection always directional
216 if (m_selection == newSelection) 340 if (m_selection == newSelection)
217 return; 341 return;
218 342
343 fprintf(stderr, "FrameSelection::setNonDirectionalSelectionIfNeeded");
219 setSelection(newSelection, granularity); 344 setSelection(newSelection, granularity);
220 } 345 }
221 346
222 void FrameSelection::setSelection(const VisibleSelection& newSelection, SetSelec tionOptions options, CursorAlignOnScroll align, TextGranularity granularity) 347 void FrameSelection::setSelection(const VisibleSelection& newSelection, SetSelec tionOptions options, CursorAlignOnScroll align, TextGranularity granularity)
223 { 348 {
349 if ((options & FrameSelection::ApplyStrategy) == 0)
350 m_granularityStrategy->Clear();
224 bool closeTyping = options & CloseTyping; 351 bool closeTyping = options & CloseTyping;
225 bool shouldClearTypingStyle = options & ClearTypingStyle; 352 bool shouldClearTypingStyle = options & ClearTypingStyle;
226 EUserTriggered userTriggered = selectionOptionsToUserTriggered(options); 353 EUserTriggered userTriggered = selectionOptionsToUserTriggered(options);
227 354
228 VisibleSelection s = validateSelection(newSelection); 355 VisibleSelection s = validateSelection(newSelection);
229 if (shouldAlwaysUseDirectionalSelection(m_frame)) 356 if (shouldAlwaysUseDirectionalSelection(m_frame))
230 s.setIsDirectional(true); 357 s.setIsDirectional(true);
231 358
232 if (!m_frame) { 359 if (!m_frame) {
233 m_selection = s; 360 m_selection = s;
(...skipping 238 matching lines...) Expand 10 before | Expand all | Expand 10 after
472 599
473 void FrameSelection::updateSelectionIfNeeded(const Position& base, const Positio n& extent, const Position& start, const Position& end) 600 void FrameSelection::updateSelectionIfNeeded(const Position& base, const Positio n& extent, const Position& start, const Position& end)
474 { 601 {
475 if (base == m_selection.base() && extent == m_selection.extent() && start == m_selection.start() && end == m_selection.end()) 602 if (base == m_selection.base() && extent == m_selection.extent() && start == m_selection.start() && end == m_selection.end())
476 return; 603 return;
477 VisibleSelection newSelection; 604 VisibleSelection newSelection;
478 if (m_selection.isBaseFirst()) 605 if (m_selection.isBaseFirst())
479 newSelection.setWithoutValidation(start, end); 606 newSelection.setWithoutValidation(start, end);
480 else 607 else
481 newSelection.setWithoutValidation(end, start); 608 newSelection.setWithoutValidation(end, start);
609 fprintf(stderr, "FrameSelection::updateSelectionIfNeeded");
482 setSelection(newSelection, DoNotSetFocus); 610 setSelection(newSelection, DoNotSetFocus);
483 } 611 }
484 612
485 TextDirection FrameSelection::directionOfEnclosingBlock() 613 TextDirection FrameSelection::directionOfEnclosingBlock()
486 { 614 {
487 return blink::directionOfEnclosingBlock(m_selection.extent()); 615 return blink::directionOfEnclosingBlock(m_selection.extent());
488 } 616 }
489 617
490 TextDirection FrameSelection::directionOfSelection() 618 TextDirection FrameSelection::directionOfSelection()
491 { 619 {
(...skipping 447 matching lines...) Expand 10 before | Expand all | Expand 10 after
939 1067
940 static bool isBoundary(TextGranularity granularity) 1068 static bool isBoundary(TextGranularity granularity)
941 { 1069 {
942 return granularity == LineBoundary || granularity == ParagraphBoundary || gr anularity == DocumentBoundary; 1070 return granularity == LineBoundary || granularity == ParagraphBoundary || gr anularity == DocumentBoundary;
943 } 1071 }
944 1072
945 bool FrameSelection::modify(EAlteration alter, SelectionDirection direction, Tex tGranularity granularity, EUserTriggered userTriggered) 1073 bool FrameSelection::modify(EAlteration alter, SelectionDirection direction, Tex tGranularity granularity, EUserTriggered userTriggered)
946 { 1074 {
947 if (userTriggered == UserTriggered) { 1075 if (userTriggered == UserTriggered) {
948 OwnPtrWillBeRawPtr<FrameSelection> trialFrameSelection = FrameSelection: :create(); 1076 OwnPtrWillBeRawPtr<FrameSelection> trialFrameSelection = FrameSelection: :create();
1077 fprintf(stderr, "FrameSelection::modify 4");
949 trialFrameSelection->setSelection(m_selection); 1078 trialFrameSelection->setSelection(m_selection);
950 trialFrameSelection->modify(alter, direction, granularity, NotUserTrigge red); 1079 trialFrameSelection->modify(alter, direction, granularity, NotUserTrigge red);
951 1080
952 if (trialFrameSelection->selection().isRange() && m_selection.isCaret() && !dispatchSelectStart()) 1081 if (trialFrameSelection->selection().isRange() && m_selection.isCaret() && !dispatchSelectStart())
953 return false; 1082 return false;
954 } 1083 }
955 1084
956 willBeModified(alter, direction); 1085 willBeModified(alter, direction);
957 1086
958 bool wasRange = m_selection.isRange(); 1087 bool wasRange = m_selection.isRange();
(...skipping 94 matching lines...) Expand 10 before | Expand all | Expand 10 after
1053 return true; 1182 return true;
1054 } 1183 }
1055 1184
1056 bool FrameSelection::modify(EAlteration alter, unsigned verticalDistance, Vertic alDirection direction, EUserTriggered userTriggered, CursorAlignOnScroll align) 1185 bool FrameSelection::modify(EAlteration alter, unsigned verticalDistance, Vertic alDirection direction, EUserTriggered userTriggered, CursorAlignOnScroll align)
1057 { 1186 {
1058 if (!verticalDistance) 1187 if (!verticalDistance)
1059 return false; 1188 return false;
1060 1189
1061 if (userTriggered == UserTriggered) { 1190 if (userTriggered == UserTriggered) {
1062 OwnPtrWillBeRawPtr<FrameSelection> trialFrameSelection = FrameSelection: :create(); 1191 OwnPtrWillBeRawPtr<FrameSelection> trialFrameSelection = FrameSelection: :create();
1192 fprintf(stderr, "FrameSelection::modify 5");
1063 trialFrameSelection->setSelection(m_selection); 1193 trialFrameSelection->setSelection(m_selection);
1064 trialFrameSelection->modify(alter, verticalDistance, direction, NotUserT riggered); 1194 trialFrameSelection->modify(alter, verticalDistance, direction, NotUserT riggered);
1065 } 1195 }
1066 1196
1067 willBeModified(alter, direction == DirectionUp ? DirectionBackward : Directi onForward); 1197 willBeModified(alter, direction == DirectionUp ? DirectionBackward : Directi onForward);
1068 1198
1069 VisiblePosition pos; 1199 VisiblePosition pos;
1070 LayoutUnit xPos = 0; 1200 LayoutUnit xPos = 0;
1071 switch (alter) { 1201 switch (alter) {
1072 case AlterationMove: 1202 case AlterationMove:
(...skipping 93 matching lines...) Expand 10 before | Expand all | Expand 10 after
1166 m_xPosForVerticalArrowNavigation = x; 1296 m_xPosForVerticalArrowNavigation = x;
1167 } else 1297 } else
1168 x = m_xPosForVerticalArrowNavigation; 1298 x = m_xPosForVerticalArrowNavigation;
1169 1299
1170 return x; 1300 return x;
1171 } 1301 }
1172 1302
1173 void FrameSelection::clear() 1303 void FrameSelection::clear()
1174 { 1304 {
1175 m_granularity = CharacterGranularity; 1305 m_granularity = CharacterGranularity;
1306 fprintf(stderr, "FrameSelection::clear");
1307 m_granularityStrategy->Clear();
1176 setSelection(VisibleSelection()); 1308 setSelection(VisibleSelection());
1177 } 1309 }
1178 1310
1179 void FrameSelection::prepareForDestruction() 1311 void FrameSelection::prepareForDestruction()
1180 { 1312 {
1181 m_granularity = CharacterGranularity; 1313 m_granularity = CharacterGranularity;
1182 1314
1183 m_caretBlinkTimer.stop(); 1315 m_caretBlinkTimer.stop();
1184 1316
1185 LayoutView* view = m_frame->contentRenderer(); 1317 LayoutView* view = m_frame->contentRenderer();
1186 if (view) 1318 if (view)
1187 view->clearSelection(); 1319 view->clearSelection();
1188 1320
1321 fprintf(stderr, "FrameSelection::prepareForDestruction");
1189 setSelection(VisibleSelection(), CloseTyping | ClearTypingStyle | DoNotUpdat eAppearance); 1322 setSelection(VisibleSelection(), CloseTyping | ClearTypingStyle | DoNotUpdat eAppearance);
1190 m_previousCaretNode.clear(); 1323 m_previousCaretNode.clear();
1191 } 1324 }
1192 1325
1193 void FrameSelection::setStart(const VisiblePosition &pos, EUserTriggered trigger ) 1326 void FrameSelection::setStart(const VisiblePosition &pos, EUserTriggered trigger )
1194 { 1327 {
1195 if (m_selection.isBaseFirst()) 1328 if (m_selection.isBaseFirst())
1196 setBase(pos, trigger); 1329 setBase(pos, trigger);
1197 else 1330 else
1198 setExtent(pos, trigger); 1331 setExtent(pos, trigger);
1199 } 1332 }
1200 1333
1201 void FrameSelection::setEnd(const VisiblePosition &pos, EUserTriggered trigger) 1334 void FrameSelection::setEnd(const VisiblePosition &pos, EUserTriggered trigger)
1202 { 1335 {
1203 if (m_selection.isBaseFirst()) 1336 if (m_selection.isBaseFirst())
1204 setExtent(pos, trigger); 1337 setExtent(pos, trigger);
1205 else 1338 else
1206 setBase(pos, trigger); 1339 setBase(pos, trigger);
1207 } 1340 }
1208 1341
1209 void FrameSelection::setBase(const VisiblePosition &pos, EUserTriggered userTrig gered) 1342 void FrameSelection::setBase(const VisiblePosition &pos, EUserTriggered userTrig gered)
1210 { 1343 {
1211 const bool selectionHasDirection = true; 1344 const bool selectionHasDirection = true;
1345 fprintf(stderr, "FrameSelection::setBase");
1212 setSelection(VisibleSelection(pos.deepEquivalent(), m_selection.extent(), po s.affinity(), selectionHasDirection), CloseTyping | ClearTypingStyle | userTrigg ered); 1346 setSelection(VisibleSelection(pos.deepEquivalent(), m_selection.extent(), po s.affinity(), selectionHasDirection), CloseTyping | ClearTypingStyle | userTrigg ered);
1213 } 1347 }
1214 1348
1215 void FrameSelection::setExtent(const VisiblePosition &pos, EUserTriggered userTr iggered) 1349 void FrameSelection::setExtent(const VisiblePosition &pos, EUserTriggered userTr iggered)
1216 { 1350 {
1217 const bool selectionHasDirection = true; 1351 const bool selectionHasDirection = true;
1352 fprintf(stderr, "FrameSelection::setExtent");
1218 setSelection(VisibleSelection(m_selection.base(), pos.deepEquivalent(), pos. affinity(), selectionHasDirection), CloseTyping | ClearTypingStyle | userTrigger ed); 1353 setSelection(VisibleSelection(m_selection.base(), pos.deepEquivalent(), pos. affinity(), selectionHasDirection), CloseTyping | ClearTypingStyle | userTrigger ed);
1219 } 1354 }
1220 1355
1221 LayoutBlock* FrameSelection::caretRenderer() const 1356 LayoutBlock* FrameSelection::caretRenderer() const
1222 { 1357 {
1223 return CaretBase::caretRenderer(m_selection.start().deprecatedNode()); 1358 return CaretBase::caretRenderer(m_selection.start().deprecatedNode());
1224 } 1359 }
1225 1360
1226 static bool isNonOrphanedCaret(const VisibleSelection& selection) 1361 static bool isNonOrphanedCaret(const VisibleSelection& selection)
1227 { 1362 {
(...skipping 132 matching lines...) Expand 10 before | Expand all | Expand 10 after
1360 return; 1495 return;
1361 1496
1362 // Create compute positions before and after the element. 1497 // Create compute positions before and after the element.
1363 unsigned ownerElementNodeIndex = ownerElement->nodeIndex(); 1498 unsigned ownerElementNodeIndex = ownerElement->nodeIndex();
1364 VisiblePosition beforeOwnerElement(VisiblePosition(Position(ownerElementPare nt, ownerElementNodeIndex, Position::PositionIsOffsetInAnchor))); 1499 VisiblePosition beforeOwnerElement(VisiblePosition(Position(ownerElementPare nt, ownerElementNodeIndex, Position::PositionIsOffsetInAnchor)));
1365 VisiblePosition afterOwnerElement(VisiblePosition(Position(ownerElementParen t, ownerElementNodeIndex + 1, Position::PositionIsOffsetInAnchor), VP_UPSTREAM_I F_POSSIBLE)); 1500 VisiblePosition afterOwnerElement(VisiblePosition(Position(ownerElementParen t, ownerElementNodeIndex + 1, Position::PositionIsOffsetInAnchor), VP_UPSTREAM_I F_POSSIBLE));
1366 1501
1367 // Focus on the parent frame, and then select from before this element to af ter. 1502 // Focus on the parent frame, and then select from before this element to af ter.
1368 VisibleSelection newSelection(beforeOwnerElement, afterOwnerElement); 1503 VisibleSelection newSelection(beforeOwnerElement, afterOwnerElement);
1369 page->focusController().setFocusedFrame(parent); 1504 page->focusController().setFocusedFrame(parent);
1505 fprintf(stderr, "FrameSelection::selectFrameElementInParentIfFullySelected") ;
1370 toLocalFrame(parent)->selection().setSelection(newSelection); 1506 toLocalFrame(parent)->selection().setSelection(newSelection);
1371 } 1507 }
1372 1508
1373 void FrameSelection::selectAll() 1509 void FrameSelection::selectAll()
1374 { 1510 {
1375 Document* document = m_frame->document(); 1511 Document* document = m_frame->document();
1376 1512
1377 if (isHTMLSelectElement(document->focusedElement())) { 1513 if (isHTMLSelectElement(document->focusedElement())) {
1378 HTMLSelectElement* selectElement = toHTMLSelectElement(document->focused Element()); 1514 HTMLSelectElement* selectElement = toHTMLSelectElement(document->focused Element());
1379 if (selectElement->canSelectAll()) { 1515 if (selectElement->canSelectAll()) {
(...skipping 19 matching lines...) Expand all
1399 selectStartTarget = document->body(); 1535 selectStartTarget = document->body();
1400 } 1536 }
1401 } 1537 }
1402 if (!root) 1538 if (!root)
1403 return; 1539 return;
1404 1540
1405 if (selectStartTarget && !selectStartTarget->dispatchEvent(Event::createCanc elableBubble(EventTypeNames::selectstart))) 1541 if (selectStartTarget && !selectStartTarget->dispatchEvent(Event::createCanc elableBubble(EventTypeNames::selectstart)))
1406 return; 1542 return;
1407 1543
1408 VisibleSelection newSelection(VisibleSelection::selectionFromContentsOfNode( root.get())); 1544 VisibleSelection newSelection(VisibleSelection::selectionFromContentsOfNode( root.get()));
1545 fprintf(stderr, "FrameSelection::selectAll");
1409 setSelection(newSelection); 1546 setSelection(newSelection);
1410 selectFrameElementInParentIfFullySelected(); 1547 selectFrameElementInParentIfFullySelected();
1411 notifyRendererOfSelectionChange(UserTriggered); 1548 notifyRendererOfSelectionChange(UserTriggered);
1412 } 1549 }
1413 1550
1414 bool FrameSelection::setSelectedRange(Range* range, EAffinity affinity, Directoi nalOption directional, SetSelectionOptions options) 1551 bool FrameSelection::setSelectedRange(Range* range, EAffinity affinity, Directoi nalOption directional, SetSelectionOptions options)
1415 { 1552 {
1416 if (!range || !range->startContainer() || !range->endContainer()) 1553 if (!range || !range->startContainer() || !range->endContainer())
1417 return false; 1554 return false;
1418 ASSERT(range->startContainer()->document() == range->endContainer()->documen t()); 1555 ASSERT(range->startContainer()->document() == range->endContainer()->documen t());
(...skipping 351 matching lines...) Expand 10 before | Expand all | Expand 10 after
1770 // FIXME: This code only handles scrolling the startContainer's layer, b ut 1907 // FIXME: This code only handles scrolling the startContainer's layer, b ut
1771 // the selection rect could intersect more than just that. 1908 // the selection rect could intersect more than just that.
1772 // See <rdar://problem/4799899>. 1909 // See <rdar://problem/4799899>.
1773 if (start.deprecatedNode()->renderer()->scrollRectToVisible(rect, alignm ent, alignment)) 1910 if (start.deprecatedNode()->renderer()->scrollRectToVisible(rect, alignm ent, alignment))
1774 updateAppearance(); 1911 updateAppearance();
1775 } 1912 }
1776 } 1913 }
1777 1914
1778 void FrameSelection::setSelectionFromNone() 1915 void FrameSelection::setSelectionFromNone()
1779 { 1916 {
1917 fprintf(stderr, "FrameSelection::setSelectionFromNone");
1780 // Put a caret inside the body if the entire frame is editable (either the 1918 // Put a caret inside the body if the entire frame is editable (either the
1781 // entire WebView is editable or designMode is on for this document). 1919 // entire WebView is editable or designMode is on for this document).
1782 1920
1783 Document* document = m_frame->document(); 1921 Document* document = m_frame->document();
1784 bool caretBrowsing = m_frame->settings() && m_frame->settings()->caretBrowsi ngEnabled(); 1922 bool caretBrowsing = m_frame->settings() && m_frame->settings()->caretBrowsi ngEnabled();
1785 if (!isNone() || !(document->hasEditableStyle() || caretBrowsing)) 1923 if (!isNone() || !(document->hasEditableStyle() || caretBrowsing))
1786 return; 1924 return;
1787 1925
1788 Element* documentElement = document->documentElement(); 1926 Element* documentElement = document->documentElement();
1789 if (!documentElement) 1927 if (!documentElement)
(...skipping 115 matching lines...) Expand 10 before | Expand all | Expand 10 after
1905 String text = plainText(start.deepEquivalent(), end.deepEquivalent()); 2043 String text = plainText(start.deepEquivalent(), end.deepEquivalent());
1906 if (!text.isEmpty() && !isSeparator(text.characterStartingAt(0))) { 2044 if (!text.isEmpty() && !isSeparator(text.characterStartingAt(0))) {
1907 setSelection(VisibleSelection(start, end), WordGranularity); 2045 setSelection(VisibleSelection(start, end), WordGranularity);
1908 return true; 2046 return true;
1909 } 2047 }
1910 } 2048 }
1911 2049
1912 return false; 2050 return false;
1913 } 2051 }
1914 2052
1915 void FrameSelection::moveRangeSelectionExtent(const VisiblePosition& extentPosit ion, TextGranularity granularity) 2053 void FrameSelection::moveRangeSelectionExtent(const VisiblePosition& extentPosit ion)
1916 { 2054 {
1917 if (isNone()) 2055 const VisiblePosition base = m_selection.isBaseFirst() ?
yosin_UTC9 2015/03/10 01:37:03 nit: Just use |visibleBase()|.
2056 m_selection.visibleStart() : m_selection.visibleEnd();
2057
2058 if (isNone() || comparePositions(base, extentPosition) == 0)
1918 return; 2059 return;
1919 2060
1920 const VisiblePosition basePosition = m_selection.isBaseFirst() ? 2061 VisiblePosition newExtentPosition = m_granularityStrategy->moveRangeSelectio nExtent(extentPosition, this);
1921 m_selection.visibleStart() : m_selection.visibleEnd(); 2062 VisibleSelection newSelection(base, newExtentPosition);
1922 2063 setSelection(
1923 int order = comparePositions(basePosition, extentPosition); 2064 newSelection,
1924 if (!order) 2065 FrameSelection::CloseTyping | FrameSelection::ClearTypingStyle | FrameSe lection::ApplyStrategy | UserTriggered,
1925 return; 2066 FrameSelection::AlignCursorOnScrollIfNeeded,
1926 2067 CharacterGranularity);
1927 // Currently we support only CharaterGranularity and WordGranurarity.
1928 // If |granurarity| is not of them, we fall back it to
1929 // CharacterGranularity.
1930 VisiblePosition newExtentPosition = extentPosition;
1931 if (granularity == WordGranularity)
1932 newExtentPosition = order < 0 ? endOfWord(extentPosition) : startOfWord( extentPosition);
1933
1934 VisibleSelection newSelection = VisibleSelection(basePosition, newExtentPosi tion);
1935 setSelection(newSelection, FrameSelection::CloseTyping | FrameSelection::Cle arTypingStyle | UserTriggered, FrameSelection::AlignCursorOnScrollIfNeeded, gran ularity);
1936 } 2068 }
1937 2069
1938 void FrameSelection::moveRangeSelection(const VisiblePosition& basePosition, con st VisiblePosition& extentPosition, TextGranularity granularity) 2070 void FrameSelection::moveRangeSelection(const VisiblePosition& basePosition, con st VisiblePosition& extentPosition, TextGranularity granularity)
1939 { 2071 {
2072 fprintf(stderr, "moveRangeSelection");
1940 VisibleSelection newSelection(basePosition, extentPosition); 2073 VisibleSelection newSelection(basePosition, extentPosition);
1941 newSelection.expandUsingGranularity(granularity); 2074 newSelection.expandUsingGranularity(granularity);
1942 2075
1943 if (newSelection.isNone()) 2076 if (newSelection.isNone())
1944 return; 2077 return;
1945 2078
1946 setSelection(newSelection, granularity); 2079 setSelection(newSelection, granularity);
1947 } 2080 }
1948 2081
1949 } 2082 }
1950 2083
1951 #ifndef NDEBUG 2084 #ifndef NDEBUG
1952 2085
1953 void showTree(const blink::FrameSelection& sel) 2086 void showTree(const blink::FrameSelection& sel)
1954 { 2087 {
1955 sel.showTreeForThis(); 2088 sel.showTreeForThis();
1956 } 2089 }
1957 2090
1958 void showTree(const blink::FrameSelection* sel) 2091 void showTree(const blink::FrameSelection* sel)
1959 { 2092 {
1960 if (sel) 2093 if (sel)
1961 sel->showTreeForThis(); 2094 sel->showTreeForThis();
1962 } 2095 }
1963 2096
1964 #endif 2097 #endif
OLDNEW
« no previous file with comments | « Source/core/editing/FrameSelection.h ('k') | Source/core/editing/FrameSelectionTest.cpp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698