Flutter macOS Embedder
flutter::TextInputModel Class Reference

#include <text_input_model.h>

Public Member Functions

 TextInputModel ()
 
virtual ~TextInputModel ()
 
bool SetText (const std::string &text, const TextRange &selection=TextRange(0), const TextRange &composing_range=TextRange(0))
 
bool SetSelection (const TextRange &range)
 
bool SetComposingRange (const TextRange &range, size_t cursor_offset)
 
void BeginComposing ()
 
void UpdateComposingText (const std::u16string &text, const TextRange &selection)
 
void UpdateComposingText (const std::u16string &text)
 
void UpdateComposingText (const std::string &text)
 
void CommitComposing ()
 
void EndComposing ()
 
void AddCodePoint (char32_t c)
 
void AddText (const std::u16string &text)
 
void AddText (const std::string &text)
 
bool Delete ()
 
bool DeleteSurrounding (int offset_from_cursor, int count)
 
bool Backspace ()
 
bool MoveCursorBack ()
 
bool MoveCursorForward ()
 
bool MoveCursorToBeginning ()
 
bool MoveCursorToEnd ()
 
bool SelectToBeginning ()
 
bool SelectToEnd ()
 
std::string GetText () const
 
int GetCursorOffset () const
 
TextRange text_range () const
 
TextRange selection () const
 
TextRange composing_range () const
 
bool composing () const
 

Detailed Description

Definition at line 18 of file text_input_model.h.

Constructor & Destructor Documentation

◆ TextInputModel()

flutter::TextInputModel::TextInputModel ( )
default

◆ ~TextInputModel()

flutter::TextInputModel::~TextInputModel ( )
virtualdefault

Member Function Documentation

◆ AddCodePoint()

void flutter::TextInputModel::AddCodePoint ( char32_t  c)

Definition at line 122 of file text_input_model.cc.

122  {
123  if (c <= 0xFFFF) {
124  AddText(std::u16string({static_cast<char16_t>(c)}));
125  } else {
126  char32_t to_decompose = c - 0x10000;
127  AddText(std::u16string({
128  // High surrogate.
129  static_cast<char16_t>((to_decompose >> 10) + 0xd800),
130  // Low surrogate.
131  static_cast<char16_t>((to_decompose % 0x400) + 0xdc00),
132  }));
133  }
134 }

References AddText().

◆ AddText() [1/2]

void flutter::TextInputModel::AddText ( const std::string &  text)

Definition at line 149 of file text_input_model.cc.

149  {
150  AddText(fml::Utf8ToUtf16(text));
151 }

References AddText().

◆ AddText() [2/2]

void flutter::TextInputModel::AddText ( const std::u16string &  text)

Definition at line 136 of file text_input_model.cc.

136  {
137  DeleteSelected();
138  if (composing_) {
139  // Delete the current composing text, set the cursor to composing start.
140  text_.erase(composing_range_.start(), composing_range_.length());
141  selection_ = TextRange(composing_range_.start());
142  composing_range_.set_end(composing_range_.start() + text.length());
143  }
144  size_t position = selection_.position();
145  text_.insert(position, text);
146  selection_ = TextRange(position + text.length());
147 }

References flutter::TextRange::length(), flutter::TextRange::position(), flutter::TextRange::set_end(), and flutter::TextRange::start().

Referenced by AddCodePoint(), and AddText().

◆ Backspace()

bool flutter::TextInputModel::Backspace ( )

Definition at line 153 of file text_input_model.cc.

153  {
154  if (DeleteSelected()) {
155  return true;
156  }
157  // There is no selection. Delete the preceding codepoint.
158  size_t position = selection_.position();
159  if (position != editable_range().start()) {
160  int count = IsTrailingSurrogate(text_.at(position - 1)) ? 2 : 1;
161  text_.erase(position - count, count);
162  selection_ = TextRange(position - count);
163  if (composing_) {
164  composing_range_.set_end(composing_range_.end() - count);
165  }
166  return true;
167  }
168  return false;
169 }

References flutter::TextRange::end(), flutter::TextRange::position(), and flutter::TextRange::set_end().

◆ BeginComposing()

