OLD | NEW |
---|---|
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #ifndef UI_GFX_RENDER_TEXT_H_ | 5 #ifndef UI_GFX_RENDER_TEXT_H_ |
6 #define UI_GFX_RENDER_TEXT_H_ | 6 #define UI_GFX_RENDER_TEXT_H_ |
7 #pragma once | 7 #pragma once |
8 | 8 |
9 #include <algorithm> | 9 #include <algorithm> |
10 #include <vector> | 10 #include <vector> |
(...skipping 72 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
83 LINE_BREAK, | 83 LINE_BREAK, |
84 }; | 84 }; |
85 | 85 |
86 // Horizontal text alignment styles. | 86 // Horizontal text alignment styles. |
87 enum HorizontalAlignment { | 87 enum HorizontalAlignment { |
88 ALIGN_LEFT, | 88 ALIGN_LEFT, |
89 ALIGN_CENTER, | 89 ALIGN_CENTER, |
90 ALIGN_RIGHT, | 90 ALIGN_RIGHT, |
91 }; | 91 }; |
92 | 92 |
93 // VisualCursorDirection and LogicalCursorDirection represent directions of | |
94 // motion of the cursor in BiDi text. The combinations that make sense are: | |
95 // | |
96 // base::i18n::TextDirection VisualCursorDirection LogicalCursorDirection | |
97 // LEFT_TO_RIGHT CURSOR_LEFT CURSOR_BACKWARD | |
98 // LEFT_TO_RIGHT CURSOR_RIGHT CURSOR_FORWARD | |
99 // RIGHT_TO_LEFT CURSOR_RIGHT CURSOR_BACKWARD | |
100 // RIGHT_TO_LEFT CURSOR_LEFT CURSOR_FORWARD | |
101 enum VisualCursorDirection { | |
102 CURSOR_LEFT, | |
103 CURSOR_RIGHT | |
104 }; | |
105 enum LogicalCursorDirection { | |
106 CURSOR_BACKWARD, | |
107 CURSOR_FORWARD | |
108 }; | |
109 | |
110 // RenderText represents an abstract model of styled text and its corresponding | 93 // RenderText represents an abstract model of styled text and its corresponding |
111 // visual layout. Support is built in for a cursor, a selection, simple styling, | 94 // visual layout. Support is built in for a cursor, a selection, simple styling, |
112 // complex scripts, and bi-directional text. Implementations provide mechanisms | 95 // complex scripts, and bi-directional text. Implementations provide mechanisms |
113 // for rendering and translation between logical and visual data. | 96 // for rendering and translation between logical and visual data. |
114 class UI_EXPORT RenderText { | 97 class UI_EXPORT RenderText { |
115 public: | 98 public: |
116 virtual ~RenderText(); | 99 virtual ~RenderText(); |
117 | 100 |
118 // Creates a platform-specific RenderText instance. | 101 // Creates a platform-specific RenderText instance. |
119 static RenderText* CreateRenderText(); | 102 static RenderText* CreateRenderText(); |
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
153 void set_default_style(const StyleRange& style) { default_style_ = style; } | 136 void set_default_style(const StyleRange& style) { default_style_ = style; } |
154 | 137 |
155 const Rect& display_rect() const { return display_rect_; } | 138 const Rect& display_rect() const { return display_rect_; } |
156 void SetDisplayRect(const Rect& r); | 139 void SetDisplayRect(const Rect& r); |
157 | 140 |
158 void set_fade_head(bool fade_head) { fade_head_ = fade_head; } | 141 void set_fade_head(bool fade_head) { fade_head_ = fade_head; } |
159 bool fade_head() const { return fade_head_; } | 142 bool fade_head() const { return fade_head_; } |
160 void set_fade_tail(bool fade_tail) { fade_tail_ = fade_tail; } | 143 void set_fade_tail(bool fade_tail) { fade_tail_ = fade_tail; } |
161 bool fade_tail() const { return fade_tail_; } | 144 bool fade_tail() const { return fade_tail_; } |
162 | 145 |
163 // This cursor position corresponds to SelectionModel::selection_end. In | 146 size_t cursor_position() const { return selection_model_.caret_pos(); } |
164 // addition to representing the selection end, it's also where logical text | |
165 // edits take place, and doesn't necessarily correspond to | |
166 // SelectionModel::caret_pos. | |
167 size_t GetCursorPosition() const; | |
168 void SetCursorPosition(size_t position); | 147 void SetCursorPosition(size_t position); |
169 | 148 |
170 // Moves the cursor left or right. Cursor movement is visual, meaning that | 149 // Moves the cursor left or right. Cursor movement is visual, meaning that |
171 // left and right are relative to screen, not the directionality of the text. | 150 // left and right are relative to screen, not the directionality of the text. |
172 // If |select| is false, the selection start is moved to the same position. | 151 // If |select| is false, the selection start is moved to the same position. |
173 void MoveCursor(BreakType break_type, | 152 void MoveCursor(BreakType break_type, |
174 VisualCursorDirection direction, | 153 VisualCursorDirection direction, |
175 bool select); | 154 bool select); |
176 | 155 |
177 // Set the selection_model_ to the value of |selection|. | 156 // Set the selection_model_ to the value of |selection|. |
178 // The selection model components are modified if invalid. | 157 // The selection range is clamped to text().length() if out of range. |
179 // Returns true if the cursor position or selection range changed. | 158 // Returns true if the cursor position or selection range changed. |
180 // If |selectin_start_| or |selection_end_| or |caret_pos_| in | 159 // If any index in |selection_model| is not a cursorable position (not on a |
181 // |selection_model| is not a cursorable position (not on grapheme boundary), | 160 // grapheme boundary), it is a no-op and returns false. |
182 // it is a NO-OP and returns false. | |
183 bool MoveCursorTo(const SelectionModel& selection_model); | 161 bool MoveCursorTo(const SelectionModel& selection_model); |
184 | 162 |
185 // Move the cursor to the position associated with the clicked point. | 163 // Move the cursor to the position associated with the clicked point. |
186 // If |select| is false, the selection start is moved to the same position. | 164 // If |select| is false, the selection start is moved to the same position. |
187 // Returns true if the cursor position or selection range changed. | 165 // Returns true if the cursor position or selection range changed. |
188 bool MoveCursorTo(const Point& point, bool select); | 166 bool MoveCursorTo(const Point& point, bool select); |
189 | 167 |
190 // Set the selection_model_ based on |range|. | 168 // Set the selection_model_ based on |range|. |
191 // If the |range| start or end is greater than text length, it is modified | 169 // If the |range| start or end is greater than text length, it is modified |
192 // to be the text length. | 170 // to be the text length. |
193 // If the |range| start or end is not a cursorable position (not on grapheme | 171 // If the |range| start or end is not a cursorable position (not on grapheme |
194 // boundary), it is a NO-OP and returns false. Otherwise, returns true. | 172 // boundary), it is a NO-OP and returns false. Otherwise, returns true. |
195 bool SelectRange(const ui::Range& range); | 173 bool SelectRange(const ui::Range& range); |
196 | 174 |
197 size_t GetSelectionStart() const { | 175 const ui::Range& selection() const { return selection_model_.selection(); } |
msw
2012/02/28 22:51:32
nit: move this up with cursor_position()
benrg
2012/03/07 01:04:44
Done. I also moved selection_model().
| |
198 return selection_model_.selection_start(); | |
199 } | |
200 size_t MinOfSelection() const { | |
201 return std::min(GetSelectionStart(), GetCursorPosition()); | |
202 } | |
203 size_t MaxOfSelection() const { | |
204 return std::max(GetSelectionStart(), GetCursorPosition()); | |
205 } | |
206 bool EmptySelection() const { | |
207 return GetSelectionStart() == GetCursorPosition(); | |
208 } | |
209 | 176 |
210 // Returns true if the local point is over selected text. | 177 // Returns true if the local point is over selected text. |
211 bool IsPointInSelection(const Point& point); | 178 bool IsPointInSelection(const Point& point); |
212 | 179 |
213 // Selects no text, all text, or the word at the current cursor position. | 180 // Selects no text, all text, or the word at the current cursor position. |
214 void ClearSelection(); | 181 void ClearSelection(); |
215 void SelectAll(); | 182 void SelectAll(); |
216 void SelectWord(); | 183 void SelectWord(); |
217 | 184 |
218 const ui::Range& GetCompositionRange() const; | 185 const ui::Range& GetCompositionRange() const; |
219 void SetCompositionRange(const ui::Range& composition_range); | 186 void SetCompositionRange(const ui::Range& composition_range); |
220 | 187 |
221 // Apply |style_range| to the internal style model. | 188 // Apply |style_range| to the internal style model. |
222 void ApplyStyleRange(const StyleRange& style_range); | 189 void ApplyStyleRange(const StyleRange& style_range); |
223 | 190 |
224 // Apply |default_style_| over the entire text range. | 191 // Apply |default_style_| over the entire text range. |
225 void ApplyDefaultStyle(); | 192 void ApplyDefaultStyle(); |
226 | 193 |
227 // Returns the dominant direction of the current text. | 194 // Returns the dominant direction of the current text. |
228 virtual base::i18n::TextDirection GetTextDirection() = 0; | 195 virtual base::i18n::TextDirection GetTextDirection() = 0; |
229 | 196 |
230 // Returns the visual movement direction corresponding to the logical end | 197 // Returns the visual movement direction corresponding to the logical end |
231 // of the text, considering only the dominant direction returned by | 198 // of the text, considering only the dominant direction returned by |
232 // |GetTextDirection()|, not the direction of a particular run. | 199 // |GetTextDirection()|, not the direction of a particular run. |
233 VisualCursorDirection GetVisualDirectionOfLogicalEnd(); | 200 VisualCursorDirection GetVisualDirectionOfLogicalEnd(); |
234 | 201 |
235 // Get the width of the entire string. | 202 // Get the size in pixels of the entire string. |
236 virtual int GetStringWidth() = 0; | 203 virtual Size GetStringSize() = 0; |
237 | 204 |
238 void Draw(Canvas* canvas); | 205 void Draw(Canvas* canvas); |
239 | 206 |
240 // Gets the SelectionModel from a visual point in local coordinates. | 207 // Gets the SelectionModel from a visual point in local coordinates. |
241 virtual SelectionModel FindCursorPosition(const Point& point) = 0; | 208 virtual SelectionModel FindCursorPosition(const Point& point) = 0; |
242 | 209 |
243 // Get the visual bounds of a cursor at |selection|. These bounds typically | 210 // Get the visual bounds of a cursor at |selection|. These bounds typically |
244 // represent a vertical line, but if |insert_mode| is true they contain the | 211 // represent a vertical line, but if |insert_mode| is true they contain the |
245 // bounds of the associated glyph. These bounds are in local coordinates, but | 212 // bounds of the associated glyph. These bounds are in local coordinates, but |
246 // may be outside the visible region if the text is longer than the textfield. | 213 // may be outside the visible region if the text is longer than the textfield. |
247 // Subsequent text, cursor, or bounds changes may invalidate returned values. | 214 // Subsequent text, cursor, or bounds changes may invalidate returned values. |
248 virtual Rect GetCursorBounds(const SelectionModel& selection, | 215 Rect GetCursorBounds(const SelectionModel& selection, bool insert_mode); |
249 bool insert_mode) = 0; | |
250 | 216 |
251 // Compute the current cursor bounds, panning the text to show the cursor in | 217 // Compute the current cursor bounds, panning the text to show the cursor in |
252 // the display rect if necessary. These bounds are in local coordinates. | 218 // the display rect if necessary. These bounds are in local coordinates. |
253 // Subsequent text, cursor, or bounds changes may invalidate returned values. | 219 // Subsequent text, cursor, or bounds changes may invalidate returned values. |
254 const Rect& GetUpdatedCursorBounds(); | 220 const Rect& GetUpdatedCursorBounds(); |
255 | 221 |
256 // Given an |index| in text(), return the next or previous grapheme boundary | 222 // Given an |index| in text(), return the next or previous grapheme boundary |
257 // in logical order (that is, the nearest index for which | 223 // in logical order (that is, the nearest index for which |
258 // |IsCursorablePosition(index)| returns true). The return value is in the | 224 // |IsCursorablePosition(index)| returns true). The return value is in the |
259 // range 0 to text().length() inclusive (the input is clamped if it is out of | 225 // range 0 to text().length() inclusive (the input is clamped if it is out of |
(...skipping 30 matching lines...) Expand all Loading... | |
290 VisualCursorDirection direction) = 0; | 256 VisualCursorDirection direction) = 0; |
291 | 257 |
292 // Get the selection model visually left/right of |selection| by one word. | 258 // Get the selection model visually left/right of |selection| by one word. |
293 // The returned value represents a cursor/caret position without a selection. | 259 // The returned value represents a cursor/caret position without a selection. |
294 virtual SelectionModel AdjacentWordSelectionModel( | 260 virtual SelectionModel AdjacentWordSelectionModel( |
295 const SelectionModel& selection, | 261 const SelectionModel& selection, |
296 VisualCursorDirection direction) = 0; | 262 VisualCursorDirection direction) = 0; |
297 | 263 |
298 // Get the SelectionModels corresponding to visual text ends. | 264 // Get the SelectionModels corresponding to visual text ends. |
299 // The returned value represents a cursor/caret position without a selection. | 265 // The returned value represents a cursor/caret position without a selection. |
300 virtual SelectionModel EdgeSelectionModel( | 266 SelectionModel EdgeSelectionModel(VisualCursorDirection direction); |
301 VisualCursorDirection direction) = 0; | |
302 | 267 |
303 // Sets the selection model, the argument is assumed to be valid. | 268 // Sets the selection model, the argument is assumed to be valid. |
304 virtual void SetSelectionModel(const SelectionModel& model); | 269 virtual void SetSelectionModel(const SelectionModel& model); |
305 | 270 |
306 // Get the visual bounds containing the logical substring within |from| to | 271 // Get the height and horizontal bounds (relative to the left of the text, not |
307 // |to|. If |from| equals |to|, the result is empty. These bounds could be | 272 // the view) of the glyph starting at |index|. If the glyph is RTL then |
308 // visually discontinuous if the substring is split by a LTR/RTL level change. | 273 // xspan->is_reversed(). This does not return a Rect because a Rect can't have |
274 // a negative width. | |
275 virtual void GetGlyphBounds(size_t index, ui::Range* xspan, int* height) = 0; | |
276 | |
277 // Get the visual bounds containing the logical substring within the |range|. | |
278 // If |range| is empty, the result is empty. These bounds could be visually | |
279 // discontinuous if the substring is split by a LTR/RTL level change. | |
309 // These bounds are in local coordinates, but may be outside the visible | 280 // These bounds are in local coordinates, but may be outside the visible |
310 // region if the text is longer than the textfield. Subsequent text, cursor, | 281 // region if the text is longer than the textfield. Subsequent text, cursor, |
311 // or bounds changes may invalidate returned values. | 282 // or bounds changes may invalidate returned values. |
312 virtual std::vector<Rect> GetSubstringBounds(size_t from, size_t to) = 0; | 283 virtual std::vector<Rect> GetSubstringBounds(ui::Range range) = 0; |
313 | 284 |
314 // Return true if cursor can appear in front of the character at |position|, | 285 // Return true if cursor can appear in front of the character at |position|, |
315 // which means it is a grapheme boundary or the first character in the text. | 286 // which means it is a grapheme boundary or the first character in the text. |
316 virtual bool IsCursorablePosition(size_t position) = 0; | 287 virtual bool IsCursorablePosition(size_t position) = 0; |
317 | 288 |
318 // Update the layout so that the next draw request can correctly | 289 // Update the layout so that the next draw request can correctly |
319 // render the text and its attributes. | 290 // render the text and its attributes. |
320 virtual void UpdateLayout() = 0; | 291 virtual void UpdateLayout() = 0; |
321 | 292 |
322 // Ensure the text is laid out. | 293 // Ensure the text is laid out. |
(...skipping 20 matching lines...) Expand all Loading... | |
343 | 314 |
344 // Returns display offset based on current text alignment. | 315 // Returns display offset based on current text alignment. |
345 Point GetAlignmentOffset(); | 316 Point GetAlignmentOffset(); |
346 | 317 |
347 // Returns the origin point for drawing text via Skia. | 318 // Returns the origin point for drawing text via Skia. |
348 Point GetOriginForSkiaDrawing(); | 319 Point GetOriginForSkiaDrawing(); |
349 | 320 |
350 // Applies fade effects to |renderer|. | 321 // Applies fade effects to |renderer|. |
351 void ApplyFadeEffects(internal::SkiaTextRenderer* renderer); | 322 void ApplyFadeEffects(internal::SkiaTextRenderer* renderer); |
352 | 323 |
324 // A convenience function to check whether the glyph attached to the caret | |
325 // is within the given range. | |
326 static bool RangeContainsCaret(const ui::Range& range, | |
327 size_t caret_pos, | |
328 LogicalCursorDirection caret_affinity); | |
329 | |
353 private: | 330 private: |
354 friend class RenderTextTest; | 331 friend class RenderTextTest; |
355 | 332 |
356 FRIEND_TEST_ALL_PREFIXES(RenderTextTest, DefaultStyle); | 333 FRIEND_TEST_ALL_PREFIXES(RenderTextTest, DefaultStyle); |
357 FRIEND_TEST_ALL_PREFIXES(RenderTextTest, CustomDefaultStyle); | 334 FRIEND_TEST_ALL_PREFIXES(RenderTextTest, CustomDefaultStyle); |
358 FRIEND_TEST_ALL_PREFIXES(RenderTextTest, ApplyStyleRange); | 335 FRIEND_TEST_ALL_PREFIXES(RenderTextTest, ApplyStyleRange); |
359 FRIEND_TEST_ALL_PREFIXES(RenderTextTest, StyleRangesAdjust); | 336 FRIEND_TEST_ALL_PREFIXES(RenderTextTest, StyleRangesAdjust); |
360 FRIEND_TEST_ALL_PREFIXES(RenderTextTest, GraphemePositions); | 337 FRIEND_TEST_ALL_PREFIXES(RenderTextTest, GraphemePositions); |
361 FRIEND_TEST_ALL_PREFIXES(RenderTextTest, SelectionModels); | 338 FRIEND_TEST_ALL_PREFIXES(RenderTextTest, EdgeSelectionModels); |
362 FRIEND_TEST_ALL_PREFIXES(RenderTextTest, OriginForSkiaDrawing); | 339 FRIEND_TEST_ALL_PREFIXES(RenderTextTest, OriginForSkiaDrawing); |
363 | 340 |
364 // Set the cursor to |position|, with the caret trailing the previous | 341 // Set the cursor to |position|, with the caret trailing the previous |
365 // grapheme, or if there is no previous grapheme, leading the cursor position. | 342 // grapheme, or if there is no previous grapheme, leading the cursor position. |
366 // If |select| is false, the selection start is moved to the same position. | 343 // If |select| is false, the selection start is moved to the same position. |
367 // If the |position| is not a cursorable position (not on grapheme boundary), | 344 // If the |position| is not a cursorable position (not on grapheme boundary), |
368 // it is a NO-OP. | 345 // it is a NO-OP. |
369 void MoveCursorTo(size_t position, bool select); | 346 void MoveCursorTo(size_t position, bool select); |
370 | 347 |
371 // Update the cached bounds and display offset to ensure that the current | 348 // Update the cached bounds and display offset to ensure that the current |
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
424 // The cached bounds and offset are invalidated by changes to the cursor, | 401 // The cached bounds and offset are invalidated by changes to the cursor, |
425 // selection, font, and other operations that adjust the visible text bounds. | 402 // selection, font, and other operations that adjust the visible text bounds. |
426 bool cached_bounds_and_offset_valid_; | 403 bool cached_bounds_and_offset_valid_; |
427 | 404 |
428 DISALLOW_COPY_AND_ASSIGN(RenderText); | 405 DISALLOW_COPY_AND_ASSIGN(RenderText); |
429 }; | 406 }; |
430 | 407 |
431 } // namespace gfx | 408 } // namespace gfx |
432 | 409 |
433 #endif // UI_GFX_RENDER_TEXT_H_ | 410 #endif // UI_GFX_RENDER_TEXT_H_ |
OLD | NEW |