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

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

Issue 2393403002: Introduce Selection class (Closed)
Patch Set: 2016-10-12T13:54:28 Created 4 years, 2 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
(Empty)
1 // Copyright 2016 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "core/editing/SelectionTemplate.h"
6
7 #include "wtf/Assertions.h"
8 #include <ostream> // NOLINT
9
10 namespace blink {
11
12 template <typename Strategy>
13 SelectionTemplate<Strategy>::SelectionTemplate(const SelectionTemplate& other)
14 : m_base(other.m_base),
15 m_extent(other.m_extent),
16 m_affinity(other.m_affinity),
17 m_granularity(other.m_granularity),
18 m_hasTrailingWhitespace(other.m_hasTrailingWhitespace),
19 m_isDirectional(other.m_isDirectional)
20 #if DCHECK_IS_ON()
21 ,
22 m_domTreeVersion(other.m_domTreeVersion)
23 #endif
24 {
25 DCHECK(other.assertValid());
26 if (!m_hasTrailingWhitespace)
27 return;
28 DCHECK_EQ(m_granularity, WordGranularity) << *this;
29 }
30
31 template <typename Strategy>
32 SelectionTemplate<Strategy>::SelectionTemplate() = default;
33
34 template <typename Strategy>
35 bool SelectionTemplate<Strategy>::operator==(
36 const SelectionTemplate& other) const {
37 DCHECK(assertValid());
38 DCHECK(other.assertValid());
39 if (isNone())
40 return other.isNone();
41 if (other.isNone())
42 return false;
43 DCHECK_EQ(m_base.document(), other.document()) << *this << ' ' << other;
44 return m_base == other.m_base && m_extent == other.m_extent &&
45 m_affinity == other.m_affinity &&
46 m_granularity == other.m_granularity &&
47 m_hasTrailingWhitespace == other.m_hasTrailingWhitespace &&
48 m_isDirectional == other.m_isDirectional;
49 }
50
51 template <typename Strategy>
52 bool SelectionTemplate<Strategy>::operator!=(
53 const SelectionTemplate& other) const {
54 return !operator==(other);
55 }
56
57 template <typename Strategy>
58 const PositionTemplate<Strategy>& SelectionTemplate<Strategy>::base() const {
59 DCHECK(assertValid());
60 DCHECK(!m_base.isOrphan()) << m_base;
61 return m_base;
62 }
63
64 template <typename Strategy>
65 Document* SelectionTemplate<Strategy>::document() const {
66 DCHECK(assertValid());
67 return m_base.document();
68 }
69
70 template <typename Strategy>
71 const PositionTemplate<Strategy>& SelectionTemplate<Strategy>::extent() const {
72 DCHECK(assertValid());
73 DCHECK(!m_extent.isOrphan()) << m_extent;
74 return m_extent;
75 }
76
77 template <typename Strategy>
78 bool SelectionTemplate<Strategy>::assertValidFor(
79 const Document& document) const {
80 if (!assertValid())
81 return false;
82 if (m_base.isNull())
83 return true;
84 DCHECK_EQ(m_base.document(), document) << *this;
85 return true;
86 }
87
88 #if DCHECK_IS_ON()
89 template <typename Strategy>
90 bool SelectionTemplate<Strategy>::assertValid() const {
Xiaocheng 2016/10/12 05:09:42 I think we should check whether m_base and m_exten
yosin_UTC9 2016/10/12 06:22:54 Done.
91 if (m_base.isNull())
92 return true;
93 DCHECK_EQ(m_base.document()->domTreeVersion(), m_domTreeVersion) << *this;
94 DCHECK(!m_base.isOrphan()) << *this;
95 DCHECK(!m_extent.isOrphan()) << *this;
96 return true;
97 }
98 #else
99 template <typename Strategy>
100 bool SelectionTemplate<Strategy>::assertValid() const {
101 return true;
102 }
103 #endif
104
105 template <typename Strategy>
106 void SelectionTemplate<Strategy>::printTo(std::ostream* ostream,
107 const char* type) const {
108 if (isNone()) {
109 *ostream << "()";
110 return;
111 }
112 *ostream << type << '(';
113 #if DCHECK_IS_ON()
114 if (m_domTreeVersion != m_base.document()->domTreeVersion()) {
115 *ostream << "Dirty: " << m_domTreeVersion;
116 *ostream << " != " << m_base.document()->domTreeVersion() << ' ';
117 }
118 #endif
119 *ostream << "base: " << m_base << ", extent: " << m_extent << ')';
120 }
121
122 std::ostream& operator<<(std::ostream& ostream,
123 const SelectionInDOMTree& selection) {
124 selection.printTo(&ostream, "Selection");
125 return ostream;
126 }
127
128 std::ostream& operator<<(std::ostream& ostream,
129 const SelectionInFlatTree& selection) {
130 selection.printTo(&ostream, "SelectionInFlatTree");
131 return ostream;
132 }
133
134 // --
135
136 template <typename Strategy>
137 SelectionTemplate<Strategy>::Builder::Builder(
138 const SelectionTemplate<Strategy>& selection)
139 : m_selection(selection) {}
140
141 template <typename Strategy>
142 SelectionTemplate<Strategy>::Builder::Builder() = default;
143
144 template <typename Strategy>
145 SelectionTemplate<Strategy> SelectionTemplate<Strategy>::Builder::build()
146 const {
147 DCHECK(m_selection.assertValid());
148 return m_selection;
149 }
150
151 template <typename Strategy>
152 typename SelectionTemplate<Strategy>::Builder&
153 SelectionTemplate<Strategy>::Builder::collapse(
154 const PositionTemplate<Strategy>& position) {
155 DCHECK(position.isConnected());
156 m_selection.m_base = position;
157 m_selection.m_extent = position;
158 #if DCHECK_IS_ON()
159 m_selection.m_domTreeVersion = position.document()->domTreeVersion();
160 #endif
161 return *this;
162 }
163
164 template <typename Strategy>
165 typename SelectionTemplate<Strategy>::Builder&
166 SelectionTemplate<Strategy>::Builder::collapse(
167 const PositionWithAffinityTemplate<Strategy>& positionWithAffinity) {
168 collapse(positionWithAffinity.position());
169 setAffinity(positionWithAffinity.affinity());
170 return *this;
171 }
172
173 template <typename Strategy>
174 typename SelectionTemplate<Strategy>::Builder&
175 SelectionTemplate<Strategy>::Builder::extend(
Xiaocheng 2016/10/12 05:09:42 I think we should DCHECK_EQ(m_selection.base().doc
yosin_UTC9 2016/10/12 06:22:54 Done.
176 const PositionTemplate<Strategy>& position) {
177 DCHECK(position.isConnected());
178 DCHECK(m_selection.base().isConnected());
179 DCHECK(m_selection.assertValid());
180 m_selection.m_extent = position;
181 return *this;
182 }
183
184 template <typename Strategy>
185 typename SelectionTemplate<Strategy>::Builder&
186 SelectionTemplate<Strategy>::Builder::setAffinity(TextAffinity affinity) {
187 m_selection.m_affinity = affinity;
188 return *this;
189 }
190
191 template <typename Strategy>
192 typename SelectionTemplate<Strategy>::Builder&
193 SelectionTemplate<Strategy>::Builder::setBaseAndExtent(
194 const EphemeralRangeTemplate<Strategy>& range) {
195 if (range.isNull()) {
196 m_selection.m_base = PositionTemplate<Strategy>();
197 m_selection.m_extent = PositionTemplate<Strategy>();
198 #if DCHECK_IS_ON()
199 m_selection.m_domTreeVersion = 0;
200 #endif
201 return *this;
202 }
203 return collapse(range.startPosition()).extend(range.endPosition());
204 }
205
206 template <typename Strategy>
207 typename SelectionTemplate<Strategy>::Builder&
208 SelectionTemplate<Strategy>::Builder::setBaseAndExtent(
209 const PositionTemplate<Strategy>& base,
210 const PositionTemplate<Strategy>& extent) {
211 if (base.isNull()) {
212 DCHECK(extent.isNull()) << extent;
213 return setBaseAndExtent(EphemeralRangeTemplate<Strategy>());
214 }
215 DCHECK(extent.isNotNull());
216 return collapse(base).extend(extent);
217 }
218
219 template <typename Strategy>
220 typename SelectionTemplate<Strategy>::Builder&
221 SelectionTemplate<Strategy>::Builder::setBaseAndExtentDeprecated(
222 const PositionTemplate<Strategy>& base,
223 const PositionTemplate<Strategy>& extent) {
224 if (base.isNotNull() && extent.isNotNull()) {
225 return setBaseAndExtent(base, extent);
226 }
227 if (base.isNotNull())
228 return collapse(base);
229 if (extent.isNotNull())
230 return collapse(extent);
231 return setBaseAndExtent(EphemeralRangeTemplate<Strategy>());
232 }
233
234 template <typename Strategy>
235 typename SelectionTemplate<Strategy>::Builder&
236 SelectionTemplate<Strategy>::Builder::setGranularity(
237 TextGranularity granularity) {
238 m_selection.m_granularity = granularity;
239 return *this;
240 }
241
242 template <typename Strategy>
243 typename SelectionTemplate<Strategy>::Builder&
244 SelectionTemplate<Strategy>::Builder::setHasTrailingWhitespace(
245 bool hasTrailingWhitespace) {
246 m_selection.m_hasTrailingWhitespace = hasTrailingWhitespace;
247 return *this;
248 }
249
250 template <typename Strategy>
251 typename SelectionTemplate<Strategy>::Builder&
252 SelectionTemplate<Strategy>::Builder::setIsDirectional(bool isDirectional) {
253 m_selection.m_isDirectional = isDirectional;
254 return *this;
255 }
256
257 template class CORE_TEMPLATE_EXPORT SelectionTemplate<EditingStrategy>;
258 template class CORE_TEMPLATE_EXPORT
259 SelectionTemplate<EditingInFlatTreeStrategy>;
260
261 } // namespace blink
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698