diff options
-rw-r--r-- | doc/src/classes/qnamespace.qdoc | 1 | ||||
-rw-r--r-- | src/corelib/global/qnamespace.h | 3 | ||||
-rw-r--r-- | src/corelib/io/qfsfileengine_iterator.cpp | 1 | ||||
-rw-r--r-- | src/corelib/io/qfsfileengine_iterator_p.h | 2 | ||||
-rw-r--r-- | src/corelib/io/qfsfileengine_iterator_unix.cpp | 2 | ||||
-rw-r--r-- | src/corelib/io/qfsfileengine_iterator_win.cpp | 12 | ||||
-rw-r--r-- | src/corelib/io/qfsfileengine_unix.cpp | 62 | ||||
-rw-r--r-- | src/corelib/io/qfsfileengine_win.cpp | 157 | ||||
-rw-r--r-- | src/corelib/tools/qpoint.h | 4 | ||||
-rw-r--r-- | src/gui/graphicsview/qgraphicsscene_p.h | 4 | ||||
-rw-r--r-- | src/gui/painting/qpainter.cpp | 83 | ||||
-rw-r--r-- | src/gui/styles/qstylehelper.cpp | 18 | ||||
-rw-r--r-- | src/gui/text/qfontmetrics.cpp | 25 | ||||
-rw-r--r-- | src/gui/text/qtextformat.cpp | 7 | ||||
-rw-r--r-- | tests/auto/qfileinfo/tst_qfileinfo.cpp | 42 | ||||
-rw-r--r-- | tests/auto/qfontmetrics/tst_qfontmetrics.cpp | 30 | ||||
-rw-r--r-- | tests/auto/qpixmapcache/tst_qpixmapcache.cpp | 17 |
17 files changed, 278 insertions, 192 deletions
diff --git a/doc/src/classes/qnamespace.qdoc b/doc/src/classes/qnamespace.qdoc index 18ecd7b..5872d04 100644 --- a/doc/src/classes/qnamespace.qdoc +++ b/doc/src/classes/qnamespace.qdoc @@ -490,6 +490,7 @@ \omitvalue WordBreak \omitvalue TextForceLeftToRight \omitvalue TextForceRightToLeft + \omitvalue TextLongestVariant Always use the longest variant when computing the size of a multi-variant string You can use as many modifier flags as you want, except that Qt::TextSingleLine and Qt::TextWordWrap cannot be combined. diff --git a/src/corelib/global/qnamespace.h b/src/corelib/global/qnamespace.h index f172d77..4024fce 100644 --- a/src/corelib/global/qnamespace.h +++ b/src/corelib/global/qnamespace.h @@ -233,7 +233,8 @@ public: TextHideMnemonic = 0x8000, TextJustificationForced = 0x10000, TextForceLeftToRight = 0x20000, - TextForceRightToLeft = 0x40000 + TextForceRightToLeft = 0x40000, + TextLongestVariant = 0x80000 #if defined(QT3_SUPPORT) && !defined(Q_MOC_RUN) ,SingleLine = TextSingleLine, diff --git a/src/corelib/io/qfsfileengine_iterator.cpp b/src/corelib/io/qfsfileengine_iterator.cpp index 35b388f..52fc80d 100644 --- a/src/corelib/io/qfsfileengine_iterator.cpp +++ b/src/corelib/io/qfsfileengine_iterator.cpp @@ -79,4 +79,3 @@ QFileInfo QFSFileEngineIterator::currentFileInfo() const QT_END_NAMESPACE #endif // QT_NO_FSFILEENGINE - diff --git a/src/corelib/io/qfsfileengine_iterator_p.h b/src/corelib/io/qfsfileengine_iterator_p.h index 7829fff..342ef8d 100644 --- a/src/corelib/io/qfsfileengine_iterator_p.h +++ b/src/corelib/io/qfsfileengine_iterator_p.h @@ -89,4 +89,4 @@ QT_END_NAMESPACE #endif // QT_NO_FSFILEENGINE -#endif +#endif // QFSFILEENGINE_ITERATOR_P_H diff --git a/src/corelib/io/qfsfileengine_iterator_unix.cpp b/src/corelib/io/qfsfileengine_iterator_unix.cpp index a6c965c..107a500 100644 --- a/src/corelib/io/qfsfileengine_iterator_unix.cpp +++ b/src/corelib/io/qfsfileengine_iterator_unix.cpp @@ -56,7 +56,7 @@ public: #if defined(_POSIX_THREAD_SAFE_FUNCTIONS) && !defined(Q_OS_CYGWIN) , mt_file(0) #endif - { } + {} DIR *dir; dirent *dirEntry; diff --git a/src/corelib/io/qfsfileengine_iterator_win.cpp b/src/corelib/io/qfsfileengine_iterator_win.cpp index dd4ddf3..3d9c20e 100644 --- a/src/corelib/io/qfsfileengine_iterator_win.cpp +++ b/src/corelib/io/qfsfileengine_iterator_win.cpp @@ -39,14 +39,11 @@ ** ****************************************************************************/ -#include "qdebug.h" #include "qfsfileengine_iterator_p.h" #include "qfsfileengine_p.h" #include "qplatformdefs.h" #include <QtCore/qvariant.h> -#include <QtCore/qmutex.h> -#include <private/qmutexpool_p.h> QT_BEGIN_NAMESPACE @@ -56,7 +53,7 @@ public: inline QFSFileEngineIteratorPlatformSpecificData() : uncShareIndex(-1), findFileHandle(INVALID_HANDLE_VALUE), done(false), uncFallback(false) - { } + {} QFSFileEngineIterator *it; @@ -68,7 +65,6 @@ public: bool done; bool uncFallback; - void advance(); void saveCurrentFileName(); }; @@ -116,10 +112,10 @@ bool QFSFileEngineIterator::hasNext() const { if (platform->done) return false; - + if (platform->uncFallback) return platform->uncShareIndex > 0 && platform->uncShareIndex <= platform->uncShares.size(); - + if (platform->findFileHandle == INVALID_HANDLE_VALUE) { QString path = this->path(); // Local directory @@ -151,7 +147,7 @@ bool QFSFileEngineIterator::hasNext() const platform->done = true; } } else { - platform->done = true; + platform->done = true; } } diff --git a/src/corelib/io/qfsfileengine_unix.cpp b/src/corelib/io/qfsfileengine_unix.cpp index c0b6820..7d91764 100644 --- a/src/corelib/io/qfsfileengine_unix.cpp +++ b/src/corelib/io/qfsfileengine_unix.cpp @@ -70,16 +70,20 @@ QT_BEGIN_NAMESPACE Returns the stdlib open string corresponding to a QIODevice::OpenMode. */ -static QByteArray openModeToFopenMode(QIODevice::OpenMode flags, const QString &fileName = QString()) +static inline QByteArray openModeToFopenMode(QIODevice::OpenMode flags, const QString &fileName) { QByteArray mode; if ((flags & QIODevice::ReadOnly) && !(flags & QIODevice::Truncate)) { mode = "rb"; if (flags & QIODevice::WriteOnly) { - if (!fileName.isEmpty() &&QFile::exists(fileName)) - mode = "rb+"; - else + QT_STATBUF statBuf; + if (!fileName.isEmpty() + && QT_STAT(QFile::encodeName(fileName), &statBuf) == 0 + && (statBuf.st_mode & S_IFMT) == S_IFREG) { + mode += "+"; + } else { mode = "wb+"; + } } } else if (flags & QIODevice::WriteOnly) { mode = "wb"; @@ -105,7 +109,7 @@ static QByteArray openModeToFopenMode(QIODevice::OpenMode flags, const QString & Returns the stdio open flags corresponding to a QIODevice::OpenMode. */ -static int openModeToOpenFlags(QIODevice::OpenMode mode) +static inline int openModeToOpenFlags(QIODevice::OpenMode mode) { int oflags = QT_OPEN_RDONLY; #ifdef QT_LARGEFILE_SUPPORT @@ -134,7 +138,7 @@ static int openModeToOpenFlags(QIODevice::OpenMode mode) Sets the file descriptor to close on exec. That is, the file descriptor is not inherited by child processes. */ -static bool setCloseOnExec(int fd) +static inline bool setCloseOnExec(int fd) { return fd != -1 && fcntl(fd, F_SETFD, FD_CLOEXEC) != -1; } @@ -414,15 +418,15 @@ bool QFSFileEngine::mkdir(const QString &name, bool createParentDirectories) con if ((st.st_mode & S_IFMT) != S_IFDIR) return false; } else if (QT_MKDIR(chunk, 0777) != 0) { - return false; + return false; } } } return true; } #if defined(Q_OS_DARWIN) // Mac X doesn't support trailing /'s - if (dirName[dirName.length() - 1] == QLatin1Char('/')) - dirName = dirName.left(dirName.length() - 1); + if (dirName.endsWith(QLatin1Char('/'))) + dirName.chop(1); #endif return (QT_MKDIR(QFile::encodeName(dirName), 0777) == 0); } @@ -520,18 +524,19 @@ QFileInfoList QFSFileEngine::drives() bool QFSFileEnginePrivate::doStat() const { - if (tried_stat == 0) { - QFSFileEnginePrivate *that = const_cast<QFSFileEnginePrivate*>(this); + if (!tried_stat) { + tried_stat = true; + could_stat = false; + if (fh && nativeFilePath.isEmpty()) { // ### actually covers two cases: d->fh and when the file is not open - that->could_stat = (QT_FSTAT(fileno(fh), &st) == 0); + could_stat = (QT_FSTAT(QT_FILENO(fh), &st) == 0); } else if (fd == -1) { // ### actually covers two cases: d->fh and when the file is not open - that->could_stat = (QT_STAT(nativeFilePath.constData(), &st) == 0); + could_stat = (QT_STAT(nativeFilePath.constData(), &st) == 0); } else { - that->could_stat = (QT_FSTAT(fd, &st) == 0); + could_stat = (QT_FSTAT(fd, &st) == 0); } - that->tried_stat = 1; } return could_stat; } @@ -539,10 +544,10 @@ bool QFSFileEnginePrivate::doStat() const bool QFSFileEnginePrivate::isSymlink() const { if (need_lstat) { - QFSFileEnginePrivate *that = const_cast<QFSFileEnginePrivate *>(this); - that->need_lstat = false; + need_lstat = false; + QT_STATBUF st; // don't clobber our main one - that->is_link = (QT_LSTAT(nativeFilePath.constData(), &st) == 0) ? S_ISLNK(st.st_mode) : false; + is_link = (QT_LSTAT(nativeFilePath.constData(), &st) == 0) ? S_ISLNK(st.st_mode) : false; } return is_link; } @@ -577,7 +582,7 @@ QAbstractFileEngine::FileFlags QFSFileEngine::fileFlags(FileFlags type) const { Q_D(const QFSFileEngine); // Force a stat, so that we're guaranteed to get up-to-date results - if (type & QAbstractFileEngine::FileFlag(QAbstractFileEngine::Refresh)) { + if (type & Refresh) { d->tried_stat = 0; d->need_lstat = 1; } @@ -651,14 +656,19 @@ QAbstractFileEngine::FileFlags QFSFileEngine::fileFlags(FileFlags type) const ret |= LocalDiskFlag; if (exists) ret |= ExistsFlag; - if (fileName(BaseName)[0] == QLatin1Char('.') + if (d->filePath == QLatin1String("/")) { + ret |= RootFlag; + } else { + QString baseName = fileName(BaseName); + if ((baseName.size() > 1 + && baseName.at(0) == QLatin1Char('.') && baseName.at(1) != QLatin1Char('.')) #if !defined(QWS) && defined(Q_OS_MAC) - || _q_isMacHidden(d->filePath) + || _q_isMacHidden(d->filePath) #endif - ) - ret |= HiddenFlag; - if (d->filePath == QLatin1String("/")) - ret |= RootFlag; + ) { + ret |= HiddenFlag; + } + } } return ret; } @@ -767,7 +777,7 @@ QString QFSFileEngine::fileName(FileName file) const s[len] = '\0'; ret += QFile::decodeName(QByteArray(s)); #if defined(__GLIBC__) && !defined(PATH_MAX) - ::free(s); + ::free(s); #endif if (!ret.startsWith(QLatin1Char('/'))) { diff --git a/src/corelib/io/qfsfileengine_win.cpp b/src/corelib/io/qfsfileengine_win.cpp index 7c75525..0cddee3 100644 --- a/src/corelib/io/qfsfileengine_win.cpp +++ b/src/corelib/io/qfsfileengine_win.cpp @@ -47,10 +47,6 @@ #include "qfile.h" #include "qdir.h" -#include "qtemporaryfile.h" -#ifndef QT_NO_REGEXP -# include "qregexp.h" -#endif #include "private/qmutexpool_p.h" #include "qvarlengtharray.h" #include "qdatetime.h" @@ -125,7 +121,7 @@ static TRUSTEE_W currentUserTrusteeW; typedef BOOL (WINAPI *PtrOpenProcessToken)(HANDLE, DWORD, PHANDLE ); static PtrOpenProcessToken ptrOpenProcessToken = 0; -typedef BOOL (WINAPI *PtrGetUserProfileDirectoryW)( HANDLE, LPWSTR, LPDWORD); +typedef BOOL (WINAPI *PtrGetUserProfileDirectoryW)(HANDLE, LPWSTR, LPDWORD); static PtrGetUserProfileDirectoryW ptrGetUserProfileDirectoryW = 0; typedef BOOL (WINAPI *PtrSetFilePointerEx)(HANDLE, LARGE_INTEGER, PLARGE_INTEGER, DWORD); static PtrSetFilePointerEx ptrSetFilePointerEx = 0; @@ -266,7 +262,7 @@ bool QFSFileEnginePrivate::uncListSharesOnServer(const QString &server, QStringL do { res = ptrNetShareEnum((wchar_t*)server.utf16(), 1, (LPBYTE *)&BufPtr, DWORD(-1), &er, &tr, &resume); if (res == ERROR_SUCCESS || res == ERROR_MORE_DATA) { - p=BufPtr; + p = BufPtr; for (i = 1; i <= er; ++i) { if (list && p->shi1_type == 0) list->append(QString::fromWCharArray(p->shi1_netname)); @@ -276,7 +272,6 @@ bool QFSFileEnginePrivate::uncListSharesOnServer(const QString &server, QStringL ptrNetApiBufferFree(BufPtr); } while (res==ERROR_MORE_DATA); return res == ERROR_SUCCESS; - } return false; } @@ -295,20 +290,22 @@ static bool isUncRoot(const QString &server) return localPath.isEmpty(); } -static bool isUncPath(const QString &path) +#if !defined(Q_OS_WINCE) +static inline bool isUncPath(const QString &path) { - // Starts with // or \\, but not \\. or //. - return (path.startsWith(QLatin1String("//")) - || path.startsWith(QLatin1String("\\\\"))) - && (path.size() > 2 && path.at(2) != QLatin1Char('.')); + // Starts with \\, but not \\. + return (path.startsWith(QLatin1String("\\\\")) + && path.size() > 2 && path.at(2) != QLatin1Char('.')); } +#endif -static bool isRelativePath(const QString &path) +static inline bool isRelativePath(const QString &path) { + // drive, e.g. "a:", or UNC root, e.q. "//" return !(path.startsWith(QLatin1Char('/')) || (path.length() >= 2 && ((path.at(0).isLetter() && path.at(1) == QLatin1Char(':')) - || (path.at(0) == QLatin1Char('/') && path.at(1) == QLatin1Char('/'))))); // drive, e.g. a: + || (path.at(0) == QLatin1Char('/') && path.at(1) == QLatin1Char('/'))))); } static QString fixIfRelativeUncPath(const QString &path) @@ -327,21 +324,24 @@ static bool uncShareExists(const QString &server) QStringList parts = server.split(QLatin1Char('\\'), QString::SkipEmptyParts); if (parts.count()) { QStringList shares; - if (QFSFileEnginePrivate::uncListSharesOnServer(QLatin1String("\\\\") + parts.at(0), &shares)) { - if (parts.count() >= 2) - return shares.contains(parts.at(1), Qt::CaseInsensitive); - else - return true; - } + if (QFSFileEnginePrivate::uncListSharesOnServer(QLatin1String("\\\\") + parts.at(0), &shares)) + return parts.count() >= 2 ? shares.contains(parts.at(1), Qt::CaseInsensitive) : true; } return false; } -static QString nativeAbsoluteFilePathCore(const QString &path) +static inline bool isDriveRoot(const QString &path) { - QString ret; + return (path.length() == 3 + && path.at(0).isLetter() && path.at(1) == QLatin1Char(':') + && path.at(2) == QLatin1Char('/')); +} + +static QString nativeAbsoluteFilePath(const QString &path) +{ + QString absPath; #if !defined(Q_OS_WINCE) - QVarLengthArray<wchar_t, MAX_PATH> buf(MAX_PATH); + QVarLengthArray<wchar_t, MAX_PATH> buf(qMax(MAX_PATH, path.size() + 1)); wchar_t *fileName = 0; DWORD retLen = GetFullPathName((wchar_t*)path.utf16(), buf.size(), buf.data(), &fileName); if (retLen > (DWORD)buf.size()) { @@ -349,33 +349,20 @@ static QString nativeAbsoluteFilePathCore(const QString &path) retLen = GetFullPathName((wchar_t*)path.utf16(), buf.size(), buf.data(), &fileName); } if (retLen != 0) - ret = QString::fromWCharArray(buf.data(), retLen); + absPath = QString::fromWCharArray(buf.data(), retLen); #else if (path.startsWith(QLatin1Char('/')) || path.startsWith(QLatin1Char('\\'))) - ret = QDir::toNativeSeparators(path); + absPath = QDir::toNativeSeparators(path); else - ret = QDir::toNativeSeparators(QDir::cleanPath(qfsPrivateCurrentDir + QLatin1Char('/') + path)); + absPath = QDir::toNativeSeparators(QDir::cleanPath(qfsPrivateCurrentDir + QLatin1Char('/') + path)); #endif - return ret; -} - -static QString nativeAbsoluteFilePath(const QString &path) -{ - QString absPath = nativeAbsoluteFilePathCore(path); // This is really ugly, but GetFullPathName strips off whitespace at the end. // If you for instance write ". " in the lineedit of QFileDialog, // (which is an invalid filename) this function will strip the space off and viola, // the file is later reported as existing. Therefore, we re-add the whitespace that // was at the end of path in order to keep the filename invalid. - int i = path.size() - 1; - while (i >= 0 && path.at(i) == QLatin1Char(' ')) --i; - int extraws = path.size() - 1 - i; - if (extraws >= 0) { - while (extraws) { - absPath.append(QLatin1Char(' ')); - --extraws; - } - } + if (!path.isEmpty() && path.at(path.size() - 1) == QLatin1Char(' ')) + absPath.append(QLatin1Char(' ')); return absPath; } @@ -391,7 +378,7 @@ QString QFSFileEnginePrivate::longFileName(const QString &path) #if !defined(Q_OS_WINCE) QString prefix = QLatin1String("\\\\?\\"); if (isUncPath(absPath)) { - prefix = QLatin1String("\\\\?\\UNC\\"); + prefix.append(QLatin1String("UNC\\")); // "\\\\?\\UNC\\" absPath.remove(0, 2); } return prefix + absPath; @@ -405,8 +392,8 @@ QString QFSFileEnginePrivate::longFileName(const QString &path) */ void QFSFileEnginePrivate::nativeInitFileName() { - QString path = longFileName(QDir::toNativeSeparators(fixIfRelativeUncPath(filePath))); - nativeFilePath = QByteArray((const char *)path.utf16(), path.size() * 2 + 1); + QString path = longFileName(QDir::toNativeSeparators(fixIfRelativeUncPath(filePath))); + nativeFilePath = QByteArray((const char *)path.utf16(), path.size() * 2 + 1); } /* @@ -428,8 +415,7 @@ bool QFSFileEnginePrivate::nativeOpen(QIODevice::OpenMode openMode) SECURITY_ATTRIBUTES securityAtts = { sizeof(SECURITY_ATTRIBUTES), NULL, FALSE }; // WriteOnly can create files, ReadOnly cannot. - DWORD creationDisp = (openMode & QIODevice::WriteOnly) - ? OPEN_ALWAYS : OPEN_EXISTING; + DWORD creationDisp = (openMode & QIODevice::WriteOnly) ? OPEN_ALWAYS : OPEN_EXISTING; // Create the file handle. fileHandle = CreateFile((const wchar_t*)nativeFilePath.constData(), @@ -893,10 +879,10 @@ static inline bool rmDir(const QString &path) return ::RemoveDirectory((wchar_t*)QFSFileEnginePrivate::longFileName(path).utf16()); } -static inline bool isDirPath(const QString &dirPath, bool *existed) +static bool isDirPath(const QString &dirPath, bool *existed) { QString path = dirPath; - if (path.length() == 2 &&path.at(1) == QLatin1Char(':')) + if (path.length() == 2 && path.at(1) == QLatin1Char(':')) path += QLatin1Char('\\'); DWORD fileAttrib = ::GetFileAttributes((wchar_t*)QFSFileEnginePrivate::longFileName(path).utf16()); @@ -958,9 +944,13 @@ bool QFSFileEngine::mkdir(const QString &name, bool createParentDirectories) con if (slash) { QString chunk = dirName.left(slash); bool existed = false; - if (!isDirPath(chunk, &existed) && !existed) { - if (!mkDir(chunk)) + if (!isDirPath(chunk, &existed)) { + if (!existed) { + if (!mkDir(chunk)) + return false; + } else { return false; + } } } } @@ -1146,10 +1136,10 @@ QFileInfoList QFSFileEngine::drives() char driveName[] = "A:/"; while(driveBits) { - if(driveBits & 1) - ret.append(QString::fromLatin1(driveName)); - driveName[0]++; - driveBits = driveBits >> 1; + if(driveBits & 1) + ret.append(QString::fromLatin1(driveName)); + driveName[0]++; + driveBits = driveBits >> 1; } return ret; #else @@ -1213,8 +1203,8 @@ bool QFSFileEnginePrivate::doStat() const could_stat = fileAttrib != INVALID_FILE_ATTRIBUTES; if (!could_stat) { #if !defined(Q_OS_WINCE) - if (!fname.isEmpty() && fname.at(0).isLetter() && fname.mid(1, fname.length()) == QLatin1String(":/")) { - // an empty drive ?? + if (isDriveRoot(fname)) { + // a valid drive ?? DWORD drivesBitmask = ::GetLogicalDrives(); int drivebit = 1 << (fname.at(0).toUpper().unicode() - QLatin1Char('A').unicode()); if (drivesBitmask & drivebit) { @@ -1470,25 +1460,26 @@ QAbstractFileEngine::FileFlags QFSFileEnginePrivate::getPermissions() const //### what to do with permissions if we don't use NTFS // for now just add all permissions and what about exe missions ?? // also qt_ntfs_permission_lookup is now not set by defualt ... should it ? - ret |= QAbstractFileEngine::ReadOtherPerm | QAbstractFileEngine::ReadGroupPerm + ret |= QAbstractFileEngine::ReadOtherPerm | QAbstractFileEngine::ReadGroupPerm | QAbstractFileEngine::ReadOwnerPerm | QAbstractFileEngine::ReadUserPerm | QAbstractFileEngine::WriteUserPerm | QAbstractFileEngine::WriteOwnerPerm | QAbstractFileEngine::WriteGroupPerm | QAbstractFileEngine::WriteOtherPerm; - } - if (doStat()) { - if (ret & (QAbstractFileEngine::WriteOwnerPerm | QAbstractFileEngine::WriteUserPerm | - QAbstractFileEngine::WriteGroupPerm | QAbstractFileEngine::WriteOtherPerm)) { - if (fileAttrib & FILE_ATTRIBUTE_READONLY) - ret &= ~(QAbstractFileEngine::WriteOwnerPerm | QAbstractFileEngine::WriteUserPerm | - QAbstractFileEngine::WriteGroupPerm | QAbstractFileEngine::WriteOtherPerm); - } + if (doStat()) { + if (ret & (QAbstractFileEngine::WriteOwnerPerm | QAbstractFileEngine::WriteUserPerm | + QAbstractFileEngine::WriteGroupPerm | QAbstractFileEngine::WriteOtherPerm)) { + if (fileAttrib & FILE_ATTRIBUTE_READONLY) + ret &= ~(QAbstractFileEngine::WriteOwnerPerm | QAbstractFileEngine::WriteUserPerm | + QAbstractFileEngine::WriteGroupPerm | QAbstractFileEngine::WriteOtherPerm); + } - QString ext = filePath.right(4).toLower(); - if (ext == QLatin1String(".exe") || ext == QLatin1String(".com") || ext == QLatin1String(".bat") || - ext == QLatin1String(".pif") || ext == QLatin1String(".cmd") || (fileAttrib & FILE_ATTRIBUTE_DIRECTORY)) - ret |= QAbstractFileEngine::ExeOwnerPerm | QAbstractFileEngine::ExeGroupPerm | - QAbstractFileEngine::ExeOtherPerm | QAbstractFileEngine::ExeUserPerm; + QString fname = filePath.endsWith(QLatin1String(".lnk")) ? readLink(filePath) : filePath; + QString ext = fname.right(4).toLower(); + if (ext == QLatin1String(".exe") || ext == QLatin1String(".com") || ext == QLatin1String(".bat") || + ext == QLatin1String(".pif") || ext == QLatin1String(".cmd") || (fileAttrib & FILE_ATTRIBUTE_DIRECTORY)) + ret |= QAbstractFileEngine::ExeOwnerPerm | QAbstractFileEngine::ExeGroupPerm | + QAbstractFileEngine::ExeOtherPerm | QAbstractFileEngine::ExeUserPerm; + } } return ret; } @@ -1501,7 +1492,7 @@ QAbstractFileEngine::FileFlags QFSFileEngine::fileFlags(QAbstractFileEngine::Fil Q_D(const QFSFileEngine); QAbstractFileEngine::FileFlags ret = 0; // Force a stat, so that we're guaranteed to get up-to-date results - if (type & QAbstractFileEngine::FileFlag(QAbstractFileEngine::Refresh)) { + if (type & Refresh) { d->tried_stat = 0; } @@ -1519,9 +1510,10 @@ QAbstractFileEngine::FileFlags QFSFileEngine::fileFlags(QAbstractFileEngine::Fil ret |= LinkType; QString l = readLink(d->filePath); if (!l.isEmpty()) { - if (isDirPath(l, 0)) + bool existed = false; + if (isDirPath(l, &existed) && existed) ret |= DirectoryType; - else + else if (existed) ret |= FileType; } } else if (d->doStat()) { @@ -1535,14 +1527,15 @@ QAbstractFileEngine::FileFlags QFSFileEngine::fileFlags(QAbstractFileEngine::Fil } } if (type & FlagsMask) { - if(d->doStat()) { - ret |= QAbstractFileEngine::FileFlags(ExistsFlag | LocalDiskFlag); - if (d->fileAttrib & FILE_ATTRIBUTE_HIDDEN) - ret |= HiddenFlag; - if (d->filePath == QLatin1String("/") || (d->filePath.at(0).isLetter() && d->filePath.mid(1,d->filePath.length()) == QLatin1String(":/")) - || isUncRoot(d->filePath)) { + ret |= LocalDiskFlag; + if (d->doStat()) { + ret |= ExistsFlag; + if (d->filePath == QLatin1String("/") || isDriveRoot(d->filePath) || isUncRoot(d->filePath)) { ret |= RootFlag; - ret &= ~HiddenFlag; + } else if (d->fileAttrib & FILE_ATTRIBUTE_HIDDEN) { + QString baseName = fileName(BaseName); + if (baseName != QLatin1String(".") && baseName != QLatin1String("..")) + ret |= HiddenFlag; } } } @@ -1645,10 +1638,11 @@ QString QFSFileEngine::fileName(FileName file) const bool QFSFileEngine::isRelativePath() const { Q_D(const QFSFileEngine); + // drive, e.g. "a:", or UNC root, e.q. "//" return !(d->filePath.startsWith(QLatin1Char('/')) || (d->filePath.length() >= 2 && ((d->filePath.at(0).isLetter() && d->filePath.at(1) == QLatin1Char(':')) - || (d->filePath.at(0) == QLatin1Char('/') && d->filePath.at(1) == QLatin1Char('/'))))); // drive, e.g. a: + || (d->filePath.at(0) == QLatin1Char('/') && d->filePath.at(1) == QLatin1Char('/'))))); } uint QFSFileEngine::ownerId(FileOwner /*own*/) const @@ -1964,4 +1958,5 @@ void QFSFileEnginePrivate::mapHandleClose() } } #endif + QT_END_NAMESPACE diff --git a/src/corelib/tools/qpoint.h b/src/corelib/tools/qpoint.h index df35eaa..8d653b0 100644 --- a/src/corelib/tools/qpoint.h +++ b/src/corelib/tools/qpoint.h @@ -302,12 +302,12 @@ inline QPointF &QPointF::operator*=(qreal c) inline bool operator==(const QPointF &p1, const QPointF &p2) { - return qFuzzyCompare(p1.xp, p2.xp) && qFuzzyCompare(p1.yp, p2.yp); + return qFuzzyIsNull(p1.xp - p2.xp) && qFuzzyIsNull(p1.yp - p2.yp); } inline bool operator!=(const QPointF &p1, const QPointF &p2) { - return !qFuzzyCompare(p1.xp, p2.xp) || !qFuzzyCompare(p1.yp, p2.yp); + return !qFuzzyIsNull(p1.xp - p2.xp) || !qFuzzyIsNull(p1.yp - p2.yp); } inline const QPointF operator+(const QPointF &p1, const QPointF &p2) diff --git a/src/gui/graphicsview/qgraphicsscene_p.h b/src/gui/graphicsview/qgraphicsscene_p.h index a4bbdd2..7415591 100644 --- a/src/gui/graphicsview/qgraphicsscene_p.h +++ b/src/gui/graphicsview/qgraphicsscene_p.h @@ -267,9 +267,9 @@ static inline void _q_adjustRect(QRectF *rect) { Q_ASSERT(rect); if (!rect->width()) - rect->adjust(-0.00001, 0, 0.00001, 0); + rect->adjust(qreal(-0.00001), 0, qreal(0.00001), 0); if (!rect->height()) - rect->adjust(0, -0.00001, 0, 0.00001); + rect->adjust(0, qreal(-0.00001), 0, qreal(0.00001)); } static inline QRectF adjustedItemBoundingRect(const QGraphicsItem *item) diff --git a/src/gui/painting/qpainter.cpp b/src/gui/painting/qpainter.cpp index 8192fb7..cd4ea86 100644 --- a/src/gui/painting/qpainter.cpp +++ b/src/gui/painting/qpainter.cpp @@ -7480,67 +7480,63 @@ void qt_format_text(const QFont &fnt, const QRectF &_r, if (!painter) tf |= Qt::TextDontPrint; - int maxUnderlines = 0; + uint maxUnderlines = 0; int numUnderlines = 0; - int underlinePositionStack[32]; - int *underlinePositions = underlinePositionStack; + QVarLengthArray<int, 32> underlinePositions(1); QFontMetricsF fm(fnt); - QString text = str; + int offset = 0; +start_lenghtVariant: + bool hasMoreLenghtVariants = false; // compatible behaviour to the old implementation. Replace // tabs by spaces - QChar *chr = text.data(); - const QChar *end = chr + str.length(); bool has_tab = false; - while (chr != end) { - if (*chr == QLatin1Char('\r') || (singleline && *chr == QLatin1Char('\n'))) { - *chr = QLatin1Char(' '); - } else if (*chr == QLatin1Char('\n')) { - *chr = QChar::LineSeparator; - } else if (*chr == QLatin1Char('&')) { + int old_offset = offset; + for (; offset < text.length(); offset++) { + QChar chr = text.at(offset); + if (chr == QLatin1Char('\r') || (singleline && chr == QLatin1Char('\n'))) { + text[offset] = QLatin1Char(' '); + } else if (chr == QLatin1Char('\n')) { + chr = QChar::LineSeparator; + } else if (chr == QLatin1Char('&')) { ++maxUnderlines; - } else if (*chr == QLatin1Char('\t')) { - has_tab = true; - } - ++chr; - } - if (has_tab) { - if (!expandtabs) { - chr = text.data(); - while (chr != end) { - if (*chr == QLatin1Char('\t')) - *chr = QLatin1Char(' '); - ++chr; + } else if (chr == QLatin1Char('\t')) { + if (!expandtabs) { + text[offset] = QLatin1Char(' '); + } else if (!tabarraylen && !tabstops) { + tabstops = qRound(fm.width(QLatin1Char('x'))*8); } - } else if (!tabarraylen && !tabstops) { - tabstops = qRound(fm.width(QLatin1Char('x'))*8); + has_tab = true; + } else if (chr == QChar(ushort(0x9c))) { + // string with multiple length variants + hasMoreLenghtVariants = true; + break; } } - if (hidemnmemonic || showmnemonic) { - if (maxUnderlines > 32) - underlinePositions = new int[maxUnderlines]; - QChar *cout = text.data(); + int length = offset - old_offset; + if ((hidemnmemonic || showmnemonic) && maxUnderlines > 0) { + underlinePositions.resize(maxUnderlines + 1); + + QChar *cout = text.data() + old_offset; QChar *cin = cout; - int l = str.length(); + int l = length; while (l) { if (*cin == QLatin1Char('&')) { ++cin; + --length; --l; if (!l) break; if (*cin != QLatin1Char('&') && !hidemnmemonic) - underlinePositions[numUnderlines++] = cout - text.unicode(); + underlinePositions[numUnderlines++] = cout - text.data() - old_offset; } *cout = *cin; ++cout; ++cin; --l; } - int newlen = cout - text.unicode(); - if (newlen != text.length()) - text.resize(newlen); } // no need to do extra work for underlines if we don't paint @@ -7551,13 +7547,12 @@ void qt_format_text(const QFont &fnt, const QRectF &_r, qreal height = 0; qreal width = 0; - QStackTextEngine engine(text, fnt); + QString finalText = text.mid(old_offset, length); + QStackTextEngine engine(finalText, fnt); if (option) { engine.option = *option; } - - engine.option.setTextDirection(layout_direction); if (tf & Qt::AlignJustify) engine.option.setAlignment(Qt::AlignJustify); @@ -7571,9 +7566,9 @@ void qt_format_text(const QFont &fnt, const QRectF &_r, engine.forceJustification = true; QTextLayout textLayout(&engine); textLayout.setCacheEnabled(true); - textLayout.engine()->underlinePositions = underlinePositions; + textLayout.engine()->underlinePositions = underlinePositions.data(); - if (text.isEmpty()) { + if (finalText.isEmpty()) { height = fm.height(); width = 0; tf |= Qt::TextDontPrint; @@ -7638,6 +7633,11 @@ void qt_format_text(const QFont &fnt, const QRectF &_r, } } QRectF bounds = QRectF(r.x() + xoff, r.y() + yoff, width, height); + + if (hasMoreLenghtVariants && !(tf & Qt::TextLongestVariant) && !r.contains(bounds)) { + offset++; + goto start_lenghtVariant; + } if (brect) *brect = bounds; @@ -7664,9 +7664,6 @@ void qt_format_text(const QFont &fnt, const QRectF &_r, painter->restore(); } } - - if (underlinePositions != underlinePositionStack) - delete [] underlinePositions; } /*! diff --git a/src/gui/styles/qstylehelper.cpp b/src/gui/styles/qstylehelper.cpp index 4877ec4..402c4d1 100644 --- a/src/gui/styles/qstylehelper.cpp +++ b/src/gui/styles/qstylehelper.cpp @@ -250,8 +250,8 @@ void drawDial(const QStyleOptionSlider *option, QPainter *painter) QRadialGradient shadowGradient(shadowRect.center().x(), shadowRect.center().y(), shadowRect.width()/2.0, shadowRect.center().x(), shadowRect.center().y()); - shadowGradient.setColorAt(0.91, QColor(0, 0, 0, 40)); - shadowGradient.setColorAt(1.0, Qt::transparent); + shadowGradient.setColorAt(qreal(0.91), QColor(0, 0, 0, 40)); + shadowGradient.setColorAt(qreal(1.0), Qt::transparent); p->setBrush(shadowGradient); p->setPen(Qt::NoPen); p->translate(shadowSize, shadowSize); @@ -263,8 +263,8 @@ void drawDial(const QStyleOptionSlider *option, QPainter *painter) br.width()*1.3, br.center().x(), br.center().y() - br.height()/2); gradient.setColorAt(0, buttonColor.lighter(110)); - gradient.setColorAt(0.5, buttonColor); - gradient.setColorAt(0.501, buttonColor.darker(102)); + gradient.setColorAt(qreal(0.5), buttonColor); + gradient.setColorAt(qreal(0.501), buttonColor.darker(102)); gradient.setColorAt(1, buttonColor.darker(115)); p->setBrush(gradient); } else { @@ -290,21 +290,21 @@ void drawDial(const QStyleOptionSlider *option, QPainter *painter) END_STYLE_PIXMAPCACHE - QPointF dp = calcRadialPos(option, 0.70); + QPointF dp = calcRadialPos(option, qreal(0.70)); buttonColor = buttonColor.lighter(104); - buttonColor.setAlphaF(0.8); - const qreal ds = r/7.0; + buttonColor.setAlphaF(qreal(0.8)); + const qreal ds = r/qreal(7.0); QRectF dialRect(dp.x() - ds, dp.y() - ds, 2*ds, 2*ds); QRadialGradient dialGradient(dialRect.center().x() + dialRect.width()/2, dialRect.center().y() + dialRect.width(), dialRect.width()*2, dialRect.center().x(), dialRect.center().y()); dialGradient.setColorAt(1, buttonColor.darker(140)); - dialGradient.setColorAt(0.4, buttonColor.darker(120)); + dialGradient.setColorAt(qreal(0.4), buttonColor.darker(120)); dialGradient.setColorAt(0, buttonColor.darker(110)); if (penSize > 3.0) { painter->setPen(QPen(QColor(0, 0, 0, 25), penSize)); - painter->drawLine(calcRadialPos(option, 0.90), calcRadialPos(option, 0.96)); + painter->drawLine(calcRadialPos(option, qreal(0.90)), calcRadialPos(option, qreal(0.96))); } painter->setBrush(dialGradient); diff --git a/src/gui/text/qfontmetrics.cpp b/src/gui/text/qfontmetrics.cpp index 012c0f6..4229d5b 100644 --- a/src/gui/text/qfontmetrics.cpp +++ b/src/gui/text/qfontmetrics.cpp @@ -528,12 +528,14 @@ int QFontMetrics::rightBearing(QChar ch) const */ int QFontMetrics::width(const QString &text, int len) const { + int pos = text.indexOf(QLatin1Char('\x9c')); + QString txt = (pos == -1) ? text : text.left(pos); if (len < 0) - len = text.length(); + len = txt.length(); if (len == 0) return 0; - QTextEngine layout(text, d); + QTextEngine layout(txt, d); layout.ignoreBidi = true; return qRound(layout.width(0, len)); } @@ -798,7 +800,7 @@ QRect QFontMetrics::boundingRect(const QRect &rect, int flags, const QString &te */ QSize QFontMetrics::size(int flags, const QString &text, int tabStops, int *tabArray) const { - return boundingRect(QRect(0,0,0,0), flags, text, tabStops, tabArray).size(); + return boundingRect(QRect(0,0,0,0), flags | Qt::TextLongestVariant, text, tabStops, tabArray).size(); } /*! @@ -859,8 +861,21 @@ QRect QFontMetrics::tightBoundingRect(const QString &text) const language. */ -QString QFontMetrics::elidedText(const QString &text, Qt::TextElideMode mode, int width, int flags) const -{ +QString QFontMetrics::elidedText(const QString &_text, Qt::TextElideMode mode, int width, int flags) const +{ + QString text = _text; + if (!(flags & Qt::TextLongestVariant)) { + int posA = 0; + int posB = text.indexOf(QLatin1Char('\x9c')); + while (posB >= 0) { + QString portion = text.mid(posA, posB - posA); + if (size(flags, portion).width() <= width) + return portion; + posA = posB + 1; + posB = text.indexOf(QLatin1Char('\x9c'), posA); + } + text = text.mid(posA); + } QStackTextEngine engine(text, QFont(d)); return engine.elidedText(mode, width, flags); } diff --git a/src/gui/text/qtextformat.cpp b/src/gui/text/qtextformat.cpp index a3dd83e..fd0c17f 100644 --- a/src/gui/text/qtextformat.cpp +++ b/src/gui/text/qtextformat.cpp @@ -875,7 +875,8 @@ int QTextFormat::intProperty(int propertyId) const /*! Returns the value of the property specified by \a propertyId. If the - property isn't of QVariant::Double type, 0 is returned instead. + property isn't of QVariant::Double or QMetaType::Float type, 0 is + returned instead. \sa setProperty() boolProperty() intProperty() stringProperty() colorProperty() lengthProperty() lengthVectorProperty() Property */ @@ -884,9 +885,9 @@ qreal QTextFormat::doubleProperty(int propertyId) const if (!d) return 0.; const QVariant prop = d->property(propertyId); - if (prop.type() != QVariant::Double) + if (prop.type() != QVariant::Double && prop.type() != QMetaType::Float) return 0.; - return prop.toDouble(); // #### + return qVariantValue<qreal>(prop); } /*! diff --git a/tests/auto/qfileinfo/tst_qfileinfo.cpp b/tests/auto/qfileinfo/tst_qfileinfo.cpp index a87e306..306ca49 100644 --- a/tests/auto/qfileinfo/tst_qfileinfo.cpp +++ b/tests/auto/qfileinfo/tst_qfileinfo.cpp @@ -147,6 +147,9 @@ private slots: void isBundle_data(); void isBundle(); + void isLocalFs_data(); + void isLocalFs(); + void refresh(); #if defined(Q_OS_WIN) && !defined(Q_OS_WINCE) @@ -974,6 +977,22 @@ void tst_QFileInfo::isHidden_data() foreach (const QFileInfo& info, QDir::drives()) { QTest::newRow(qPrintable("drive." + info.path())) << info.path() << false; } + +#if defined(Q_OS_WIN) && !defined(Q_OS_WINCE) + QTest::newRow("C:/RECYCLER") << QString::fromLatin1("C:/RECYCLER") << true; + QTest::newRow("C:/RECYCLER/.") << QString::fromLatin1("C:/RECYCLER/.") << false; + QTest::newRow("C:/RECYCLER/..") << QString::fromLatin1("C:/RECYCLER/..") << false; +#endif +#if defined(Q_OS_UNIX) + QTest::newRow("~/.qt") << QDir::homePath() + QString("/.qt") << true; + QTest::newRow("~/.qt/.") << QDir::homePath() + QString("/.qt/.") << false; + QTest::newRow("~/.qt/..") << QDir::homePath() + QString("/.qt/..") << false; +#endif + +#if !defined(Q_OS_WIN) + QTest::newRow("/bin/") << QString::fromLatin1("/bin/") << false; +#endif + #ifdef Q_OS_MAC QTest::newRow("mac_etc") << QString::fromLatin1("/etc") << true; QTest::newRow("mac_private_etc") << QString::fromLatin1("/private/etc") << false; @@ -1008,6 +1027,29 @@ void tst_QFileInfo::isBundle() QCOMPARE(fi.isBundle(), isBundle); } +void tst_QFileInfo::isLocalFs_data() +{ + QTest::addColumn<QString>("path"); + QTest::addColumn<bool>("isLocalFs"); + + QTest::newRow("local root") << QString::fromLatin1("/") << true; + QTest::newRow("local non-existent file") << QString::fromLatin1("/abrakadabra.boo") << true; + + QTest::newRow("qresource root") << QString::fromLatin1(":/") << false; +} + +void tst_QFileInfo::isLocalFs() +{ + QFETCH(QString, path); + QFETCH(bool, isLocalFs); + + QFileInfo info(path); + QFileInfoPrivate *privateInfo = getPrivate(info); + QVERIFY(privateInfo->data->fileEngine); + QCOMPARE(bool(privateInfo->data->fileEngine->fileFlags(QAbstractFileEngine::LocalDiskFlag) + & QAbstractFileEngine::LocalDiskFlag), isLocalFs); +} + void tst_QFileInfo::refresh() { #if defined(Q_OS_WINCE) diff --git a/tests/auto/qfontmetrics/tst_qfontmetrics.cpp b/tests/auto/qfontmetrics/tst_qfontmetrics.cpp index 5658055..cae1126 100644 --- a/tests/auto/qfontmetrics/tst_qfontmetrics.cpp +++ b/tests/auto/qfontmetrics/tst_qfontmetrics.cpp @@ -71,6 +71,7 @@ private slots: void elidedText(); void veryNarrowElidedText(); void averageCharWidth(); + void elidedMultiLenght(); }; tst_QFontMetrics::tst_QFontMetrics() @@ -168,7 +169,8 @@ void tst_QFontMetrics::elidedText_data() QTest::addColumn<QFont>("font"); QTest::addColumn<QString>("text"); - QTest::newRow("helvetica hello") << QFont("helvetica",10) << QString("hello"); + QTest::newRow("helvetica hello") << QFont("helvetica",10) << QString("hello") ; + QTest::newRow("helvetica hello &Bye") << QFont("helvetica",10) << QString("hello&Bye") ; } @@ -178,9 +180,9 @@ void tst_QFontMetrics::elidedText() QFETCH(QString, text); QFontMetrics fm(font); int w = fm.width(text); - QString newtext = fm.elidedText(text,Qt::ElideRight,w); + QString newtext = fm.elidedText(text,Qt::ElideRight,w, 0); QCOMPARE(text,newtext); // should not elide - newtext = fm.elidedText(text,Qt::ElideRight,w-1); + newtext = fm.elidedText(text,Qt::ElideRight,w-1, 0); QVERIFY(text != newtext); // should elide } @@ -201,5 +203,27 @@ void tst_QFontMetrics::averageCharWidth() QVERIFY(fmf.averageCharWidth() != 0); } +void tst_QFontMetrics::elidedMultiLenght() +{ + QString text1 = "Long Text 1\x9cShorter\x9csmall"; + QString text1_long = "Long Text 1"; + QString text1_short = "Shorter"; + QString text1_small = "small"; + QFontMetrics fm = QFontMetrics(QFont()); + int width_long = fm.width(text1_long); + QCOMPARE(fm.elidedText(text1,Qt::ElideRight, 8000), text1_long); + QCOMPARE(fm.elidedText(text1,Qt::ElideRight, width_long), text1_long); + QCOMPARE(fm.elidedText(text1,Qt::ElideRight, width_long - 1), text1_short); + int width_short = fm.width(text1_short); + QCOMPARE(fm.elidedText(text1,Qt::ElideRight, width_short), text1_short); + QCOMPARE(fm.elidedText(text1,Qt::ElideRight, width_short - 1), text1_small); + + QChar ellipsisChar(0x2026); + QString text1_el = QString::fromLatin1("sm") + ellipsisChar; + int width_small = fm.width(text1_el); + QCOMPARE(fm.elidedText(text1,Qt::ElideRight, width_small + 1), text1_el); + +} + QTEST_MAIN(tst_QFontMetrics) #include "tst_qfontmetrics.moc" diff --git a/tests/auto/qpixmapcache/tst_qpixmapcache.cpp b/tests/auto/qpixmapcache/tst_qpixmapcache.cpp index e71bd5d..7866df8 100644 --- a/tests/auto/qpixmapcache/tst_qpixmapcache.cpp +++ b/tests/auto/qpixmapcache/tst_qpixmapcache.cpp @@ -392,14 +392,19 @@ void tst_QPixmapCache::clear() QPixmap p1(10, 10); p1.fill(Qt::red); - for (int i = 0; i < 20000; ++i) +#ifdef Q_OS_WINCE + const int numberOfKeys = 10000; +#else + const int numberOfKeys = 20000; +#endif + for (int i = 0; i < numberOfKeys; ++i) QVERIFY(QPixmapCache::find("x" + QString::number(i)) == 0); - for (int j = 0; j < 20000; ++j) + for (int j = 0; j < numberOfKeys; ++j) QPixmapCache::insert(QString::number(j), p1); int num = 0; - for (int k = 0; k < 20000; ++k) { + for (int k = 0; k < numberOfKeys; ++k) { if (QPixmapCache::find(QString::number(k), p1)) ++num; } @@ -407,7 +412,7 @@ void tst_QPixmapCache::clear() QPixmapCache::clear(); - for (int k = 0; k < 20000; ++k) + for (int k = 0; k < numberOfKeys; ++k) QVERIFY(QPixmapCache::find(QString::number(k)) == 0); //The int part of the API @@ -415,12 +420,12 @@ void tst_QPixmapCache::clear() p2.fill(Qt::red); QList<QPixmapCache::Key> keys; - for (int k = 0; k < 20000; ++k) + for (int k = 0; k < numberOfKeys; ++k) keys.append(QPixmapCache::insert(p2)); QPixmapCache::clear(); - for (int k = 0; k < 20000; ++k) { + for (int k = 0; k < numberOfKeys; ++k) { QVERIFY(QPixmapCache::find(keys.at(k), &p1) == 0); QCOMPARE(getPrivate(keys[k])->isValid, false); } |