home *** CD-ROM | disk | FTP | other *** search
/ PC World Komputer 1997 May / Pcwk0597.iso / sybase / starbuck / hpp.z / WSTRING.HPP < prev    next >
C/C++ Source or Header  |  1996-11-14  |  29KB  |  868 lines

  1. /*************************************************************************
  2.  *
  3.  * WString
  4.  *
  5.  *    This class defines the basic string type used by the library.
  6.  *    The class is DBCS-enabled when running on a DBCS version of the
  7.  *    operating system.
  8.  *
  9.  *    Some important terms to know:
  10.  *
  11.  *        length: number of characters (not bytes) in a string, excluding
  12.  *                terminating null
  13.  *
  14.  *        size: number of bytes (not characters) in a string, excluding
  15.  *              terminating null
  16.  *
  17.  *        empty string: string of length 0
  18.  *
  19.  *        null string: a string with no length or data
  20.  *
  21.  *************************************************************************/
  22.  
  23. #ifndef _WSTRING_HPP_INCLUDED
  24. #define _WSTRING_HPP_INCLUDED
  25.  
  26. #ifndef _WNO_PRAGMA_PUSH
  27. #pragma pack(push,8);
  28. #pragma enum int;
  29. #endif
  30.  
  31. #ifndef _WOBJECT_HPP_INCLUDED
  32. #  include "wobject.hpp"
  33. #endif
  34. #ifndef _WARRAY_HPP_INCLUDED
  35. #  include "warray.hpp"
  36. #endif
  37.  
  38. extern "C" {
  39.     #include <string.h>
  40. #ifndef _SBCS
  41.     #include <mbstring.h>
  42. #endif
  43.     #include <stdarg.h>
  44. };
  45.  
  46. class ostream;
  47. class istream;
  48.  
  49. class WResourceID;
  50. class WModule;   
  51. class WStringReference;
  52. class WString;
  53. class WMessageID;
  54.  
  55. // this is used for multibyte strings where the index of a character is
  56. // not the same as its actual position
  57. struct StringIndex {
  58.         WAnsiChar *     pointer;
  59.         WLong           index;  // the index the user wants
  60. };
  61.  
  62. enum WStringType {
  63.     WAnsiString = 0,
  64.     WUnicodeString = 1,
  65.  
  66.     #ifdef _UNICODE
  67.         WDefaultString = WUnicodeString
  68.     #else
  69.         WDefaultString = WAnsiString
  70.     #endif
  71. };
  72.  
  73. #define USE_STR_LEN                 0xFFFFFFFF
  74. #define NOT_FOUND                   0xFFFFFFFF
  75. #define WSTRING_DEFAULT_QUOTELIST   __WTEXT("\"\"''")
  76.  
  77. #ifndef _WIN16
  78. #undef LoadString
  79. #if defined( _UNICODE )
  80.     #define LoadString LoadStringW
  81. #else
  82.     #define LoadString LoadStringA
  83. #endif
  84. #endif
  85.  
  86. //
  87. // WString
  88. //
  89.  
  90. extern template WArrayReference<WString>;
  91. extern template WArray<WString>;
  92.  
  93. typedef WArray<WString> WStringArray;
  94.  
  95. class WCMCLASS WString : public WObject {
  96.     WDeclareSubclass( WString, WObject )
  97.  
  98.     public:
  99.  
  100.         /**********************************************************
  101.          * WStringElement
  102.          *********************************************************/
  103.  
  104.         //
  105.         // WStringElement
  106.         //
  107.         //    This class represents an individual character in a string
  108.         //    and is used in conjunction with the [] operator on WString
  109.         //    to ensure that characters get inserted into the proper
  110.         //    area in the string (mostly for DBCS strings).
  111.         //
  112.  
  113.         class WCMCLASS WStringElement {
  114.  
  115.             friend class WString;
  116.  
  117.             public:
  118.  
  119.                 WStringElement& operator=( const WWidestChar ch )
  120.                     { string->SetCharacter( index, ch ); return *this; }
  121.  
  122.                 WStringElement& operator=( const WStringElement & e )
  123.                     { string->SetCharacter( index,
  124.                                            e.string->GetCharacter( e.index ) );
  125.                       return *this; }
  126.  
  127.                 operator WWidestChar() const
  128.                     { return string->GetCharacter( index ); }
  129.  
  130.             private:
  131.                 WStringElement( WString *str ) : string( str ), index( 0 ) {}
  132.  
  133.                 WStringElement( const WStringElement & e );
  134.  
  135.                 ~WStringElement() {}
  136.  
  137.             private:
  138.                 WString *string;
  139.                 WULong   index;
  140.         };
  141.  
  142.         /**********************************************************
  143.          * Constructors and Destructors
  144.          *********************************************************/
  145.  
  146.         WString();
  147.         WString( const WChar *string, WULong numChars=USE_STR_LEN );
  148.         WString( const WResourceID & id, WModuleHandle module=_ApplicationModule );
  149.         WString( const WMessageID & id, WModuleHandle module=_ApplicationModule );
  150.         WString( const WString & s, WBool makeCopy=FALSE );
  151.  
  152.         ~WString();
  153.  
  154.         /**********************************************************
  155.          * Properties
  156.          *********************************************************/
  157.  
  158.         // Character
  159.         //
  160.         //    Set/get an individual character in the string.  Forces
  161.         //    the string to be the default type.
  162.  
  163.         WWidestChar GetCharacter( WULong index ) const;
  164.         WBool       SetCharacter( WULong index, WWidestChar ch );
  165.  
  166.         // Dirty
  167.  
  168.         WBool         GetDirty() const { return _dirty; }
  169.         virtual WBool SetDirty( WBool dirty=TRUE );
  170.  
  171.         // Double
  172.         //
  173.         //    Convert the string to a WDouble, optionally setting an error
  174.         //    flag.
  175.  
  176.         WDouble WCMRETURNSFLOAT GetDouble( WBool *ok=NULL ) const;
  177.  
  178.         // Empty
  179.         //
  180.         //    TRUE if the string is null or is empty.
  181.  
  182.         WBool GetEmpty() const;
  183.  
  184.         // Length
  185.         //
  186.         //    Returns the length of the string in characters, not
  187.         //    including the null terminator.
  188.  
  189.         WULong GetAnsiLength() const;
  190.         WULong GetUnicodeLength() const;
  191.  
  192.         #ifdef _UNICODE
  193.             WULong GetLength() const { return GetUnicodeLength(); }
  194.         #else
  195.             WULong GetLength() const { return GetAnsiLength(); }
  196.         #endif
  197.  
  198.         // Long
  199.         //
  200.         //    Convert the string to a WLong, optionally setting an error
  201.         //    flag.
  202.  
  203.         WLong GetLong( WBool *ok=NULL ) const;
  204.  
  205.         // Null
  206.         //
  207.         //    TRUE if the string is a null (but not an empty) string.
  208.  
  209.         WBool GetNull() const;
  210.  
  211.         // Size
  212.         //
  213.         //    Returns the size of the string in bytes, not including
  214.         //    the null terminator.
  215.  
  216.         WULong GetAnsiSize() const;
  217.         WULong GetUnicodeSize() const;
  218.  
  219.         #ifdef _UNICODE
  220.             WULong GetSize() const { return GetUnicodeSize(); }
  221.         #else
  222.             WULong GetSize() const { return GetAnsiSize(); }
  223.         #endif
  224.  
  225.         // Text
  226.         //
  227.         //    Set/get the actual text of the string.  The optional parm
  228.         //    on the set controls whether or not the string should store
  229.         //    just a pointer to the text or make a copy of the text.
  230.  
  231.         const WAnsiChar    *const GetAnsiText() const;
  232.         WBool                     SetAnsiText( const WAnsiChar *text,
  233.                                                WBool makeCopy=TRUE );
  234.  
  235.         const WUnicodeChar *const GetUnicodeText() const;
  236.         WBool                     SetUnicodeText( const WUnicodeChar *text,
  237.                                                   WBool makeCopy=TRUE );
  238.  
  239.         #ifdef _UNICODE
  240.         const WChar *const GetText() const { return GetUnicodeText(); }
  241.         WBool              SetText( const WChar *str, WBool makeCopy=TRUE )
  242.                                 { return SetUnicodeText( str, makeCopy ); }
  243.         #else
  244.         const WChar *const GetText() const { return GetAnsiText(); }
  245.         WBool              SetText( const WChar *str, WBool makeCopy=TRUE )
  246.                                 { return SetAnsiText( str, makeCopy ); }
  247.         #endif
  248.  
  249.         // Type
  250.         //
  251.         //    Sets/gets the primary type of a string.
  252.  
  253.         WStringType GetType() const;
  254.         WBool       SetType( WStringType type ) const;
  255.  
  256.         // ULong
  257.         //
  258.         //    Convert the string to a WULong, optionally setting an error
  259.         //    flag.
  260.  
  261.         WULong GetULong( WBool *ok=NULL ) const;
  262.  
  263.         /**********************************************************
  264.          * Methods
  265.          *********************************************************/
  266.  
  267.         // Chop
  268.         //
  269.         //    If given a non-negative value, removes all the characters
  270.         //    up to but not including charPos.  If given a negative value,
  271.         //    removes the last charPos*-1 characters.
  272.  
  273.         WBool Chop( WLong charPos );
  274.  
  275.         // Clear
  276.         //
  277.         //    Frees the string, leaving a null string.
  278.  
  279.         void Clear();
  280.     
  281.         // Compare
  282.  
  283.         static int Compare( const WString & a, const WString & b,
  284.                             WBool caseSensitive=TRUE, WULong numChars=0 );
  285.         static int Compare( const WString & a, const WAnsiChar *b );
  286.         static int Compare( const WString & a, const WUnicodeChar *b );
  287.         static int Compare( const WAnsiChar *a, const WString & b );
  288.         static int Compare( const WUnicodeChar *a, const WString & b );
  289.  
  290.         // CompareToSelf
  291.         //
  292.         //    Used by WVector/WMTVector for sorting.
  293.  
  294.         int CompareToSelf( const WString & obj ) const;
  295.  
  296.         // Concat
  297.         //
  298.         //    Concatenate a string onto another.
  299.  
  300.         WBool Concat( const WString & suffix );
  301.         WBool Concat( const WAnsiChar *string );
  302.         WBool Concat( const WUnicodeChar *string );
  303.         WBool Concat( WWidestChar singleChar );
  304.  
  305.         // Concatf
  306.  
  307.         WBool Concatf( const WAnsiChar *parms, ... );
  308.         WBool Concatf( const WUnicodeChar *parms, ... );
  309.  
  310.         // ConvertToInteger
  311.  
  312.         WInt ConvertToInteger() const;
  313.  
  314.         // ConvertToLong
  315.  
  316.         WLong ConvertToLong() const;
  317.  
  318.         // Create
  319.         //
  320.         //    Various constructors for building a new string.  First
  321.         //    frees the old string.  
  322.  
  323.         WBool Create();
  324.         WBool Create( const WResourceID & id, WModuleHandle module=_ApplicationModule );
  325.         WBool Create( const WMessageID & id, WModuleHandle module=_ApplicationModule );
  326.         WBool Create( const WString & s, WBool makeCopy=FALSE );
  327.  
  328.         WBool CreateAnsi( const WAnsiChar *string,
  329.                           WULong numChars=USE_STR_LEN );
  330.         WBool CreateUnicode( const WUnicodeChar *string,
  331.                              WULong numChars=USE_STR_LEN );
  332.  
  333.         #ifdef _UNICODE
  334.         WBool Create( const WChar *string, WULong numChars=USE_STR_LEN )
  335.             { return CreateUnicode( string, numChars ); }
  336.         #else
  337.         WBool Create( const WChar *string, WULong numChars=USE_STR_LEN )
  338.             { return CreateAnsi( string, numChars ); }
  339.         #endif
  340.  
  341.         // Format
  342.         //
  343.         //    Formats a message.  
  344.         //    Returns number of characters
  345.         //    (not bytes) copied into the string.
  346.  
  347.         WULong Format( const WChar *format, ... );
  348.         WULong Format( WULong messageID, WULong langID, ... );
  349.         WULong Format( const WModule *module, WULong messageID,
  350.                        WULong langID, ... );
  351.  
  352.         // FormatEx
  353.         //
  354.         //    Formats a message, but with more options.
  355.  
  356.         #define WSTRF_NOFORMAT   0x0200
  357.         #define WSTRF_FROMSTRING 0x0400
  358.         #define WSTRF_FROMMODULE 0x0800
  359.         #define WSTRF_FROMSYSTEM 0x1000
  360.         #define WSTRF_USEARRAY   0x2000
  361.  
  362.         WULong FormatEx( WULong flags, const WChar *format,
  363.                          WByte maxWidth, ... );
  364.         WULong FormatEx( WULong flags, const WModule *module,
  365.                          WULong messageID, WULong langID,
  366.                          WByte maxWidth, ... );
  367.  
  368.         // FormatV
  369.         //
  370.         //    The basic form of Format/FormatEx.
  371.  
  372.         WULong FormatV( WULong flags, const WChar *format,
  373.                         WByte maxWidth, va_list args );
  374.         WULong FormatV( WULong flags, const WModule *module,
  375.                         WULong messageID, WULong langID,
  376.                         WByte maxWidth, va_list args );
  377.         // Left
  378.         //
  379.         //    Returns the n leftmost characters of a string.  If string
  380.         //    is smaller than n, just returns the string.
  381.  
  382.         WString Left( WULong numChars ) const;
  383.  
  384.         // Lock
  385.         //
  386.         //    Call this if you want to work directly on the buffer
  387.         //    inside the WString.  It will ensure that no one else
  388.         //    is referencing it, that it has a minimum size (in bytes),
  389.         //    return its pointer.  Call Unlock when you're done.
  390.  
  391.         WChar *Lock( WULong minimumSize=0, WStringType type=WDefaultString );
  392.  
  393.         // Parse
  394.         //
  395.         //    Parse a string into an array of substrings.  The original
  396.         //    string is left unchanged.  The delimeterList specifies
  397.         //    the list of characters that delimit the substrings
  398.         //    (default is whitespace).  If quoteList is non-NULL,
  399.         //    it consists of pairs of begin-end characters which are
  400.         //    used to declare a substring with delimiter characters
  401.         //    embedded in it.  If ignoreMultiple is TRUE, multiple
  402.         //    delimiter characters (such as multiple spaces) are
  403.         //    ignored.  You can specify an index to start and end at.
  404.         //    Finally, if allowEscapes is TRUE, you can use a backslash
  405.         //    within a quoted string as an escape character to escape
  406.         //    either delimiter character or a backslash itself.
  407.  
  408.         WStringArray Parse( const WChar *delimiterList=NULL,
  409.                             WBool ignoreMultiples=TRUE,
  410.                             const WChar *quoteList=WSTRING_DEFAULT_QUOTELIST,
  411.                             WBool stripQuotes=TRUE,
  412.                             WULong startAt=0,
  413.                             WULong endAt=USE_STR_LEN,
  414.                             WBool allowEscapes=TRUE ) const;
  415.  
  416.         // Position
  417.         //
  418.         //    Search for a given character or substring in the string
  419.         //    and return its position. NOT_FOUND is returned if not
  420.         //    found.
  421.  
  422.         WULong Position( const WWidestChar character, WULong startAt=0,
  423.                          WBool ignoreCase=FALSE ) const;
  424.         WULong Position( const WChar *substring, WULong startAt=0,
  425.                          WBool ignoreCase=FALSE ) const;
  426.         WULong Position( const WString & substring, WULong startAt=0,
  427.                          WBool ignoreCase=FALSE ) const;
  428.  
  429.         // Right
  430.         //
  431.         //    Return the n rightmost characters of a string.  If string
  432.         //    is smaller than n, just returns the string.
  433.  
  434.         WString Right( WULong numChars ) const;
  435.  
  436.         // Sprintf
  437.         //
  438.         //    Calls with the C function sprintf functionality.
  439.  
  440.         WULong Sprintf( const WAnsiChar *parms, ... );
  441.         WULong Sprintf( const WUnicodeChar *parms, ... );
  442.  
  443.         // Strip
  444.         //
  445.         //    Remove spaces from one or both ends.
  446.  
  447.         WString Strip( WBool fromBeg=TRUE, WBool fromEnd=TRUE ) const;
  448.  
  449.         // SubString
  450.         //
  451.         //    Returns the substring starting at position start and
  452.         //    of length n.  Start is 0-based.  If n is not specified,
  453.         //    the rest of the string is returned.
  454.  
  455.         WString Substring( WULong startAt, WULong numChars=USE_STR_LEN ) const;
  456.  
  457.         // ToLowercase
  458.         //
  459.         //    Convert the string (in-place) to lowercase.
  460.  
  461.         WBool ToLowercase();
  462.  
  463.         // ToUppercase
  464.         //
  465.         //    Convert the string (in-place) to uppercase.
  466.  
  467.         WBool ToUppercase();
  468.  
  469.         // Trim
  470.         //
  471.         //    Strip the string in place.
  472.  
  473.         WBool Trim( WBool fromBeg=TRUE, WBool fromEnd=TRUE );
  474.  
  475.         // Truncate
  476.         //
  477.         //    Truncate the string to the given length.
  478.  
  479.         WBool Truncate( WULong length );
  480.  
  481.         // Unlock
  482.         //
  483.         //    Call this when done writing directly to the buffer.
  484.         //    The string then recalculates its size and length.
  485.  
  486.         WBool Unlock();
  487.  
  488.         // OSIsMultiByte
  489.  
  490.         static WBool OSIsMultiByte();
  491.  
  492.         // OSIsUnicode
  493.  
  494.         static WBool OSIsUnicode();
  495.  
  496.         // StringLength 
  497.         //
  498.         //    Returns length in characters, not including null.
  499.  
  500.         static WULong StringLength( const WAnsiChar *str );
  501.         static WULong StringLength( const WUnicodeChar *str );
  502.  
  503.         // StringSize 
  504.         //
  505.         //    Returns size in bytes, not including null.
  506.  
  507.         static WULong StringSize( const WAnsiChar *str );
  508.         static WULong StringSize( const WUnicodeChar *str );
  509.  
  510.         /**********************************************************
  511.          * Static Methods
  512.          *********************************************************/
  513.  
  514.         // LoadString
  515.         //
  516.         //    Load a string directly into a user-allocated buffer.
  517.  
  518.         static WBool LoadString( const WResourceID & id, WChar *buffer,
  519.                                  WULong bufferLength,
  520.                                  WModuleHandle module=_ApplicationModule );
  521.  
  522.         /**********************************************************
  523.          * Static Properties
  524.          *********************************************************/
  525.  
  526.         // DefaultDelimiterList
  527.  
  528.         static const WChar *const GetDefaultDelimiterList();
  529.  
  530.         // DefaultQuoteList
  531.  
  532.         static const WChar *const GetDefaultQuoteList();
  533.  
  534.         // EmptyAnsiCString
  535.  
  536.         static const WAnsiChar    *const GetEmptyAnsiCString();
  537.  
  538.         // EmptyCString
  539.  
  540.         static const WChar        *const GetEmptyCString();
  541.  
  542.         // EmptyString
  543.  
  544.         static const WString & GetEmptyString();
  545.  
  546.         // EmptyUnicodeCString
  547.  
  548.         static const WUnicodeChar *const GetEmptyUnicodeCString();
  549.  
  550.         // NullString
  551.  
  552.         static const WString & GetNullString();
  553.  
  554.         /*********************************************************
  555.          * Operators
  556.          *********************************************************/
  557.  
  558.         //
  559.         // [] operator -- Note that a WWidestChar is always used,
  560.         //                not a WChar, to ensure that the result
  561.         //                can handle the largest type of char.
  562.  
  563.         const WStringElement& operator[]( int index ) const;
  564.  
  565.         WStringElement& operator[]( int index );
  566.  
  567.         //
  568.         // casting operators
  569.         //
  570.  
  571.         operator const WAnsiChar*() const { return GetAnsiText(); }
  572.         operator const WUnicodeChar*() const { return GetUnicodeText(); }
  573.  
  574.         /*********************************************************
  575.          * Cache
  576.          *********************************************************/
  577.  
  578.         // CacheSize
  579.  
  580.         static WULong GetCacheSize();
  581.         static WBool  SetCacheSize( WULong size );
  582.  
  583.         // FlushCache
  584.  
  585.         static void FlushCache();
  586.  
  587. #if 0
  588.     private:
  589.         // Note: This operator should not be used.  Instead, call Lock().
  590.         operator WChar*() const;
  591. #endif
  592.  
  593.     public:
  594.  
  595.         //
  596.         // = operator
  597.         //
  598.  
  599.         WString & operator=( const WAnsiChar *s );
  600.         WString & operator=( const WUnicodeChar *s );
  601.         WString & operator=( const WString & s );
  602.  
  603.         //
  604.         // == operator
  605.         //
  606.  
  607.         friend int WEXPORT operator==( const WString & a, const WString & b );
  608.         friend int WEXPORT operator==( const WString & a, WAnsiChar * b );
  609.         friend int WEXPORT operator==( const WString & a, WUnicodeChar * b );
  610.         friend int WEXPORT operator==( WAnsiChar * a, const WString & b );
  611.         friend int WEXPORT operator==( WUnicodeChar * a, const WString & b );
  612.         friend int WEXPORT operator==( const WString & a, const WAnsiChar * b );
  613.         friend int WEXPORT operator==( const WString & a, const WUnicodeChar *b );
  614.         friend int WEXPORT operator==( const WAnsiChar * a, const WString & b );
  615.         friend int WEXPORT operator==( const WUnicodeChar * a, const WString & b );
  616.  
  617.         //
  618.         // <= operator
  619.         //
  620.  
  621.         friend int WEXPORT operator<=( const WString & a, const WString & b );
  622.         friend int WEXPORT operator<=( const WString & a, const WAnsiChar *b );
  623.         friend int WEXPORT operator<=( const WString & a, const WUnicodeChar *b );
  624.         friend int WEXPORT operator<=( const WAnsiChar *a, const WString & b );
  625.         friend int WEXPORT operator<=( const WUnicodeChar *a, const WString & b );
  626.  
  627.         //
  628.         // < operator
  629.         //
  630.  
  631.         friend int WEXPORT operator<( const WString & a, const WString & b );
  632.         friend int WEXPORT operator<( const WString & a, const WAnsiChar *b );
  633.         friend int WEXPORT operator<( const WString & a, const WUnicodeChar *b );
  634.         friend int WEXPORT operator<( const WAnsiChar *a, const WString & b );
  635.         friend int WEXPORT operator<( const WUnicodeChar *a, const WString & b );
  636.  
  637.         //
  638.         // >= operator
  639.         //
  640.  
  641.         friend int WEXPORT operator>=( const WString & a, const WString & b );
  642.         friend int WEXPORT operator>=( const WString & a, const WAnsiChar *b );
  643.         friend int WEXPORT operator>=( const WString & a, const WUnicodeChar *b );
  644.         friend int WEXPORT operator>=( const WAnsiChar *a, const WString & b );
  645.         friend int WEXPORT operator>=( const WUnicodeChar *a, const WString & b );
  646.  
  647.         //
  648.         // > operator
  649.         //
  650.  
  651.         friend int WEXPORT operator>( const WString & a, const WString & b );
  652.         friend int WEXPORT operator>( const WString & a, const WAnsiChar *b );
  653.         friend int WEXPORT operator>( const WString & a, const WUnicodeChar *b );
  654.         friend int WEXPORT operator>( const WAnsiChar *a, const WString & b );
  655.         friend int WEXPORT operator>( const WUnicodeChar *a, const WString & b );
  656.  
  657.         //
  658.         // != operator
  659.         //
  660.  
  661.         friend int WEXPORT operator!=( const WString & a, const WString & b );
  662.         friend int WEXPORT operator!=( const WString & a, const WAnsiChar *b );
  663.         friend int WEXPORT operator!=( const WString & a, const WUnicodeChar *b );
  664.         friend int WEXPORT operator!=( const WAnsiChar *a, const WString & b );
  665.         friend int WEXPORT operator!=( const WUnicodeChar *a, const WString & b );
  666.         friend int WEXPORT operator!=( const WString & a, WAnsiChar * b );
  667.         friend int WEXPORT operator!=( const WString & a, WUnicodeChar * b );
  668.         friend int WEXPORT operator!=( WAnsiChar * a, const WString & b );
  669.         friend int WEXPORT operator!=( WUnicodeChar * a, const WString & b );
  670.  
  671.         //
  672.         // << operator
  673.         //
  674.  
  675.         friend ostream& WEXPORT operator<<( ostream & out, const WString & str );
  676.         friend ostream& WEXPORT operator<<( ostream & out, const WUnicodeChar *str );
  677.  
  678.         //
  679.         // >> operator
  680.         //
  681.  
  682.         friend istream& WEXPORT operator>>( istream & in, WString & str );
  683.         friend istream& WEXPORT operator>>( istream & in, WUnicodeChar *str );
  684.  
  685.         //
  686.         // += operator
  687.         //
  688.  
  689.         WString& operator+=( const WString & a );
  690.         WString& operator+=( const WAnsiChar * a );
  691.         WString& operator+=( const WUnicodeChar * a );
  692.         WString& operator+=( WAnsiChar a );
  693.         WString& operator+=( WUnicodeChar a );
  694.  
  695.         //
  696.         // + operator
  697.         //
  698.  
  699.         WString operator+( const WString & a ) const;
  700.         WString operator+( const WAnsiChar * a ) const;
  701.         WString operator+( const WUnicodeChar * a ) const;
  702.         WString operator+( WAnsiChar a ) const;
  703.         WString operator+( WUnicodeChar a ) const;
  704.         friend WString WEXPORT operator+( const WAnsiChar * a, const WString & b );
  705.         friend WString WEXPORT operator+( const WUnicodeChar * a, const WString & b );
  706.  
  707.         /**********************************************************
  708.          * Private
  709.          *********************************************************/
  710.  
  711.     protected:
  712.  
  713.         virtual WBool CopyOnWrite( WStringType type=WDefaultString );
  714.         virtual WBool PrepareForRead() const;
  715.  
  716.         WBool  ReallocateRef( WByte newType, WULong minimumSize );
  717.         WBool  GrowTo( WULong size );
  718.         WULong SearchFor( const WChar *buf, WULong size, WULong at,
  719.                           WBool ignoreCase ) const;
  720.  
  721.     protected:
  722.  
  723.         WStringReference *_ref;
  724.         const WChar      *_stringData;  // for easier debugging only!
  725.         WStringElement    _element;
  726.  
  727.         static WBool      _osIsMultiByte;
  728.         static WBool      _osIsUnicode;
  729.  
  730.     private:
  731.  
  732.         WBool             _locked;      // TRUE if string is locked
  733.         WBool             _dirty;
  734.         StringIndex       _lastIndex;   // used for direct accessing of an
  735.                                         // element in the string (usually
  736.                                         // through the array [] operator)
  737.  
  738.     private:
  739.         void              invalidateLastIndex( void );
  740.         WBool             isLastIndexValid( void ) const;
  741. };
  742.  
  743. //
  744. // WResourceString
  745. //
  746.  
  747. class WCMCLASS WResourceString : public WString {
  748.     WDeclareSubclass( WResourceString, WString )
  749.  
  750.     public:
  751.         WResourceString( const WResourceID & id, WModuleHandle module=_ApplicationModule );
  752.         WResourceString( const WResourceString & other );
  753.  
  754.         ~WResourceString();
  755.  
  756.         WResourceString & operator=( const WResourceString & other );
  757.         WResourceString & operator=( const WAnsiChar *s );
  758.         WResourceString & operator=( const WUnicodeChar *s );
  759.         WResourceString & operator=( const WString & s );
  760.  
  761.     protected:
  762.         virtual WBool    PrepareForRead() const;
  763.  
  764.         WULong           _id;
  765.         WModuleHandle    _handle;
  766. };
  767.  
  768. //
  769. // WConstantString
  770. //
  771.  
  772. class WCMCLASS WConstantString : public WString {
  773.     WDeclareSubclass( WConstantString, WString )
  774.  
  775.     public:
  776.         WConstantString( const WChar *fixedString );
  777.         WConstantString( const WConstantString & other );
  778.  
  779.         ~WConstantString();
  780.  
  781.         WConstantString & operator=( const WConstantString & other );
  782.         WConstantString & operator=( const WAnsiChar *s );
  783.         WConstantString & operator=( const WUnicodeChar *s );
  784.         WConstantString & operator=( const WString & s );
  785.  
  786.         /**********************************************************
  787.          * Overrides
  788.          *********************************************************/
  789. };
  790.  
  791. /*******************************************************************
  792.  *
  793.  * Library functions and macros
  794.  *
  795.  *   The following macros and functions are covers for the appropriate
  796.  *   C library functions and expand out to the correct function
  797.  *   depending on the _UNICODE, _DBCS and _SBCS macro settings.
  798.  *
  799.  *   You should use the functions wherever possible, not the macros,
  800.  *   as the functions provide type checking.
  801.  *
  802.  *   Remember that the length of a string is not necessarily the
  803.  *   same as its size!
  804.  *
  805.  ******************************************************************/
  806.  
  807. #define _MBCast1(x) ((const unsigned char *)(x))
  808. #define _MBCast2(x) ((unsigned char *)(x))
  809.  
  810. #ifdef _SBCS
  811. #define A_StrLen(x)   strlen(x)
  812. #define A_StrSize(x)  strlen(x)
  813. #define A_StrCpy(d,s) strcpy(d,s)
  814. #else
  815. #define A_StrLen(x)   (WString::OSIsMultiByte()?_mbslen(_MBCast1(x)):strlen(x))
  816. #define A_StrSize(x)  strlen(x)
  817. #define A_StrCpy(d,s) (WString::OSIsMultiByte()?(WChar *)_mbscpy(_MBCast2(d),_MBCast1(s)):\
  818.                        (WChar *)strcpy(d,s))
  819. #endif
  820.  
  821. #define U_StrLen(x)   wcslen(x)
  822. #define U_StrSize(x)  (wcslen(x)*sizeof(WUnicodeChar))
  823. #define U_StrCpy(d,s) wcscpy(d,s)
  824.  
  825. #ifdef _UNICODE
  826. #define D_StrLen(x)   U_StrLen(x)
  827. #define D_StrSize(x)  U_StrSize(x)
  828. #define D_StrCpy(d,s) U_StrCpy(d,s)
  829. #else
  830. #define D_StrLen(x)   A_StrLen(x)
  831. #define D_StrSize(x)  A_StrSize(x)
  832. #define D_StrCpy(d,s) A_StrCpy(d,s)
  833. #endif
  834.  
  835. //
  836. // WStrLen -- Return length of string in characters. (See StrSize for bytes.)
  837. //
  838.  
  839. inline WULong WStrLen( const WChar *string ){
  840.     return D_StrLen( string );
  841. }
  842.  
  843. //
  844. // WStrSize -- Return length of string in bytes.  (See StrLen for characters.)
  845. //
  846.  
  847. inline WULong WStrSize( const WChar *string ){
  848.     return D_StrSize( string );
  849. }
  850.  
  851. //
  852. // WStrCpy -- Cover for strcpy.
  853. //
  854.  
  855. inline WChar *WStrCpy( WChar *dst, const WChar *src ){
  856.     return D_StrCpy( dst, src );
  857. }
  858.  
  859. #define WNullString     WString::GetNullString()
  860. #define WEmptyString    WString::GetEmptyString()
  861.  
  862. #ifndef _WNO_PRAGMA_PUSH
  863. #pragma enum pop;
  864. #pragma pack(pop);
  865. #endif
  866.  
  867. #endif // _WSTRING_HPP_INCLUDED
  868.