first phase of transition to unified Unicode build:

1. changed c_str() to return wxCStrData (implicitly convertible to wxChar*)
2. added template type-safe wrappers for vararg functions
3. added wxUniChar class representing single Unicode character
4. changed wxString::operator[] and wxString::iterator to return wxUniChar


git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@44865 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775
This commit is contained in:
Václav Slavík
2007-03-17 10:26:10 +00:00
parent cd632a8617
commit c9f7896861
80 changed files with 2229 additions and 435 deletions

View File

@@ -389,7 +389,7 @@ public:
static wxString GetPathTerminators(wxPathFormat format = wxPATH_NATIVE);
// get the canonical path separator for this format
static wxChar GetPathSeparator(wxPathFormat format = wxPATH_NATIVE)
static wxUniChar GetPathSeparator(wxPathFormat format = wxPATH_NATIVE)
{ return GetPathSeparators(format)[0u]; }
// is the char a path separator for this format?

View File

@@ -21,6 +21,7 @@
#include "wx/dialog.h"
#include "wx/module.h"
#include "wx/cmndata.h"
#include "wx/strvararg.h"
extern WXDLLIMPEXP_DATA_CORE(int) wxPageNumber;
@@ -85,7 +86,7 @@ public:
static void SetResolution(int ppi);
static int GetResolution();
void PsPrintf( const wxChar* fmt, ... );
WX_DEFINE_VARARG_FUNC_VOID(PsPrintf, DoPsPrintfFormat)
void PsPrint( const char* psdata );
void PsPrint( int ch );
@@ -94,6 +95,8 @@ public:
#endif
private:
void DoPsPrintfFormat(const wxChar *fmt, ... );
static float ms_PSScaleFactor;
protected:

View File

@@ -45,6 +45,7 @@ typedef unsigned long wxLogLevel;
// ----------------------------------------------------------------------------
#include "wx/string.h"
#include "wx/strvararg.h"
#if wxUSE_LOG
@@ -470,33 +471,39 @@ WXDLLIMPEXP_BASE const wxChar* wxSysErrorMsg(unsigned long nErrCode = 0);
// define wxLog<level>
// ----------------------------------------------------------------------------
#define DECLARE_LOG_FUNCTION(level) \
extern void WXDLLIMPEXP_BASE wxVLog##level(const wxChar *szFormat, \
va_list argptr); \
extern void WXDLLIMPEXP_BASE wxLog##level(const wxChar *szFormat, \
...) ATTRIBUTE_PRINTF_1
#define DECLARE_LOG_FUNCTION2_EXP(level, argclass, arg, expdecl) \
extern void expdecl wxVLog##level(argclass arg, \
const wxChar *szFormat, \
va_list argptr); \
extern void expdecl wxLog##level(argclass arg, \
const wxChar *szFormat, \
...) ATTRIBUTE_PRINTF_2
#define DECLARE_LOG_FUNCTION_PUBLIC(level) \
/* void wxLog##level(const wxChar *szFormat, ...); */ \
WX_DEFINE_VARARG_FUNC_VOID(wxLog##level, wxDoLog##level)
#define DECLARE_LOG_FUNCTION_IMPL(level) \
extern void WXDLLIMPEXP_BASE wxVLog##level(const wxChar *szFormat, \
va_list argptr); \
extern void WXDLLIMPEXP_BASE wxDoLog##level(const wxChar *szFormat, \
...) ATTRIBUTE_PRINTF_1
#define DECLARE_LOG_FUNCTION2_EXP_IMPL(level, argclass, arg, expdecl) \
extern void expdecl wxVLog##level(argclass arg, \
const wxChar *szFormat, \
va_list argptr); \
extern void expdecl wxDoLog##level(argclass arg, \
const wxChar *szFormat, \
...) ATTRIBUTE_PRINTF_2
#else // !wxUSE_LOG
// log functions do nothing at all
#define DECLARE_LOG_FUNCTION(level) \
inline void wxVLog##level(const wxChar *WXUNUSED(szFormat), \
va_list WXUNUSED(argptr)) { } \
inline void wxLog##level(const wxChar *WXUNUSED(szFormat), \
...) { }
#define DECLARE_LOG_FUNCTION2_EXP(level, argclass, arg, expdecl) \
inline void wxVLog##level(argclass WXUNUSED(arg), \
const wxChar *WXUNUSED(szFormat), \
va_list WXUNUSED(argptr)) {} \
inline void wxLog##level(argclass WXUNUSED(arg), \
const wxChar *WXUNUSED(szFormat), \
...) { }
#define DECLARE_LOG_FUNCTION_PUBLIC(level) \
/* void wxLog##level(const wxChar *szFormat, ...) {} */ \
WX_DEFINE_VARARG_FUNC_NOP(wxLog##level)
#define DECLARE_LOG_FUNCTION_IMPL(level) \
inline void wxVLog##level(const wxChar *WXUNUSED(szFormat), \
va_list WXUNUSED(argptr)) { } \
#define DECLARE_LOG_FUNCTION2_EXP_IMPL(level, argclass, arg, expdecl) \
inline void wxVLog##level(argclass WXUNUSED(arg), \
const wxChar *WXUNUSED(szFormat), \
va_list WXUNUSED(argptr)) {}
// Empty Class to fake wxLogNull
class WXDLLIMPEXP_BASE wxLogNull
@@ -514,6 +521,21 @@ public:
#endif // wxUSE_LOG/!wxUSE_LOG
#define DECLARE_LOG_FUNCTION(level) \
DECLARE_LOG_FUNCTION_PUBLIC(level) \
DECLARE_LOG_FUNCTION_IMPL(level)
#define DECLARE_LOG_FUNCTION2_EXP(level, argclass, arg, expdecl) \
DECLARE_LOG_FUNCTION_PUBLIC(level) \
DECLARE_LOG_FUNCTION2_EXP_IMPL(level, argclass, arg, expdecl)
#define DECLARE_LOG_FUNCTION2_EXP(level, argclass, arg, expdecl) \
DECLARE_LOG_FUNCTION_PUBLIC(level) \
DECLARE_LOG_FUNCTION2_EXP_IMPL(level, argclass, arg, expdecl)
#define DECLARE_LOG_FUNCTION2_IMPL(level, argclass, arg) \
DECLARE_LOG_FUNCTION2_EXP_IMPL(level, argclass, arg, WXDLLIMPEXP_BASE)
#define DECLARE_LOG_FUNCTION2(level, argclass, arg) \
DECLARE_LOG_FUNCTION2_EXP(level, argclass, arg, WXDLLIMPEXP_BASE)
@@ -531,22 +553,26 @@ DECLARE_LOG_FUNCTION(Verbose);
// this function sends the log message to the status line of the top level
// application frame, if any
DECLARE_LOG_FUNCTION(Status);
DECLARE_LOG_FUNCTION_IMPL(Status);
#if wxUSE_GUI
// this one is the same as previous except that it allows to explicitly
class WXDLLEXPORT wxFrame;
// specify the frame to which the output should go
DECLARE_LOG_FUNCTION2_EXP(Status, wxFrame *, pFrame, WXDLLIMPEXP_CORE);
DECLARE_LOG_FUNCTION2_EXP_IMPL(Status, wxFrame *, pFrame, WXDLLIMPEXP_CORE);
#endif // wxUSE_GUI
DECLARE_LOG_FUNCTION_PUBLIC(Status);
// additional one: as wxLogError, but also logs last system call error code
// and the corresponding error message if available
DECLARE_LOG_FUNCTION(SysError);
DECLARE_LOG_FUNCTION_IMPL(SysError);
// and another one which also takes the error code (for those broken APIs
// that don't set the errno (like registry APIs in Win32))
DECLARE_LOG_FUNCTION2(SysError, long, lErrCode);
DECLARE_LOG_FUNCTION2_IMPL(SysError, long, lErrCode);
DECLARE_LOG_FUNCTION_PUBLIC(SysError);
// debug functions do nothing in release mode
#if wxUSE_LOG && wxUSE_LOG_DEBUG
@@ -558,12 +584,12 @@ DECLARE_LOG_FUNCTION2(SysError, long, lErrCode);
// this version only logs the message if the mask had been added to the
// list of masks with AddTraceMask()
DECLARE_LOG_FUNCTION2(Trace, const wxChar *, mask);
DECLARE_LOG_FUNCTION2_IMPL(Trace, const wxChar*, mask);
// and this one does nothing if all of level bits are not set in
// wxLog::GetActive()->GetTraceMask() -- it's deprecated in favour of
// string identifiers
DECLARE_LOG_FUNCTION2(Trace, wxTraceMask, mask);
DECLARE_LOG_FUNCTION2_IMPL(Trace, wxTraceMask, mask);
DECLARE_LOG_FUNCTION_PUBLIC(Trace);
#else //!debug || !wxUSE_LOG
// these functions do nothing in release builds, but don't define them as
// nothing as it could result in different code structure in debug and
@@ -586,11 +612,11 @@ DECLARE_LOG_FUNCTION2(SysError, long, lErrCode);
#define wxLogDebug(fmt, ...) wxLogNop()
#define wxLogTrace(mask, fmt, ...) wxLogNop()
#else // !HAVE_VARIADIC_MACROS
// note that leaving out "fmt" in the vararg functions provokes a warning
// from SGI CC: "the last argument of the varargs function is unnamed"
inline void wxLogDebug(const wxChar *fmt, ...) { wxUnusedVar(fmt); }
inline void wxLogTrace(wxTraceMask, const wxChar *fmt, ...) { wxUnusedVar(fmt); }
inline void wxLogTrace(const wxChar *, const wxChar *fmt, ...) { wxUnusedVar(fmt); }
//inline void wxLogDebug(const wxString& fmt, ...) {}
WX_DEFINE_VARARG_FUNC_NOP(wxLogDebug, wxLogNopVararg)
//inline void wxLogTrace(wxTraceMask, const wxString& fmt, ...) {}
//inline void wxLogTrace(const wxString&, const wxString& fmt, ...) {}
WX_DEFINE_VARARG_FUNC_NOP(wxLogTrace, wxLogNopVararg)
#endif // HAVE_VARIADIC_MACROS/!HAVE_VARIADIC_MACROS
#endif // debug/!debug

View File

@@ -18,20 +18,42 @@
#include "wx/defs.h"
#include "wx/wxchar.h"
#include "wx/strvararg.h"
// ----------------------------------------------------------------------------
// wxMessageOutput is a class abstracting formatted output target, i.e.
// something you can printf() to
// ----------------------------------------------------------------------------
class WXDLLIMPEXP_BASE wxMessageOutput
// NB: VC6 has a bug that causes linker errors if you have template methods
// in a class using __declspec(dllimport). The solution is to split such
// class into two classes, one that contains the template methods and does
// *not* use WXDLLIMPEXP_BASE and another class that contains the rest
// (with DLL linkage).
class wxMessageOutputBase
{
public:
virtual ~wxMessageOutputBase() { }
// show a message to the user
// void Printf(const wxChar* format, ...) ATTRIBUTE_PRINTF_2 = 0;
WX_DEFINE_VARARG_FUNC_VOID(Printf, DoPrintf)
protected:
virtual void DoPrintf(const wxChar* format, ...) ATTRIBUTE_PRINTF_2 = 0;
};
#ifdef __VISUALC__
// "non dll-interface class 'wxStringPrintfMixin' used as base interface
// for dll-interface class 'wxString'" -- this is OK in our case
#pragma warning (disable:4275)
#endif
class WXDLLIMPEXP_BASE wxMessageOutput : public wxMessageOutputBase
{
public:
virtual ~wxMessageOutput() { }
// show a message to the user
virtual void Printf(const wxChar* format, ...) ATTRIBUTE_PRINTF_2 = 0;
// gets the current wxMessageOutput object (may be NULL during
// initialization or shutdown)
static wxMessageOutput* Get();
@@ -43,6 +65,10 @@ private:
static wxMessageOutput* ms_msgOut;
};
#ifdef __VISUALC__
#pragma warning (default:4275)
#endif
// ----------------------------------------------------------------------------
// implementation showing the message to the user in "best" possible way: uses
// native message box if available (currently only under Windows) and stderr
@@ -54,7 +80,8 @@ class WXDLLIMPEXP_BASE wxMessageOutputBest : public wxMessageOutput
public:
wxMessageOutputBest() { }
virtual void Printf(const wxChar* format, ...) ATTRIBUTE_PRINTF_2;
protected:
virtual void DoPrintf(const wxChar* format, ...) ATTRIBUTE_PRINTF_2;
};
// ----------------------------------------------------------------------------
@@ -66,7 +93,8 @@ class WXDLLIMPEXP_BASE wxMessageOutputStderr : public wxMessageOutput
public:
wxMessageOutputStderr() { }
virtual void Printf(const wxChar* format, ...) ATTRIBUTE_PRINTF_2;
protected:
virtual void DoPrintf(const wxChar* format, ...) ATTRIBUTE_PRINTF_2;
};
// ----------------------------------------------------------------------------
@@ -80,7 +108,8 @@ class WXDLLIMPEXP_CORE wxMessageOutputMessageBox : public wxMessageOutput
public:
wxMessageOutputMessageBox() { }
virtual void Printf(const wxChar* format, ...) ATTRIBUTE_PRINTF_2;
protected:
virtual void DoPrintf(const wxChar* format, ...) ATTRIBUTE_PRINTF_2;
};
#endif // wxUSE_GUI
@@ -94,7 +123,8 @@ class WXDLLIMPEXP_BASE wxMessageOutputDebug : public wxMessageOutput
public:
wxMessageOutputDebug() { }
virtual void Printf(const wxChar* format, ...) ATTRIBUTE_PRINTF_2;
protected:
virtual void DoPrintf(const wxChar* format, ...) ATTRIBUTE_PRINTF_2;
};
// ----------------------------------------------------------------------------
@@ -106,7 +136,8 @@ class WXDLLIMPEXP_BASE wxMessageOutputLog : public wxMessageOutput
public:
wxMessageOutputLog() { }
virtual void Printf(const wxChar* format, ...) ATTRIBUTE_PRINTF_2;
protected:
virtual void DoPrintf(const wxChar* format, ...) ATTRIBUTE_PRINTF_2;
};
#endif