void flutter::TextInputModel::BeginComposing ( )

Definition at line 67 of file text_input_model.cc.

67  {
68  composing_ = true;
69  composing_range_ = TextRange(selection_.start());
70 }

References flutter::TextRange::start().

◆ CommitComposing()

void flutter::TextInputModel::CommitComposing ( )

Definition at line 94 of file text_input_model.cc.

94  {
95  // Preserve selection if no composing text was entered.
96  if (composing_range_.collapsed()) {
97  return;
98  }
99  composing_range_ = TextRange(composing_range_.end());
100  selection_ = composing_range_;
101 }

References flutter::TextRange::collapsed(), and flutter::TextRange::end().

◆ composing()

bool flutter::TextInputModel::composing ( ) const
inline

Definition at line 209 of file text_input_model.h.

209 { return composing_; }

◆ composing_range()

TextRange flutter::TextInputModel::composing_range ( ) const
inline

Definition at line 206 of file text_input_model.h.

206 { return composing_range_; }

Referenced by SetText().

◆ Delete()

bool flutter::TextInputModel::Delete ( )

Definition at line 171 of file text_input_model.cc.

171  {
172  if (DeleteSelected()) {
173  return true;
174  }
175  // There is no selection. Delete the preceding codepoint.
176  size_t position = selection_.position();
177  if (position < editable_range().end()) {
178  int count = IsLeadingSurrogate(text_.at(position)) ? 2 : 1;
179  text_.erase(position, count);
180  if (composing_) {
181  composing_range_.set_end(composing_range_.end() - count);
182  }
183  return true;
184  }
185  return false;
186 }

References flutter::TextRange::end(), flutter::TextRange::position(), and flutter::TextRange::set_end().

◆ DeleteSurrounding()

bool flutter::TextInputModel::DeleteSurrounding ( int  offset_from_cursor,
int  count 
)

Definition at line 188 of file text_input_model.cc.

188  {
189  size_t max_pos = editable_range().end();
190  size_t start = selection_.extent();
191  if (offset_from_cursor < 0) {
192  for (int i = 0; i < -offset_from_cursor; i++) {
193  // If requested start is before the available text then reduce the
194  // number of characters to delete.
195  if (start == editable_range().start()) {
196  count = i;
197  break;
198  }
199  start -= IsTrailingSurrogate(text_.at(start - 1)) ? 2 : 1;
200  }
201  } else {
202  for (int i = 0; i < offset_from_cursor && start != max_pos; i++) {
203  start += IsLeadingSurrogate(text_.at(start)) ? 2 : 1;
204  }
205  }
206 
207  auto end = start;
208  for (int i = 0; i < count && end != max_pos; i++) {
209  end += IsLeadingSurrogate(text_.at(start)) ? 2 : 1;
210  }
211 
212  if (start == end) {
213  return false;
214  }
215 
216  auto deleted_length = end - start;
217  text_.erase(start, deleted_length);
218 
219  // Cursor moves only if deleted area is before it.
220  selection_ = TextRange(offset_from_cursor <= 0 ? start : selection_.start());
221 
222  // Adjust composing range.
223  if (composing_) {
224  composing_range_.set_end(composing_range_.end() - deleted_length);
225  }
226  return true;
227 }

References flutter::TextRange::end(), flutter::TextRange::extent(), flutter::TextRange::set_end(), and flutter::TextRange::start().

◆ EndComposing()

void flutter::TextInputModel::EndComposing ( )

Definition at line 103 of file text_input_model.cc.

103  {
104  composing_ = false;
105  composing_range_ = TextRange(0);
106 }

◆ GetCursorOffset()

int flutter::TextInputModel::GetCursorOffset ( ) const

Definition at line 301 of file text_input_model.cc.

301  {
302  // Measure the length of the current text up to the selection extent.
303  // There is probably a much more efficient way of doing this.
304  auto leading_text = text_.substr(0, selection_.extent());
305  return fml::Utf16ToUtf8(leading_text).size();
306 }

References flutter::TextRange::extent().

◆ GetText()

std::string flutter::TextInputModel::GetText ( ) const

Definition at line 297 of file text_input_model.cc.

