KHTML
dom_string.cpp
Go to the documentation of this file.
00001 00022 #include "dom/dom_string.h" 00023 #include "xml/dom_stringimpl.h" 00024 00025 #include <wtf/Vector.h> 00026 00027 using namespace DOM; 00028 00029 00030 DOMString::DOMString(const QChar *str, uint len) 00031 { 00032 impl = new DOMStringImpl( str, len ); 00033 impl->ref(); 00034 } 00035 00036 DOMString::DOMString(const QString &str) 00037 { 00038 if (str.isNull()) { 00039 impl = 0; 00040 return; 00041 } 00042 00043 impl = new DOMStringImpl( str.unicode(), str.length() ); 00044 impl->ref(); 00045 } 00046 00047 DOMString::DOMString(const char *str) 00048 { 00049 if (!str) { 00050 impl = 0; 00051 return; 00052 } 00053 00054 impl = new DOMStringImpl( str ); 00055 impl->ref(); 00056 } 00057 00058 DOMString::DOMString(const char *str, uint len) 00059 { 00060 if (!str) { 00061 impl = 0; 00062 return; 00063 } 00064 impl = new DOMStringImpl(str, len); 00065 impl->ref(); 00066 } 00067 00068 DOMString::DOMString(DOMStringImpl *i) 00069 { 00070 impl = i; 00071 if(impl) impl->ref(); 00072 } 00073 00074 DOMString::DOMString(const DOMString &other) 00075 { 00076 impl = other.impl; 00077 if(impl) impl->ref(); 00078 } 00079 00080 DOMString::~DOMString() 00081 { 00082 if(impl) impl->deref(); 00083 } 00084 00085 DOMString &DOMString::operator =(const DOMString &other) 00086 { 00087 if ( impl != other.impl ) { 00088 if(impl) impl->deref(); 00089 impl = other.impl; 00090 if(impl) impl->ref(); 00091 } 00092 return *this; 00093 } 00094 00095 DOMString &DOMString::operator += (const DOMString &str) 00096 { 00097 if(!impl) 00098 { 00099 // ### FIXME!!! 00100 impl = str.impl; 00101 if (impl) 00102 impl->ref(); 00103 return *this; 00104 } 00105 if(str.impl) 00106 { 00107 DOMStringImpl *i = impl->copy(); 00108 impl->deref(); 00109 impl = i; 00110 impl->ref(); 00111 impl->append(str.impl); 00112 } 00113 return *this; 00114 } 00115 00116 DOMString DOMString::operator + (const DOMString &str) 00117 { 00118 if(!impl) return str.copy(); 00119 if(str.impl) 00120 { 00121 DOMString s = copy(); 00122 s += str; 00123 return s; 00124 } 00125 00126 return copy(); 00127 } 00128 00129 void DOMString::insert(DOMString str, uint pos) 00130 { 00131 if(!impl) 00132 { 00133 impl = str.impl->copy(); 00134 impl->ref(); 00135 } 00136 else 00137 impl->insert(str.impl, pos); 00138 } 00139 00140 00141 const QChar &DOMString::operator [](unsigned int i) const 00142 { 00143 static const QChar nullChar = 0; 00144 00145 if(!impl || i >= impl->l ) return nullChar; 00146 00147 return *(impl->s+i); 00148 } 00149 00150 int DOMString::find(const QChar c, int start) const 00151 { 00152 unsigned int l = start; 00153 if(!impl || l >= impl->l ) return -1; 00154 while( l < impl->l ) 00155 { 00156 if( *(impl->s+l) == c ) return l; 00157 l++; 00158 } 00159 return -1; 00160 } 00161 00162 int DOMString::reverseFind(const QChar c, int start) const 00163 { 00164 unsigned int l = start; 00165 if (!impl || l < -impl->l) return -1; 00166 l += impl->l; 00167 while (1) { 00168 if (*(impl->s + l) == c) return l; 00169 l--; 00170 if (l == 0) 00171 return -1; 00172 } 00173 return -1; 00174 } 00175 00176 DOMString DOMString::substring(unsigned pos, unsigned len) const 00177 { 00178 return (impl) ? impl->substring(pos, len) : DOMString(); 00179 } 00180 00181 uint DOMString::length() const 00182 { 00183 if(!impl) return 0; 00184 return impl->l; 00185 } 00186 00187 void DOMString::truncate( unsigned int len ) 00188 { 00189 if(impl) impl->truncate(len); 00190 } 00191 00192 void DOMString::remove(unsigned int pos, int len) 00193 { 00194 if(impl) impl->remove(pos, len); 00195 } 00196 00197 DOMString DOMString::split(unsigned int pos) 00198 { 00199 if(!impl) return DOMString(); 00200 return impl->split(pos); 00201 } 00202 00203 DOMString DOMString::lower() const 00204 { 00205 if(!impl) return DOMString(); 00206 return impl->lower(); 00207 } 00208 00209 DOMString DOMString::upper() const 00210 { 00211 if(!impl) return DOMString(); 00212 return impl->upper(); 00213 } 00214 00215 bool DOMString::percentage(int &_percentage) const 00216 { 00217 if(!impl || !impl->l) return false; 00218 00219 if ( *(impl->s+impl->l-1) != QChar('%')) 00220 return false; 00221 00222 _percentage = QString::fromRawData(impl->s, impl->l-1).toInt(); 00223 return true; 00224 } 00225 00226 QChar *DOMString::unicode() const 00227 { 00228 if(!impl) return 0; 00229 return impl->unicode(); 00230 } 00231 00232 QString DOMString::string() const 00233 { 00234 if(!impl) return QString(); 00235 00236 return impl->string(); 00237 } 00238 00239 int DOMString::toInt() const 00240 { 00241 if(!impl) return 0; 00242 00243 return impl->toInt(); 00244 } 00245 00246 int DOMString::toInt(bool* ok) const 00247 { 00248 if (!impl) { 00249 *ok = false; 00250 return 0; 00251 } 00252 00253 return impl->toInt(ok); 00254 } 00255 00256 float DOMString::toFloat(bool* ok) const 00257 { 00258 if (!impl) { 00259 if (ok) 00260 *ok = false; 00261 return 0; 00262 } 00263 return impl->toFloat(ok); 00264 } 00265 00266 DOMString DOMString::number(float f) 00267 { 00268 return DOMString(QString::number(f)); 00269 } 00270 00271 DOMString DOMString::copy() const 00272 { 00273 if(!impl) return DOMString(); 00274 return impl->copy(); 00275 } 00276 00277 bool DOMString::endsWith(const DOMString& str) const 00278 { 00279 if (str.length() > length()) return false; 00280 return impl->endsWith(str.implementation()); 00281 } 00282 00283 bool DOMString::startsWith(const DOMString& str) const 00284 { 00285 if (str.length() > length()) return false; 00286 return impl->startsWith(str.implementation()); 00287 } 00288 00289 // ------------------------------------------------------------------------ 00290 00291 bool DOM::strcasecmp( const DOMString &as, const DOMString &bs ) 00292 { 00293 return strcasecmp(as.implementation(), bs.implementation()); 00294 } 00295 00296 bool DOM::strcasecmp( const DOMString &as, const char* bs ) 00297 { 00298 const QChar *a = as.unicode(); 00299 int l = as.length(); 00300 if ( !bs ) return ( l != 0 ); 00301 while ( l-- ) { 00302 if ( a->toLatin1() != *bs ) { 00303 char cc = ( ( *bs >= 'A' ) && ( *bs <= 'Z' ) ) ? ( ( *bs ) + 'a' - 'A' ) : ( *bs ); 00304 if ( a->toLower().toLatin1() != cc ) return true; 00305 } 00306 a++, bs++; 00307 } 00308 return ( *bs != '\0' ); 00309 } 00310 00311 bool DOMString::isEmpty() const 00312 { 00313 return (!impl || impl->l == 0); 00314 } 00315 00316 DOMString DOMString::format(const char *format, ...) 00317 { 00318 va_list args; 00319 va_start(args, format); 00320 00321 Vector<char, 256> buffer; 00322 00323 // Do the format once to get the length. 00324 #if COMPILER(MSVC) 00325 int result = _vscprintf(format, args); 00326 #else 00327 char ch; 00328 int result = vsnprintf(&ch, 1, format, args); 00329 // We need to call va_end() and then va_start() again here, as the 00330 // contents of args is undefined after the call to vsnprintf 00331 // according to http://man.cx/snprintf(3) 00332 // 00333 // Not calling va_end/va_start here happens to work on lots of 00334 // systems, but fails e.g. on 64bit Linux. 00335 va_end(args); 00336 va_start(args, format); 00337 #endif 00338 00339 if (result == 0) 00340 return DOMString(""); 00341 if (result < 0) 00342 return DOMString(); 00343 unsigned len = result; 00344 buffer.grow(len + 1); 00345 00346 // Now do the formatting again, guaranteed to fit. 00347 vsnprintf(buffer.data(), buffer.size(), format, args); 00348 00349 va_end(args); 00350 00351 buffer[len] = 0; // we don't really need this I guess 00352 return new DOMStringImpl(buffer.data()/*, len*/); 00353 } 00354 00355 //----------------------------------------------------------------------------- 00356 00357 bool DOM::operator==( const DOMString &a, const DOMString &b ) 00358 { 00359 return !strcmp(a.implementation(), b.implementation()); 00360 } 00361 00362 bool DOM::operator==( const DOMString &a, const QString &b ) 00363 { 00364 int l = a.length(); 00365 00366 if( l != b.length() ) return false; 00367 00368 if(!memcmp(a.unicode(), b.unicode(), l*sizeof(QChar))) 00369 return true; 00370 return false; 00371 } 00372 00373 bool DOM::operator==( const DOMString &a, const char *b ) 00374 { 00375 DOMStringImpl* aimpl = a.impl; 00376 if ( !b ) return !aimpl; 00377 00378 if ( aimpl ) { 00379 int alen = aimpl->l; 00380 const QChar *aptr = aimpl->s; 00381 while ( alen-- ) { 00382 unsigned char c = *b++; 00383 if ( !c || ( *aptr++ ).unicode() != c ) 00384 return false; 00385 } 00386 } 00387 00388 return !*b; 00389 }
KDE 4.6 API Reference