View File

@@ -52,6 +52,7 @@
#endif
#include "wx/wxchar.h" // for wxChar
#include "wx/strvararg.h"
#include "wx/buffer.h" // for wxCharBuffer
#include "wx/strconv.h" // for wxConvertXXX() macros and wxMBConv classes
@@ -251,9 +252,6 @@ struct WXDLLIMPEXP_BASE wxStringData
class WXDLLIMPEXP_BASE wxStringBase
{
#if !wxUSE_STL
friend class WXDLLIMPEXP_BASE wxArrayString;
#endif
public :
// an 'invalid' value for string index, moved to this place due to a CW bug
static const size_t npos;
@@ -295,51 +293,141 @@ protected:
bool Alloc(size_t nLen);
public:
// standard types
typedef wxChar value_type;
typedef wxChar char_type;
typedef wxUniChar value_type;
typedef wxUniChar char_type;
typedef wxUniCharRef reference;
typedef wxChar* pointer;
typedef const wxChar* const_pointer;
typedef size_t size_type;
typedef value_type& reference;
typedef const value_type& const_reference;
typedef value_type* pointer;
typedef const value_type* const_pointer;
typedef value_type *iterator;
typedef const value_type *const_iterator;
typedef wxUniChar const_reference;
#define wxSTRING_REVERSE_ITERATOR(name, const_or_not) \
class name \
{ \
public: \
typedef wxChar value_type; \
typedef const_or_not value_type& reference; \
typedef const_or_not value_type *pointer; \
typedef const_or_not value_type *iterator_type; \
\
name(iterator_type i) : m_cur(i) { } \
name(const name& ri) : m_cur(ri.m_cur) { } \
\
iterator_type base() const { return m_cur; } \
\
reference operator*() const { return *(m_cur - 1); } \
\
name& operator++() { --m_cur; return *this; } \
name operator++(int) { name tmp = *this; --m_cur; return tmp; } \
name& operator--() { ++m_cur; return *this; } \
name operator--(int) { name tmp = *this; ++m_cur; return tmp; } \
\
bool operator==(name ri) const { return m_cur == ri.m_cur; } \
bool operator!=(name ri) const { return !(*this == ri); } \
\
private: \
iterator_type m_cur; \
}
#define WX_STR_ITERATOR_IMPL(iterator_name, pointer_type, \
reference_type, reference_ctor) \
public: \
typedef wxUniChar value_type; \
typedef reference_type reference; \
typedef pointer_type pointer; \
\
iterator_name(const iterator_name& i) : m_cur(i.m_cur) {} \
\
reference operator*() const { return reference_ctor; } \
\
iterator_name& operator++() \
{ ++m_cur; return *this; } \
iterator_name operator++(int) \
{ iterator_name tmp = *this; ++m_cur; return tmp; } \
iterator_name& operator--() \
{ --m_cur; return *this; } \
iterator_name operator--(int) \
{ iterator_name tmp = *this; --m_cur; return tmp; } \
\
iterator_name operator+(int n) const \
{ return iterator_name(m_cur + n); } \
iterator_name operator+(size_t n) const \
{ return iterator_name(m_cur + n); } \
iterator_name operator-(int n) const \
{ return iterator_name(m_cur - n); } \
iterator_name operator-(size_t n) const \
{ return iterator_name(m_cur - n); } \
iterator_name operator+=(int n) \
{ m_cur += n; return *this; } \
iterator_name operator+=(size_t n) \
{ m_cur += n; return *this; } \
iterator_name operator-=(int n) \
{ m_cur -= n; return *this; } \
iterator_name operator-=(size_t n) \
{ m_cur -= n; return *this; } \
\
unsigned operator-(const iterator_name& i) const \
{ return m_cur - i.m_cur; } \
\
bool operator==(const iterator_name&i) const \
{ return m_cur == i.m_cur; } \
bool operator!=(const iterator_name& i) const \
{ return m_cur != i.m_cur; } \
\
bool operator<(const iterator_name& i) const \
{ return m_cur < i.m_cur; } \
bool operator>(const iterator_name& i) const \
{ return m_cur > i.m_cur; } \
bool operator<=(const iterator_name& i) const \
{ return m_cur <= i.m_cur; } \
bool operator>=(const iterator_name& i) const \
{ return m_cur >= i.m_cur; } \
\
protected: \
/* for internal wxString use only: */ \
iterator_name(pointer ptr) : m_cur(ptr) {} \
operator pointer() const { return m_cur; } \
\
friend class WXDLLIMPEXP_BASE wxString; \
friend class WXDLLIMPEXP_BASE wxStringBase; \
friend class WXDLLIMPEXP_BASE wxCStrData; \
\
protected: \
pointer m_cur;
wxSTRING_REVERSE_ITERATOR(const_reverse_iterator, const);
class const_iterator;
#define wxSTRING_CONST
wxSTRING_REVERSE_ITERATOR(reverse_iterator, wxSTRING_CONST);
#undef wxSTRING_CONST
class iterator
{
WX_STR_ITERATOR_IMPL(iterator, wxChar*, wxUniCharRef,
wxUniCharRef::CreateForString(m_cur))
#undef wxSTRING_REVERSE_ITERATOR
friend class const_iterator;
};
class const_iterator
{
// NB: reference_type is intentionally value, not reference, the character
// may be encoded differently in wxString data:
WX_STR_ITERATOR_IMPL(const_iterator, const wxChar*, wxUniChar,
wxUniChar(*m_cur))
public:
const_iterator(const iterator& i) : m_cur(i.m_cur) {}
};
#undef WX_STR_ITERATOR
template <typename T>
class reverse_iterator_impl
{
public:
typedef T iterator_type;
typedef typename T::value_type value_type;
typedef typename T::reference reference;
typedef typename T::pointer *pointer;
reverse_iterator_impl(iterator_type i) : m_cur(i) {}
reverse_iterator_impl(const reverse_iterator_impl& ri)
: m_cur(ri.m_cur) {}
iterator_type base() const { return m_cur; }
reference operator*() const { return *(m_cur-1); }
reverse_iterator_impl& operator++()
{ --m_cur; return *this; }
reverse_iterator_impl operator++(int)
{ reverse_iterator_impl tmp = *this; --m_cur; return tmp; }
reverse_iterator_impl& operator--()
{ ++m_cur; return *this; }
reverse_iterator_impl operator--(int)
{ reverse_iterator_impl tmp = *this; ++m_cur; return tmp; }
bool operator==(const reverse_iterator_impl& ri) const
{ return m_cur == ri.m_cur; }
bool operator!=(const reverse_iterator_impl& ri) const
{ return !(*this == ri); }
private:
iterator_type m_cur;
};
typedef reverse_iterator_impl<iterator> reverse_iterator;
typedef reverse_iterator_impl<const_iterator> const_reverse_iterator;
// constructors and destructor
@@ -361,7 +449,7 @@ public:
}
}
// string containing nRepeat copies of ch
wxStringBase(size_type nRepeat, wxChar ch);
wxStringBase(size_type nRepeat, wxUniChar ch);
// ctor takes first nLength characters from C string
// (default value of npos means take all the string)
wxStringBase(const wxChar *psz)
@@ -404,7 +492,7 @@ public:
// from another wxString
wxStringBase& operator=(const wxStringBase& stringSrc);
// from a character
wxStringBase& operator=(wxChar ch);
wxStringBase& operator=(wxUniChar ch);
// from a C string
wxStringBase& operator=(const wxChar *psz);
@@ -415,7 +503,7 @@ public:
// return the maximum size of the string
size_type max_size() const { return npos; }
// resize the string, filling the space with c if c != 0
void resize(size_t nSize, wxChar ch = wxT('\0'));
void resize(size_t nSize, wxUniChar ch = wxT('\0'));
// delete the contents of the string
void clear() { erase(0, npos); }
// returns true if the string is empty
@@ -430,7 +518,11 @@ public:
{ wxASSERT_VALID_INDEX( n ); return m_pchData[n]; }
// returns the writable character at position n
reference at(size_type n)
{ wxASSERT_VALID_INDEX( n ); CopyBeforeWrite(); return m_pchData[n]; }
{
wxASSERT_VALID_INDEX( n );
CopyBeforeWrite();
return wxUniCharRef::CreateForString(&m_pchData[n]);
}
// lib.string.modifiers
// append elements str[pos], ..., str[pos+n]
@@ -449,7 +541,7 @@ public:
wxStringBase& append(const wxChar *sz, size_t n)
{ ConcatSelf(n, sz); return *this; }
// append n copies of ch
wxStringBase& append(size_t n, wxChar ch);
wxStringBase& append(size_t n, wxUniChar ch);
// append from first to last
wxStringBase& append(const_iterator first, const_iterator last)
{ ConcatSelf(last - first, first); return *this; }
@@ -466,7 +558,7 @@ public:
wxStringBase& assign(const wxChar *sz, size_t n)
{ clear(); return append(sz, n); }
// same as `= n copies of ch'
wxStringBase& assign(size_t n, wxChar ch)
wxStringBase& assign(size_t n, wxUniChar ch)
{ clear(); return append(n, ch); }
// assign from first to last
wxStringBase& assign(const_iterator first, const_iterator last)
@@ -504,13 +596,13 @@ public:
// insert first n (or all if n == npos) characters of sz
wxStringBase& insert(size_t nPos, const wxChar *sz, size_t n = npos);
// insert n copies of ch
wxStringBase& insert(size_t nPos, size_t n, wxChar ch)
wxStringBase& insert(size_t nPos, size_t n, wxUniChar ch)
{ return insert(nPos, wxStringBase(n, ch)); }
iterator insert(iterator it, wxChar ch)
iterator insert(iterator it, wxUniChar ch)
{ size_t idx = it - begin(); insert(idx, 1, ch); return begin() + idx; }
void insert(iterator it, const_iterator first, const_iterator last)
{ insert(it - begin(), first, last - first); }
void insert(iterator it, size_type n, wxChar ch)
void insert(iterator it, size_type n, wxUniChar ch)
{ insert(it - begin(), n, ch); }
// delete characters from nStart to nStart + nLen
@@ -533,7 +625,7 @@ public:
wxStringBase& replace(size_t nStart, size_t nLen, const wxStringBase& str)
{ return replace(nStart, nLen, str.c_str()); }
// replaces the substring with nCount copies of ch
wxStringBase& replace(size_t nStart, size_t nLen, size_t nCount, wxChar ch);
wxStringBase& replace(size_t nStart, size_t nLen, size_t nCount, wxUniChar ch);
// replaces a substring with another substring
wxStringBase& replace(size_t nStart, size_t nLen,
const wxStringBase& str, size_t nStart2, size_t nLen2);
@@ -547,7 +639,7 @@ public:
{ return replace(first - begin(), last - first, s, n); }
wxStringBase& replace(iterator first, iterator last, const wxStringBase& s)
{ return replace(first - begin(), last - first, s); }
wxStringBase& replace(iterator first, iterator last, size_type n, wxChar c)
wxStringBase& replace(iterator first, iterator last, size_type n, wxUniChar c)
{ return replace(first - begin(), last - first, n, c); }
wxStringBase& replace(iterator first, iterator last,
const_iterator first1, const_iterator last1)
@@ -567,7 +659,7 @@ public:
size_t find(const wxChar* sz, size_t nStart = 0, size_t n = npos) const;
// find the first occurence of character ch after nStart
size_t find(wxChar ch, size_t nStart = 0) const;
size_t find(wxUniChar ch, size_t nStart = 0) const;
// rfind() family is exactly like find() but works right to left
@@ -578,7 +670,7 @@ public:
size_t rfind(const wxChar* sz, size_t nStart = npos,
size_t n = npos) const;
// as find, but from the end
size_t rfind(wxChar ch, size_t nStart = npos) const;
size_t rfind(wxUniChar ch, size_t nStart = npos) const;
// find first/last occurence of any character in the set
@@ -589,7 +681,7 @@ public:
size_t find_first_of(const wxChar* sz, size_t nStart = 0) const;
size_t find_first_of(const wxChar* sz, size_t nStart, size_t n) const;
// same as find(char, size_t)
size_t find_first_of(wxChar c, size_t nStart = 0) const
size_t find_first_of(wxUniChar c, size_t nStart = 0) const
{ return find(c, nStart); }
// find the last (starting from nStart) char from str in this string
size_t find_last_of (const wxStringBase& str, size_t nStart = npos) const
@@ -598,7 +690,7 @@ public:
size_t find_last_of (const wxChar* sz, size_t nStart = npos) const;
size_t find_last_of(const wxChar* sz, size_t nStart, size_t n) const;
// same as above
size_t find_last_of(wxChar c, size_t nStart = npos) const
size_t find_last_of(wxUniChar c, size_t nStart = npos) const
{ return rfind(c, nStart); }
// find first/last occurence of any character not in the set
@@ -610,7 +702,7 @@ public:
size_t find_first_not_of(const wxChar* sz, size_t nStart = 0) const;
size_t find_first_not_of(const wxChar* sz, size_t nStart, size_t n) const;
// same as above
size_t find_first_not_of(wxChar ch, size_t nStart = 0) const;
size_t find_first_not_of(wxUniChar ch, size_t nStart = 0) const;
// as strcspn()
size_t find_last_not_of(const wxStringBase& str, size_t nStart = npos) const
{ return find_last_not_of(str.c_str(), nStart); }
@@ -618,7 +710,7 @@ public:
size_t find_last_not_of(const wxChar* sz, size_t nStart = npos) const;
size_t find_last_not_of(const wxChar* sz, size_t nStart, size_t n) const;
// same as above
size_t find_last_not_of(wxChar ch, size_t nStart = npos) const;
size_t find_last_not_of(wxUniChar ch, size_t nStart = npos) const;
// All compare functions return -1, 0 or 1 if the [sub]string is less,
// equal or greater than the compare() argument.
@@ -646,22 +738,157 @@ public:
// string += C string
wxStringBase& operator+=(const wxChar *psz) { return append(psz); }
// string += char
wxStringBase& operator+=(wxChar ch) { return append(1, ch); }
wxStringBase& operator+=(wxUniChar ch) { return append(1, ch); }
wxStringBase& operator+=(wxUniCharRef ch) { return append(1, ch); }
wxStringBase& operator+=(char ch) { return append(1, ch); }
wxStringBase& operator+=(wchar_t ch) { return append(1, ch); }
};
#endif // !wxUSE_STL
// ----------------------------------------------------------------------------
// wxCStrData
// ----------------------------------------------------------------------------
// Lightweight object returned by wxString::c_str() and implicitly convertible
// to either const char* or const wchar_t*.
class WXDLLIMPEXP_BASE wxCStrData
{
private:
// Ctors; for internal use by wxString and wxCStrData only
wxCStrData(const wxString *str, size_t offset = 0, bool owned = false)
: m_str(str), m_offset(offset), m_owned(owned) {}
public:
// Ctor constructs the object from char literal; they are needed to make
// operator?: compile and they intentionally take char*, not const char*
wxCStrData(char *buf);
wxCStrData(wchar_t *buf);
~wxCStrData();
// FIXME: we'll need convertors for both char* and wchar_t* and NONE
// for wxChar*, but that's after completing the transition to
// "smart" wxUniChar class. For now, just have conversion to
// char* in ANSI build and wchar_t in Unicode build.
#if wxUSE_UNICODE
const wchar_t* AsWChar() const;
operator const wchar_t*() const { return AsWChar(); }
#else
const char* AsChar() const;
operator const char*() const { return AsChar(); }
#endif
wxString AsString() const;
operator wxString() const;
// allow expressions like "c_str()[0]":
wxUniChar operator[](int n) const { return operator[](size_t(n)); }
wxUniChar operator[](size_t n) const;
#ifndef wxSIZE_T_IS_UINT
wxUniChar operator[](unsigned int n) const { return operator[](size_t(n)); }
#endif // size_t != unsigned int
// this operator is needed to emulate the pointer semantics of c_str():
// expressions like "wxChar *p = str.c_str() + 1;" should continue to work
// (we need both versions to resolve ambiguities):
wxCStrData operator+(int n) const
{ return wxCStrData(m_str, m_offset + n, m_owned); }
wxCStrData operator+(size_t n) const
{ return wxCStrData(m_str, m_offset + n, m_owned); }
// this operator is need to make expressions like "*c_str()" or
// "*(c_str() + 2)" work
wxUniChar operator*() const;
private:
const wxString *m_str;
size_t m_offset;
bool m_owned;
friend class WXDLLIMPEXP_BASE wxString;
};
// ----------------------------------------------------------------------------
// wxStringPrintfMixin
// ---------------------------------------------------------------------------
// NB: VC6 has a bug that causes linker errors if you have template methods
// in a class using __declspec(dllimport). The solution is to split such
// class into two classes, one that contains the template methods and does
// *not* use WXDLLIMPEXP_BASE and another class that contains the rest
// (with DLL linkage).
//
// We only do this for VC6 here, because the code is less efficient
// (Printf() has to use dynamic_cast<>) and because OpenWatcom compiler
// cannot compile this code.
#if defined(__VISUALC__) && __VISUALC__ < 1300
#define wxNEEDS_WXSTRING_PRINTF_MIXIN
#endif
#ifdef wxNEEDS_WXSTRING_PRINTF_MIXIN
// this class contains implementation of wxString's vararg methods, it's
// exported from wxBase DLL
class WXDLLIMPEXP_BASE wxStringPrintfMixinBase
{
protected:
wxStringPrintfMixinBase() {}
int DoPrintf(const wxChar *format, ...) ATTRIBUTE_PRINTF_2;
static wxString DoFormat(const wxChar *format, ...) ATTRIBUTE_PRINTF_1;
};
// this class contains template wrappers for wxString's vararg methods, it's
// intentionally *not* exported from the DLL in order to fix the VC6 bug
// described above
class wxStringPrintfMixin : public wxStringPrintfMixinBase
{
private:
// to further complicate things, we can't return wxString from
// wxStringPrintfMixin::Format() because wxString is not yet declared at
// this point; the solution is to use this fake type trait template - this
// way the compiler won't know the return type until Format() is used
// (this doesn't compile with Watcom, but VC6 compiles it just fine):
template<typename T> struct StringReturnType
{
typedef wxString type;
};
public:
// these are duplicated wxString methods, they're also declared below
// if !wxNEEDS_WXSTRING_PRINTF_MIXIN:
// int Printf(const wxChar *pszFormat, ...);
WX_DEFINE_VARARG_FUNC(int, Printf, DoPrintf)
// static wxString Format(const wxChar *pszFormat, ...) ATTRIBUTE_PRINTF_1;
WX_DEFINE_VARARG_FUNC(static typename StringReturnType<T1>::type,
Format, DoFormat)
// int sprintf(const wxChar *pszFormat, ...) ATTRIBUTE_PRINTF_2;
WX_DEFINE_VARARG_FUNC(int, sprintf, DoPrintf)
protected:
wxStringPrintfMixin() : wxStringPrintfMixinBase() {}
};
#endif // wxNEEDS_WXSTRING_PRINTF_MIXIN
// ----------------------------------------------------------------------------
// wxString: string class trying to be compatible with std::string, MFC
// CString and wxWindows 1.x wxString all at once
// ---------------------------------------------------------------------------
class WXDLLIMPEXP_BASE wxString : public wxStringBase
{
#if !wxUSE_STL
friend class WXDLLIMPEXP_BASE wxArrayString;
#ifdef wxNEEDS_WXSTRING_PRINTF_MIXIN
// "non dll-interface class 'wxStringPrintfMixin' used as base interface
// for dll-interface class 'wxString'" -- this is OK in our case
#pragma warning (disable:4275)
#endif
class WXDLLIMPEXP_BASE wxString : public wxStringBase
#ifdef wxNEEDS_WXSTRING_PRINTF_MIXIN
,public wxStringPrintfMixin
#endif
{
// NB: special care was taken in arranging the member functions in such order
// that all inline functions can be effectively inlined, verify that all
// performance critical functions are still inlined if you change order!
@@ -689,9 +916,21 @@ public:
wxString(const wxStringBase& stringSrc) : wxStringBase(stringSrc) { }
wxString(const wxString& stringSrc) : wxStringBase(stringSrc) { }
// string containing nRepeat copies of ch
wxString(wxChar ch, size_t nRepeat = 1)
wxString(wxUniChar ch, size_t nRepeat = 1)
: wxStringBase(nRepeat, ch) { }
wxString(size_t nRepeat, wxChar ch)
wxString(size_t nRepeat, wxUniChar ch)
: wxStringBase(nRepeat, ch) { }
wxString(wxUniCharRef ch, size_t nRepeat = 1)
: wxStringBase(nRepeat, ch) { }
wxString(size_t nRepeat, wxUniCharRef ch)
: wxStringBase(nRepeat, ch) { }
wxString(char ch, size_t nRepeat = 1)
: wxStringBase(nRepeat, ch) { }
wxString(size_t nRepeat, char ch)
: wxStringBase(nRepeat, ch) { }
wxString(wchar_t ch, size_t nRepeat = 1)
: wxStringBase(nRepeat, ch) { }
wxString(size_t nRepeat, wchar_t ch)
: wxStringBase(nRepeat, ch) { }
// ctor takes first nLength characters from C string
// (default value of npos means take all the string)
@@ -775,17 +1014,17 @@ public:
// data access (all indexes are 0 based)
// read access
wxChar GetChar(size_t n) const
wxUniChar GetChar(size_t n) const
{ return at(n); }
// read/write access
wxChar& GetWritableChar(size_t n)
wxUniCharRef GetWritableChar(size_t n)
{ return at(n); }
// write access
void SetChar(size_t n, wxChar ch)
void SetChar(size_t n, wxUniChar ch)
{ at(n) = ch; }
// get last character
wxChar Last() const
wxUniChar Last() const
{
wxASSERT_MSG( !empty(), _T("wxString: index out of bounds") );
@@ -793,7 +1032,7 @@ public:
}
// get writable last character
wxChar& Last()
wxUniCharRef Last()
{
wxASSERT_MSG( !empty(), _T("wxString: index out of bounds") );
return at(length() - 1);
@@ -801,42 +1040,40 @@ public:
/*
Note that we we must define all of the overloads below to avoid
ambiguity when using str[0]. Also note that for a conforming compiler we
don't need const version of operatorp[] at all as indexed access to
const string is provided by implicit conversion to "const wxChar *"
below and defining them would only result in ambiguities, but some other
compilers refuse to compile "str[0]" without them.
ambiguity when using str[0].
*/
#if defined(__BORLANDC__) || defined(__WATCOMC__) || defined(__MWERKS__)
wxChar operator[](int n) const
wxUniChar operator[](int n) const
{ return wxStringBase::at(n); }
wxChar operator[](size_type n) const
wxUniChar operator[](size_t n) const
{ return wxStringBase::at(n); }
#ifndef wxSIZE_T_IS_UINT
wxChar operator[](unsigned int n) const
wxUniChar operator[](unsigned int n) const
{ return wxStringBase::at(n); }
#endif // size_t != unsigned int
#endif // broken compiler
// operator versions of GetWriteableChar()
wxChar& operator[](int n)
wxUniCharRef operator[](int n)
{ return wxStringBase::at(n); }
wxChar& operator[](size_type n)
wxUniCharRef operator[](size_t n)
{ return wxStringBase::at(n); }
#ifndef wxSIZE_T_IS_UINT
wxChar& operator[](unsigned int n)
wxUniCharRef operator[](unsigned int n)
{ return wxStringBase::at(n); }
#endif // size_t != unsigned int
// explicit conversion to C string (use this with printf()!)
wxCStrData c_str() const { return wxCStrData(this); }
// implicit conversion to C string
operator wxCStrData() const { return c_str(); }
operator const wxChar*() const { return c_str(); }
// identical to c_str(), for wxWin 1.6x compatibility
const wxChar* wx_str() const { return c_str(); }
// identical to c_str(), for MFC compatibility
const wxChar* GetData() const { return c_str(); }
const wxCStrData GetData() const { return c_str(); }
// explicit conversion to C string in internal representation (char*,
// wchar_t*, UTF-8-encoded char*, depending on the build):
const_pointer wx_str() const { return data(); }
// conversion to/from plain (i.e. 7 bit) ASCII: this is useful for
// converting numbers or strings which are certain not to contain special
@@ -901,8 +1138,14 @@ public:
wxString& operator=(const wxStringBase& stringSrc)
{ return (wxString&)wxStringBase::operator=(stringSrc); }
// from a character
wxString& operator=(wxChar ch)
wxString& operator=(wxUniChar ch)
{ return (wxString&)wxStringBase::operator=(ch); }
wxString& operator=(wxUniCharRef ch)
{ return (wxString&)wxStringBase::operator=((wxUniChar)ch); }
wxString& operator=(char ch)
{ return (wxString&)wxStringBase::operator=(wxUniChar(ch)); }
wxString& operator=(wchar_t ch)
{ return (wxString&)wxStringBase::operator=(wxUniChar(ch)); }
// from a C string - STL probably will crash on NULL,
// so we need to compensate in that case
#if wxUSE_STL
@@ -952,9 +1195,14 @@ public:
}
// string += C string
wxString& operator<<(const wxChar *psz)
{ append(psz); return *this; }
wxString& operator<<(const wxCStrData& psz)
{ append(psz); return *this; }
// string += char
wxString& operator<<(wxChar ch) { append(1, ch); return *this; }
wxString& operator<<(wxUniChar ch) { append(1, ch); return *this; }
wxString& operator<<(wxUniCharRef ch) { append(1, ch); return *this; }
wxString& operator<<(char ch) { append(1, ch); return *this; }
wxString& operator<<(wchar_t ch) { append(1, ch); return *this; }
// string += buffer (i.e. from wxGetString)
#if wxUSE_UNICODE
@@ -987,10 +1235,18 @@ public:
append(s);
return *this;
}
wxString& Append(const wxCStrData& psz)
{ append(psz); return *this; }
wxString& Append(const wxChar* psz)
{ append(psz); return *this; }
// append count copies of given character
wxString& Append(wxChar ch, size_t count = 1u)
wxString& Append(wxUniChar ch, size_t count = 1u)
{ append(count, ch); return *this; }
wxString& Append(wxUniCharRef ch, size_t count = 1u)
{ append(count, ch); return *this; }
wxString& Append(char ch, size_t count = 1u)
{ append(count, ch); return *this; }
wxString& Append(wchar_t ch, size_t count = 1u)
{ append(count, ch); return *this; }
wxString& Append(const wxChar* psz, size_t nLen)
{ append(psz, nLen); return *this; }
@@ -1004,9 +1260,9 @@ public:
friend wxString WXDLLIMPEXP_BASE operator+(const wxString& string1,
const wxString& string2);
// string with a single char
friend wxString WXDLLIMPEXP_BASE operator+(const wxString& string, wxChar ch);
friend wxString WXDLLIMPEXP_BASE operator+(const wxString& string, wxUniChar ch);
// char with a string
friend wxString WXDLLIMPEXP_BASE operator+(wxChar ch, const wxString& string);
friend wxString WXDLLIMPEXP_BASE operator+(wxUniChar ch, const wxString& string);
// string with C string
friend wxString WXDLLIMPEXP_BASE operator+(const wxString& string,
const wxChar *psz);
@@ -1060,7 +1316,7 @@ public:
bool IsSameAs(const wxChar *psz, bool compareWithCase = true) const
{ return (compareWithCase ? Cmp(psz) : CmpNoCase(psz)) == 0; }
// comparison with a single character: returns true if equal
bool IsSameAs(wxChar c, bool compareWithCase = true) const
bool IsSameAs(wxUniChar c, bool compareWithCase = true) const
{
return (length() == 1) && (compareWithCase ? GetChar(0u) == c
: wxToupper(GetChar(0u)) == wxToupper(c));
@@ -1090,20 +1346,20 @@ public:
wxString Right(size_t nCount) const;
// get all characters before the first occurance of ch
// (returns the whole string if ch not found)
wxString BeforeFirst(wxChar ch) const;
wxString BeforeFirst(wxUniChar ch) const;
// get all characters before the last occurence of ch
// (returns empty string if ch not found)
wxString BeforeLast(wxChar ch) const;
wxString BeforeLast(wxUniChar ch) const;
// get all characters after the first occurence of ch
// (returns empty string if ch not found)
wxString AfterFirst(wxChar ch) const;
wxString AfterFirst(wxUniChar ch) const;
// get all characters after the last occurence of ch
// (returns the whole string if ch not found)
wxString AfterLast(wxChar ch) const;
wxString AfterLast(wxUniChar ch) const;
// for compatibility only, use more explicitly named functions above
wxString Before(wxChar ch) const { return BeforeLast(ch); }
wxString After(wxChar ch) const { return AfterFirst(ch); }
wxString Before(wxUniChar ch) const { return BeforeLast(ch); }
wxString After(wxUniChar ch) const { return AfterFirst(ch); }
// case conversion
// convert to upper case in place, return the string itself
@@ -1120,11 +1376,11 @@ public:
// remove spaces from left or from right (default) side
wxString& Trim(bool bFromRight = true);
// add nCount copies chPad in the beginning or at the end (default)
wxString& Pad(size_t nCount, wxChar chPad = wxT(' '), bool bFromRight = true);
wxString& Pad(size_t nCount, wxUniChar chPad = wxT(' '), bool bFromRight = true);
// searching and replacing
// searching (return starting index, or -1 if not found)
int Find(wxChar ch, bool bFromEnd = false) const; // like strchr/strrchr
int Find(wxUniChar ch, bool bFromEnd = false) const; // like strchr/strrchr
// searching (return starting index, or -1 if not found)
int Find(const wxChar *pszSub) const; // like strstr
// replace first (or all of bReplaceAll) occurences of substring with
@@ -1155,18 +1411,23 @@ public:
bool ToDouble(double *val) const;
#ifndef wxNEEDS_WXSTRING_PRINTF_MIXIN
// formatted input/output
// as sprintf(), returns the number of characters written or < 0 on error
// (take 'this' into account in attribute parameter count)
int Printf(const wxChar *pszFormat, ...) ATTRIBUTE_PRINTF_2;
// int Printf(const wxChar *pszFormat, ...);
WX_DEFINE_VARARG_FUNC(int, Printf, DoPrintf)
#endif // !wxNEEDS_WXSTRING_PRINTF_MIXIN
// as vprintf(), returns the number of characters written or < 0 on error
int PrintfV(const wxChar* pszFormat, va_list argptr);
int PrintfV(const wxString& format, va_list argptr);
#ifndef wxNEEDS_WXSTRING_PRINTF_MIXIN
// returns the string containing the result of Printf() to it
static wxString Format(const wxChar *pszFormat, ...) ATTRIBUTE_PRINTF_1;
// static wxString Format(const wxChar *pszFormat, ...) ATTRIBUTE_PRINTF_1;
WX_DEFINE_VARARG_FUNC(static wxString, Format, DoFormat)
#endif
// the same as above, but takes a va_list
static wxString FormatV(const wxChar *pszFormat, va_list argptr);
static wxString FormatV(const wxString& format, va_list argptr);
// raw access to string memory
// ensure that string has space for at least nLen characters
@@ -1196,9 +1457,12 @@ public:
// values for first parameter of Strip function
enum stripType {leading = 0x1, trailing = 0x2, both = 0x3};
#ifndef wxNEEDS_WXSTRING_PRINTF_MIXIN
// use Printf()
// (take 'this' into account in attribute parameter count)
int sprintf(const wxChar *pszFormat, ...) ATTRIBUTE_PRINTF_2;
// int sprintf(const wxChar *pszFormat, ...) ATTRIBUTE_PRINTF_2;
WX_DEFINE_VARARG_FUNC(int, sprintf, DoPrintf)
#endif // wxNEEDS_WXSTRING_PRINTF_MIXIN
// use Cmp()
inline int CompareTo(const wxChar* psz, caseCompare cmp = exact) const
@@ -1207,7 +1471,7 @@ public:
// use Len
size_t Length() const { return length(); }
// Count the number of characters
int Freq(wxChar ch) const;
int Freq(wxUniChar ch) const;
// use MakeLower
void LowerCase() { MakeLower(); }
// use MakeUpper
@@ -1217,7 +1481,7 @@ public:
// use Find (more general variants not yet supported)
size_t Index(const wxChar* psz) const { return Find(psz); }
size_t Index(wxChar ch) const { return Find(ch); }
size_t Index(wxUniChar ch) const { return Find(ch); }
// use Truncate
wxString& Remove(size_t pos) { return Truncate(pos); }
wxString& RemoveLast(size_t n = 1) { return Truncate(length() - n); }
@@ -1226,10 +1490,12 @@ public:
{ return (wxString&)erase( nStart, nLen ); }
// use Find()
int First( const wxChar ch ) const { return Find(ch); }
int First( const wxUniChar ch ) const { return Find(ch); }
int First( char ch ) const { return Find(ch); }
int First( wchar_t ch ) const { return Find(ch); }
int First( const wxChar* psz ) const { return Find(psz); }
int First( const wxString &str ) const { return Find(str); }
int Last( const wxChar ch ) const { return Find(ch, true); }
int Last( const wxUniChar ch ) const { return Find(ch, true); }
bool Contains(const wxString& str) const { return Find(str) != wxNOT_FOUND; }
// use empty()
@@ -1243,10 +1509,10 @@ public:
// take all characters from pStart to pEnd
wxString(const void *pStart, const void *pEnd)
: wxStringBase((const wxChar*)pStart, (const wxChar*)pEnd) { }
#if wxUSE_STL
wxString(const_iterator first, const_iterator last)
: wxStringBase(first, last) { }
#endif
wxString(iterator first, iterator last)
: wxStringBase(first, last) { }
// lib.string.modifiers
// append elements str[pos], ..., str[pos+n]
@@ -1255,13 +1521,15 @@ public:
// append a string
wxString& append(const wxString& str)
{ return (wxString&)wxStringBase::append(str); }
wxString& append(const wxCStrData& str)
{ return (wxString&)wxStringBase::append(str.AsString()); }
// append first n (or all if n == npos) characters of sz
wxString& append(const wxChar *sz)
{ return (wxString&)wxStringBase::append(sz); }
wxString& append(const wxChar *sz, size_t n)
{ return (wxString&)wxStringBase::append(sz, n); }
// append n copies of ch
wxString& append(size_t n, wxChar ch)
wxString& append(size_t n, wxUniChar ch)
{ return (wxString&)wxStringBase::append(n, ch); }
// append from first to last
wxString& append(const_iterator first, const_iterator last)
@@ -1279,7 +1547,7 @@ public:
wxString& assign(const wxChar *sz, size_t n)
{ return (wxString&)wxStringBase::assign(sz, n); }
// same as `= n copies of ch'
wxString& assign(size_t n, wxChar ch)
wxString& assign(size_t n, wxUniChar ch)
{ return (wxString&)wxStringBase::assign(n, ch); }
// assign from first to last
wxString& assign(const_iterator first, const_iterator last)
@@ -1312,13 +1580,13 @@ public:
wxString& insert(size_t nPos, const wxChar *sz, size_t n)
{ return (wxString&)wxStringBase::insert(nPos, sz, n); }
// insert n copies of ch
wxString& insert(size_t nPos, size_t n, wxChar ch)
wxString& insert(size_t nPos, size_t n, wxUniChar ch)
{ return (wxString&)wxStringBase::insert(nPos, n, ch); }
iterator insert(iterator it, wxChar ch)
iterator insert(iterator it, wxUniChar ch)
{ return wxStringBase::insert(it, ch); }
void insert(iterator it, const_iterator first, const_iterator last)
{ wxStringBase::insert(it, first, last); }
void insert(iterator it, size_type n, wxChar ch)
void insert(iterator it, size_type n, wxUniChar ch)
{ wxStringBase::insert(it, n, ch); }
// delete characters from nStart to nStart + nLen
@@ -1340,7 +1608,7 @@ public:
wxString& replace(size_t nStart, size_t nLen, const wxString& str)
{ return (wxString&)wxStringBase::replace(nStart, nLen, str); }
// replaces the substring with nCount copies of ch
wxString& replace(size_t nStart, size_t nLen, size_t nCount, wxChar ch)
wxString& replace(size_t nStart, size_t nLen, size_t nCount, wxUniChar ch)
{ return (wxString&)wxStringBase::replace(nStart, nLen, nCount, ch); }
// replaces a substring with another substring
wxString& replace(size_t nStart, size_t nLen,
@@ -1358,7 +1626,7 @@ public:
{ return (wxString&)wxStringBase::replace(first, last, s, n); }
wxString& replace(iterator first, iterator last, const wxString& s)
{ return (wxString&)wxStringBase::replace(first, last, s); }
wxString& replace(iterator first, iterator last, size_type n, wxChar c)
wxString& replace(iterator first, iterator last, size_type n, wxUniChar c)
{ return (wxString&)wxStringBase::replace(first, last, n, c); }
wxString& replace(iterator first, iterator last,
const_iterator first1, const_iterator last1)
@@ -1370,9 +1638,14 @@ public:
// string += C string
wxString& operator+=(const wxChar *psz)
{ return (wxString&)wxStringBase::operator+=(psz); }
wxString& operator+=(const wxCStrData& s)
{ return (wxString&)wxStringBase::operator+=(s.AsString()); }
// string += char
wxString& operator+=(wxChar ch)
wxString& operator+=(wxUniChar ch)
{ return (wxString&)wxStringBase::operator+=(ch); }
wxString& operator+=(wxUniCharRef ch) { return *this += wxUniChar(ch); }
wxString& operator+=(char ch) { return *this += wxUniChar(ch); }
wxString& operator+=(wchar_t ch) { return *this += wxUniChar(ch); }
private:
#if !wxUSE_STL
@@ -1384,18 +1657,41 @@ private:
friend class WXDLLIMPEXP_BASE wxStringBuffer;
friend class WXDLLIMPEXP_BASE wxStringBufferLength;
#endif
#ifndef wxNEEDS_WXSTRING_PRINTF_MIXIN
int DoPrintf(const wxChar *format, ...) ATTRIBUTE_PRINTF_2;
static wxString DoFormat(const wxChar *format, ...) ATTRIBUTE_PRINTF_1;
#endif
};
#ifdef wxNEEDS_WXSTRING_PRINTF_MIXIN
#pragma warning (default:4275)
#endif
// notice that even though for many compilers the friend declarations above are
// enough, from the point of view of C++ standard we must have the declarations
// here as friend ones are not injected in the enclosing namespace and without
// them the code fails to compile with conforming compilers such as xlC or g++4
wxString WXDLLIMPEXP_BASE operator+(const wxString& string1, const wxString& string2);
wxString WXDLLIMPEXP_BASE operator+(const wxString& string, wxChar ch);
wxString WXDLLIMPEXP_BASE operator+(wxChar ch, const wxString& string);
wxString WXDLLIMPEXP_BASE operator+(const wxString& string1, const wxString& string2);
wxString WXDLLIMPEXP_BASE operator+(const wxString& string, const wxChar *psz);
wxString WXDLLIMPEXP_BASE operator+(const wxChar *psz, const wxString& string);
wxString WXDLLIMPEXP_BASE operator+(const wxString& string, wxUniChar ch);
wxString WXDLLIMPEXP_BASE operator+(wxUniChar ch, const wxString& string);
inline wxString operator+(const wxString& string, wxUniCharRef ch)
{ return string + (wxUniChar)ch; }
inline wxString operator+(const wxString& string, char ch)
{ return string + wxUniChar(ch); }
inline wxString operator+(const wxString& string, wchar_t ch)
{ return string + wxUniChar(ch); }
inline wxString operator+(wxUniCharRef ch, const wxString& string)
{ return (wxUniChar)ch + string; }
inline wxString operator+(char ch, const wxString& string)
{ return wxUniChar(ch) + string; }
inline wxString operator+(wchar_t ch, const wxString& string)
{ return wxUniChar(ch) + string; }
#if wxUSE_STL
// return an empty wxString (not very useful with wxUSE_STL == 1)
@@ -1597,10 +1893,24 @@ inline wxString operator+(const wxCharBuffer& buf, const wxString& string)
// comparison with char (those are not defined by std::[w]string and so should
// be always available)
inline bool operator==(wxChar c, const wxString& s) { return s.IsSameAs(c); }
inline bool operator==(const wxString& s, wxChar c) { return s.IsSameAs(c); }
inline bool operator!=(wxChar c, const wxString& s) { return !s.IsSameAs(c); }
inline bool operator!=(const wxString& s, wxChar c) { return !s.IsSameAs(c); }
inline bool operator==(const wxUniChar& c, const wxString& s) { return s.IsSameAs(c); }
inline bool operator==(const wxUniCharRef& c, const wxString& s) { return s.IsSameAs(c); }
inline bool operator==(char c, const wxString& s) { return s.IsSameAs(c); }
inline bool operator==(wchar_t c, const wxString& s) { return s.IsSameAs(c); }
inline bool operator==(int c, const wxString& s) { return s.IsSameAs(c); }
inline bool operator==(const wxString& s, const wxUniChar& c) { return s.IsSameAs(c); }
inline bool operator==(const wxString& s, const wxUniCharRef& c) { return s.IsSameAs(c); }
inline bool operator==(const wxString& s, char c) { return s.IsSameAs(c); }
inline bool operator==(const wxString& s, wchar_t c) { return s.IsSameAs(c); }
inline bool operator!=(const wxUniChar& c, const wxString& s) { return !s.IsSameAs(c); }
inline bool operator!=(const wxUniCharRef& c, const wxString& s) { return !s.IsSameAs(c); }
inline bool operator!=(char c, const wxString& s) { return !s.IsSameAs(c); }
inline bool operator!=(wchar_t c, const wxString& s) { return !s.IsSameAs(c); }
inline bool operator!=(int c, const wxString& s) { return !s.IsSameAs(c); }
inline bool operator!=(const wxString& s, const wxUniChar& c) { return !s.IsSameAs(c); }
inline bool operator!=(const wxString& s, const wxUniCharRef& c) { return !s.IsSameAs(c); }
inline bool operator!=(const wxString& s, char c) { return !s.IsSameAs(c); }
inline bool operator!=(const wxString& s, wchar_t c) { return !s.IsSameAs(c); }
// comparison with C string in Unicode build
#if wxUSE_UNICODE
@@ -1642,7 +1952,58 @@ inline bool operator>=(const char* s1, const wxString& s2)
#include "wx/iosfwrap.h"
WXDLLIMPEXP_BASE wxSTD ostream& operator<<(wxSTD ostream&, const wxString&);
WXDLLIMPEXP_BASE wxSTD ostream& operator<<(wxSTD ostream&, const wxCStrData&);
#endif // wxSTD_STRING_COMPATIBILITY
// ---------------------------------------------------------------------------
// wxCStrData implementation
// ---------------------------------------------------------------------------
inline wxCStrData::wxCStrData(char *buf)
: m_str(new wxString(buf)), m_offset(0), m_owned(true) {}
inline wxCStrData::wxCStrData(wchar_t *buf)
: m_str(new wxString(buf)), m_offset(0), m_owned(true) {}
inline wxCStrData::~wxCStrData()
{
if ( m_owned )
delete m_str;
}
#if wxUSE_UNICODE
inline const wchar_t* wxCStrData::AsWChar() const
#else
inline const char* wxCStrData::AsChar() const
#endif
{
if ( m_offset == 0 )
return m_str->wx_str(); // FIXME
else
return (const wxChar*)(m_str->begin() + m_offset);
}
inline wxString wxCStrData::AsString() const
{
if ( m_offset == 0 )
return *m_str;
else
return m_str->Mid(m_offset);
}
inline wxCStrData::operator wxString() const { return AsString(); }
inline wxUniChar wxCStrData::operator*() const
{
if ( m_str->empty() )
return wxUniChar(_T('\0'));
else
return (*m_str)[m_offset];
}
inline wxUniChar wxCStrData::operator[](size_t n) const
{
return m_str->at(m_offset + n);
}
#endif // _WX_WXSTRINGH__

326
include/wx/strvararg.h Normal file
View File

@@ -0,0 +1,326 @@
///////////////////////////////////////////////////////////////////////////////
// Name: wx/strvararg.h
// Purpose: macros for implementing type-safe vararg passing of strings
// Author: Vaclav Slavik
// Created: 2007-02-19
// RCS-ID: $Id$
// Copyright: (c) 2007 REA Elektronik GmbH
// Licence: wxWindows licence
///////////////////////////////////////////////////////////////////////////////
#ifndef _WX_STRVARARG_H_
#define _WX_STRVARARG_H_
#include "wx/platform.h"
#if wxONLY_WATCOM_EARLIER_THAN(1,4)
#error "OpenWatcom version >= 1.4 is required to compile this code"
#endif
// include wchar_t definition if needed:
#if defined(__WATCOMC__)
#include <inttypes.h>
#elif defined(__VISUALC__)
#include <stdlib.h>
#endif
class WXDLLIMPEXP_BASE wxCStrData;
class WXDLLIMPEXP_BASE wxString;
class WXDLLIMPEXP_BASE wxCharBuffer;
class WXDLLIMPEXP_BASE wxWCharBuffer;
// ----------------------------------------------------------------------------
// WX_DEFINE_VARARG_FUNC* macros
// ----------------------------------------------------------------------------
// This macro is used to implement type-safe wrappers for variadic functions
// that accept strings as arguments. This makes it possible to pass char*,
// wchar_t* or even wxString (as opposed to having to use wxString::c_str())
// to e.g. wxPrintf().
//
// This is done by defining a set of N template function taking 1..N arguments
// (currently, N is set to 30 in this header). These functions are just thin
// wrappers around another variadic function (@a impl) and the only thing
// the wrapper does is that it normalizes the arguments passed in so that
// they are of the type expected by variadic functions taking string
// arguments, i.e., char* or wchar_t*, depending on the build:
// * char* in the current locale's charset in ANSI build
// * whchar_t* in the Unicode build
//
// Parameters:
// rettype Functions' return type.
// name Name of the function.
// impl Name of the variadic function that implements 'name'.
#define WX_DEFINE_VARARG_FUNC(rettype, name, impl) \
_WX_VARARG_ITER(_WX_VARARG_MAX_ARGS, \
_WX_VARARG_DEFINE_FUNC, \
rettype, name, impl)
// Like WX_DEFINE_VARARG_FUNC, but for variadic functions that don't return
// a value.
#define WX_DEFINE_VARARG_FUNC_VOID(name, impl) \
_WX_VARARG_ITER(_WX_VARARG_MAX_ARGS, \
_WX_VARARG_DEFINE_FUNC_VOID, \
void, name, impl)
// Like WX_DEFINE_VARARG_FUNC_VOID, but instead of wrapping an implementation
// function, does nothing in defined functions' bodies.
//
// Used to implement wxLogXXX functions if wxUSE_LOG=0.
#define WX_DEFINE_VARARG_FUNC_NOP(name) \
_WX_VARARG_ITER(_WX_VARARG_MAX_ARGS, \
_WX_VARARG_DEFINE_FUNC_NOP, \
void, name, dummy)
// ----------------------------------------------------------------------------
// implementation
// ----------------------------------------------------------------------------
// Converts an argument passed to wxPrint etc. into standard form expected,
// by wxXXX functions, e.g. all strings (wxString, char*, wchar_t*) are
// converted into wchar_t* or char* depending on the build.
template<typename T>
struct wxArgNormalizer
{
wxArgNormalizer(const T& value) : m_value(value) {}
// Returns the value in a form that can be safely passed to real vararg
// functions. In case of strings, this is char* in ANSI build and wchar_t*
// in Unicode build.
const T& get() const { return m_value; }
const T& m_value;
};
// special cases for converting strings:
// FIXME-UTF8: move this to wxchartype.h!
#if wxUSE_UNICODE
/* for now, all Unicode builds are wchar_t* based: */
#define wxUSE_UNICODE_WCHAR 1
#else
#define wxUSE_UNICODE_WCHAR 0
#endif
// FIXME-UTF8: include wx/wxchartype.h and use wxChar after headers split
// FIXME-UTF8: this will be char* in UTF-8 build and wchar_t* on Windows
#if wxUSE_UNICODE_WCHAR
typedef wchar_t wxArgNativeCharType;
#else
typedef char wxArgNativeCharType;
#endif
template<>
struct WXDLLIMPEXP_BASE wxArgNormalizer<const wxCStrData&>
{
wxArgNormalizer(const wxCStrData& value) : m_value(value) {}
const wxArgNativeCharType *get() const;
const wxCStrData& m_value;
};
template<>
struct wxArgNormalizer<wxCStrData> : public wxArgNormalizer<const wxCStrData&>
{
wxArgNormalizer(const wxCStrData& value)
: wxArgNormalizer<const wxCStrData&>(value) {}
};
template<>
struct WXDLLIMPEXP_BASE wxArgNormalizer<const wxString&>
{
wxArgNormalizer(const wxString& value) : m_value(value) {}
const wxArgNativeCharType *get() const;
const wxString& m_value;
};
template<>
struct wxArgNormalizer<wxString> : public wxArgNormalizer<const wxString&>
{
wxArgNormalizer(const wxString& value)
: wxArgNormalizer<const wxString&>(value) {}
};
#if wxUSE_UNICODE_WCHAR
template<>
struct WXDLLIMPEXP_BASE wxArgNormalizer<const char*>
{
wxArgNormalizer(const char *value);
~wxArgNormalizer();
const wchar_t *get() const;
wxWCharBuffer *m_value;
};
template<>
struct wxArgNormalizer<char*> : public wxArgNormalizer<const char*>
{
wxArgNormalizer(char *value)
: wxArgNormalizer<const char*>(value) {}
};
#elif wxUSE_WCHAR_T // !wxUSE_UNICODE_WCHAR && wxUSE_WCHAR_T
template<>
struct WXDLLIMPEXP_BASE wxArgNormalizer<const wchar_t*>
{
wxArgNormalizer(const wchar_t *value);
~wxArgNormalizer();
const char *get() const;
wxCharBuffer *m_value;
};
template<>
struct wxArgNormalizer<wchar_t*> : public wxArgNormalizer<const wchar_t*>
{
wxArgNormalizer(wchar_t *value)
: wxArgNormalizer<const wchar_t*>(value) {}
};
#endif // wxUSE_UNICODE_WCHAR / !wxUSE_UNICODE_WCHAR && wxUSE_WCHAR_T
// NB: The vararg emulation code is limited to 30 arguments at the moment.
// If you need more, you need to
// 1) increase the value of _WX_VARARG_MAX_ARGS
// 2) add _WX_VARARG_JOIN_* and _WX_VARARG_ITER_* up to the new
// _WX_VARARG_MAX_ARGS value to the lists below
#define _WX_VARARG_MAX_ARGS 30
#define _WX_VARARG_JOIN_1(m) m(1)
#define _WX_VARARG_JOIN_2(m) _WX_VARARG_JOIN_1(m), m(2)
#define _WX_VARARG_JOIN_3(m) _WX_VARARG_JOIN_2(m), m(3)
#define _WX_VARARG_JOIN_4(m) _WX_VARARG_JOIN_3(m), m(4)
#define _WX_VARARG_JOIN_5(m) _WX_VARARG_JOIN_4(m), m(5)
#define _WX_VARARG_JOIN_6(m) _WX_VARARG_JOIN_5(m), m(6)
#define _WX_VARARG_JOIN_7(m) _WX_VARARG_JOIN_6(m), m(7)
#define _WX_VARARG_JOIN_8(m) _WX_VARARG_JOIN_7(m), m(8)
#define _WX_VARARG_JOIN_9(m) _WX_VARARG_JOIN_8(m), m(9)
#define _WX_VARARG_JOIN_10(m) _WX_VARARG_JOIN_9(m), m(10)
#define _WX_VARARG_JOIN_11(m) _WX_VARARG_JOIN_10(m), m(11)
#define _WX_VARARG_JOIN_12(m) _WX_VARARG_JOIN_11(m), m(12)
#define _WX_VARARG_JOIN_13(m) _WX_VARARG_JOIN_12(m), m(13)
#define _WX_VARARG_JOIN_14(m) _WX_VARARG_JOIN_13(m), m(14)
#define _WX_VARARG_JOIN_15(m) _WX_VARARG_JOIN_14(m), m(15)
#define _WX_VARARG_JOIN_16(m) _WX_VARARG_JOIN_15(m), m(16)
#define _WX_VARARG_JOIN_17(m) _WX_VARARG_JOIN_16(m), m(17)
#define _WX_VARARG_JOIN_18(m) _WX_VARARG_JOIN_17(m), m(18)
#define _WX_VARARG_JOIN_19(m) _WX_VARARG_JOIN_18(m), m(19)
#define _WX_VARARG_JOIN_20(m) _WX_VARARG_JOIN_19(m), m(20)
#define _WX_VARARG_JOIN_21(m) _WX_VARARG_JOIN_20(m), m(21)
#define _WX_VARARG_JOIN_22(m) _WX_VARARG_JOIN_21(m), m(22)
#define _WX_VARARG_JOIN_23(m) _WX_VARARG_JOIN_22(m), m(23)
#define _WX_VARARG_JOIN_24(m) _WX_VARARG_JOIN_23(m), m(24)
#define _WX_VARARG_JOIN_25(m) _WX_VARARG_JOIN_24(m), m(25)
#define _WX_VARARG_JOIN_26(m) _WX_VARARG_JOIN_25(m), m(26)
#define _WX_VARARG_JOIN_27(m) _WX_VARARG_JOIN_26(m), m(27)
#define _WX_VARARG_JOIN_28(m) _WX_VARARG_JOIN_27(m), m(28)
#define _WX_VARARG_JOIN_29(m) _WX_VARARG_JOIN_28(m), m(29)
#define _WX_VARARG_JOIN_30(m) _WX_VARARG_JOIN_29(m), m(30)
#define _WX_VARARG_ITER_1(m,a,b,c) m(1,a,b,c)
#define _WX_VARARG_ITER_2(m,a,b,c) _WX_VARARG_ITER_1(m,a,b,c) m(2,a,b,c)
#define _WX_VARARG_ITER_3(m,a,b,c) _WX_VARARG_ITER_2(m,a,b,c) m(3,a,b,c)
#define _WX_VARARG_ITER_4(m,a,b,c) _WX_VARARG_ITER_3(m,a,b,c) m(4,a,b,c)
#define _WX_VARARG_ITER_5(m,a,b,c) _WX_VARARG_ITER_4(m,a,b,c) m(5,a,b,c)
#define _WX_VARARG_ITER_6(m,a,b,c) _WX_VARARG_ITER_5(m,a,b,c) m(6,a,b,c)
#define _WX_VARARG_ITER_7(m,a,b,c) _WX_VARARG_ITER_6(m,a,b,c) m(7,a,b,c)
#define _WX_VARARG_ITER_8(m,a,b,c) _WX_VARARG_ITER_7(m,a,b,c) m(8,a,b,c)
#define _WX_VARARG_ITER_9(m,a,b,c) _WX_VARARG_ITER_8(m,a,b,c) m(9,a,b,c)
#define _WX_VARARG_ITER_10(m,a,b,c) _WX_VARARG_ITER_9(m,a,b,c) m(10,a,b,c)
#define _WX_VARARG_ITER_11(m,a,b,c) _WX_VARARG_ITER_10(m,a,b,c) m(11,a,b,c)
#define _WX_VARARG_ITER_12(m,a,b,c) _WX_VARARG_ITER_11(m,a,b,c) m(12,a,b,c)
#define _WX_VARARG_ITER_13(m,a,b,c) _WX_VARARG_ITER_12(m,a,b,c) m(13,a,b,c)
#define _WX_VARARG_ITER_14(m,a,b,c) _WX_VARARG_ITER_13(m,a,b,c) m(14,a,b,c)
#define _WX_VARARG_ITER_15(m,a,b,c) _WX_VARARG_ITER_14(m,a,b,c) m(15,a,b,c)
#define _WX_VARARG_ITER_16(m,a,b,c) _WX_VARARG_ITER_15(m,a,b,c) m(16,a,b,c)
#define _WX_VARARG_ITER_17(m,a,b,c) _WX_VARARG_ITER_16(m,a,b,c) m(17,a,b,c)
#define _WX_VARARG_ITER_18(m,a,b,c) _WX_VARARG_ITER_17(m,a,b,c) m(18,a,b,c)
#define _WX_VARARG_ITER_19(m,a,b,c) _WX_VARARG_ITER_18(m,a,b,c) m(19,a,b,c)
#define _WX_VARARG_ITER_20(m,a,b,c) _WX_VARARG_ITER_19(m,a,b,c) m(20,a,b,c)
#define _WX_VARARG_ITER_21(m,a,b,c) _WX_VARARG_ITER_20(m,a,b,c) m(21,a,b,c)
#define _WX_VARARG_ITER_22(m,a,b,c) _WX_VARARG_ITER_21(m,a,b,c) m(22,a,b,c)
#define _WX_VARARG_ITER_23(m,a,b,c) _WX_VARARG_ITER_22(m,a,b,c) m(23,a,b,c)
#define _WX_VARARG_ITER_24(m,a,b,c) _WX_VARARG_ITER_23(m,a,b,c) m(24,a,b,c)
#define _WX_VARARG_ITER_25(m,a,b,c) _WX_VARARG_ITER_24(m,a,b,c) m(25,a,b,c)
#define _WX_VARARG_ITER_26(m,a,b,c) _WX_VARARG_ITER_25(m,a,b,c) m(26,a,b,c)
#define _WX_VARARG_ITER_27(m,a,b,c) _WX_VARARG_ITER_26(m,a,b,c) m(27,a,b,c)
#define _WX_VARARG_ITER_28(m,a,b,c) _WX_VARARG_ITER_27(m,a,b,c) m(28,a,b,c)
#define _WX_VARARG_ITER_29(m,a,b,c) _WX_VARARG_ITER_28(m,a,b,c) m(29,a,b,c)
#define _WX_VARARG_ITER_30(m,a,b,c) _WX_VARARG_ITER_29(m,a,b,c) m(30,a,b,c)
// This macro calls another macro 'm' passed as second argument 'N' times,
// with its only argument set to 1..N, and concatenates the results using
// comma as separator.
//
// An example:
// #define foo(i) x##i
// // this expands to "x1,x2,x3,x4"
// _WX_VARARG_JOIN(4, foo)
//
//
// N must not be greater than _WX_VARARG_MAX_ARGS (=30).
#define _WX_VARARG_JOIN(N, m) _WX_VARARG_JOIN_IMPL(N, m)
#define _WX_VARARG_JOIN_IMPL(N, m) _WX_VARARG_JOIN_##N(m)
// This macro calls another macro 'm' passed as second argument 'N' times, with
// its first argument set to 1..N and the remaining arguments set to 'a', 'b'
// and 'c'. The results are separated with whitespace in the expansion.
//
// An example:
// // this macro expands to:
// // foo(1,a,b,c)
// // foo(2,a,b,c)
// // foo(3,a,b,c)
// _WX_VARARG_ITER(3, foo, a, b, c)
//
// N must not be greater than _WX_VARARG_MAX_ARGS (=30).
#define _WX_VARARG_ITER(N, m,a,b,c) _WX_VARARG_ITER_IMPL(N, m, a, b, c)
#define _WX_VARARG_ITER_IMPL(N, m,a,b,c) _WX_VARARG_ITER_##N(m, a, b, c)
// Generates code snippet for i-th argument in vararg function's prototype.
#define _WX_VARARG_ARG(i) T##i a##i
// Like _WX_VARARG_ARG_UNUSED, but outputs argument's type with WXUNUSED.
#define _WX_VARARG_ARG_UNUSED(i) T##i WXUNUSED(a##i)
// Generates code snippet for i-th type in vararg function's template<...>.
#define _WX_VARARG_TEMPL(i) typename T##i
// Generates code snippet for passing i-th argument of vararg function
// wrapper to its implementation, normalizing it in the process
#define _WX_VARARG_PASS(i) wxArgNormalizer<T##i>(a##i).get()
// Macro to be used with _WX_VARARG_ITER in the implementation of
// WX_DEFINE_VARARG_FUNC (see its documentation for the meaning of arguments)
#define _WX_VARARG_DEFINE_FUNC(N, rettype, name, impl) \
template<_WX_VARARG_JOIN(N, _WX_VARARG_TEMPL)> \
rettype name(_WX_VARARG_JOIN(N, _WX_VARARG_ARG)) \
{ \
return impl(_WX_VARARG_JOIN(N, _WX_VARARG_PASS)); \
}
// Macro to be used with _WX_VARARG_ITER in the implementation of
// WX_DEFINE_VARARG_FUNC_VOID (see its documentation for the meaning of
// arguments; rettype is ignored and is used only to satisfy _WX_VARARG_ITER's
// requirements).
#define _WX_VARARG_DEFINE_FUNC_VOID(N, rettype, name, impl) \
template<_WX_VARARG_JOIN(N, _WX_VARARG_TEMPL)> \
void name(_WX_VARARG_JOIN(N, _WX_VARARG_ARG)) \
{ \
impl(_WX_VARARG_JOIN(N, _WX_VARARG_PASS)); \
}
// Macro to be used with _WX_VARARG_ITER in the implementation of
// WX_DEFINE_VARARG_FUNC_NOP, i.e. empty stub for a disabled vararg function.
// The rettype and impl arguments are ignored.
#define _WX_VARARG_DEFINE_FUNC_NOP(N, rettype, name, impl) \
template<_WX_VARARG_JOIN(N, _WX_VARARG_TEMPL)> \
void name(_WX_VARARG_JOIN(N, _WX_VARARG_ARG_UNUSED)) {}
#endif // _WX_STRVARARG_H_

View File

@@ -116,9 +116,11 @@ protected:
static void Normalize(wxChar* uri, bool bIgnoreLeads = false);
static void UpTree(const wxChar* uristart, const wxChar*& uri);
static void UpTree(wxString::const_iterator uristart,
wxString::const_iterator& uri);
static wxChar TranslateEscape(const wxChar* s);
static void Escape (wxString& s, const wxChar& c);
static wxUniChar TranslateEscape(const wxString::const_iterator& s);
static void Escape(wxString& s, const wxChar& c);
static bool IsEscape(const wxChar*& uri);
static wxChar CharToHex(const wxChar& c);

View File

@@ -18,6 +18,13 @@
#include "wx/platform.h"
#include "wx/dlimpexp.h"
#ifdef __cplusplus
#include "wx/strvararg.h"
#else
/* make the file compile without doing anything in C code: */
#define WX_DEFINE_VARARG_FUNC(rettype, name, impl)
#endif
#include <stdio.h> /* we use FILE below */
#if defined(HAVE_STRTOK_R) && defined(__DARWIN__) && defined(_MSL_USING_MW_C_HEADERS) && _MSL_USING_MW_C_HEADERS
@@ -115,6 +122,10 @@
#ifdef HAVE_WIDEC_H
#include <widec.h>
#endif
#if !defined(__GNUC__) || defined(__DARWIN__)
#define wxWINT_T_IS_TYPEDEF
#endif
#endif /* wxUSE_WCHAR_T */
/* ---------------------------------------------------------------------------- */
@@ -212,13 +223,16 @@
typedef wchar_t wxSChar;
typedef wchar_t wxUChar;
#else /* __WCHAR_TYPE__ and gcc < 2.96 */
/* VS: wxWidgets used to define wxChar as __WCHAR_TYPE__ here. However, */
/* this doesn't work with new GCC 3.x compilers because wchar_t is */
/* C++'s builtin type in the new standard. OTOH, old compilers (GCC */
/* 2.x) won't accept new definition of wx{S,U}Char, therefore we */
/* have to define wxChar conditionally depending on detected */
/* compiler & compiler version. */
/* VS: wxWidgets used to define wxChar as __WCHAR_TYPE__ here. */
/* However, this doesn't work with new GCC 3.x compilers because */
/* wchar_t is C++'s builtin type in the new standard. OTOH, old */
/* compilers (GCC 2.x) won't accept new definition of */
/* wx{S,U}CharType, so we have to define wxChar */
/* conditionally depending on detected compiler & compiler */
/* version. */
/* with old definition of wxChar. */
#define wchar_t __WCHAR_TYPE__
typedef __WCHAR_TYPE__ wxChar;
typedef __WCHAR_TYPE__ wxSChar;
typedef __WCHAR_TYPE__ wxUChar;
@@ -270,8 +284,8 @@
define wxFoo() function for each standard foo() function whose signature
(exceptionally including the return type) includes any mention of char:
wxFoo() is going to be a Unicode-friendly version of foo(), i.e. will have
the same signature but with char replaced by wxChar which allows us to use
it in Unicode build as well
the same signature but with char replaced by wxChar which allows us to
use it in Unicode build as well
*/
#ifdef wxHAVE_TCHAR_SUPPORT
@@ -300,8 +314,8 @@
There is a bug in VC6 C RTL: toxxx() functions dosn't do anything with
signed chars < 0, so "fix" it here.
*/
#define wxTolower(c) _totlower((wxUChar)(c))
#define wxToupper(c) _totupper((wxUChar)(c))
#define wxTolower(c) _totlower((wxUChar)(wxChar)(c))
#define wxToupper(c) _totupper((wxUChar)(wxChar)(c))
/* locale.h functons */
#define wxSetlocale _tsetlocale
@@ -349,7 +363,7 @@
#endif
#define wxFputc _fputtc
#define wxFputchar _fputtchar
#define wxFprintf _ftprintf
WX_DEFINE_VARARG_FUNC(int, wxFprintf, _ftprintf)
#define wxFputs _fputts
#define wxFreopen _tfreopen
#define wxFscanf _ftscanf
@@ -357,7 +371,7 @@
#define wxGetchar _gettchar
#define wxGets _getts
#define wxPerror _tperror
#define wxPrintf _tprintf
WX_DEFINE_VARARG_FUNC(int, wxPrintf, _tprintf)
#define wxPutc(c,f) _puttc(WXWCHAR_T_CAST(c),f)
#define wxPutchar _puttchar
#define wxPuts _putts
@@ -365,13 +379,14 @@
#if defined(__DMC__)
#if wxUSE_UNICODE
/* Digital Mars adds count to _stprintf (C99) so prototype conversion see wxchar.cpp */
int wxSprintf (wchar_t * __RESTRICT s, const wchar_t * __RESTRICT format, ... ) ;
int wxDoSprintf (wchar_t * __RESTRICT s, const wchar_t * __RESTRICT format, ... ) ;
WX_DEFINE_VARARG_FUNC(int, wxSprintf, wxDoSprintf)
#else
/* and there is a bug in D Mars tchar.h prior to 8.39.4n, so define as sprintf */
#define wxSprintf sprintf
WX_DEFINE_VARARG_FUNC(int, wxSprintf, sprintf)
#endif
#else
#define wxSprintf _stprintf
WX_DEFINE_VARARG_FUNC(int, wxSprintf, _stprintf)
#endif
#define wxSscanf _stscanf
@@ -748,17 +763,17 @@
#define wxFputc fputc
#define wxFputs fputs
#define wxFputchar fputchar
#define wxFprintf fprintf
WX_DEFINE_VARARG_FUNC(int, wxFprintf, fprintf)
#define wxFscanf fscanf
#define wxGetc getc
#define wxGetchar getchar
#define wxGets gets
#define wxPrintf printf
WX_DEFINE_VARARG_FUNC(int, wxPrintf, printf)
#define wxPutc putc
#define wxPutchar putchar
#define wxPuts puts
#define wxScanf scanf
#define wxSprintf sprintf
WX_DEFINE_VARARG_FUNC(int, wxSprintf, sprintf)
#define wxSscanf sscanf
#define wxUngetc ungetc
#define wxVfprintf vfprintf
@@ -943,7 +958,7 @@ WXDLLIMPEXP_BASE bool wxOKlibc(); /* for internal use */
#if defined(__VISUALC__) || \
(defined(__BORLANDC__) && __BORLANDC__ >= 0x540)
#define wxVsnprintf_ _vsntprintf
#define wxSnprintf_ _sntprintf
WX_DEFINE_VARARG_FUNC(int, wxSnprintf_, _sntprintf)
#endif
#endif
@@ -956,7 +971,7 @@ WXDLLIMPEXP_BASE bool wxOKlibc(); /* for internal use */
#define wxVsnprintf_ vswprintf
#elif defined(__WATCOMC__)
#define wxVsnprintf_ _vsnwprintf
#define wxSnprintf_ _snwprintf
WX_DEFINE_VARARG_FUNC(int, wxSnprintf_, _snwprintf)
#endif
#else /* ASCII */
/*
@@ -966,7 +981,7 @@ WXDLLIMPEXP_BASE bool wxOKlibc(); /* for internal use */
#if defined(HAVE_SNPRINTF) \
|| defined(__MWERKS__) || defined(__WATCOMC__)
#ifndef HAVE_BROKEN_SNPRINTF_DECL
#define wxSnprintf_ snprintf
WX_DEFINE_VARARG_FUNC(int, wxSnprintf_, snprintf)
#endif
#endif
#if defined(HAVE_VSNPRINTF) \
@@ -984,12 +999,15 @@ WXDLLIMPEXP_BASE bool wxOKlibc(); /* for internal use */
#ifndef wxSnprintf_
/* no snprintf(), cook our own */
WXDLLIMPEXP_BASE int
wxSnprintf_(wxChar *buf, size_t len, const wxChar *format, ...) ATTRIBUTE_PRINTF_3;
wxDoSnprintf_(wxChar *buf, size_t len,
const wxChar *format, ...) ATTRIBUTE_PRINTF_3;
WX_DEFINE_VARARG_FUNC(int, wxSnprintf_, wxDoSnprintf_)
#endif
#ifndef wxVsnprintf_
/* no (suitable) vsnprintf(), cook our own */
WXDLLIMPEXP_BASE int
wxVsnprintf_(wxChar *buf, size_t len, const wxChar *format, va_list argptr);
wxVsnprintf_(wxChar *buf, size_t len,
const wxChar *format, va_list argptr);
#define wxUSE_WXVSNPRINTF 1
#else
@@ -1024,13 +1042,25 @@ WXDLLIMPEXP_BASE bool wxOKlibc(); /* for internal use */
either because we don't have them at all or because they don't have the
semantics we need
*/
int wxScanf( const wxChar *format, ... ) ATTRIBUTE_PRINTF_1;
int wxSscanf( const wxChar *str, const wxChar *format, ... ) ATTRIBUTE_PRINTF_2;
int wxFscanf( FILE *stream, const wxChar *format, ... ) ATTRIBUTE_PRINTF_2;
WX_DEFINE_VARARG_FUNC(int, wxScanf, wxDoScanf)
int wxDoScanf( const wxChar *format, ... ) ATTRIBUTE_PRINTF_1;
WX_DEFINE_VARARG_FUNC(int, wxSscanf, wxDoSscanf)
int wxDoSscanf( const wxChar *str, const wxChar *format, ... ) ATTRIBUTE_PRINTF_2;
WX_DEFINE_VARARG_FUNC(int, wxFscanf, wxDoFscanf)
int wxDoFscanf( FILE *stream, const wxChar *format, ... ) ATTRIBUTE_PRINTF_2;
WX_DEFINE_VARARG_FUNC(int, wxPrintf, wxDoPrintf)
int wxDoPrintf( const wxChar *format, ... ) ATTRIBUTE_PRINTF_1;
WX_DEFINE_VARARG_FUNC(int, wxSprintf, wxDoSprintf)
int wxDoSprintf( wxChar *str, const wxChar *format, ... ) ATTRIBUTE_PRINTF_2;
WX_DEFINE_VARARG_FUNC(int, wxFprintf, wxDoFprintf)
int wxDoFprintf( FILE *stream, const wxChar *format, ... ) ATTRIBUTE_PRINTF_2;
int wxVsscanf( const wxChar *str, const wxChar *format, va_list ap );
int wxPrintf( const wxChar *format, ... ) ATTRIBUTE_PRINTF_1;
int wxSprintf( wxChar *str, const wxChar *format, ... ) ATTRIBUTE_PRINTF_2;
int wxFprintf( FILE *stream, const wxChar *format, ... ) ATTRIBUTE_PRINTF_2;
int wxVfprintf( FILE *stream, const wxChar *format, va_list ap );
int wxVprintf( const wxChar *format, va_list ap );
int wxVsprintf( wxChar *str, const wxChar *format, va_list ap );
@@ -1043,7 +1073,8 @@ WXDLLIMPEXP_BASE bool wxOKlibc(); /* for internal use */
anything as our own wxVsnprintf_() already behaves as needed.
*/
#if defined(wxNEED_PRINTF_CONVERSION) && defined(wxVsnprintf_)
int wxSnprintf( wxChar *str, size_t size, const wxChar *format, ... ) ATTRIBUTE_PRINTF_3;
WX_DEFINE_VARARG_FUNC(int, wxSnprintf, wxDoSnprintf)
int wxDoSnprintf( wxChar *str, size_t size, const wxChar *format, ... ) ATTRIBUTE_PRINTF_3;
int wxVsnprintf( wxChar *str, size_t size, const wxChar *format, va_list ap );
#else
#define wxSnprintf wxSnprintf_
@@ -1078,7 +1109,7 @@ WXDLLIMPEXP_BASE bool wxOKlibc(); /* for internal use */
/* the file parsing -- this may be true for 5.0 as well, update #ifdef then */
#if defined(__VISUALC__) && (__VISUALC__ >= 1200) && !wxUSE_UNICODE
#undef wxIsspace
#define wxIsspace(c) ((((unsigned)c) < 128) && isspace(c))
#define wxIsspace(c) ((((unsigned)(wxChar)c) < 128) && isspace(c))
#endif /* VC++ */
/*
@@ -1233,7 +1264,8 @@ WXDLLIMPEXP_BASE int wxSystem(const wxChar *psz);
/*silent gabby compilers*/
struct tm;
WXDLLIMPEXP_BASE size_t wxStrftime(wxChar *s, size_t max,
const wxChar *fmt, const struct tm *tm);
const wxChar *fmt,
const struct tm *tm);
#endif /* wxNEED_WX_TIME_H */
#ifndef wxCtime
@@ -1348,6 +1380,352 @@ WXDLLIMPEXP_BASE void *calloc( size_t num, size_t size );
#endif /*__cplusplus*/
/*
FIXME-UTF8: split this header into more:
wxchartype.h for wxChar definition (only this one will have to
remain C header, the rest can be C++)
wxcrt.h for CRT wrappers
wxchar.h for wxChar+wxCharRef classes
*/
#ifdef __cplusplus
class WXDLLIMPEXP_BASE wxString;
class WXDLLIMPEXP_BASE wxUniCharRef;
// This class represents single Unicode character. It can be converted to
// and from char or wchar_t and implements commonly used character operations.
class WXDLLIMPEXP_BASE wxUniChar
{
public:
// NB: this is not wchar_t on purpose, it needs to represent the entire
// Unicode code points range and wchar_t may be too small for that
// (e.g. on Win32 where wchar_t* is encoded in UTF-16)
typedef unsigned int unicode_type;
wxUniChar() : m_value(0) {}
// Create the character from 8bit character value encoded in the current
// locale's charset.
wxUniChar(char c) { m_value = From8bit(c); }
// Create the character from a wchar_t character value.
wxUniChar(wchar_t c) { m_value = c; }
#ifndef wxWINT_T_IS_TYPEDEF
// Create the character from a wint_t character value.
wxUniChar(wint_t c) { m_value = c; }
#endif
wxUniChar(int c) { m_value = c; }
wxUniChar(const wxUniCharRef& c);
// Returns Unicode code point value of the character
unicode_type GetValue() const { return m_value; }
// Casts to char and wchar_t types:
operator char() const { return To8bit(m_value); }
operator wchar_t() const { return m_value; }
#ifndef wxWINT_T_IS_TYPEDEF
operator wint_t() const { return m_value; }
#endif
operator int() const { return m_value; }
// We need this operator for the "*p" part of expressions like "for (
// const_iterator p = begin() + nStart; *p; ++p )". In this case,
// compilation would fail without it because the conversion to bool would
// be ambiguous (there are all these int types conversions...). (And adding
// operator unspecified_bool_type() would only makes the ambiguity worse.)
operator bool() const { return m_value != 0; }
bool operator!() const { return !((bool)*this); }
#if (defined(__VISUALC__) && __VISUALC__ < 1400) || \
defined(__DIGITALMARS__) || defined(__BORLANDC__)
// We need this for VC++ < 8 or DigitalMars and expressions like
// "str[0] && *p":
bool operator&&(bool v) const { return (bool)*this && v; }
#endif
// Assignment operators:
wxUniChar& operator=(const wxUniChar& c) { m_value = c.m_value; return *this; }
wxUniChar& operator=(char c) { m_value = From8bit(c); return *this; }
wxUniChar& operator=(wchar_t c) { m_value = c; return *this; }
#ifndef wxWINT_T_IS_TYPEDEF
wxUniChar& operator=(wint_t c) { m_value = c; return *this; }
#endif
// Comparision operators:
bool operator==(const wxUniChar& c) const { return m_value == c.m_value; }
bool operator==(char c) const { return m_value == From8bit(c); }
bool operator==(wchar_t c) const { return m_value == (unicode_type)c; }
#ifndef wxWINT_T_IS_TYPEDEF
bool operator==(wint_t c) const { return m_value == (unicode_type)c; }
#endif
bool operator!=(const wxUniChar& c) const { return m_value != c.m_value; }
bool operator!=(char c) const { return m_value != From8bit(c); }
bool operator!=(wchar_t c) const { return m_value != (unicode_type)c; }
#ifndef wxWINT_T_IS_TYPEDEF
bool operator!=(wint_t c) const { return m_value != (unicode_type)c; }
#endif
bool operator>(const wxUniChar& c) const { return m_value > c.m_value; }
bool operator>(char c) const { return m_value > (unicode_type)c; }
bool operator>(wchar_t c) const { return m_value > (unicode_type)c; }
#ifndef wxWINT_T_IS_TYPEDEF
bool operator>(wint_t c) const { return m_value > (unicode_type)c; }
#endif
bool operator<(const wxUniChar& c) const { return m_value < c.m_value; }
bool operator<(char c) const { return m_value < From8bit(c); }
bool operator<(wchar_t c) const { return m_value < (unicode_type)c; }
#ifndef wxWINT_T_IS_TYPEDEF
bool operator<(wint_t c) const { return m_value < (unicode_type)c; }
#endif
bool operator>=(const wxUniChar& c) const { return m_value >= c.m_value; }
bool operator>=(char c) const { return m_value >= From8bit(c); }
bool operator>=(wchar_t c) const { return m_value >= (unicode_type)c; }
#ifndef wxWINT_T_IS_TYPEDEF
bool operator>=(wint_t c) const { return m_value >= (unicode_type)c; }
#endif
bool operator<=(const wxUniChar& c) const { return m_value <= c.m_value; }
bool operator<=(char c) const { return m_value <= From8bit(c); }
bool operator<=(wchar_t c) const { return m_value <= (unicode_type)c; }
#ifndef wxWINT_T_IS_TYPEDEF
bool operator<=(wint_t c) const { return m_value <= (unicode_type)c; }
#endif
int operator-(const wxUniChar& c) const { return m_value - c.m_value; }
int operator-(char c) const { return m_value - From8bit(c); }
int operator-(wchar_t c) const { return m_value - (unicode_type)c; }
#ifndef wxWINT_T_IS_TYPEDEF
int operator-(wint_t c) const { return m_value - (unicode_type)c; }
#endif
private:
static unicode_type From8bit(char c);
static char To8bit(unicode_type c);
private:
unicode_type m_value;
};
// Writeable reference to a character in wxString.
//
// This class can be used in the same way wxChar is used, except that changing
// its value updates the underlying string object.
class WXDLLIMPEXP_BASE wxUniCharRef
{
private:
// create the reference
// FIXME: the interface will need changes for UTF-8 build
wxUniCharRef(wxChar *pos) : m_pos(pos) {}
public:
// NB: we have to make this public, because we don't have wxString
// declaration available here and so can't declare wxString::iterator
// as friend; so at least don't use a ctor but a static function
// that must be used explicitly (this is more than using 'explicit'
// keyword on ctor!):
//
// FIXME: the interface will need changes for UTF-8 build
static wxUniCharRef CreateForString(wxChar *pos)
{ return wxUniCharRef(pos); }
wxUniChar::unicode_type GetValue() const { return UniChar().GetValue(); }
// Assignment operators:
wxUniCharRef& operator=(const wxUniCharRef& c)
{
*m_pos = *c.m_pos;
return *this;
};
wxUniCharRef& operator=(const wxUniChar& c)
{
*m_pos = c;
return *this;
};
wxUniCharRef& operator=(char c) { return *this = wxUniChar(c); }
wxUniCharRef& operator=(wchar_t c) { return *this = wxUniChar(c); }
// Casts to wxUniChar type:
operator char() const { return UniChar(); }
operator wchar_t() const { return UniChar(); }
#ifndef wxWINT_T_IS_TYPEDEF
operator wint_t() const { return UniChar(); }
#endif
operator int() const { return UniChar(); }
// see wxUniChar::operator bool etc. for explanation
operator bool() const { return (bool)UniChar(); }
bool operator!() const { return !UniChar(); }
#if (defined(__VISUALC__) && __VISUALC__ < 1400) || \
defined(__DIGITALMARS__) || defined(__BORLANDC__)
bool operator&&(bool v) const { return UniChar() && v; }
#endif
// Comparision operators:
bool operator==(const wxUniCharRef& c) const { return m_pos == c.m_pos; }
bool operator==(const wxUniChar& c) const { return UniChar() == c; }
bool operator==(char c) const { return UniChar() == c; }
bool operator==(wchar_t c) const { return UniChar() == c; }
#ifndef wxWINT_T_IS_TYPEDEF
bool operator==(wint_t c) const { return UniChar() == c; }
#endif
bool operator!=(const wxUniCharRef& c) const { return m_pos != c.m_pos; }
bool operator!=(const wxUniChar& c) const { return UniChar() != c; }
bool operator!=(char c) const { return UniChar() != c; }
bool operator!=(wchar_t c) const { return UniChar() != c; }
#ifndef wxWINT_T_IS_TYPEDEF
bool operator!=(wint_t c) const { return UniChar() != c; }
#endif
bool operator>(const wxUniCharRef& c) const { return UniChar() > c.UniChar(); }
bool operator>(const wxUniChar& c) const { return UniChar() > c; }
bool operator>(char c) const { return UniChar() > c; }
bool operator>(wchar_t c) const { return UniChar() > c; }
#ifndef wxWINT_T_IS_TYPEDEF
bool operator>(wint_t c) const { return UniChar() > c; }
#endif
bool operator<(const wxUniCharRef& c) const { return UniChar() < c.UniChar(); }
bool operator<(const wxUniChar& c) const { return UniChar() < c; }
bool operator<(char c) const { return UniChar() < c; }
bool operator<(wchar_t c) const { return UniChar() < c; }
#ifndef wxWINT_T_IS_TYPEDEF
bool operator<(wint_t c) const { return UniChar() < c; }
#endif
bool operator>=(const wxUniCharRef& c) const { return UniChar() >= c.UniChar(); }
bool operator>=(const wxUniChar& c) const { return UniChar() >= c; }
bool operator>=(char c) const { return UniChar() >= c; }
bool operator>=(wchar_t c) const { return UniChar() >= c; }
#ifndef wxWINT_T_IS_TYPEDEF
bool operator>=(wint_t c) const { return UniChar() >= c; }
#endif
bool operator<=(const wxUniCharRef& c) const { return UniChar() <= c.UniChar(); }
bool operator<=(const wxUniChar& c) const { return UniChar() <= c; }
bool operator<=(char c) const { return UniChar() <= c; }
bool operator<=(wchar_t c) const { return UniChar() <= c; }
#ifndef wxWINT_T_IS_TYPEDEF
bool operator<=(wint_t c) const { return UniChar() <= c; }
#endif
int operator-(const wxUniCharRef& c) const { return UniChar() - c.UniChar(); }
int operator-(const wxUniChar& c) const { return UniChar() - c; }
int operator-(char c) const { return UniChar() - c; }
int operator-(wchar_t c) const { return UniChar() - c; }
#ifndef wxWINT_T_IS_TYPEDEF
int operator-(wint_t c) const { return UniChar() - c; }
#endif
private:
wxUniChar UniChar() const { return *m_pos; }
friend class WXDLLIMPEXP_BASE wxUniChar;
private:
// pointer to the character in string
wxChar *m_pos;
};
inline wxUniChar::wxUniChar(const wxUniCharRef& c)
{
m_value = c.UniChar().m_value;
}
// Comparision operators for the case when wxUniChar(Ref) is the second operand:
inline bool operator==(char c1, const wxUniChar& c2) { return c2 == c1; }
inline bool operator==(wchar_t c1, const wxUniChar& c2) { return c2 == c1; }
#ifndef wxWINT_T_IS_TYPEDEF
inline bool operator==(wint_t c1, const wxUniChar& c2) { return c2 == c1; }
#endif
inline bool operator!=(char c1, const wxUniChar& c2) { return c2 != c1; }
inline bool operator!=(wchar_t c1, const wxUniChar& c2) { return c2 != c1; }
#ifndef wxWINT_T_IS_TYPEDEF
inline bool operator!=(wint_t c1, const wxUniChar& c2) { return c2 != c1; }
#endif
inline bool operator>(char c1, const wxUniChar& c2) { return c2 < c1; }
inline bool operator>(wchar_t c1, const wxUniChar& c2) { return c2 < c1; }
#ifndef wxWINT_T_IS_TYPEDEF
inline bool operator>(wint_t c1, const wxUniChar& c2) { return c2 < c1; }
#endif
inline bool operator<(char c1, const wxUniChar& c2) { return c2 > c1; }
inline bool operator<(wchar_t c1, const wxUniChar& c2) { return c2 > c1; }
#ifndef wxWINT_T_IS_TYPEDEF
inline bool operator<(wint_t c1, const wxUniChar& c2) { return c2 > c1; }
#endif
inline bool operator>=(char c1, const wxUniChar& c2) { return c2 <= c1; }
inline bool operator>=(wchar_t c1, const wxUniChar& c2) { return c2 <= c1; }
#ifndef wxWINT_T_IS_TYPEDEF
inline bool operator>=(wint_t c1, const wxUniChar& c2) { return c2 <= c1; }
#endif
inline bool operator<=(char c1, const wxUniChar& c2) { return c2 >= c1; }
inline bool operator<=(wchar_t c1, const wxUniChar& c2) { return c2 >= c1; }
#ifndef wxWINT_T_IS_TYPEDEF
inline bool operator<=(wint_t c1, const wxUniChar& c2) { return c2 >= c1; }
#endif
inline bool operator==(char c1, const wxUniCharRef& c2) { return c2 == c1; }
inline bool operator==(wchar_t c1, const wxUniCharRef& c2) { return c2 == c1; }
#ifndef wxWINT_T_IS_TYPEDEF
inline bool operator==(wint_t c1, const wxUniCharRef& c2) { return c2 == c1; }
#endif
inline bool operator==(const wxUniChar& c1, const wxUniCharRef& c2) { return c2 == c1; }
inline bool operator!=(char c1, const wxUniCharRef& c2) { return c2 != c1; }
inline bool operator!=(wchar_t c1, const wxUniCharRef& c2) { return c2 != c1; }
#ifndef wxWINT_T_IS_TYPEDEF
inline bool operator!=(wint_t c1, const wxUniCharRef& c2) { return c2 != c1; }
#endif
inline bool operator!=(const wxUniChar& c1, const wxUniCharRef& c2) { return c2 != c1; }
inline bool operator>(char c1, const wxUniCharRef& c2) { return c2 < c1; }
inline bool operator>(wchar_t c1, const wxUniCharRef& c2) { return c2 < c1; }
#ifndef wxWINT_T_IS_TYPEDEF
inline bool operator>(wint_t c1, const wxUniCharRef& c2) { return c2 < c1; }
#endif
inline bool operator>(const wxUniChar& c1, const wxUniCharRef& c2) { return c2 < c1; }
inline bool operator<(char c1, const wxUniCharRef& c2) { return c2 > c1; }
inline bool operator<(wchar_t c1, const wxUniCharRef& c2) { return c2 > c1; }
#ifndef wxWINT_T_IS_TYPEDEF
inline bool operator<(wint_t c1, const wxUniCharRef& c2) { return c2 > c1; }
#endif
inline bool operator<(const wxUniChar& c1, const wxUniCharRef& c2) { return c2 > c1; }
inline bool operator>=(char c1, const wxUniCharRef& c2) { return c2 <= c1; }
inline bool operator>=(wchar_t c1, const wxUniCharRef& c2) { return c2 <= c1; }
#ifndef wxWINT_T_IS_TYPEDEF
inline bool operator>=(wint_t c1, const wxUniCharRef& c2) { return c2 <= c1; }
#endif
inline bool operator>=(const wxUniChar& c1, const wxUniCharRef& c2) { return c2 <= c1; }
inline bool operator<=(char c1, const wxUniCharRef& c2) { return c2 >= c1; }
inline bool operator<=(wchar_t c1, const wxUniCharRef& c2) { return c2 >= c1; }
#ifndef wxWINT_T_IS_TYPEDEF
inline bool operator<=(wint_t c1, const wxUniCharRef& c2) { return c2 >= c1; }
#endif
inline bool operator<=(const wxUniChar& c1, const wxUniCharRef& c2) { return c2 >= c1; }
inline int operator-(char c1, const wxUniCharRef& c2) { return -(c2 - c1); }
inline int operator-(wchar_t c1, const wxUniCharRef& c2) { return -(c2 - c1); }
#ifndef wxWINT_T_IS_TYPEDEF
inline int operator-(wint_t c1, const wxUniCharRef& c2) { return -(c2 - c1); }
#endif
inline int operator-(const wxUniChar& c1, const wxUniCharRef& c2) { return -(c2 - c1); }
#endif // __cplusplus
#endif /* _WX_WXCHAR_H_ */