]> git.saurik.com Git - wxWidgets.git/blobdiff - src/common/string.cpp
avoid duplicated empty help menu in localized applications (patch 1600747)
[wxWidgets.git] / src / common / string.cpp
index 6bfe815b8ea28af90eb010f75abaeae3af3f2c71..208a77c0203b12bf196990100322363083b2728e 100644 (file)
 #endif
 
 #include <ctype.h>
-#include <errno.h>
+
+#ifndef __WXWINCE__
+    #include <errno.h>
+#endif
+
 #include <string.h>
 #include <stdlib.h>
 
@@ -1057,7 +1061,7 @@ bool wxString::Shrink()
 
 #if !wxUSE_STL
 // get the pointer to writable buffer of (at least) nLen bytes
-wxChar *wxString::GetWriteBuf(size_t nLen)
+wxChar *wxString::DoGetWriteBuf(size_t nLen)
 {
   if ( !AllocBeforeWrite(nLen) ) {
     // allocation failure handled by caller
@@ -1071,18 +1075,43 @@ wxChar *wxString::GetWriteBuf(size_t nLen)
 }
 
 // put string back in a reasonable state after GetWriteBuf
+void wxString::DoUngetWriteBuf()
+{
+  DoUngetWriteBuf(wxStrlen(m_pchData));
+}
+
+void wxString::DoUngetWriteBuf(size_t nLen)
+{
+  wxStringData * const pData = GetStringData();
+
+  wxASSERT_MSG( nLen < pData->nAllocLength, _T("buffer overrun") );
+
+  // the strings we store are always NUL-terminated
+  pData->data()[nLen] = _T('\0');
+  pData->nDataLength = nLen;
+  pData->Validate(true);
+}
+
+// deprecated compatibility code:
+#if WXWIN_COMPATIBILITY_2_8
+wxChar *wxString::GetWriteBuf(size_t nLen)
+{
+    return DoGetWriteBuf(nLen);
+}
+
 void wxString::UngetWriteBuf()
 {
-  GetStringData()->nDataLength = wxStrlen(m_pchData);
-  GetStringData()->Validate(true);
+    DoUngetWriteBuf();
 }
 
 void wxString::UngetWriteBuf(size_t nLen)
 {
-  GetStringData()->nDataLength = nLen;
-  GetStringData()->Validate(true);
+    DoUngetWriteBuf(nLen);
 }
-#endif
+#endif // WXWIN_COMPATIBILITY_2_8
+
+#endif // !wxUSE_STL
+
 
 // ---------------------------------------------------------------------------
 // data access
@@ -1604,7 +1633,7 @@ wxString& wxString::Trim(bool bFromRight)
             reverse_iterator psz = rbegin();
             while ( (psz != rend()) && wxSafeIsspace(*psz) )
                 psz++;
-            
+
             // truncate at trailing space start
             erase(psz.base(), end());
         }
@@ -1677,68 +1706,46 @@ int wxString::Find(const wxChar *pszSub) const
 
 // the implementation of all the functions below is exactly the same so factor
 // it out
-#ifndef __WATCOMC__
 
-template <typename T>
+template <typename T, typename F>
 bool wxStringToIntType(const wxChar *start,
                        T *val,
                        int base,
-                       T (*func)(const wxChar *, wxChar **, int))
+                       F func)
 {
     wxCHECK_MSG( val, false, _T("NULL output pointer") );
     wxASSERT_MSG( !base || (base > 1 && base <= 36), _T("invalid base") );
 
+#ifndef __WXWINCE__
     errno = 0;
+#endif
 
     wxChar *end;
     *val = (*func)(start, &end, base);
 
     // return true only if scan was stopped by the terminating NUL and if the
     // string was not empty to start with and no under/overflow occurred
-    return !*end && (end != start) && (errno != ERANGE);
-}
-
-#else
-
-//  FIXME, TODO, ASAP !!! - ugly trick to make release for Open Watcom possible
-//  without changing code flow for other compilers
-
-#define wxStringToIntType(start, val, base, func)                             \
-    wxCHECK_MSG( val, false, _T("NULL output pointer") );                     \
-    wxASSERT_MSG( !base || (base > 1 && base <= 36), _T("invalid base") );    \
-                                                                              \
-    errno = 0;                                                                \
-                                                                              \
-    wxChar *end;                                                              \
-    *val = (*func)(start, &end, base);                                        \
-                                                                              \
-    return !*end && (end != start) && (errno != ERANGE)
-
+    return !*end && (end != start)
+#ifndef __WXWINCE__
+        && (errno != ERANGE)
 #endif
