1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216 |
- /*
- ===========================================================================
- Doom 3 BFG Edition GPL Source Code
- Copyright (C) 1993-2012 id Software LLC, a ZeniMax Media company.
- This file is part of the Doom 3 BFG Edition GPL Source Code ("Doom 3 BFG Edition Source Code").
- Doom 3 BFG Edition Source Code is free software: you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation, either version 3 of the License, or
- (at your option) any later version.
- Doom 3 BFG Edition Source Code 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 General Public License for more details.
- You should have received a copy of the GNU General Public License
- along with Doom 3 BFG Edition Source Code. If not, see <http://www.gnu.org/licenses/>.
- In addition, the Doom 3 BFG Edition Source Code is also subject to certain additional terms. You should have received a copy of these additional terms immediately following the terms and conditions of the GNU General Public License which accompanied the Doom 3 BFG Edition Source Code. If not, please request a copy in writing from id Software at the address below.
- If you have questions concerning this license or the applicable additional terms, you may contact in writing id Software LLC, c/o ZeniMax Media Inc., Suite 120, Rockville, Maryland 20850 USA.
- ===========================================================================
- */
- #ifndef __STR_H__
- #define __STR_H__
- /*
- ===============================================================================
- Character string
- ===============================================================================
- */
- #define ASSERT_ENUM_STRING( string, index ) ( 1 / (int)!( string - index ) ) ? #string : ""
- enum utf8Encoding_t {
- UTF8_PURE_ASCII, // no characters with values > 127
- UTF8_ENCODED_BOM, // characters > 128 encoded with UTF8, but no byte-order-marker at the beginning
- UTF8_ENCODED_NO_BOM, // characters > 128 encoded with UTF8, with a byte-order-marker at the beginning
- UTF8_INVALID, // has values > 127 but isn't valid UTF8
- UTF8_INVALID_BOM // has a byte-order-marker at the beginning, but isn't valuid UTF8 -- it's messed up
- };
- // these library functions should not be used for cross platform compatibility
- #define strcmp idStr::Cmp // use_idStr_Cmp
- #define strncmp use_idStr_Cmpn
- #if defined( StrCmpN )
- #undef StrCmpN
- #endif
- #define StrCmpN use_idStr_Cmpn
- #if defined( strcmpi )
- #undef strcmpi
- #endif
- #define strcmpi use_idStr_Icmp
- #if defined( StrCmpI )
- #undef StrCmpI
- #endif
- #define StrCmpI use_idStr_Icmp
- #if defined( StrCmpNI )
- #undef StrCmpNI
- #endif
- #define StrCmpNI use_idStr_Icmpn
- #define stricmp idStr::Icmp // use_idStr_Icmp
- #define _stricmp use_idStr_Icmp
- #define strcasecmp use_idStr_Icmp
- #define strnicmp use_idStr_Icmpn
- #define _strnicmp use_idStr_Icmpn
- #define _memicmp use_idStr_Icmpn
- #define snprintf use_idStr_snPrintf
- #define _snprintf use_idStr_snPrintf
- #define vsnprintf use_idStr_vsnPrintf
- #define _vsnprintf use_idStr_vsnPrintf
- class idVec4;
- #ifndef FILE_HASH_SIZE
- #define FILE_HASH_SIZE 1024
- #endif
- // color escape character
- const int C_COLOR_ESCAPE = '^';
- const int C_COLOR_DEFAULT = '0';
- const int C_COLOR_RED = '1';
- const int C_COLOR_GREEN = '2';
- const int C_COLOR_YELLOW = '3';
- const int C_COLOR_BLUE = '4';
- const int C_COLOR_CYAN = '5';
- const int C_COLOR_ORANGE = '6';
- const int C_COLOR_WHITE = '7';
- const int C_COLOR_GRAY = '8';
- const int C_COLOR_BLACK = '9';
- // color escape string
- #define S_COLOR_DEFAULT "^0"
- #define S_COLOR_RED "^1"
- #define S_COLOR_GREEN "^2"
- #define S_COLOR_YELLOW "^3"
- #define S_COLOR_BLUE "^4"
- #define S_COLOR_CYAN "^5"
- #define S_COLOR_ORANGE "^6"
- #define S_COLOR_WHITE "^7"
- #define S_COLOR_GRAY "^8"
- #define S_COLOR_BLACK "^9"
- // make idStr a multiple of 16 bytes long
- // don't make too large to keep memory requirements to a minimum
- const int STR_ALLOC_BASE = 20;
- const int STR_ALLOC_GRAN = 32;
- typedef enum {
- MEASURE_SIZE = 0,
- MEASURE_BANDWIDTH
- } Measure_t;
- class idStr {
- public:
- idStr();
- idStr( const idStr &text );
- idStr( const idStr &text, int start, int end );
- idStr( const char *text );
- idStr( const char *text, int start, int end );
- explicit idStr( const bool b );
- explicit idStr( const char c );
- explicit idStr( const int i );
- explicit idStr( const unsigned u );
- explicit idStr( const float f );
- ~idStr();
- size_t Size() const;
- const char * c_str() const;
- operator const char *() const;
- operator const char *();
- char operator[]( int index ) const;
- char & operator[]( int index );
- void operator=( const idStr &text );
- void operator=( const char *text );
- friend idStr operator+( const idStr &a, const idStr &b );
- friend idStr operator+( const idStr &a, const char *b );
- friend idStr operator+( const char *a, const idStr &b );
- friend idStr operator+( const idStr &a, const float b );
- friend idStr operator+( const idStr &a, const int b );
- friend idStr operator+( const idStr &a, const unsigned b );
- friend idStr operator+( const idStr &a, const bool b );
- friend idStr operator+( const idStr &a, const char b );
- idStr & operator+=( const idStr &a );
- idStr & operator+=( const char *a );
- idStr & operator+=( const float a );
- idStr & operator+=( const char a );
- idStr & operator+=( const int a );
- idStr & operator+=( const unsigned a );
- idStr & operator+=( const bool a );
- // case sensitive compare
- friend bool operator==( const idStr &a, const idStr &b );
- friend bool operator==( const idStr &a, const char *b );
- friend bool operator==( const char *a, const idStr &b );
- // case sensitive compare
- friend bool operator!=( const idStr &a, const idStr &b );
- friend bool operator!=( const idStr &a, const char *b );
- friend bool operator!=( const char *a, const idStr &b );
- // case sensitive compare
- int Cmp( const char *text ) const;
- int Cmpn( const char *text, int n ) const;
- int CmpPrefix( const char *text ) const;
- // case insensitive compare
- int Icmp( const char *text ) const;
- int Icmpn( const char *text, int n ) const;
- int IcmpPrefix( const char *text ) const;
- // case insensitive compare ignoring color
- int IcmpNoColor( const char *text ) const;
- // compares paths and makes sure folders come first
- int IcmpPath( const char *text ) const;
- int IcmpnPath( const char *text, int n ) const;
- int IcmpPrefixPath( const char *text ) const;
- int Length() const;
- int Allocated() const;
- void Empty();
- bool IsEmpty() const;
- void Clear();
- void Append( const char a );
- void Append( const idStr &text );
- void Append( const char *text );
- void Append( const char *text, int len );
- void Insert( const char a, int index );
- void Insert( const char *text, int index );
- void ToLower();
- void ToUpper();
- bool IsNumeric() const;
- bool IsColor() const;
- bool HasLower() const;
- bool HasUpper() const;
- int LengthWithoutColors() const;
- idStr & RemoveColors();
- void CapLength( int );
- void Fill( const char ch, int newlen );
- ID_INLINE int UTF8Length();
- ID_INLINE uint32 UTF8Char( int & idx );
- static int UTF8Length( const byte * s );
- static ID_INLINE uint32 UTF8Char( const char * s, int & idx );
- static uint32 UTF8Char( const byte * s, int & idx );
- void AppendUTF8Char( uint32 c );
- ID_INLINE void ConvertToUTF8();
- static bool IsValidUTF8( const uint8 * s, const int maxLen, utf8Encoding_t & encoding );
- static ID_INLINE bool IsValidUTF8( const char * s, const int maxLen, utf8Encoding_t & encoding ) { return IsValidUTF8( ( const uint8* )s, maxLen, encoding ); }
- static ID_INLINE bool IsValidUTF8( const uint8 * s, const int maxLen );
- static ID_INLINE bool IsValidUTF8( const char * s, const int maxLen ) { return IsValidUTF8( ( const uint8* )s, maxLen ); }
- int Find( const char c, int start = 0, int end = -1 ) const;
- int Find( const char *text, bool casesensitive = true, int start = 0, int end = -1 ) const;
- bool Filter( const char *filter, bool casesensitive ) const;
- int Last( const char c ) const; // return the index to the last occurance of 'c', returns -1 if not found
- const char * Left( int len, idStr &result ) const; // store the leftmost 'len' characters in the result
- const char * Right( int len, idStr &result ) const; // store the rightmost 'len' characters in the result
- const char * Mid( int start, int len, idStr &result ) const; // store 'len' characters starting at 'start' in result
- idStr Left( int len ) const; // return the leftmost 'len' characters
- idStr Right( int len ) const; // return the rightmost 'len' characters
- idStr Mid( int start, int len ) const; // return 'len' characters starting at 'start'
- void Format( VERIFY_FORMAT_STRING const char *fmt, ... ); // perform a threadsafe sprintf to the string
- static idStr FormatInt( const int num, bool isCash = false ); // formats an integer as a value with commas
- static idStr FormatCash( const int num ) { return FormatInt( num, true ); }
- void StripLeading( const char c ); // strip char from front as many times as the char occurs
- void StripLeading( const char *string ); // strip string from front as many times as the string occurs
- bool StripLeadingOnce( const char *string ); // strip string from front just once if it occurs
- void StripTrailing( const char c ); // strip char from end as many times as the char occurs
- void StripTrailing( const char *string ); // strip string from end as many times as the string occurs
- bool StripTrailingOnce( const char *string ); // strip string from end just once if it occurs
- void Strip( const char c ); // strip char from front and end as many times as the char occurs
- void Strip( const char *string ); // strip string from front and end as many times as the string occurs
- void StripTrailingWhitespace(); // strip trailing white space characters
- idStr & StripQuotes(); // strip quotes around string
- bool Replace( const char *old, const char *nw );
- bool ReplaceChar( const char old, const char nw );
- ID_INLINE void CopyRange( const char * text, int start, int end );
- // file name methods
- int FileNameHash() const; // hash key for the filename (skips extension)
- idStr & BackSlashesToSlashes(); // convert slashes
- idStr & SlashesToBackSlashes(); // convert slashes
- idStr & SetFileExtension( const char *extension ); // set the given file extension
- idStr & StripFileExtension(); // remove any file extension
- idStr & StripAbsoluteFileExtension(); // remove any file extension looking from front (useful if there are multiple .'s)
- idStr & DefaultFileExtension( const char *extension ); // if there's no file extension use the default
- idStr & DefaultPath( const char *basepath ); // if there's no path use the default
- void AppendPath( const char *text ); // append a partial path
- idStr & StripFilename(); // remove the filename from a path
- idStr & StripPath(); // remove the path from the filename
- void ExtractFilePath( idStr &dest ) const; // copy the file path to another string
- void ExtractFileName( idStr &dest ) const; // copy the filename to another string
- void ExtractFileBase( idStr &dest ) const; // copy the filename minus the extension to another string
- void ExtractFileExtension( idStr &dest ) const; // copy the file extension to another string
- bool CheckExtension( const char *ext );
- // char * methods to replace library functions
- static int Length( const char *s );
- static char * ToLower( char *s );
- static char * ToUpper( char *s );
- static bool IsNumeric( const char *s );
- static bool IsColor( const char *s );
- static bool HasLower( const char *s );
- static bool HasUpper( const char *s );
- static int LengthWithoutColors( const char *s );
- static char * RemoveColors( char *s );
- static int Cmp( const char *s1, const char *s2 );
- static int Cmpn( const char *s1, const char *s2, int n );
- static int Icmp( const char *s1, const char *s2 );
- static int Icmpn( const char *s1, const char *s2, int n );
- static int IcmpNoColor( const char *s1, const char *s2 );
- static int IcmpPath( const char *s1, const char *s2 ); // compares paths and makes sure folders come first
- static int IcmpnPath( const char *s1, const char *s2, int n ); // compares paths and makes sure folders come first
- static void Append( char *dest, int size, const char *src );
- static void Copynz( char *dest, const char *src, int destsize );
- static int snPrintf( char *dest, int size, VERIFY_FORMAT_STRING const char *fmt, ... );
- static int vsnPrintf( char *dest, int size, const char *fmt, va_list argptr );
- static int FindChar( const char *str, const char c, int start = 0, int end = -1 );
- static int FindText( const char *str, const char *text, bool casesensitive = true, int start = 0, int end = -1 );
- static bool Filter( const char *filter, const char *name, bool casesensitive );
- static void StripMediaName( const char *name, idStr &mediaName );
- static bool CheckExtension( const char *name, const char *ext );
- static const char * FloatArrayToString( const float *array, const int length, const int precision );
- static const char * CStyleQuote( const char *str );
- static const char * CStyleUnQuote( const char *str );
- // hash keys
- static int Hash( const char *string );
- static int Hash( const char *string, int length );
- static int IHash( const char *string ); // case insensitive
- static int IHash( const char *string, int length ); // case insensitive
- // character methods
- static char ToLower( char c );
- static char ToUpper( char c );
- static bool CharIsPrintable( int c );
- static bool CharIsLower( int c );
- static bool CharIsUpper( int c );
- static bool CharIsAlpha( int c );
- static bool CharIsNumeric( int c );
- static bool CharIsNewLine( char c );
- static bool CharIsTab( char c );
- static int ColorIndex( int c );
- static idVec4 & ColorForIndex( int i );
- friend int sprintf( idStr &dest, const char *fmt, ... );
- friend int vsprintf( idStr &dest, const char *fmt, va_list ap );
- void ReAllocate( int amount, bool keepold ); // reallocate string data buffer
- void FreeData(); // free allocated string memory
- // format value in the given measurement with the best unit, returns the best unit
- int BestUnit( const char *format, float value, Measure_t measure );
- // format value in the requested unit and measurement
- void SetUnit( const char *format, float value, int unit, Measure_t measure );
- static void InitMemory();
- static void ShutdownMemory();
- static void PurgeMemory();
- static void ShowMemoryUsage_f( const idCmdArgs &args );
- int DynamicMemoryUsed() const;
- static idStr FormatNumber( int number );
- protected:
- int len;
- char * data;
- int allocedAndFlag; // top bit is used to store a flag that indicates if the string data is static or not
- char baseBuffer[ STR_ALLOC_BASE ];
- void EnsureAlloced( int amount, bool keepold = true ); // ensure string data buffer is large anough
- // sets the data point to the specified buffer... note that this ignores makes the passed buffer empty and ignores
- // anything currently in the idStr's dynamic buffer. This method is intended to be called only from a derived class's constructor.
- ID_INLINE void SetStaticBuffer( char * buffer, const int bufferLength );
- private:
- // initialize string using base buffer... call ONLY FROM CONSTRUCTOR
- ID_INLINE void Construct();
- static const uint32 STATIC_BIT = 31;
- static const uint32 STATIC_MASK = 1u << STATIC_BIT;
- static const uint32 ALLOCED_MASK = STATIC_MASK - 1;
- ID_INLINE int GetAlloced() const { return allocedAndFlag & ALLOCED_MASK; }
- ID_INLINE void SetAlloced( const int a ) { allocedAndFlag = ( allocedAndFlag & STATIC_MASK ) | ( a & ALLOCED_MASK); }
- ID_INLINE bool IsStatic() const { return ( allocedAndFlag & STATIC_MASK ) != 0; }
- ID_INLINE void SetStatic( const bool isStatic ) { allocedAndFlag = ( allocedAndFlag & ALLOCED_MASK ) | ( isStatic << STATIC_BIT ); }
- public:
- static const int INVALID_POSITION = -1;
- };
- char * va( VERIFY_FORMAT_STRING const char *fmt, ... );
- /*
- ================================================================================================
- Sort routines for sorting idList<idStr>
- ================================================================================================
- */
- class idSort_Str : public idSort_Quick< idStr, idSort_Str > {
- public:
- int Compare( const idStr & a, const idStr & b ) const { return a.Icmp( b ); }
- };
- class idSort_PathStr : public idSort_Quick< idStr, idSort_PathStr > {
- public:
- int Compare( const idStr & a, const idStr & b ) const { return a.IcmpPath( b ); }
- };
- /*
- ========================
- idStr::Construct
- ========================
- */
- ID_INLINE void idStr::Construct() {
- SetStatic( false );
- SetAlloced( STR_ALLOC_BASE );
- data = baseBuffer;
- len = 0;
- data[ 0 ] = '\0';
- #ifdef ID_DEBUG_UNINITIALIZED_MEMORY
- memset( baseBuffer, 0, sizeof( baseBuffer ) );
- #endif
- }
- ID_INLINE void idStr::EnsureAlloced( int amount, bool keepold ) {
- // static string's can't reallocate
- if ( IsStatic() ) {
- release_assert( amount <= GetAlloced() );
- return;
- }
- if ( amount > GetAlloced() ) {
- ReAllocate( amount, keepold );
- }
- }
- /*
- ========================
- idStr::SetStaticBuffer
- ========================
- */
- ID_INLINE void idStr::SetStaticBuffer( char * buffer, const int bufferLength ) {
- // this should only be called on a freshly constructed idStr
- assert( data == baseBuffer );
- data = buffer;
- len = 0;
- SetAlloced( bufferLength );
- SetStatic( true );
- }
- ID_INLINE idStr::idStr() {
- Construct();
- }
- ID_INLINE idStr::idStr( const idStr &text ) {
- Construct();
- int l;
- l = text.Length();
- EnsureAlloced( l + 1 );
- strcpy( data, text.data );
- len = l;
- }
- ID_INLINE idStr::idStr( const idStr &text, int start, int end ) {
- Construct();
- int i;
- int l;
- if ( end > text.Length() ) {
- end = text.Length();
- }
- if ( start > text.Length() ) {
- start = text.Length();
- } else if ( start < 0 ) {
- start = 0;
- }
- l = end - start;
- if ( l < 0 ) {
- l = 0;
- }
- EnsureAlloced( l + 1 );
- for ( i = 0; i < l; i++ ) {
- data[ i ] = text[ start + i ];
- }
- data[ l ] = '\0';
- len = l;
- }
- ID_INLINE idStr::idStr( const char *text ) {
- Construct();
- int l;
- if ( text ) {
- l = strlen( text );
- EnsureAlloced( l + 1 );
- strcpy( data, text );
- len = l;
- }
- }
- ID_INLINE idStr::idStr( const char *text, int start, int end ) {
- Construct();
- int i;
- int l = strlen( text );
- if ( end > l ) {
- end = l;
- }
- if ( start > l ) {
- start = l;
- } else if ( start < 0 ) {
- start = 0;
- }
- l = end - start;
- if ( l < 0 ) {
- l = 0;
- }
- EnsureAlloced( l + 1 );
- for ( i = 0; i < l; i++ ) {
- data[ i ] = text[ start + i ];
- }
- data[ l ] = '\0';
- len = l;
- }
- ID_INLINE idStr::idStr( const bool b ) {
- Construct();
- EnsureAlloced( 2 );
- data[ 0 ] = b ? '1' : '0';
- data[ 1 ] = '\0';
- len = 1;
- }
- ID_INLINE idStr::idStr( const char c ) {
- Construct();
- EnsureAlloced( 2 );
- data[ 0 ] = c;
- data[ 1 ] = '\0';
- len = 1;
- }
- ID_INLINE idStr::idStr( const int i ) {
- Construct();
- char text[ 64 ];
- int l;
- l = sprintf( text, "%d", i );
- EnsureAlloced( l + 1 );
- strcpy( data, text );
- len = l;
- }
- ID_INLINE idStr::idStr( const unsigned u ) {
- Construct();
- char text[ 64 ];
- int l;
- l = sprintf( text, "%u", u );
- EnsureAlloced( l + 1 );
- strcpy( data, text );
- len = l;
- }
- ID_INLINE idStr::idStr( const float f ) {
- Construct();
- char text[ 64 ];
- int l;
- l = idStr::snPrintf( text, sizeof( text ), "%f", f );
- while( l > 0 && text[l-1] == '0' ) text[--l] = '\0';
- while( l > 0 && text[l-1] == '.' ) text[--l] = '\0';
- EnsureAlloced( l + 1 );
- strcpy( data, text );
- len = l;
- }
- ID_INLINE idStr::~idStr() {
- FreeData();
- }
- ID_INLINE size_t idStr::Size() const {
- return sizeof( *this ) + Allocated();
- }
- ID_INLINE const char *idStr::c_str() const {
- return data;
- }
- ID_INLINE idStr::operator const char *() {
- return c_str();
- }
- ID_INLINE idStr::operator const char *() const {
- return c_str();
- }
- ID_INLINE char idStr::operator[]( int index ) const {
- assert( ( index >= 0 ) && ( index <= len ) );
- return data[ index ];
- }
- ID_INLINE char &idStr::operator[]( int index ) {
- assert( ( index >= 0 ) && ( index <= len ) );
- return data[ index ];
- }
- ID_INLINE void idStr::operator=( const idStr &text ) {
- int l;
- l = text.Length();
- EnsureAlloced( l + 1, false );
- memcpy( data, text.data, l );
- data[l] = '\0';
- len = l;
- }
- ID_INLINE idStr operator+( const idStr &a, const idStr &b ) {
- idStr result( a );
- result.Append( b );
- return result;
- }
- ID_INLINE idStr operator+( const idStr &a, const char *b ) {
- idStr result( a );
- result.Append( b );
- return result;
- }
- ID_INLINE idStr operator+( const char *a, const idStr &b ) {
- idStr result( a );
- result.Append( b );
- return result;
- }
- ID_INLINE idStr operator+( const idStr &a, const bool b ) {
- idStr result( a );
- result.Append( b ? "true" : "false" );
- return result;
- }
- ID_INLINE idStr operator+( const idStr &a, const char b ) {
- idStr result( a );
- result.Append( b );
- return result;
- }
- ID_INLINE idStr operator+( const idStr &a, const float b ) {
- char text[ 64 ];
- idStr result( a );
- sprintf( text, "%f", b );
- result.Append( text );
- return result;
- }
- ID_INLINE idStr operator+( const idStr &a, const int b ) {
- char text[ 64 ];
- idStr result( a );
- sprintf( text, "%d", b );
- result.Append( text );
- return result;
- }
- ID_INLINE idStr operator+( const idStr &a, const unsigned b ) {
- char text[ 64 ];
- idStr result( a );
- sprintf( text, "%u", b );
- result.Append( text );
- return result;
- }
- ID_INLINE idStr &idStr::operator+=( const float a ) {
- char text[ 64 ];
- sprintf( text, "%f", a );
- Append( text );
- return *this;
- }
- ID_INLINE idStr &idStr::operator+=( const int a ) {
- char text[ 64 ];
- sprintf( text, "%d", a );
- Append( text );
- return *this;
- }
- ID_INLINE idStr &idStr::operator+=( const unsigned a ) {
- char text[ 64 ];
- sprintf( text, "%u", a );
- Append( text );
- return *this;
- }
- ID_INLINE idStr &idStr::operator+=( const idStr &a ) {
- Append( a );
- return *this;
- }
- ID_INLINE idStr &idStr::operator+=( const char *a ) {
- Append( a );
- return *this;
- }
- ID_INLINE idStr &idStr::operator+=( const char a ) {
- Append( a );
- return *this;
- }
- ID_INLINE idStr &idStr::operator+=( const bool a ) {
- Append( a ? "true" : "false" );
- return *this;
- }
- ID_INLINE bool operator==( const idStr &a, const idStr &b ) {
- return ( !idStr::Cmp( a.data, b.data ) );
- }
- ID_INLINE bool operator==( const idStr &a, const char *b ) {
- assert( b );
- return ( !idStr::Cmp( a.data, b ) );
- }
- ID_INLINE bool operator==( const char *a, const idStr &b ) {
- assert( a );
- return ( !idStr::Cmp( a, b.data ) );
- }
- ID_INLINE bool operator!=( const idStr &a, const idStr &b ) {
- return !( a == b );
- }
- ID_INLINE bool operator!=( const idStr &a, const char *b ) {
- return !( a == b );
- }
- ID_INLINE bool operator!=( const char *a, const idStr &b ) {
- return !( a == b );
- }
- ID_INLINE int idStr::Cmp( const char *text ) const {
- assert( text );
- return idStr::Cmp( data, text );
- }
- ID_INLINE int idStr::Cmpn( const char *text, int n ) const {
- assert( text );
- return idStr::Cmpn( data, text, n );
- }
- ID_INLINE int idStr::CmpPrefix( const char *text ) const {
- assert( text );
- return idStr::Cmpn( data, text, strlen( text ) );
- }
- ID_INLINE int idStr::Icmp( const char *text ) const {
- assert( text );
- return idStr::Icmp( data, text );
- }
- ID_INLINE int idStr::Icmpn( const char *text, int n ) const {
- assert( text );
- return idStr::Icmpn( data, text, n );
- }
- ID_INLINE int idStr::IcmpPrefix( const char *text ) const {
- assert( text );
- return idStr::Icmpn( data, text, strlen( text ) );
- }
- ID_INLINE int idStr::IcmpNoColor( const char *text ) const {
- assert( text );
- return idStr::IcmpNoColor( data, text );
- }
- ID_INLINE int idStr::IcmpPath( const char *text ) const {
- assert( text );
- return idStr::IcmpPath( data, text );
- }
- ID_INLINE int idStr::IcmpnPath( const char *text, int n ) const {
- assert( text );
- return idStr::IcmpnPath( data, text, n );
- }
- ID_INLINE int idStr::IcmpPrefixPath( const char *text ) const {
- assert( text );
- return idStr::IcmpnPath( data, text, strlen( text ) );
- }
- ID_INLINE int idStr::Length() const {
- return len;
- }
- ID_INLINE int idStr::Allocated() const {
- if ( data != baseBuffer ) {
- return GetAlloced();
- } else {
- return 0;
- }
- }
- ID_INLINE void idStr::Empty() {
- EnsureAlloced( 1 );
- data[ 0 ] = '\0';
- len = 0;
- }
- ID_INLINE bool idStr::IsEmpty() const {
- return ( idStr::Cmp( data, "" ) == 0 );
- }
- ID_INLINE void idStr::Clear() {
- if ( IsStatic() ) {
- len = 0;
- data[ 0 ] = '\0';
- return;
- }
- FreeData();
- Construct();
- }
- ID_INLINE void idStr::Append( const char a ) {
- EnsureAlloced( len + 2 );
- data[ len ] = a;
- len++;
- data[ len ] = '\0';
- }
- ID_INLINE void idStr::Append( const idStr &text ) {
- int newLen;
- int i;
- newLen = len + text.Length();
- EnsureAlloced( newLen + 1 );
- for ( i = 0; i < text.len; i++ ) {
- data[ len + i ] = text[ i ];
- }
- len = newLen;
- data[ len ] = '\0';
- }
- ID_INLINE void idStr::Append( const char *text ) {
- int newLen;
- int i;
- if ( text ) {
- newLen = len + strlen( text );
- EnsureAlloced( newLen + 1 );
- for ( i = 0; text[ i ]; i++ ) {
- data[ len + i ] = text[ i ];
- }
- len = newLen;
- data[ len ] = '\0';
- }
- }
- ID_INLINE void idStr::Append( const char *text, int l ) {
- int newLen;
- int i;
- if ( text && l ) {
- newLen = len + l;
- EnsureAlloced( newLen + 1 );
- for ( i = 0; text[ i ] && i < l; i++ ) {
- data[ len + i ] = text[ i ];
- }
- len = newLen;
- data[ len ] = '\0';
- }
- }
- ID_INLINE void idStr::Insert( const char a, int index ) {
- int i, l;
- if ( index < 0 ) {
- index = 0;
- } else if ( index > len ) {
- index = len;
- }
- l = 1;
- EnsureAlloced( len + l + 1 );
- for ( i = len; i >= index; i-- ) {
- data[i+l] = data[i];
- }
- data[index] = a;
- len++;
- }
- ID_INLINE void idStr::Insert( const char *text, int index ) {
- int i, l;
- if ( index < 0 ) {
- index = 0;
- } else if ( index > len ) {
- index = len;
- }
- l = strlen( text );
- EnsureAlloced( len + l + 1 );
- for ( i = len; i >= index; i-- ) {
- data[i+l] = data[i];
- }
- for ( i = 0; i < l; i++ ) {
- data[index+i] = text[i];
- }
- len += l;
- }
- ID_INLINE void idStr::ToLower() {
- for (int i = 0; data[i]; i++ ) {
- if ( CharIsUpper( data[i] ) ) {
- data[i] += ( 'a' - 'A' );
- }
- }
- }
- ID_INLINE void idStr::ToUpper() {
- for (int i = 0; data[i]; i++ ) {
- if ( CharIsLower( data[i] ) ) {
- data[i] -= ( 'a' - 'A' );
- }
- }
- }
- ID_INLINE bool idStr::IsNumeric() const {
- return idStr::IsNumeric( data );
- }
- ID_INLINE bool idStr::IsColor() const {
- return idStr::IsColor( data );
- }
- ID_INLINE bool idStr::HasLower() const {
- return idStr::HasLower( data );
- }
- ID_INLINE bool idStr::HasUpper() const {
- return idStr::HasUpper( data );
- }
- ID_INLINE idStr &idStr::RemoveColors() {
- idStr::RemoveColors( data );
- len = Length( data );
- return *this;
- }
- ID_INLINE int idStr::LengthWithoutColors() const {
- return idStr::LengthWithoutColors( data );
- }
- ID_INLINE void idStr::CapLength( int newlen ) {
- if ( len <= newlen ) {
- return;
- }
- data[ newlen ] = 0;
- len = newlen;
- }
- ID_INLINE void idStr::Fill( const char ch, int newlen ) {
- EnsureAlloced( newlen + 1 );
- len = newlen;
- memset( data, ch, len );
- data[ len ] = 0;
- }
- /*
- ========================
- idStr::UTF8Length
- ========================
- */
- ID_INLINE int idStr::UTF8Length() {
- return UTF8Length( (byte *)data );
- }
- /*
- ========================
- idStr::UTF8Char
- ========================
- */
- ID_INLINE uint32 idStr::UTF8Char( int & idx ) {
- return UTF8Char( (byte *)data, idx );
- }
- /*
- ========================
- idStr::ConvertToUTF8
- ========================
- */
- ID_INLINE void idStr::ConvertToUTF8() {
- idStr temp( *this );
- Clear();
- for( int index = 0; index < temp.Length(); ++index ) {
- AppendUTF8Char( temp[index] );
- }
- }
- /*
- ========================
- idStr::UTF8Char
- ========================
- */
- ID_INLINE uint32 idStr::UTF8Char( const char * s, int & idx ) {
- return UTF8Char( (byte *)s, idx );
- }
- /*
- ========================
- idStr::IsValidUTF8
- ========================
- */
- ID_INLINE bool idStr::IsValidUTF8( const uint8 * s, const int maxLen ) {
- utf8Encoding_t encoding;
- return IsValidUTF8( s, maxLen, encoding );
- }
- ID_INLINE int idStr::Find( const char c, int start, int end ) const {
- if ( end == -1 ) {
- end = len;
- }
- return idStr::FindChar( data, c, start, end );
- }
- ID_INLINE int idStr::Find( const char *text, bool casesensitive, int start, int end ) const {
- if ( end == -1 ) {
- end = len;
- }
- return idStr::FindText( data, text, casesensitive, start, end );
- }
- ID_INLINE bool idStr::Filter( const char *filter, bool casesensitive ) const {
- return idStr::Filter( filter, data, casesensitive );
- }
- ID_INLINE const char *idStr::Left( int len, idStr &result ) const {
- return Mid( 0, len, result );
- }
- ID_INLINE const char *idStr::Right( int len, idStr &result ) const {
- if ( len >= Length() ) {
- result = *this;
- return result;
- }
- return Mid( Length() - len, len, result );
- }
- ID_INLINE idStr idStr::Left( int len ) const {
- return Mid( 0, len );
- }
- ID_INLINE idStr idStr::Right( int len ) const {
- if ( len >= Length() ) {
- return *this;
- }
- return Mid( Length() - len, len );
- }
- ID_INLINE void idStr::Strip( const char c ) {
- StripLeading( c );
- StripTrailing( c );
- }
- ID_INLINE void idStr::Strip( const char *string ) {
- StripLeading( string );
- StripTrailing( string );
- }
- ID_INLINE bool idStr::CheckExtension( const char *ext ) {
- return idStr::CheckExtension( data, ext );
- }
- ID_INLINE int idStr::Length( const char *s ) {
- int i;
- for ( i = 0; s[i]; i++ ) {}
- return i;
- }
- ID_INLINE char *idStr::ToLower( char *s ) {
- for ( int i = 0; s[i]; i++ ) {
- if ( CharIsUpper( s[i] ) ) {
- s[i] += ( 'a' - 'A' );
- }
- }
- return s;
- }
- ID_INLINE char *idStr::ToUpper( char *s ) {
- for ( int i = 0; s[i]; i++ ) {
- if ( CharIsLower( s[i] ) ) {
- s[i] -= ( 'a' - 'A' );
- }
- }
- return s;
- }
- ID_INLINE int idStr::Hash( const char *string ) {
- int i, hash = 0;
- for ( i = 0; *string != '\0'; i++ ) {
- hash += ( *string++ ) * ( i + 119 );
- }
- return hash;
- }
- ID_INLINE int idStr::Hash( const char *string, int length ) {
- int i, hash = 0;
- for ( i = 0; i < length; i++ ) {
- hash += ( *string++ ) * ( i + 119 );
- }
- return hash;
- }
- ID_INLINE int idStr::IHash( const char *string ) {
- int i, hash = 0;
- for( i = 0; *string != '\0'; i++ ) {
- hash += ToLower( *string++ ) * ( i + 119 );
- }
- return hash;
- }
- ID_INLINE int idStr::IHash( const char *string, int length ) {
- int i, hash = 0;
- for ( i = 0; i < length; i++ ) {
- hash += ToLower( *string++ ) * ( i + 119 );
- }
- return hash;
- }
- ID_INLINE bool idStr::IsColor( const char *s ) {
- return ( s[0] == C_COLOR_ESCAPE && s[1] != '\0' && s[1] != ' ' );
- }
- ID_INLINE char idStr::ToLower( char c ) {
- if ( c <= 'Z' && c >= 'A' ) {
- return ( c + ( 'a' - 'A' ) );
- }
- return c;
- }
- ID_INLINE char idStr::ToUpper( char c ) {
- if ( c >= 'a' && c <= 'z' ) {
- return ( c - ( 'a' - 'A' ) );
- }
- return c;
- }
- ID_INLINE bool idStr::CharIsPrintable( int c ) {
- // test for regular ascii and western European high-ascii chars
- return ( c >= 0x20 && c <= 0x7E ) || ( c >= 0xA1 && c <= 0xFF );
- }
- ID_INLINE bool idStr::CharIsLower( int c ) {
- // test for regular ascii and western European high-ascii chars
- return ( c >= 'a' && c <= 'z' ) || ( c >= 0xE0 && c <= 0xFF );
- }
- ID_INLINE bool idStr::CharIsUpper( int c ) {
- // test for regular ascii and western European high-ascii chars
- return ( c <= 'Z' && c >= 'A' ) || ( c >= 0xC0 && c <= 0xDF );
- }
- ID_INLINE bool idStr::CharIsAlpha( int c ) {
- // test for regular ascii and western European high-ascii chars
- return ( ( c >= 'a' && c <= 'z' ) || ( c >= 'A' && c <= 'Z' ) ||
- ( c >= 0xC0 && c <= 0xFF ) );
- }
- ID_INLINE bool idStr::CharIsNumeric( int c ) {
- return ( c <= '9' && c >= '0' );
- }
- ID_INLINE bool idStr::CharIsNewLine( char c ) {
- return ( c == '\n' || c == '\r' || c == '\v' );
- }
- ID_INLINE bool idStr::CharIsTab( char c ) {
- return ( c == '\t' );
- }
- ID_INLINE int idStr::ColorIndex( int c ) {
- return ( c & 15 );
- }
- ID_INLINE int idStr::DynamicMemoryUsed() const {
- return ( data == baseBuffer ) ? 0 : GetAlloced();
- }
- /*
- ========================
- idStr::CopyRange
- ========================
- */
- ID_INLINE void idStr::CopyRange( const char * text, int start, int end ) {
- int l = end - start;
- if ( l < 0 ) {
- l = 0;
- }
- EnsureAlloced( l + 1 );
- for ( int i = 0; i < l; i++ ) {
- data[ i ] = text[ start + i ];
- }
- data[ l ] = '\0';
- len = l;
- }
- #endif /* !__STR_H__ */
|