297  {
298  return fml::Utf16ToUtf8(text_);
299 }

◆ MoveCursorBack()

bool flutter::TextInputModel::MoveCursorBack ( )

Definition at line 281 of file text_input_model.cc.

281  {
282  // If there's a selection, move to the beginning of the selection.
283  if (!selection_.collapsed()) {
284  selection_ = TextRange(selection_.start());
285  return true;
286  }
287  // Otherwise, move the cursor backward.
288  size_t position = selection_.position();
289  if (position != editable_range().start()) {
290  int count = IsTrailingSurrogate(text_.at(position - 1)) ? 2 : 1;
291  selection_ = TextRange(position - count);
292  return true;
293  }
294  return false;
295 }

References flutter::TextRange::collapsed(), flutter::TextRange::position(), and flutter::TextRange::start().

◆ MoveCursorForward()

bool flutter::TextInputModel::MoveCursorForward ( )

Definition at line 265 of file text_input_model.cc.

265  {
266  // If there's a selection, move to the end of the selection.
267  if (!selection_.collapsed()) {
268  selection_ = TextRange(selection_.end());
269  return true;
270  }
271  // Otherwise, move the cursor forward.
272  size_t position = selection_.position();
273  if (position != editable_range().end()) {
274  int count = IsLeadingSurrogate(text_.at(position)) ? 2 : 1;
275  selection_ = TextRange(position + count);
276  return true;
277  }
278  return false;
279 }

References flutter::TextRange::collapsed(), flutter::TextRange::end(), and flutter::TextRange::position().

◆ MoveCursorToBeginning()

bool flutter::TextInputModel::MoveCursorToBeginning ( )

Definition at line 229 of file text_input_model.cc.

229  {
230  size_t min_pos = editable_range().start();
231  if (selection_.collapsed() && selection_.position() == min_pos) {
232  return false;
233  }
234  selection_ = TextRange(min_pos);
235  return true;
236 }

References flutter::TextRange::collapsed(), flutter::TextRange::position(), and flutter::TextRange::start().

◆ MoveCursorToEnd()

bool flutter::TextInputModel::MoveCursorToEnd ( )

Definition at line 238 of file text_input_model.cc.

238  {
239  size_t max_pos = editable_range().end();
240  if (selection_.collapsed() && selection_.position() == max_pos) {
241  return false;
242  }
243  selection_ = TextRange(max_pos);
244  return true;
245 }

References flutter::TextRange::collapsed(), flutter::TextRange::end(), and flutter::TextRange::position().

◆ selection()

TextRange flutter::TextInputModel::selection ( ) const
inline

Definition at line 201 of file text_input_model.h.

201 { return selection_; }

Referenced by SetText(), and UpdateComposingText().

◆ SelectToBeginning()

bool flutter::TextInputModel::SelectToBeginning ( )

Definition at line 247 of file text_input_model.cc.

247  {
248  size_t min_pos = editable_range().start();
249  if (selection_.collapsed() && selection_.position() == min_pos) {
250  return false;
251  }
252  selection_ = TextRange(selection_.base(), min_pos);
253  return true;
254 }

References flutter::TextRange::base(), flutter::TextRange::collapsed(), flutter::TextRange::position(), and flutter::TextRange::start().

◆ SelectToEnd()

bool flutter::TextInputModel::SelectToEnd ( )

Definition at line 256 of file text_input_model.cc.

256  {
257  size_t max_pos = editable_range().end();
258  if (selection_.collapsed() && selection_.position() == max_pos) {
259  return false;
260  }
261  selection_ = TextRange(selection_.base(), max_pos);
262  return true;
263 }

References flutter::TextRange::base(), flutter::TextRange::collapsed(), flutter::TextRange::end(), and flutter::TextRange::position().

◆ SetComposingRange()

bool flutter::TextInputModel::SetComposingRange ( const TextRange range,
size_t  cursor_offset 
)

Definition at line 57 of file text_input_model.cc.

58  {
59  if (!composing_ || !text_range().Contains(range)) {
60  return false;
61  }
62  composing_range_ = range;
63  selection_ = TextRange(range.start() + cursor_offset);
64  return true;
65 }

