- /* This file is part of the KDE libraries
- Copyright (C) 2003, 2004 Anders Lund <anders@alweb.dk>
- Copyright (C) 2003 Hamish Rodda <rodda@kde.org>
- Copyright (C) 2001,2002 Joseph Wenninger <jowenn@kde.org>
- Copyright (C) 2001 Christoph Cullmann <cullmann@kde.org>
- Copyright (C) 1999 Jochen Wilhelmy <digisnap@cs.tu-berlin.de>
-
- This library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Library General Public
- License version 2 as published by the Free Software Foundation.
-
- This library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Library General Public License for more details.
-
- You should have received a copy of the GNU Library General Public License
- along with this library; see the file COPYING.LIB. If not, write to
- the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
- Boston, MA 02110-1301, USA.
- */
-
- //BEGIN INCLUDES
- #include "katehighlight.h"
- #include "katehighlight.moc"
-
- #include "katetextline.h"
- #include "katedocument.h"
- #include "katesyntaxdocument.h"
- #include "katerenderer.h"
- #include "katefactory.h"
- #include "kateschema.h"
- #include "kateconfig.h"
-
- #include <tdeconfig.h>
- #include <tdeglobal.h>
- #include <kinstance.h>
- #include <kmimetype.h>
- #include <tdelocale.h>
- #include <kregexp.h>
- #include <tdepopupmenu.h>
- #include <tdeglobalsettings.h>
- #include <kdebug.h>
- #include <kstandarddirs.h>
- #include <tdemessagebox.h>
- #include <kstaticdeleter.h>
- #include <tdeapplication.h>
-
- #include <tqstringlist.h>
- #include <tqtextstream.h>
- //END
-
- //BEGIN defines
- // same as in kmimemagic, no need to feed more data
- #define KATE_HL_HOWMANY 1024
-
- // min. x seconds between two dynamic contexts reset
- static const int KATE_DYNAMIC_CONTEXTS_RESET_DELAY = 30 * 1000;
-
- // x is a TQString. if x is "true" or "1" this expression returns "true"
- #define IS_TRUE(x) x.lower() == TQString("true") || x.toInt() == 1
- //END defines
-
- //BEGIN Prviate HL classes
-
- inline bool kateInsideString (const TQString &str, TQChar ch)
- {
- const TQChar *unicode = str.unicode();
- const uint len = str.length();
- for (uint i=0; i < len; i++)
- if (unicode[i] == ch)
- return true;
-
- return false;
- }
-
- class KateHlItem
- {
- public:
- KateHlItem(int attribute, int context,signed char regionId, signed char regionId2);
- virtual ~KateHlItem();
-
- public:
- // caller must keep in mind: LEN > 0 is a must !!!!!!!!!!!!!!!!!!!!!1
- // Now, the function returns the offset detected, or 0 if no match is found.
- // bool linestart isn't needed, this is equivalent to offset == 0.
- virtual int checkHgl(const TQString& text, int offset, int len) = 0;
-
- virtual bool lineContinue(){return false;}
-
- virtual TQStringList *capturedTexts() {return 0;}
- virtual KateHlItem *clone(const TQStringList *) {return this;}
-
- static void dynamicSubstitute(TQString& str, const TQStringList *args);
-
- TQMemArray<KateHlItem*> subItems;
- int attr;
- int ctx;
- signed char region;
- signed char region2;
-
- bool lookAhead;
-
- bool dynamic;
- bool dynamicChild;
- bool firstNonSpace;
- bool onlyConsume;
- int column;
-
- // start enable flags, nicer than the virtual methodes
- // saves function calls
- bool alwaysStartEnable;
- bool customStartEnable;
- };
-
- class KateHlContext
- {
- public:
- KateHlContext(const TQString &_hlId, int attribute, int lineEndContext,int _lineBeginContext,
- bool _fallthrough, int _fallthroughContext, bool _dynamic,bool _noIndentationBasedFolding);
- virtual ~KateHlContext();
- KateHlContext *clone(const TQStringList *args);
-
- TQValueVector<KateHlItem*> items;
- TQString hlId; ///< A unique highlight identifier. Used to look up correct properties.
- int attr;
- int ctx;
- int lineBeginContext;
- /** @internal anders: possible escape if no rules matches.
- false unless 'fallthrough="1|true"' (insensitive)
- if true, go to ftcxt w/o eating of string.
- ftctx is "fallthroughContext" in xml files, valid values are int or #pop[..]
- see in KateHighlighting::doHighlight */
- bool fallthrough;
- int ftctx; // where to go after no rules matched
-
- bool dynamic;
- bool dynamicChild;
- bool noIndentationBasedFolding;
- };
-
- class KateEmbeddedHlInfo
- {
- public:
- KateEmbeddedHlInfo() {loaded=false;context0=-1;}
- KateEmbeddedHlInfo(bool l, int ctx0) {loaded=l;context0=ctx0;}
-
- public:
- bool loaded;
- int context0;
- };
-
- class KateHlIncludeRule
- {
- public:
- KateHlIncludeRule(int ctx_=0, uint pos_=0, const TQString &incCtxN_="", bool incAttrib=false)
- : ctx(ctx_)
- , pos( pos_)
- , incCtxN( incCtxN_ )
- , includeAttrib( incAttrib )
- {
- incCtx=-1;
- }
- //KateHlIncludeRule(int ctx_, uint pos_, bool incAttrib) {ctx=ctx_;pos=pos_;incCtx=-1;incCtxN="";includeAttrib=incAttrib}
-
- public:
- int ctx;
- uint pos;
- int incCtx;
- TQString incCtxN;
- bool includeAttrib;
- };
-
- class KateHlCharDetect : public KateHlItem
- {
- public:
- KateHlCharDetect(int attribute, int context,signed char regionId,signed char regionId2, TQChar);
-
- virtual int checkHgl(const TQString& text, int offset, int len);
- virtual KateHlItem *clone(const TQStringList *args);
-
- private:
- TQChar sChar;
- };
-
- class KateHl2CharDetect : public KateHlItem
- {
- public:
- KateHl2CharDetect(int attribute, int context, signed char regionId,signed char regionId2, TQChar ch1, TQChar ch2);
- KateHl2CharDetect(int attribute, int context,signed char regionId,signed char regionId2, const TQChar *ch);
-
- virtual int checkHgl(const TQString& text, int offset, int len);
- virtual KateHlItem *clone(const TQStringList *args);
-
- private:
- TQChar sChar1;
- TQChar sChar2;
- };
-
- class KateHlStringDetect : public KateHlItem
- {
- public:
- KateHlStringDetect(int attribute, int context, signed char regionId,signed char regionId2, const TQString &, bool inSensitive=false);
-
- virtual int checkHgl(const TQString& text, int offset, int len);
- virtual KateHlItem *clone(const TQStringList *args);
-
- private:
- const TQString str;
- const int strLen;
- const bool _inSensitive;
- };
-
- class KateHlRangeDetect : public KateHlItem
- {
- public:
- KateHlRangeDetect(int attribute, int context, signed char regionId,signed char regionId2, TQChar ch1, TQChar ch2);
-
- virtual int checkHgl(const TQString& text, int offset, int len);
-
- private:
- TQChar sChar1;
- TQChar sChar2;
- };
-
- class KateHlKeyword : public KateHlItem
- {
- public:
- KateHlKeyword(int attribute, int context,signed char regionId,signed char regionId2, bool insensitive, const TQString& delims);
- virtual ~KateHlKeyword ();
-
- void addList(const TQStringList &);
- virtual int checkHgl(const TQString& text, int offset, int len);
-
- private:
- TQMemArray< TQDict<bool>* > dict;
- bool _insensitive;
- const TQString& deliminators;
- int minLen;
- int maxLen;
- };
-
- class KateHlInt : public KateHlItem
- {
- public:
- KateHlInt(int attribute, int context, signed char regionId,signed char regionId2);
-
- virtual int checkHgl(const TQString& text, int offset, int len);
- };
-
- class KateHlFloat : public KateHlItem
- {
- public:
- KateHlFloat(int attribute, int context, signed char regionId,signed char regionId2);
- virtual ~KateHlFloat () {}
-
- virtual int checkHgl(const TQString& text, int offset, int len);
- };
-
- class KateHlCFloat : public KateHlFloat
- {
- public:
- KateHlCFloat(int attribute, int context, signed char regionId,signed char regionId2);
-
- virtual int checkHgl(const TQString& text, int offset, int len);
- int checkIntHgl(const TQString& text, int offset, int len);
- };
-
- class KateHlCOct : public KateHlItem
- {
- public:
- KateHlCOct(int attribute, int context, signed char regionId,signed char regionId2);
-
- virtual int checkHgl(const TQString& text, int offset, int len);
- };
-
- class KateHlCHex : public KateHlItem
- {
- public:
- KateHlCHex(int attribute, int context, signed char regionId,signed char regionId2);
-
- virtual int checkHgl(const TQString& text, int offset, int len);
- };
-
- class KateHlLineContinue : public KateHlItem
- {
- public:
- KateHlLineContinue(int attribute, int context, signed char regionId,signed char regionId2);
-
- virtual bool endEnable(TQChar c) {return c == '\0';}
- virtual int checkHgl(const TQString& text, int offset, int len);
- virtual bool lineContinue(){return true;}
- };
-
- class KateHlCStringChar : public KateHlItem
- {
- public:
- KateHlCStringChar(int attribute, int context, signed char regionId,signed char regionId2);
-
- virtual int checkHgl(const TQString& text, int offset, int len);
- };
-
- class KateHlCChar : public KateHlItem
- {
- public:
- KateHlCChar(int attribute, int context,signed char regionId,signed char regionId2);
-
- virtual int checkHgl(const TQString& text, int offset, int len);
- };
-
- class KateHlAnyChar : public KateHlItem
- {
- public:
- KateHlAnyChar(int attribute, int context, signed char regionId,signed char regionId2, const TQString& charList);
-
- virtual int checkHgl(const TQString& text, int offset, int len);
-
- private:
- const TQString _charList;
- };
-
- class KateHlRegExpr : public KateHlItem
- {
- public:
- KateHlRegExpr(int attribute, int context,signed char regionId,signed char regionId2 ,TQString expr, bool insensitive, bool minimal);
- ~KateHlRegExpr() { delete Expr; };
-
- virtual int checkHgl(const TQString& text, int offset, int len);
- virtual TQStringList *capturedTexts();
- virtual KateHlItem *clone(const TQStringList *args);
-
- private:
- TQRegExp *Expr;
- bool handlesLinestart;
- TQString _regexp;
- bool _insensitive;
- bool _minimal;
- };
-
- class KateHlDetectSpaces : public KateHlItem
- {
- public:
- KateHlDetectSpaces (int attribute, int context,signed char regionId,signed char regionId2)
- : KateHlItem(attribute,context,regionId,regionId2) {}
-
- virtual int checkHgl(const TQString& text, int offset, int len)
- {
- int len2 = offset + len;
- while ((offset < len2) && text[offset].isSpace()) offset++;
- return offset;
- }
- };
-
- class KateHlDetectIdentifier : public KateHlItem
- {
- public:
- KateHlDetectIdentifier (int attribute, int context,signed char regionId,signed char regionId2)
- : KateHlItem(attribute,context,regionId,regionId2) { alwaysStartEnable = false; }
-
- virtual int checkHgl(const TQString& text, int offset, int len)
- {
- // first char should be a letter or underscore
- if ( text[offset].isLetter() || text[offset] == TQChar ('_') )
- {
- // memorize length
- int len2 = offset+len;
-
- // one char seen
- offset++;
-
- // now loop for all other thingies
- while (
- (offset < len2)
- && (text[offset].isLetterOrNumber() || (text[offset] == TQChar ('_')))
- )
- offset++;
-
- return offset;
- }
-
- return 0;
- }
- };
-
- //END
-
- //BEGIN STATICS
- KateHlManager *KateHlManager::s_self = 0;
-
- static const bool trueBool = true;
- static const TQString stdDeliminator = TQString (" \t.():!+,-<=>%&*/;?[]^{|}~\\");
- //END
-
- //BEGIN NON MEMBER FUNCTIONS
- static KateHlItemData::ItemStyles getDefStyleNum(TQString name)
- {
- if (name=="dsNormal") return KateHlItemData::dsNormal;
- else if (name=="dsKeyword") return KateHlItemData::dsKeyword;
- else if (name=="dsDataType") return KateHlItemData::dsDataType;
- else if (name=="dsDecVal") return KateHlItemData::dsDecVal;
- else if (name=="dsBaseN") return KateHlItemData::dsBaseN;
- else if (name=="dsFloat") return KateHlItemData::dsFloat;
- else if (name=="dsChar") return KateHlItemData::dsChar;
- else if (name=="dsString") return KateHlItemData::dsString;
- else if (name=="dsComment") return KateHlItemData::dsComment;
- else if (name=="dsOthers") return KateHlItemData::dsOthers;
- else if (name=="dsAlert") return KateHlItemData::dsAlert;
- else if (name=="dsFunction") return KateHlItemData::dsFunction;
- else if (name=="dsRegionMarker") return KateHlItemData::dsRegionMarker;
- else if (name=="dsError") return KateHlItemData::dsError;
-
- return KateHlItemData::dsNormal;
- }
- //END
-
- //BEGIN KateHlItem
- KateHlItem::KateHlItem(int attribute, int context,signed char regionId,signed char regionId2)
- : attr(attribute),
- ctx(context),
- region(regionId),
- region2(regionId2),
- lookAhead(false),
- dynamic(false),
- dynamicChild(false),
- firstNonSpace(false),
- onlyConsume(false),
- column (-1),
- alwaysStartEnable (true),
- customStartEnable (false)
- {
- }
-
- KateHlItem::~KateHlItem()
- {
- //kdDebug(13010)<<"In hlItem::~KateHlItem()"<<endl;
- for (uint i=0; i < subItems.size(); i++)
- delete subItems[i];
- }
-
- void KateHlItem::dynamicSubstitute(TQString &str, const TQStringList *args)
- {
- for (uint i = 0; i < str.length() - 1; ++i)
- {
- if (str[i] == '%')
- {
- char c = str[i + 1].latin1();
- if (c == '%')
- str.replace(i, 1, "");
- else if (c >= '0' && c <= '9')
- {
- if ((uint)(c - '0') < args->size())
- {
- str.replace(i, 2, (*args)[c - '0']);
- i += ((*args)[c - '0']).length() - 1;
- }
- else
- {
- str.replace(i, 2, "");
- --i;
- }
- }
- }
- }
- }
- //END
-
- //BEGIN KateHlCharDetect
- KateHlCharDetect::KateHlCharDetect(int attribute, int context, signed char regionId,signed char regionId2, TQChar c)
- : KateHlItem(attribute,context,regionId,regionId2)
- , sChar(c)
- {
- }
-
- int KateHlCharDetect::checkHgl(const TQString& text, int offset, int /*len*/)
- {
- if (text[offset] == sChar)
- return offset + 1;
-
- return 0;
- }
-
- KateHlItem *KateHlCharDetect::clone(const TQStringList *args)
- {
- char c = sChar.latin1();
-
- if (c < '0' || c > '9' || (unsigned)(c - '0') >= args->size())
- return this;
-
- KateHlCharDetect *ret = new KateHlCharDetect(attr, ctx, region, region2, (*args)[c - '0'][0]);
- ret->dynamicChild = true;
- return ret;
- }
- //END
-
- //BEGIN KateHl2CharDetect
- KateHl2CharDetect::KateHl2CharDetect(int attribute, int context, signed char regionId,signed char regionId2, TQChar ch1, TQChar ch2)
- : KateHlItem(attribute,context,regionId,regionId2)
- , sChar1 (ch1)
- , sChar2 (ch2)
- {
- }
-
- int KateHl2CharDetect::checkHgl(const TQString& text, int offset, int len)
- {
- if ((len >= 2) && text[offset++] == sChar1 && text[offset++] == sChar2)
- return offset;
-
- return 0;
- }
-
- KateHlItem *KateHl2CharDetect::clone(const TQStringList *args)
- {
- char c1 = sChar1.latin1();
- char c2 = sChar2.latin1();
-
- if (c1 < '0' || c1 > '9' || (unsigned)(c1 - '0') >= args->size())
- return this;
-
- if (c2 < '0' || c2 > '9' || (unsigned)(c2 - '0') >= args->size())
- return this;
-
- KateHl2CharDetect *ret = new KateHl2CharDetect(attr, ctx, region, region2, (*args)[c1 - '0'][0], (*args)[c2 - '0'][0]);
- ret->dynamicChild = true;
- return ret;
- }
- //END
-
- //BEGIN KateHlStringDetect
- KateHlStringDetect::KateHlStringDetect(int attribute, int context, signed char regionId,signed char regionId2,const TQString &s, bool inSensitive)
- : KateHlItem(attribute, context,regionId,regionId2)
- , str(inSensitive ? s.upper() : s)
- , strLen (str.length())
- , _inSensitive(inSensitive)
- {
- }
-
- int KateHlStringDetect::checkHgl(const TQString& text, int offset, int len)
- {
- if (len < strLen)
- return 0;
-
- if (_inSensitive)
- {
- for (int i=0; i < strLen; i++)
- if (text[offset++].upper() != str[i])
- return 0;
-
- return offset;
- }
- else
- {
- for (int i=0; i < strLen; i++)
- if (text[offset++] != str[i])
- return 0;
-
- return offset;
- }
-
- return 0;
- }
-
- KateHlItem *KateHlStringDetect::clone(const TQStringList *args)
- {
- TQString newstr = str;
-
- dynamicSubstitute(newstr, args);
-
- if (newstr == str)
- return this;
-
- KateHlStringDetect *ret = new KateHlStringDetect(attr, ctx, region, region2, newstr, _inSensitive);
- ret->dynamicChild = true;
- return ret;
- }
- //END
-
- //BEGIN KateHlRangeDetect
- KateHlRangeDetect::KateHlRangeDetect(int attribute, int context, signed char regionId,signed char regionId2, TQChar ch1, TQChar ch2)
- : KateHlItem(attribute,context,regionId,regionId2)
- , sChar1 (ch1)
- , sChar2 (ch2)
- {
- }
-
- int KateHlRangeDetect::checkHgl(const TQString& text, int offset, int len)
- {
- if (text[offset] == sChar1)
- {
- do
- {
- offset++;
- len--;
- if (len < 1) return 0;
- }
- while (text[offset] != sChar2);
-
- return offset + 1;
- }
- return 0;
- }
- //END
-
- //BEGIN KateHlKeyword
- KateHlKeyword::KateHlKeyword (int attribute, int context, signed char regionId,signed char regionId2, bool insensitive, const TQString& delims)
- : KateHlItem(attribute,context,regionId,regionId2)
- , _insensitive(insensitive)
- , deliminators(delims)
- , minLen (0xFFFFFF)
- , maxLen (0)
- {
- alwaysStartEnable = false;
- customStartEnable = true;
- }
-
- KateHlKeyword::~KateHlKeyword ()
- {
- for (uint i=0; i < dict.size(); ++i)
- delete dict[i];
- }
-
- void KateHlKeyword::addList(const TQStringList& list)
- {
- for(uint i=0; i < list.count(); ++i)
- {
- int len = list[i].length();
-
- if (minLen > len)
- minLen = len;
-
- if (maxLen < len)
- maxLen = len;
-
- if ((uint)len >= dict.size())
- {
- uint oldSize = dict.size();
- dict.resize (len+1);
-
- for (uint m=oldSize; m < dict.size(); ++m)
- dict[m] = 0;
- }
-
- if (!dict[len])
- dict[len] = new TQDict<bool> (17, !_insensitive);
-
- dict[len]->insert(list[i], &trueBool);
- }
- }
-
- int KateHlKeyword::checkHgl(const TQString& text, int offset, int len)
- {
- int offset2 = offset;
- int wordLen = 0;
-
- while ((len > wordLen) && !kateInsideString (deliminators, text[offset2]))
- {
- offset2++;
- wordLen++;
-
- if (wordLen > maxLen) return 0;
- }
-
- if (wordLen < minLen) return 0;
-
- if ( dict[wordLen] && dict[wordLen]->find(TQConstString(text.unicode() + offset, wordLen).string()) )
- return offset2;
-
- return 0;
- }
- //END
-
- //BEGIN KateHlInt
- KateHlInt::KateHlInt(int attribute, int context, signed char regionId,signed char regionId2)
- : KateHlItem(attribute,context,regionId,regionId2)
- {
- alwaysStartEnable = false;
- }
-
- int KateHlInt::checkHgl(const TQString& text, int offset, int len)
- {
- int offset2 = offset;
-
- while ((len > 0) && text[offset2].isDigit())
- {
- offset2++;
- len--;
- }
-
- if (offset2 > offset)
- {
- if (len > 0)
- {
- for (uint i=0; i < subItems.size(); i++)
- {
- if ( (offset = subItems[i]->checkHgl(text, offset2, len)) )
- return offset;
- }
- }
-
- return offset2;
- }
-
- return 0;
- }
- //END
-
- //BEGIN KateHlFloat
- KateHlFloat::KateHlFloat(int attribute, int context, signed char regionId,signed char regionId2)
- : KateHlItem(attribute,context, regionId,regionId2)
- {
- alwaysStartEnable = false;
- }
-
- int KateHlFloat::checkHgl(const TQString& text, int offset, int len)
- {
- bool b = false;
- bool p = false;
-
- while ((len > 0) && text[offset].isDigit())
- {
- offset++;
- len--;
- b = true;
- }
-
- if ((len > 0) && (p = (text[offset] == '.')))
- {
- offset++;
- len--;
-
- while ((len > 0) && text[offset].isDigit())
- {
- offset++;
- len--;
- b = true;
- }
- }
-
- if (!b)
- return 0;
-
- if ((len > 0) && ((text[offset] & 0xdf) == 'E'))
- {
- offset++;
- len--;
- }
- else
- {
- if (!p)
- return 0;
- else
- {
- if (len > 0)
- {
- for (uint i=0; i < subItems.size(); i++)
- {
- int offset2 = subItems[i]->checkHgl(text, offset, len);
-
- if (offset2)
- return offset2;
- }
- }
-
- return offset;
- }
- }
-
- if ((len > 0) && (text[offset] == '-' || text[offset] =='+'))
- {
- offset++;
- len--;
- }
-
- b = false;
-
- while ((len > 0) && text[offset].isDigit())
- {
- offset++;
- len--;
- b = true;
- }
-
- if (b)
- {
- if (len > 0)
- {
- for (uint i=0; i < subItems.size(); i++)
- {
- int offset2 = subItems[i]->checkHgl(text, offset, len);
-
- if (offset2)
- return offset2;
- }
- }
-
- return offset;
- }
-
- return 0;
- }
- //END
-
- //BEGIN KateHlCOct
- KateHlCOct::KateHlCOct(int attribute, int context, signed char regionId,signed char regionId2)
- : KateHlItem(attribute,context,regionId,regionId2)
- {
- alwaysStartEnable = false;
- }
-
- int KateHlCOct::checkHgl(const TQString& text, int offset, int len)
- {
- if (text[offset] == '0')
- {
- offset++;
- len--;
-
- int offset2 = offset;
-
- while ((len > 0) && (text.at(offset2) >= TQChar('0') && text.at(offset2) <= TQChar('7')))
- {
- offset2++;
- len--;
- }
-
- if (offset2 > offset)
- {
- if ((len > 0) && ((text[offset2] & 0xdf) == 'L' || (text[offset] & 0xdf) == 'U' ))
- offset2++;
-
- return offset2;
- }
- }
-
- return 0;
- }
- //END
-
- //BEGIN KateHlCHex
- KateHlCHex::KateHlCHex(int attribute, int context,signed char regionId,signed char regionId2)
- : KateHlItem(attribute,context,regionId,regionId2)
- {
- alwaysStartEnable = false;
- }
-
- int KateHlCHex::checkHgl(const TQString& text, int offset, int len)
- {
- if ((len > 1) && (text[offset++] == '0') && ((text[offset++] & 0xdf) == 'X' ))
- {
- len -= 2;
-
- int offset2 = offset;
-
- while ((len > 0) && (text[offset2].isDigit() || ((text[offset2] & 0xdf) >= 'A' && (text[offset2] & 0xdf) <= 'F')))
- {
- offset2++;
- len--;
- }
-
- if (offset2 > offset)
- {
- if ((len > 0) && ((text[offset2] & 0xdf) == 'L' || (text[offset2] & 0xdf) == 'U' ))
- offset2++;
-
- return offset2;
- }
- }
-
- return 0;
- }
- //END
-
- //BEGIN KateHlCFloat
- KateHlCFloat::KateHlCFloat(int attribute, int context, signed char regionId,signed char regionId2)
- : KateHlFloat(attribute,context,regionId,regionId2)
- {
- alwaysStartEnable = false;
- }
-
- int KateHlCFloat::checkIntHgl(const TQString& text, int offset, int len)
- {
- int offset2 = offset;
-
- while ((len > 0) && text[offset].isDigit()) {
- offset2++;
- len--;
- }
-
- if (offset2 > offset)
- return offset2;
-
- return 0;
- }
-
- int KateHlCFloat::checkHgl(const TQString& text, int offset, int len)
- {
- int offset2 = KateHlFloat::checkHgl(text, offset, len);
-
- if (offset2)
- {
- if ((text[offset2] & 0xdf) == 'F' )
- offset2++;
-
- return offset2;
- }
- else
- {
- offset2 = checkIntHgl(text, offset, len);
-
- if (offset2 && ((text[offset2] & 0xdf) == 'F' ))
- return ++offset2;
- else
- return 0;
- }
- }
- //END
-
- //BEGIN KateHlAnyChar
- KateHlAnyChar::KateHlAnyChar(int attribute, int context, signed char regionId,signed char regionId2, const TQString& charList)
- : KateHlItem(attribute, context,regionId,regionId2)
- , _charList(charList)
- {
- }
-
- int KateHlAnyChar::checkHgl(const TQString& text, int offset, int)
- {
- if (kateInsideString (_charList, text[offset]))
- return ++offset;
-
- return 0;
- }
- //END
-
- //BEGIN KateHlRegExpr
- KateHlRegExpr::KateHlRegExpr( int attribute, int context, signed char regionId,signed char regionId2, TQString regexp, bool insensitive, bool minimal)
- : KateHlItem(attribute, context, regionId,regionId2)
- , handlesLinestart (regexp.startsWith("^"))
- , _regexp(regexp)
- , _insensitive(insensitive)
- , _minimal(minimal)
- {
- if (!handlesLinestart)
- regexp.prepend("^");
-
- Expr = new TQRegExp(regexp, !_insensitive);
- Expr->setMinimal(_minimal);
- }
-
- int KateHlRegExpr::checkHgl(const TQString& text, int offset, int /*len*/)
- {
- if (offset && handlesLinestart)
- return 0;
-
- int offset2 = Expr->search( text, offset, TQRegExp::CaretAtOffset );
-
- if (offset2 == -1) return 0;
-
- return (offset + Expr->matchedLength());
- }
-
- TQStringList *KateHlRegExpr::capturedTexts()
- {
- return new TQStringList(Expr->capturedTexts());
- }
-
- KateHlItem *KateHlRegExpr::clone(const TQStringList *args)
- {
- TQString regexp = _regexp;
- TQStringList escArgs = *args;
-
- for (TQStringList::Iterator it = escArgs.begin(); it != escArgs.end(); ++it)
- {
- (*it).replace(TQRegExp("(\\W)"), "\\\\1");
- }
-
- dynamicSubstitute(regexp, &escArgs);
-
- if (regexp == _regexp)
- return this;
-
- // kdDebug (13010) << "clone regexp: " << regexp << endl;
-
- KateHlRegExpr *ret = new KateHlRegExpr(attr, ctx, region, region2, regexp, _insensitive, _minimal);
- ret->dynamicChild = true;
- return ret;
- }
- //END
-
- //BEGIN KateHlLineContinue
- KateHlLineContinue::KateHlLineContinue(int attribute, int context, signed char regionId,signed char regionId2)
- : KateHlItem(attribute,context,regionId,regionId2) {
- }
-
- int KateHlLineContinue::checkHgl(const TQString& text, int offset, int len)
- {
- if ((len == 1) && (text[offset] == '\\'))
- return ++offset;
-
- return 0;
- }
- //END
-
- //BEGIN KateHlCStringChar
- KateHlCStringChar::KateHlCStringChar(int attribute, int context,signed char regionId,signed char regionId2)
- : KateHlItem(attribute,context,regionId,regionId2) {
- }
-
- // checks for C escaped chars \n and escaped hex/octal chars
- static int checkEscapedChar(const TQString& text, int offset, int& len)
- {
- int i;
- if (text[offset] == '\\' && len > 1)
- {
- offset++;
- len--;
-
- switch(text[offset])
- {
- case 'a': // checks for control chars
- case 'b': // we want to fall through
- case 'e':
- case 'f':
-
- case 'n':
- case 'r':
- case 't':
- case 'v':
- case '\'':
- case '\"':
- case '?' : // added ? ANSI C classifies this as an escaped char
- case '\\':
- offset++;
- len--;
- break;
-
- case 'x': // if it's like \xff
- offset++; // eat the x
- len--;
- // these for loops can probably be
- // replaced with something else but
- // for right now they work
- // check for hexdigits
- for (i = 0; (len > 0) && (i < 2) && (static_cast<const char>(text.at(offset)) >= '0' && static_cast<const char>(text.at(offset)) <= '9' || (text[offset] & 0xdf) >= 'A' && (text[offset] & 0xdf) <= 'F'); i++)
- {
- offset++;
- len--;
- }
-
- if (i == 0)
- return 0; // takes care of case '\x'
-
- break;
-
- case '0': case '1': case '2': case '3' :
- case '4': case '5': case '6': case '7' :
- for (i = 0; (len > 0) && (i < 3) && (static_cast<const char>(text.at(offset)) >= '0' && static_cast<const char>(text.at(offset)) <= '7'); i++)
- {
- offset++;
- len--;
- }
- break;
-
- default:
- return 0;
- }
-
- return offset;
- }
-
- return 0;
- }
-
- int KateHlCStringChar::checkHgl(const TQString& text, int offset, int len)
- {
- return checkEscapedChar(text, offset, len);
- }
- //END
-
- //BEGIN KateHlCChar
- KateHlCChar::KateHlCChar(int attribute, int context,signed char regionId,signed char regionId2)
- : KateHlItem(attribute,context,regionId,regionId2) {
- }
-
- int KateHlCChar::checkHgl(const TQString& text, int offset, int len)
- {
- if ((len > 1) && (text[offset] == '\'') && (text[offset+1] != '\''))
- {
- int oldl;
- oldl = len;
-
- len--;
-
- int offset2 = checkEscapedChar(text, offset + 1, len);
-
- if (!offset2)
- {
- if (oldl > 2)
- {
- offset2 = offset + 2;
- len = oldl - 2;
- }
- else
- {
- return 0;
- }
- }
-
- if ((len > 0) && (text[offset2] == '\''))
- return ++offset2;
- }
-
- return 0;
- }
- //END
-
- //BEGIN KateHl2CharDetect
- KateHl2CharDetect::KateHl2CharDetect(int attribute, int context, signed char regionId,signed char regionId2, const TQChar *s)
- : KateHlItem(attribute,context,regionId,regionId2) {
- sChar1 = s[0];
- sChar2 = s[1];
- }
- //END KateHl2CharDetect
-
- KateHlItemData::KateHlItemData(const TQString name, int defStyleNum)
- : name(name), defStyleNum(defStyleNum) {
- }
-
- KateHlData::KateHlData(const TQString &wildcards, const TQString &mimetypes, const TQString &identifier, int priority)
- : wildcards(wildcards), mimetypes(mimetypes), identifier(identifier), priority(priority)
- {
- }
-
- //BEGIN KateHlContext
- KateHlContext::KateHlContext (const TQString &_hlId, int attribute, int lineEndContext, int _lineBeginContext, bool _fallthrough,
- int _fallthroughContext, bool _dynamic, bool _noIndentationBasedFolding)
- {
- hlId = _hlId;
- attr = attribute;
- ctx = lineEndContext;
- lineBeginContext = _lineBeginContext;
- fallthrough = _fallthrough;
- ftctx = _fallthroughContext;
- dynamic = _dynamic;
- dynamicChild = false;
- noIndentationBasedFolding=_noIndentationBasedFolding;
- if (_noIndentationBasedFolding) kdDebug(13010)<<TQString("**********************_noIndentationBasedFolding is TRUE*****************")<<endl;
-
- }
-
- KateHlContext *KateHlContext::clone(const TQStringList *args)
- {
- KateHlContext *ret = new KateHlContext(hlId, attr, ctx, lineBeginContext, fallthrough, ftctx, false,noIndentationBasedFolding);
-
- for (uint n=0; n < items.size(); ++n)
- {
- KateHlItem *item = items[n];
- KateHlItem *i = (item->dynamic ? item->clone(args) : item);
- ret->items.append(i);
- }
-
- ret->dynamicChild = true;
-
- return ret;
- }
-
- KateHlContext::~KateHlContext()
- {
- if (dynamicChild)
- {
- for (uint n=0; n < items.size(); ++n)
- {
- if (items[n]->dynamicChild)
- delete items[n];
- }
- }
- }
- //END
-
- //BEGIN KateHighlighting
- KateHighlighting::KateHighlighting(const KateSyntaxModeListItem *def) : refCount(0)
- {
- m_attributeArrays.setAutoDelete (true);
-
- errorsAndWarnings = "";
- building=false;
- noHl = false;
- m_foldingIndentationSensitive = false;
- folding=false;
- internalIDList.setAutoDelete(true);
-
- if (def == 0)
- {
- noHl = true;
- iName = "None"; // not translated internal name (for config and more)
- iNameTranslated = i18n("None"); // user visible name
- iSection = "";
- m_priority = 0;
- iHidden = false;
- m_additionalData.insert( "none", new HighlightPropertyBag );
- m_additionalData["none"]->deliminator = stdDeliminator;
- m_additionalData["none"]->wordWrapDeliminator = stdDeliminator;
- m_hlIndex[0] = "none";
- }
- else
- {
- iName = def->name;
- iNameTranslated = def->nameTranslated;
- iSection = def->section;
- iHidden = def->hidden;
- iWildcards = def->extension;
- iMimetypes = def->mimetype;
- identifier = def->identifier;
- iVersion=def->version;
- iAuthor=def->author;
- iLicense=def->license;
- m_priority=def->priority.toInt();
- }
-
- deliminator = stdDeliminator;
- }
-
- KateHighlighting::~KateHighlighting()
- {
- // cu contexts
- for (uint i=0; i < m_contexts.size(); ++i)
- delete m_contexts[i];
- m_contexts.clear ();
- }
-
- void KateHighlighting::generateContextStack(int *ctxNum, int ctx, TQMemArray<short>* ctxs, int *prevLine)
- {
- //kdDebug(13010)<<TQString("Entering generateContextStack with %1").arg(ctx)<<endl;
- while (true)
- {
- if (ctx >= 0)
- {
- (*ctxNum) = ctx;
-
- ctxs->resize (ctxs->size()+1, TQGArray::SpeedOptim);
- (*ctxs)[ctxs->size()-1]=(*ctxNum);
-
- return;
- }
- else
- {
- if (ctx == -1)
- {
- (*ctxNum)=( (ctxs->isEmpty() ) ? 0 : (*ctxs)[ctxs->size()-1]);
- }
- else
- {
- int size = ctxs->size() + ctx + 1;
-
- if (size > 0)
- {
- ctxs->resize (size, TQGArray::SpeedOptim);
- (*ctxNum)=(*ctxs)[size-1];
- }
- else
- {
- ctxs->resize (0, TQGArray::SpeedOptim);
- (*ctxNum)=0;
- }
-
- ctx = 0;
-
- if ((*prevLine) >= (int)(ctxs->size()-1))
- {
- *prevLine=ctxs->size()-1;
-
- if ( ctxs->isEmpty() )
- return;
-
- KateHlContext *c = contextNum((*ctxs)[ctxs->size()-1]);
- if (c && (c->ctx != -1))
- {
- //kdDebug(13010)<<"PrevLine > size()-1 and ctx!=-1)"<<endl;
- ctx = c->ctx;
-
- continue;
- }
- }
- }
-
- return;
- }
- }
- }
-
- /**
- * Creates a new dynamic context or reuse an old one if it has already been created.
- */
- int KateHighlighting::makeDynamicContext(KateHlContext *model, const TQStringList *args)
- {
- QPair<KateHlContext *, TQString> key(model, args->front());
- short value;
-
- if (dynamicCtxs.contains(key))
- value = dynamicCtxs[key];
- else
- {
- kdDebug(13010) << "new stuff: " << startctx << endl;
-
- KateHlContext *newctx = model->clone(args);
-
- m_contexts.push_back (newctx);
-
- value = startctx++;
- dynamicCtxs[key] = value;
- KateHlManager::self()->incDynamicCtxs();
- }
-
- // kdDebug(13010) << "Dynamic context: using context #" << value << " (for model " << model << " with args " << *args << ")" << endl;
-
- return value;
- }
-
- /**
- * Drop all dynamic contexts. Shall be called with extreme care, and shall be immediatly
- * followed by a full HL invalidation.
- */
- void KateHighlighting::dropDynamicContexts()
- {
- for (uint i=base_startctx; i < m_contexts.size(); ++i)
- delete m_contexts[i];
-
- m_contexts.resize (base_startctx);
-
- dynamicCtxs.clear();
- startctx = base_startctx;
- }
-
- /**
- * Parse the text and fill in the context array and folding list array
- *
- * @param prevLine The previous line, the context array is picked up from that if present.
- * @param textLine The text line to parse
- * @param foldingList will be filled
- * @param ctxChanged will be set to reflect if the context changed
- */
- void KateHighlighting::doHighlight ( KateTextLine *prevLine,
- KateTextLine *textLine,
- TQMemArray<uint>* foldingList,
- bool *ctxChanged )
- {
- if (!textLine)
- return;
-
- if (noHl)
- {
- if (textLine->length() > 0)
- memset (textLine->attributes(), 0, textLine->length());
-
- return;
- }
-
- // duplicate the ctx stack, only once !
- TQMemArray<short> ctx;
- ctx.duplicate (prevLine->ctxArray());
-
- int ctxNum = 0;
- int previousLine = -1;
- KateHlContext *context;
-
- if (ctx.isEmpty())
- {
- // If the stack is empty, we assume to be in Context 0 (Normal)
- context = contextNum(ctxNum);
- }
- else
- {
- // There does an old context stack exist -> find the context at the line start
- ctxNum = ctx[ctx.size()-1]; //context ID of the last character in the previous line
-
- //kdDebug(13010) << "\t\tctxNum = " << ctxNum << " contextList[ctxNum] = " << contextList[ctxNum] << endl; // ellis
-
- //if (lineContinue) kdDebug(13010)<<TQString("The old context should be %1").arg((int)ctxNum)<<endl;
-
- if (!(context = contextNum(ctxNum)))
- context = contextNum(0);
-
- //kdDebug(13010)<<"test1-2-1-text2"<<endl;
-
- previousLine=ctx.size()-1; //position of the last context ID of th previous line within the stack
-
- // hl continue set or not ???
- if (prevLine->hlLineContinue())
- {
- prevLine--;
- }
- else
- {
- generateContextStack(&ctxNum, context->ctx, &ctx, &previousLine); //get stack ID to use
-
- if (!(context = contextNum(ctxNum)))
- context = contextNum(0);
- }
-
- //kdDebug(13010)<<"test1-2-1-text4"<<endl;
-
- //if (lineContinue) kdDebug(13010)<<TQString("The new context is %1").arg((int)ctxNum)<<endl;
- }
-
- // text, for programming convenience :)
- TQChar lastChar = ' ';
- const TQString& text = textLine->string();
- const int len = textLine->length();
-
- // calc at which char the first char occurs, set it to length of line if never
- const int firstChar = textLine->firstChar();
- const int startNonSpace = (firstChar == -1) ? len : firstChar;
-
- // last found item
- KateHlItem *item = 0;
-
- // loop over the line, offset gives current offset
- int offset = 0;
- while (offset < len)
- {
- bool anItemMatched = false;
- bool standardStartEnableDetermined = false;
- bool customStartEnableDetermined = false;
-
- uint index = 0;
- for (item = context->items.empty() ? 0 : context->items[0]; item; item = (++index < context->items.size()) ? context->items[index] : 0 )
- {
- // does we only match if we are firstNonSpace?
- if (item->firstNonSpace && (offset > startNonSpace))
|