00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
#include "katetextline.h"
00024
00025
#include <qregexp.h>
00026
#include <kglobal.h>
00027
00028 KateTextLine::KateTextLine ()
00029 : m_flags(
KateTextLine::flagVisible)
00030 {
00031 }
00032
00033 KateTextLine::~KateTextLine()
00034 {
00035 }
00036
00037 void KateTextLine::insertText (uint pos, uint insLen,
const QChar *insText, uchar *insAttribs)
00038 {
00039
00040
if (insLen == 0)
00041
return;
00042
00043
00044 uint oldTextLen = m_text.length();
00045 m_text.insert (pos, insText, insLen);
00046 uint textLen = m_text.length();
00047
00048
00049 m_attributes.resize (textLen);
00050
00051
00052
if (pos >= oldTextLen)
00053 {
00054
for (uint z = oldTextLen; z < pos; z++)
00055 m_attributes[z] = 0;
00056 }
00057
00058
else if (oldTextLen > 0)
00059 {
00060
for (
int z = oldTextLen -1; z >= (
int) pos; z--)
00061 m_attributes[z+insLen] = m_attributes[z];
00062 }
00063
00064
00065
for (uint z = 0; z < insLen; z++)
00066 {
00067
if (insAttribs == 0)
00068 m_attributes[z+pos] = 0;
00069
else
00070 m_attributes[z+pos] = insAttribs[z];
00071 }
00072 }
00073
00074 void KateTextLine::removeText (uint pos, uint delLen)
00075 {
00076
00077
if (delLen == 0)
00078
return;
00079
00080 uint textLen = m_text.length();
00081
00082
if (textLen == 0)
00083
return;
00084
00085
if (pos >= textLen)
00086
return;
00087
00088
if ((pos + delLen) > textLen)
00089 delLen = textLen - pos;
00090
00091
00092
for (uint z = pos; z < textLen - delLen; z++)
00093 m_attributes[z] = m_attributes[z+delLen];
00094
00095 m_text.remove (pos, delLen);
00096 m_attributes.resize (m_text.length ());
00097 }
00098
00099 void KateTextLine::truncate(uint newLen)
00100 {
00101
if (newLen < m_text.length())
00102 {
00103 m_text.truncate (newLen);
00104 m_attributes.truncate (newLen);
00105 }
00106 }
00107
00108 int KateTextLine::nextNonSpaceChar(uint pos)
const
00109
{
00110
for(
int i = pos; i < (
int)m_text.length(); i++)
00111 {
00112
if(!m_text[i].isSpace())
00113
return i;
00114 }
00115
00116
return -1;
00117 }
00118
00119 int KateTextLine::previousNonSpaceChar(uint pos)
const
00120
{
00121
if (pos >= m_text.length())
00122 pos = m_text.length() - 1;
00123
00124
for(
int i = pos; i >= 0; i--)
00125 {
00126
if(!m_text[i].isSpace())
00127
return i;
00128 }
00129
00130
return -1;
00131 }
00132
00133 int KateTextLine::firstChar()
const
00134
{
00135
return nextNonSpaceChar(0);
00136 }
00137
00138 int KateTextLine::lastChar()
const
00139
{
00140
return previousNonSpaceChar(m_text.length() - 1);
00141 }
00142
00143 const QChar *
KateTextLine::firstNonSpace()
const
00144
{
00145
int first =
firstChar();
00146
return (first > -1) ? ((
QChar*)m_text.unicode())+first : m_text.unicode();
00147 }
00148
00149 uint
KateTextLine::indentDepth (uint tabwidth)
const
00150
{
00151 uint d = 0;
00152
00153
for(uint i = 0; i < m_text.length(); i++)
00154 {
00155
if(m_text[i].isSpace())
00156 {
00157
if (m_text[i] ==
QChar(
'\t'))
00158 d += tabwidth - (d % tabwidth);
00159
else
00160 d++;
00161 }
00162
else
00163
return d;
00164 }
00165
00166
return d;
00167 }
00168
00169 bool KateTextLine::stringAtPos(uint pos,
const QString& match)
const
00170
{
00171
return (m_text.mid(pos, match.length()) == match);
00172 }
00173
00174 bool KateTextLine::startingWith(
const QString& match)
const
00175
{
00176
return (m_text.left(match.length()) == match);
00177 }
00178
00179 bool KateTextLine::endingWith(
const QString& match)
const
00180
{
00181
return (m_text.right(match.length()) == match);
00182 }
00183
00184 int KateTextLine::cursorX(uint pos, uint tabChars)
const
00185
{
00186 uint x = 0;
00187
00188
for ( uint z = 0; z < kMin (pos, m_text.length()); z++)
00189 {
00190
if (m_text[z] ==
QChar(
'\t'))
00191 x += tabChars - (x % tabChars);
00192
else
00193 x++;
00194 }
00195
00196
return x;
00197 }
00198
00199 uint
KateTextLine::lengthWithTabs (uint tabChars)
const
00200
{
00201 uint x = 0;
00202
00203
for ( uint z = 0; z < m_text.length(); z++)
00204 {
00205
if (m_text[z] ==
QChar(
'\t'))
00206 x += tabChars - (x % tabChars);
00207
else
00208 x++;
00209 }
00210
00211
return x;
00212 }
00213
00214 void KateTextLine::setAttribs(uchar attribute, uint start, uint end)
00215 {
00216
if (end > m_attributes.size())
00217 end = m_attributes.size();
00218
00219
for (uint z = start; z < end; z++)
00220 m_attributes[z] = attribute;
00221 }
00222
00223 bool KateTextLine::searchText (uint startCol,
const QString &text, uint *foundAtCol, uint *matchLen,
bool casesensitive,
bool backwards)
00224 {
00225
int index;
00226
00227
if (backwards)
00228 {
00229
int col = startCol;
00230 uint l = text.length();
00231
do {
00232 index = m_text.findRev( text, col, casesensitive );
00233 col--;
00234 }
while ( col >= 0 && l + index >= startCol );
00235 }
00236
else
00237 index = m_text.find (text, startCol, casesensitive);
00238
00239
if (index > -1)
00240 {
00241 (*foundAtCol) = index;
00242 (*matchLen)=text.length();
00243
return true;
00244 }
00245
00246
return false;
00247 }
00248
00249 bool KateTextLine::searchText (uint startCol,
const QRegExp ®exp, uint *foundAtCol, uint *matchLen,
bool backwards)
00250 {
00251
int index;
00252
00253
if (backwards)
00254 {
00255
int col = startCol;
00256
do {
00257 index = regexp.searchRev (m_text, col);
00258 col--;
00259 }
while ( col >= 0 && regexp.matchedLength() + index >= (
int)startCol );
00260 }
00261
else
00262 index = regexp.search (m_text, startCol);
00263
00264
if (index > -1)
00265 {
00266 (*foundAtCol) = index;
00267 (*matchLen)=regexp.matchedLength();
00268
return true;
00269 }
00270
00271
return false;
00272 }
00273
00274 char *
KateTextLine::dump (
char *buf,
bool withHighlighting)
const
00275
{
00276 uint l = m_text.length();
00277
char f = m_flags;
00278
00279
if (!withHighlighting)
00280 f = f | KateTextLine::flagNoOtherData;
00281
00282 memcpy(buf, (
char *) &f, 1);
00283 buf += 1;
00284
00285 memcpy(buf, &l,
sizeof(uint));
00286 buf +=
sizeof(uint);
00287
00288 memcpy(buf, (
char *) m_text.unicode(),
sizeof(
QChar)*l);
00289 buf +=
sizeof(
QChar) * l;
00290
00291
if (!withHighlighting)
00292
return buf;
00293
00294 memcpy(buf, (
char *)m_attributes.data(),
sizeof(uchar) * l);
00295 buf +=
sizeof (uchar) * l;
00296
00297 uint lctx = m_ctx.size();
00298 uint lfold = m_foldingList.size();
00299 uint lind = m_indentationDepth.size();
00300
00301 memcpy(buf, &lctx,
sizeof(uint));
00302 buf +=
sizeof(uint);
00303
00304 memcpy(buf, &lfold,
sizeof(uint));
00305 buf +=
sizeof(uint);
00306
00307 memcpy(buf, &lind,
sizeof(uint));
00308 buf +=
sizeof(uint);
00309
00310 memcpy(buf, (
char *)m_ctx.data(),
sizeof(
short) * lctx);
00311 buf +=
sizeof (
short) * lctx;
00312
00313 memcpy(buf, (
char *)m_foldingList.data(), lfold);
00314 buf +=
sizeof (
signed char) * lfold;
00315
00316 memcpy(buf, (
char *)m_indentationDepth.data(),
sizeof(
unsigned short) * lind);
00317 buf +=
sizeof (
unsigned short) * lind;
00318
00319
return buf;
00320 }
00321
00322 char *
KateTextLine::restore (
char *buf)
00323 {
00324 uint l = 0;
00325
char f = 0;
00326
00327 memcpy((
char *) &f, buf, 1);
00328 buf += 1;
00329
00330
00331 memcpy((
char *) &l, buf,
sizeof(uint));
00332 buf +=
sizeof(uint);
00333
00334
00335 m_text.setUnicode ((
QChar *) buf, l);
00336 buf +=
sizeof(
QChar) * l;
00337
00338
00339
if (f & KateTextLine::flagNoOtherData)
00340 {
00341 m_flags = KateTextLine::flagVisible;
00342
00343
if (f & KateTextLine::flagAutoWrapped)
00344 m_flags = m_flags | KateTextLine::flagAutoWrapped;
00345
00346
00347 m_attributes.fill (0, l);
00348
00349
return buf;
00350 }
00351
else
00352 m_flags = f;
00353
00354 m_attributes.duplicate ((uchar *) buf, l);
00355 buf +=
sizeof(uchar) * l;
00356
00357 uint lctx = 0;
00358 uint lfold = 0;
00359 uint lind = 0;
00360
00361 memcpy((
char *) &lctx, buf,
sizeof(uint));
00362 buf +=
sizeof(uint);
00363
00364 memcpy((
char *) &lfold, buf,
sizeof(uint));
00365 buf +=
sizeof(uint);
00366
00367 memcpy((
char *) &lind, buf,
sizeof(uint));
00368 buf +=
sizeof(uint);
00369
00370 m_ctx.duplicate ((
short *) buf, lctx);
00371 buf +=
sizeof(
short) * lctx;
00372
00373 m_foldingList.duplicate ((
signed char *) buf, lfold);
00374 buf += lfold;
00375
00376 m_indentationDepth.duplicate ((
unsigned short *) buf, lind);
00377 buf +=
sizeof(
unsigned short) * lind;
00378
00379
return buf;
00380 }
00381
00382