References flutter::TextRange::start(), and text_range().

◆ SetSelection()

bool flutter::TextInputModel::SetSelection ( const TextRange range)

Definition at line 46 of file text_input_model.cc.

46  {
47  if (composing_ && !range.collapsed()) {
48  return false;
49  }
50  if (!editable_range().Contains(range)) {
51  return false;
52  }
53  selection_ = range;
54  return true;
55 }

References flutter::TextRange::collapsed().

◆ SetText()

bool flutter::TextInputModel::SetText ( const std::string &  text,
const TextRange selection = TextRange(0),
const TextRange composing_range = TextRange(0) 
)

Definition at line 31 of file text_input_model.cc.

33  {
34  text_ = fml::Utf8ToUtf16(text);
35  if (!text_range().Contains(selection) ||
36  !text_range().Contains(composing_range)) {
37  return false;
38  }
39 
40  selection_ = selection;
41  composing_range_ = composing_range;
42  composing_ = !composing_range.collapsed();
43  return true;
44 }

References flutter::TextRange::collapsed(), composing_range(), selection(), and text_range().

◆ text_range()

TextRange flutter::TextInputModel::text_range ( ) const
inline

Definition at line 198 of file text_input_model.h.

198 { return TextRange(0, text_.length()); }

Referenced by SetComposingRange(), and SetText().

◆ UpdateComposingText() [1/3]

void flutter::TextInputModel::UpdateComposingText ( const std::string &  text)

Definition at line 90 of file text_input_model.cc.

90  {
91  UpdateComposingText(fml::Utf8ToUtf16(text));
92 }

References UpdateComposingText().

◆ UpdateComposingText() [2/3]

void flutter::TextInputModel::UpdateComposingText ( const std::u16string &  text)

Definition at line 86 of file text_input_model.cc.

86  {
87  UpdateComposingText(text, TextRange(text.length()));
88 }

References UpdateComposingText().

◆ UpdateComposingText() [3/3]

void flutter::TextInputModel::UpdateComposingText ( const std::u16string &  text,
const TextRange selection 
)

Definition at line 72 of file text_input_model.cc.

73  {
74  // Preserve selection if we get a no-op update to the composing region.
75  if (text.length() == 0 && composing_range_.collapsed()) {
76  return;
77  }
78  const TextRange& rangeToDelete =
79  composing_range_.collapsed() ? selection_ : composing_range_;
80  text_.replace(rangeToDelete.start(), rangeToDelete.length(), text);
81  composing_range_.set_end(composing_range_.start() + text.length());
82  selection_ = TextRange(selection.start() + composing_range_.start(),
83  selection.extent() + composing_range_.start());
84 }

References flutter::TextRange::collapsed(), flutter::TextRange::extent(), flutter::TextRange::length(), selection(), flutter::TextRange::set_end(), and flutter::TextRange::start().

Referenced by UpdateComposingText().


The documentation for this class was generated from the following files:
flutter::TextRange::end
size_t end() const
Definition: text_range.h:54
flutter::TextInputModel::text_range
TextRange text_range() const
Definition: text_input_model.h:198
flutter::TextInputModel::composing_range
TextRange composing_range() const
Definition: text_input_model.h:206
flutter::TextRange::position
size_t position() const
Definition: text_range.h:68
flutter::TextInputModel::selection
TextRange selection() const
Definition: text_input_model.h:201
flutter::TextRange::base
size_t base() const
Definition: text_range.h:30
flutter::TextRange::collapsed
bool collapsed() const
Definition: text_range.h:77
flutter::TextInputModel::UpdateComposingText
void UpdateComposingText(const std::u16string &text, const TextRange &selection)
Definition: text_input_model.cc:72
flutter::TextRange::extent
size_t extent() const
Definition: text_range.h:36
flutter::TextRange::start
size_t start() const
Definition: text_range.h:42
flutter::TextRange::length
size_t length() const
Definition: text_range.h:74
flutter::TextRange::set_end
void set_end(size_t pos)
Definition: text_range.h:57
flutter::TextInputModel::AddText
void AddText(const std::u16string &text)
Definition: text_input_model.cc:136