+    ;
+}
 
 bool wxString::ToLong(long *val, int base) const
 {
-#ifndef __WATCOMC__
-    return
-#endif
-           wxStringToIntType(c_str(), val, base, wxStrtol);
+    return wxStringToIntType(c_str(), val, base, wxStrtol);
 }
 
 bool wxString::ToULong(unsigned long *val, int base) const
 {
-#ifndef __WATCOMC__
-    return
-#endif
-           wxStringToIntType(c_str(), val, base, wxStrtoul);
+    return wxStringToIntType(c_str(), val, base, wxStrtoul);
 }
 
 bool wxString::ToLongLong(wxLongLong_t *val, int base) const
 {
 #ifdef wxHAS_STRTOLL
-#ifndef __WATCOMC__
-    return
-#endif
-           wxStringToIntType(c_str(), val, base, wxStrtoll);
+    return wxStringToIntType(c_str(), val, base, wxStrtoll);
 #else
     // TODO: implement this ourselves
     wxUnusedVar(val);
@@ -1750,10 +1757,7 @@ bool wxString::ToLongLong(wxLongLong_t *val, int base) const
 bool wxString::ToULongLong(wxULongLong_t *val, int base) const
 {
 #ifdef wxHAS_STRTOLL
-#ifndef __WATCOMC__
-    return
-#endif
-           wxStringToIntType(c_str(), val, base, wxStrtoull);
+    return wxStringToIntType(c_str(), val, base, wxStrtoull);
 #else
     // TODO: implement this ourselves
     wxUnusedVar(val);
@@ -1766,7 +1770,9 @@ bool wxString::ToDouble(double *val) const
 {
     wxCHECK_MSG( val, false, _T("NULL pointer in wxString::ToDouble") );
 
+#ifndef __WXWINCE__
     errno = 0;
+#endif
 
     const wxChar *start = c_str();
     wxChar *end;
@@ -1774,7 +1780,11 @@ bool wxString::ToDouble(double *val) const
 
     // return true only if scan was stopped by the terminating NUL and if the
     // string was not empty to start with and no under/overflow occurred
-    return !*end && (end != start) && (errno != ERANGE);
+    return !*end && (end != start)
+#ifndef __WXWINCE__
+        && (errno != ERANGE)
+#endif
+    ;
 }
 
 // ---------------------------------------------------------------------------
@@ -1847,15 +1857,29 @@ int wxString::PrintfV(const wxChar* pszFormat, va_list argptr)
         // buffer were large enough (newer standards such as Unix98)
         if ( len < 0 )
         {
+#if wxUSE_WXVSNPRINTF
+            // we know that our own implementation of wxVsnprintf() returns -1
+            // only for a format error - thus there's something wrong with
+            // the user's format string
+            return -1;
+#else // assume that system version only returns error if not enough space
             // still not enough, as we don't know how much we need, double the
             // current size of the buffer
             size *= 2;
+#endif // wxUSE_WXVSNPRINTF/!wxUSE_WXVSNPRINTF
         }
         else if ( len >= size )
         {
+#if wxUSE_WXVSNPRINTF
+            // we know that our own implementation of wxVsnprintf() returns 
+            // size+1 when there's not enough space but that's not the size
+            // of the required buffer!
+            size *= 2;      // so we just double the current size of the buffer
+#else
             // some vsnprintf() implementations NUL-terminate the buffer and
             // some don't in len == size case, to be safe always add 1
             size = len + 1;
+#endif
         }
         else // ok, there was enough space
         {
@@ -2080,7 +2104,7 @@ void wxArrayString::Init(bool autoSort)
 {
   m_nSize  =
   m_nCount = 0;
-  m_pItems = (wxChar **) NULL;
+  m_pItems = (const wxChar **) NULL;
   m_autoSort = autoSort;
 }
 
@@ -2130,7 +2154,7 @@ void wxArrayString::Grow(size_t nIncrement)
       m_nSize = ARRAY_DEFAULT_INITIAL_SIZE;
       if (m_nSize < nIncrement)
           m_nSize = nIncrement;
-      m_pItems = new wxChar *[m_nSize];
+      m_pItems = new const wxChar *[m_nSize];
     }
     else {
       // otherwise when it's called for the first time, nIncrement would be 0
@@ -2143,7 +2167,7 @@ void wxArrayString::Grow(size_t nIncrement)
       if ( nIncrement < ndefIncrement )
         nIncrement = ndefIncrement;
       m_nSize += nIncrement;
-      wxChar **pNew = new wxChar *[m_nSize];
+      const wxChar **pNew = new const wxChar *[m_nSize];
 
       // copy data to new location
       memcpy(pNew, m_pItems, m_nCount*sizeof(wxChar *));
@@ -2200,13 +2224,16 @@ void wxArrayString::Alloc(size_t nSize)
 {
   // only if old buffer was not big enough
   if ( nSize > m_nSize ) {
-    Free();
-    wxDELETEA(m_pItems);
-    m_pItems = new wxChar *[nSize];
+    const wxChar **pNew = new const wxChar *[nSize];
+    if ( !pNew )
+        return;
+
+    memcpy(pNew, m_pItems, m_nCount*sizeof(wxChar *));
+    delete [] m_pItems;
+
+    m_pItems = pNew;
     m_nSize  = nSize;
   }
-
-  m_nCount = 0;
 }
 
 // minimizes the memory usage by freeing unused memory
@@ -2215,7 +2242,7 @@ void wxArrayString::Shrink()
   // only do it if we have some memory to free
   if( m_nCount < m_nSize ) {
     // allocates exactly as much memory as we need
-    wxChar **pNew = new wxChar *[m_nCount];
+    const wxChar **pNew = new const wxChar *[m_nCount];
 
     // copy data to new location
     memcpy(pNew, m_pItems, m_nCount*sizeof(wxChar *));
@@ -2224,30 +2251,6 @@ void wxArrayString::Shrink()
   }
 }
 
-#if WXWIN_COMPATIBILITY_2_4
-
-// return a wxString[] as required for some control ctors.
-wxString* wxArrayString::GetStringArray() const
-{
-    wxString *array = 0;
-
-    if( m_nCount > 0 )
-    {
-        array = new wxString[m_nCount];
-        for( size_t i = 0; i < m_nCount; i++ )
-            array[i] = m_pItems[i];
-    }
-
-    return array;
-}
-
-void wxArrayString::Remove(size_t nIndex, size_t nRemove)
-{
-    RemoveAt(nIndex, nRemove);
-}
-
-#endif // WXWIN_COMPATIBILITY_2_4
-
 // searches the array for an item (forward or backwards)
 int wxArrayString::Index(const wxChar *sz, bool bCase, bool bFromEnd) const
 {
@@ -2337,7 +2340,7 @@ size_t wxArrayString::Add(const wxString& str, size_t nInsert)
         str.GetStringData()->Lock();
 
         // just append
-        m_pItems[m_nCount + i] = (wxChar *)str.c_str(); // const_cast
+        m_pItems[m_nCount + i] = str.c_str();
     }
     size_t ret = m_nCount;
     m_nCount += nInsert;
@@ -2362,7 +2365,7 @@ void wxArrayString::Insert(const wxString& str, size_t nIndex, size_t nInsert)
   for (size_t i = 0; i < nInsert; i++)
   {
       str.GetStringData()->Lock();
-      m_pItems[nIndex + i] = (wxChar *)str.c_str();
+      m_pItems[nIndex + i] = str.c_str();
   }
   m_nCount += nInsert;
 }
@@ -2398,7 +2401,7 @@ void wxArrayString::SetCount(size_t count)
 
     wxString s;
     while ( m_nCount < count )
-        m_pItems[m_nCount++] = (wxChar *)s.c_str();
+        m_pItems[m_nCount++] = s.c_str();
 }
 
 // removes item from array (by index)