00001
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023 #include "MyGUI_Precompiled.h"
00024 #include "MyGUI_TextIterator.h"
00025
00026 namespace MyGUI
00027 {
00028
00029 TextIterator::TextIterator() :
00030 mPosition(0),
00031 mSize(ITEM_NONE),
00032 mFirst(true),
00033 mHistory(nullptr)
00034 {
00035 }
00036
00037 TextIterator::TextIterator(const UString& _text, VectorChangeInfo * _history) :
00038 mText(_text),
00039 mCurrent(mText.begin()),
00040 mEnd(mText.end()),
00041 mSave(mEnd),
00042 mPosition(0),
00043 mSize(ITEM_NONE),
00044 mFirst(true),
00045 mHistory(_history)
00046 {
00047 }
00048
00049 bool TextIterator::moveNext()
00050 {
00051 if (mCurrent == mEnd) return false;
00052 else if (mFirst)
00053 {
00054 mFirst = false;
00055 return true;
00056 }
00057
00058
00059 for (UString::iterator iter=mCurrent; iter!=mEnd; ++iter)
00060 {
00061
00062 if ((*iter) == L'#')
00063 {
00064
00065
00066 ++ iter;
00067 if (iter == mEnd)
00068 {
00069 mCurrent = mEnd;
00070 return false;
00071 }
00072
00073
00074 if ((*iter) == L'#')
00075 {
00076
00077
00078 mPosition ++;
00079 iter++;
00080 if (iter == mEnd)
00081 {
00082 mCurrent = mEnd;
00083 return false;
00084 }
00085
00086
00087 mCurrent = iter;
00088 return true;
00089 }
00090
00091
00092 for (size_t pos=0; pos<5; pos++)
00093 {
00094
00095 ++ iter;
00096 if (iter == mEnd)
00097 {
00098 mCurrent = mEnd;
00099 return false;
00100 }
00101 }
00102
00103 }
00104 else
00105 {
00106
00107
00108 mPosition ++;
00109 iter++;
00110 if (iter == mEnd)
00111 {
00112 mCurrent = mEnd;
00113 return false;
00114 }
00115
00116
00117 mCurrent = iter;
00118 return true;
00119 }
00120 }
00121
00122 return false;
00123 }
00124
00125
00126 UString TextIterator::getTagColour(bool _clear)
00127 {
00128 if (mCurrent == mEnd) return L"";
00129
00130 UString::iterator iter = mCurrent;
00131 UString colour;
00132
00133 while (getTagColour(colour, iter))
00134 {
00135 if (_clear)
00136 {
00137
00138 iter = mCurrent = erase(mCurrent, iter);
00139 mEnd = mText.end();
00140 }
00141 }
00142 return colour;
00143 }
00144
00145
00146 bool TextIterator::getTagColour(UString& _colour)
00147 {
00148 if (mCurrent == mEnd) return false;
00149
00150 UString::iterator iter = mCurrent;
00151
00152
00153 bool ret = false;
00154 while (true)
00155 {
00156 if (!getTagColour(_colour, iter)) break;
00157 ret = true;
00158 }
00159
00160 return ret;
00161 }
00162
00163 bool TextIterator::setTagColour(const Colour& _colour)
00164 {
00165 if (mCurrent == mEnd) return false;
00166
00167 clearTagColour();
00168
00169 if (mCurrent == mEnd) return false;
00170
00171 const size_t SIZE = 16;
00172 wchar_t buff[SIZE];
00173
00174 #ifdef __MINGW32__
00175 swprintf(buff, L"#%.2X%.2X%.2X\0", (int)(_colour.red*255), (int)(_colour.green*255), (int)(_colour.blue*255));
00176 #else
00177 swprintf(buff, SIZE, L"#%.2X%.2X%.2X\0", (int)(_colour.red*255), (int)(_colour.green*255), (int)(_colour.blue*255));
00178 #endif
00179
00180 UString tmpStr = UString(buff);
00181 insert(mCurrent, tmpStr);
00182
00183 return true;
00184 }
00185
00186 bool TextIterator::setTagColour(UString _colour)
00187 {
00188 if (mCurrent == mEnd) return false;
00189
00190 clearTagColour();
00191
00192 if (mCurrent == mEnd) return false;
00193
00194
00195 if ( (_colour.size() != 7) || (_colour.find(L'#', 1) != _colour.npos) ) return false;
00196
00197
00198 insert(mCurrent, _colour);
00199
00200 return true;
00201 }
00202
00203
00204 size_t TextIterator::getSize() const
00205 {
00206 if (mSize != ITEM_NONE) return mSize;
00207 mSize = mPosition;
00208
00209 for (UString::iterator iter=mCurrent; iter!=mEnd; ++iter)
00210 {
00211
00212 if ((*iter) == L'#')
00213 {
00214
00215 ++ iter;
00216 if (iter == mEnd) break;
00217
00218
00219 if ((*iter) != L'#')
00220 {
00221
00222 for (size_t pos=0; pos<5; pos++)
00223 {
00224 ++ iter;
00225 if (iter == mEnd)
00226 {
00227 --iter;
00228 break;
00229 }
00230 }
00231 continue;
00232 }
00233 }
00234
00235
00236 mSize ++;
00237 }
00238
00239 return mSize;
00240 }
00241
00242
00243 UString TextIterator::getOnlyText(const UString& _text)
00244 {
00245 UString ret;
00246 ret.reserve(_text.size());
00247
00248 UString::const_iterator end = _text.end();
00249 for (UString::const_iterator iter=_text.begin(); iter!=end; ++iter)
00250 {
00251
00252 if ((*iter) == L'#')
00253 {
00254
00255 ++ iter;
00256 if (iter == end) break;
00257
00258
00259 if ((*iter) != L'#')
00260 {
00261
00262 for (size_t pos=0; pos<5; pos++)
00263 {
00264 ++ iter;
00265 if (iter == end)
00266 {
00267 --iter;
00268 break;
00269 }
00270 }
00271 continue;
00272 }
00273 }
00274
00275
00276 ret.push_back(*iter);
00277 }
00278
00279 return ret;
00280 }
00281
00282
00283 bool TextIterator::getTagColour(UString& _colour, UString::iterator& _iter)
00284 {
00285 if ( (_iter == mEnd) || ((*_iter) != L'#') ) return false;
00286
00287
00288 ++_iter;
00289 if ( (_iter == mEnd) || ((*_iter) == L'#') ) return false;
00290
00291
00292 wchar_t buff[16] = L"#FFFFFF\0";
00293 buff[1] = (wchar_t)(*_iter);
00294 for (size_t pos=2; pos<7; pos++)
00295 {
00296 ++_iter;
00297 if ( _iter == mEnd ) return false;
00298 buff[pos] = (Char)(*_iter);
00299 }
00300
00301
00302 ++_iter;
00303
00304
00305 _colour = buff;
00306 return true;
00307 }
00308
00309 void TextIterator::clearNewLine(UString& _text)
00310 {
00311 for (UString::iterator iter=_text.begin(); iter!=_text.end(); ++iter)
00312 {
00313 if ( ((*iter) == FontCodeType::NEL) ||
00314 ((*iter) == FontCodeType::CR) ||
00315 ((*iter) == FontCodeType::LF) )
00316 {
00317 (*iter) = FontCodeType::Space;
00318 }
00319 }
00320 }
00321
00322 bool TextIterator::saveStartPoint()
00323 {
00324 if (mCurrent == mEnd) return false;
00325 mSave = mCurrent;
00326 return true;
00327 }
00328
00329 UString TextIterator::getFromStart()
00330 {
00331 if (mSave == mEnd) return L"";
00332 size_t start = mSave-mText.begin();
00333 return mText.substr(start, mCurrent-mText.begin()-start);
00334 }
00335
00336 bool TextIterator::eraseFromStart()
00337 {
00338 if (mSave == mEnd) return false;
00339 mCurrent = erase(mSave, mCurrent);
00340 mSave = mEnd = mText.end();
00341 return true;
00342 }
00343
00344 void TextIterator::insertText(const UString& _insert, bool _multiLine)
00345 {
00346 UString text = _insert;
00347 if (!_multiLine) clearNewLine(text);
00348 insert(mCurrent, text);
00349 }
00350
00351 void TextIterator::setText(const UString& _text, bool _multiLine)
00352 {
00353
00354 clear();
00355
00356 UString text = _text;
00357 if (!_multiLine) clearNewLine(text);
00358 insert(mCurrent, text);
00359 }
00360
00361 UString TextIterator::getTextCharInfo(Char _char)
00362 {
00363 if (_char == L'#') return L"##";
00364 wchar_t buff[16] = L"_\0";
00365 buff[0] = _char;
00366 return buff;
00367 }
00368
00369 UString TextIterator::convertTagColour(const Colour& _colour)
00370 {
00371 const size_t SIZE = 16;
00372 wchar_t buff[SIZE];
00373
00374 #ifdef __MINGW32__
00375 swprintf(buff, L"#%.2X%.2X%.2X\0", (int)(_colour.red*255), (int)(_colour.green*255), (int)(_colour.blue*255));
00376 #else
00377 swprintf(buff, SIZE, L"#%.2X%.2X%.2X\0", (int)(_colour.red*255), (int)(_colour.green*255), (int)(_colour.blue*255));
00378 #endif
00379 return buff;
00380 }
00381
00382 UString TextIterator::toTagsString(const UString& _text)
00383 {
00384
00385 UString text(_text);
00386 for (UString::iterator iter=text.begin(); iter!=text.end(); ++iter)
00387 {
00388
00389 if (L'#' == (*iter)) iter = text.insert(++iter, L'#');
00390 }
00391 return text;
00392 }
00393
00394 void TextIterator::insert(UString::iterator& _start, UString& _insert)
00395 {
00396
00397 mSize = ITEM_NONE;
00398
00399 if (mHistory) mHistory->push_back(TextCommandInfo(_insert, _start-mText.begin(), TextCommandInfo::COMMAND_INSERT));
00400
00401 size_t pos = _start - mText.begin();
00402 size_t pos_save = (mSave==mEnd) ? ITEM_NONE : _start - mText.begin();
00403
00404 mText.insert(_start, _insert.begin(), _insert.end());
00405
00406 _start = mText.begin() + pos;
00407 mEnd = mText.end();
00408 (pos_save==ITEM_NONE) ? mSave = mEnd : mSave = mText.begin() + pos_save;
00409 }
00410
00411 UString::iterator TextIterator::erase(UString::iterator _start, UString::iterator _end)
00412 {
00413
00414 mSize = ITEM_NONE;
00415
00416 size_t start = _start-mText.begin();
00417 if (mHistory) mHistory->push_back(TextCommandInfo(mText.substr(start, _end-_start), start, TextCommandInfo::COMMAND_ERASE));
00418
00419 return mText.erase(_start, _end);
00420 }
00421
00422 void TextIterator::clear()
00423 {
00424 if (mText.empty()) return;
00425
00426
00427 if (mHistory) mHistory->push_back(TextCommandInfo(mText, 0, TextCommandInfo::COMMAND_ERASE));
00428
00429
00430 mText.clear();
00431 mCurrent = mText.begin();
00432 mEnd = mSave = mText.end();
00433 mSize = ITEM_NONE;
00434 }
00435
00436 void TextIterator::cutMaxLength(size_t _max)
00437 {
00438 if ( (mSize != ITEM_NONE) && (mSize <= _max) ) return;
00439 if (mPosition > _max)
00440 {
00441
00442 mSize = mPosition = 0;
00443 mCurrent = mText.begin();
00444 mEnd = mSave = mText.end();
00445 }
00446
00447 mSize = mPosition;
00448
00449 for (UString::iterator iter=mCurrent; iter!=mEnd; ++iter)
00450 {
00451
00452 if ((*iter) == L'#')
00453 {
00454
00455 ++ iter;
00456 if (iter == mEnd) break;
00457
00458
00459 if ((*iter) != L'#')
00460 {
00461
00462 for (size_t pos=0; pos<5; pos++)
00463 {
00464 ++ iter;
00465 if (iter == mEnd)
00466 {
00467 -- iter;
00468 break;
00469 }
00470 }
00471 continue;
00472 }
00473 }
00474
00475
00476 if (mSize == _max)
00477 {
00478 mPosition = mSize;
00479 mCurrent = erase(iter, mEnd);
00480 mSave = mEnd = mText.end();
00481 mSize = mPosition;
00482 return;
00483 }
00484
00485
00486 mSize ++;
00487 }
00488 }
00489
00490 void TextIterator::cutMaxLengthFromBeginning(size_t _max)
00491 {
00492
00493 size_t size = getSize();
00494 if (size <= _max) return;
00495
00496
00497 size_t diff = size - _max;
00498
00499
00500 UString::iterator iter_colour = mEnd;
00501
00502
00503 UString::iterator iter=mText.begin();
00504 for (; iter!=mEnd; ++iter)
00505 {
00506 if ((*iter) == L'#')
00507 {
00508 UString::iterator save = iter;
00509
00510
00511 ++ iter;
00512 if (iter == mEnd) break;
00513
00514
00515 if ((*iter) != L'#')
00516 {
00517
00518 for (size_t pos=0; pos<5; pos++)
00519 {
00520 ++ iter;
00521 if (iter == mEnd)
00522 {
00523 -- iter;
00524 break;
00525 }
00526 }
00527
00528 iter_colour = save;
00529 }
00530 continue;
00531 }
00532
00533 if (diff == 0) break;
00534 -- diff;
00535 }
00536
00537 UString colour;
00538
00539 if (iter_colour != mEnd)
00540 {
00541 colour.append(iter_colour, iter_colour + size_t(7));
00542 }
00543
00544 mCurrent = erase(mText.begin(), iter);
00545 mEnd = mText.end();
00546 mSave = mText.end();
00547 mPosition = 0;
00548 mSize = _max;
00549
00550 if ( ! colour.empty() ) setTagColour(colour);
00551
00552 }
00553
00554 }