Add Windows XP support (#146)
* improve Qt 5.6 support * switch registry API to Windows XP compatible Unicode API * update docs * add comment for `CONFIG += c++14 c++17` in qmake .pro files * fix logic for lockFile
This commit is contained in:
parent
539439b0a8
commit
a62acc2eb0
|
@ -7,6 +7,9 @@
|
||||||
/packages/debian/01-in-docker.sh eol=lf
|
/packages/debian/01-in-docker.sh eol=lf
|
||||||
/packages/debian/rules eol=lf
|
/packages/debian/rules eol=lf
|
||||||
|
|
||||||
|
# files to be processed with Unix utils
|
||||||
|
/packages/windows/qtbase-5.6.3-redpanda.patch eol=lf
|
||||||
|
|
||||||
# text files to be packed
|
# text files to be packed
|
||||||
/packages/appimage/AppRun.sh eol=lf
|
/packages/appimage/AppRun.sh eol=lf
|
||||||
/packages/debian/changelog eol=lf
|
/packages/debian/changelog eol=lf
|
||||||
|
|
15
BUILD.md
15
BUILD.md
|
@ -4,6 +4,8 @@
|
||||||
|
|
||||||
# Windows
|
# Windows
|
||||||
|
|
||||||
|
For Windows 7 or later:
|
||||||
|
|
||||||
| Library + Toolchain \ Target | x86 | x64 | ARM64 |
|
| Library + Toolchain \ Target | x86 | x64 | ARM64 |
|
||||||
| ---------------------------- | --- | --- | ----- |
|
| ---------------------------- | --- | --- | ----- |
|
||||||
| MSYS2 + GNU-based MinGW | ✔️ | ✔️ | ❌ |
|
| MSYS2 + GNU-based MinGW | ✔️ | ✔️ | ❌ |
|
||||||
|
@ -19,6 +21,19 @@ Notes for Windows on ARM:
|
||||||
- However, ARM64EC will allow users to use their favorite input methods, fancy Qt styles.
|
- However, ARM64EC will allow users to use their favorite input methods, fancy Qt styles.
|
||||||
- With the [ARM32 deprecation in Windows 11 Insider Preview Build 25905](https://blogs.windows.com/windows-insider/2023/07/12/announcing-windows-11-insider-preview-build-25905/), ARM32 support will never be added.
|
- With the [ARM32 deprecation in Windows 11 Insider Preview Build 25905](https://blogs.windows.com/windows-insider/2023/07/12/announcing-windows-11-insider-preview-build-25905/), ARM32 support will never be added.
|
||||||
|
|
||||||
|
For legacy Windows (NT 5.1 – 6.0):
|
||||||
|
|
||||||
|
| Library + Toolchain \ Target | x86 | x64 |
|
||||||
|
| ---------------------------- | --- | --- |
|
||||||
|
| Qt 5.6 from [patched source](packages/windows/qtbase-5.6.3-redpanda.patch) + MinGW | ✔️ | ✔️ |
|
||||||
|
|
||||||
|
Notes for legacy Windows:
|
||||||
|
- Supported Windows versions:
|
||||||
|
- Windows XP SP3 or later;
|
||||||
|
- Windows Server 2003 x64 Edition (a.k.a. Windows XP x64 Edition) SP2 or later.
|
||||||
|
- Windows 7 x64 or later required as build host.
|
||||||
|
- Here is [a script](packages/windows/build-qt5.6-mingw-static.sh) for building Qt 5.6 from source alongside official Qt installation (with Qt.io MinGW GCC 8.1.0).
|
||||||
|
|
||||||
## MSYS2 Qt Library with MinGW Toolchain (Recommended)
|
## MSYS2 Qt Library with MinGW Toolchain (Recommended)
|
||||||
|
|
||||||
Red Panda C++ should work with any MinGW toolchain from MSYS2, including GCCs and Clangs in three GNU-based environments (MINGW32, MINGW64 and UCRT64), and Clangs in three LLVM-based environments (CLANG32, CLANG64 and CLANGARM64; see also [MSYS2’s document](https://www.msys2.org/docs/environments/)), while the following toolchains are frequently tested:
|
Red Panda C++ should work with any MinGW toolchain from MSYS2, including GCCs and Clangs in three GNU-based environments (MINGW32, MINGW64 and UCRT64), and Clangs in three LLVM-based environments (CLANG32, CLANG64 and CLANGARM64; see also [MSYS2’s document](https://www.msys2.org/docs/environments/)), while the following toolchains are frequently tested:
|
||||||
|
|
15
BUILD_cn.md
15
BUILD_cn.md
|
@ -4,6 +4,8 @@
|
||||||
|
|
||||||
# Windows
|
# Windows
|
||||||
|
|
||||||
|
适用于 Windows 7 或更高版本:
|
||||||
|
|
||||||
| 库 + 工具链 \ 目标 | x86 | x64 | ARM64 |
|
| 库 + 工具链 \ 目标 | x86 | x64 | ARM64 |
|
||||||
| ------------------ | --- | --- | ----- |
|
| ------------------ | --- | --- | ----- |
|
||||||
| MSYS2 + 基于 GNU 的 MinGW | ✔️ | ✔️ | ❌ |
|
| MSYS2 + 基于 GNU 的 MinGW | ✔️ | ✔️ | ❌ |
|
||||||
|
@ -19,6 +21,19 @@
|
||||||
- 但是 ARM64EC 可以支持用户习惯的输入法和喜欢的 Qt 样式。
|
- 但是 ARM64EC 可以支持用户习惯的输入法和喜欢的 Qt 样式。
|
||||||
- 随着 [Windows 11 Insider Preview Build 25905 弃用 ARM32](https://blogs.windows.com/windows-insider/2023/07/12/announcing-windows-11-insider-preview-build-25905/),小熊猫 C++ 今后也不会添加 ARM32 支持了。
|
- 随着 [Windows 11 Insider Preview Build 25905 弃用 ARM32](https://blogs.windows.com/windows-insider/2023/07/12/announcing-windows-11-insider-preview-build-25905/),小熊猫 C++ 今后也不会添加 ARM32 支持了。
|
||||||
|
|
||||||
|
适用于旧版 Windows(NT 5.1 – 6.0):
|
||||||
|
|
||||||
|
| 库 + 工具链 \ 目标 | x86 | x64 |
|
||||||
|
| ------------------ | --- | --- |
|
||||||
|
| 从[打过补丁的源代码](packages/windows/qtbase-5.6.3-redpanda.patch)构建的 Qt 5.6 + MinGW | ✔️ | ✔️ |
|
||||||
|
|
||||||
|
关于旧版 Windows 的注记:
|
||||||
|
- 支持的 Windows 版本:
|
||||||
|
- Windows XP SP3 或更高版本;
|
||||||
|
- Windows Server 2003 x64 Edition(也叫 Windows XP x64 Edition)SP2 或更高版本。
|
||||||
|
- 构建环境需要 Windows 7 x64 或更高版本。
|
||||||
|
- 从源代码构建 Qt 5.6 并与官方 Qt 安装共存可参考[这个脚本](packages/windows/build-qt5.6-mingw-static.sh)(使用 Qt.io MinGW GCC 8.1.0)。
|
||||||
|
|
||||||
## MSYS2 的 Qt 库 + MinGW 工具链(推荐)
|
## MSYS2 的 Qt 库 + MinGW 工具链(推荐)
|
||||||
|
|
||||||
小熊猫 C++ 应该能在 MSYS2 的 MinGW 工具链上构建,包括 3 个基于 GNU 的环境(MINGW32、MINGW64、UCRT64)中的 GCC 和 Clang,以及 3 个基于 LLVM 的环境(CLANG32、CLANG64、CLANGARM64)中的 Clang,关于环境的详情可参考 [MSYS2 的文档](https://www.msys2.org/docs/environments/)。以下几个工具链测试较充分:
|
小熊猫 C++ 应该能在 MSYS2 的 MinGW 工具链上构建,包括 3 个基于 GNU 的环境(MINGW32、MINGW64、UCRT64)中的 GCC 和 Clang,以及 3 个基于 LLVM 的环境(CLANG32、CLANG64、CLANGARM64)中的 Clang,关于环境的详情可参考 [MSYS2 的文档](https://www.msys2.org/docs/environments/)。以下几个工具链测试较充分:
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
QT += core gui printsupport network svg xml widgets
|
QT += core gui printsupport network svg xml widgets
|
||||||
|
|
||||||
CONFIG += c++17
|
# without `c++14` old versions of qmake will explicitly set `-std=gnu++98`
|
||||||
|
CONFIG += c++14 c++17
|
||||||
CONFIG += nokey
|
CONFIG += nokey
|
||||||
|
|
||||||
# uncomment the following line to enable vcs (git) support
|
# uncomment the following line to enable vcs (git) support
|
||||||
|
@ -44,9 +45,10 @@ isEmpty(LIBEXECDIR) {
|
||||||
LIBEXECDIR = $${PREFIX}/libexec
|
LIBEXECDIR = $${PREFIX}/libexec
|
||||||
}
|
}
|
||||||
|
|
||||||
# windows 7 is the minimum windows version
|
|
||||||
win32: {
|
win32: {
|
||||||
DEFINES += _WIN32_WINNT=0x0601
|
DEFINES += _WIN32_WINNT=0x0501
|
||||||
|
LIBS += -lpsapi # GetModuleFileNameEx, GetProcessMemoryInfo
|
||||||
|
LIBS += -lshlwapi # SHDeleteKey
|
||||||
}
|
}
|
||||||
|
|
||||||
DEFINES += PREFIX=\\\"$${PREFIX}\\\"
|
DEFINES += PREFIX=\\\"$${PREFIX}\\\"
|
||||||
|
|
|
@ -20,6 +20,7 @@
|
||||||
#include "runner.h"
|
#include "runner.h"
|
||||||
#include <QProcess>
|
#include <QProcess>
|
||||||
#include <QSemaphore>
|
#include <QSemaphore>
|
||||||
|
#include <memory>
|
||||||
|
|
||||||
class ExecutableRunner : public Runner
|
class ExecutableRunner : public Runner
|
||||||
{
|
{
|
||||||
|
|
|
@ -1888,7 +1888,7 @@ void Editor::onAutoBackupTimer()
|
||||||
if (mBackupTime>lastModifyTime())
|
if (mBackupTime>lastModifyTime())
|
||||||
return;
|
return;
|
||||||
QDateTime current=QDateTime::currentDateTime();
|
QDateTime current=QDateTime::currentDateTime();
|
||||||
if (current.toSecsSinceEpoch()-lastModifyTime().toSecsSinceEpoch()<=3)
|
if (lastModifyTime().secsTo(current) <= 3)
|
||||||
return;
|
return;
|
||||||
saveAutoBackup();
|
saveAutoBackup();
|
||||||
}
|
}
|
||||||
|
|
|
@ -28,6 +28,7 @@
|
||||||
#include <QDesktopWidget>
|
#include <QDesktopWidget>
|
||||||
#include <QDir>
|
#include <QDir>
|
||||||
#include <QScreen>
|
#include <QScreen>
|
||||||
|
#include <QLockFile>
|
||||||
#include "common.h"
|
#include "common.h"
|
||||||
#include "colorscheme.h"
|
#include "colorscheme.h"
|
||||||
#include "iconsmanager.h"
|
#include "iconsmanager.h"
|
||||||
|
@ -58,7 +59,13 @@ public:
|
||||||
bool nativeEventFilter(const QByteArray &eventType, void *message, long *result) override;
|
bool nativeEventFilter(const QByteArray &eventType, void *message, long *result) override;
|
||||||
};
|
};
|
||||||
|
|
||||||
#define WM_USER_OPEN_FILE (WM_USER+1)
|
#ifndef WM_DPICHANGED
|
||||||
|
# define WM_DPICHANGED 0x02e0
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#define WM_APP_OPEN_FILE (WM_APP + 6736 /* “OPEN” on dial pad */)
|
||||||
|
static_assert(WM_APP_OPEN_FILE < 0xc000);
|
||||||
|
|
||||||
HWND prevAppInstance = NULL;
|
HWND prevAppInstance = NULL;
|
||||||
BOOL CALLBACK GetPreviousInstanceCallback(HWND hwnd, LPARAM param){
|
BOOL CALLBACK GetPreviousInstanceCallback(HWND hwnd, LPARAM param){
|
||||||
BOOL result = TRUE;
|
BOOL result = TRUE;
|
||||||
|
@ -144,7 +151,7 @@ bool WindowLogoutEventFilter::nativeEventFilter(const QByteArray & /*eventType*/
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case WM_USER_OPEN_FILE: {
|
case WM_APP_OPEN_FILE: {
|
||||||
QSharedMemory sharedMemory("RedPandaCpp/openfiles");
|
QSharedMemory sharedMemory("RedPandaCpp/openfiles");
|
||||||
if (sharedMemory.attach()) {
|
if (sharedMemory.attach()) {
|
||||||
QBuffer buffer;
|
QBuffer buffer;
|
||||||
|
@ -184,7 +191,7 @@ bool sendFilesToInstance() {
|
||||||
const char *from = buffer.data().data();
|
const char *from = buffer.data().data();
|
||||||
memcpy(to, from, qMin(sharedMemory.size(), size));
|
memcpy(to, from, qMin(sharedMemory.size(), size));
|
||||||
sharedMemory.unlock();
|
sharedMemory.unlock();
|
||||||
SendMessage(prevInstance,WM_USER_OPEN_FILE,0,0);
|
SendMessage(prevInstance,WM_APP_OPEN_FILE,0,0);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -270,7 +277,7 @@ int main(int argc, char *argv[])
|
||||||
|
|
||||||
app.setAttribute(Qt::AA_UseHighDpiPixmaps);
|
app.setAttribute(Qt::AA_UseHighDpiPixmaps);
|
||||||
|
|
||||||
QFile tempFile(QDir::tempPath()+QDir::separator()+"RedPandaDevCppStartUp.lock");
|
QLockFile lockFile(QDir::tempPath()+QDir::separator()+"RedPandaDevCppStartUp.lock");
|
||||||
{
|
{
|
||||||
bool firstRun;
|
bool firstRun;
|
||||||
QString settingFilename = getSettingFilename(QString(), firstRun);
|
QString settingFilename = getSettingFilename(QString(), firstRun);
|
||||||
|
@ -288,7 +295,7 @@ int main(int argc, char *argv[])
|
||||||
if (openInSingleInstance) {
|
if (openInSingleInstance) {
|
||||||
int openCount = 0;
|
int openCount = 0;
|
||||||
while (true) {
|
while (true) {
|
||||||
if (tempFile.open(QFile::NewOnly))
|
if (lockFile.tryLock())
|
||||||
break;
|
break;
|
||||||
QThread::msleep(100);
|
QThread::msleep(100);
|
||||||
openCount++;
|
openCount++;
|
||||||
|
@ -299,7 +306,7 @@ int main(int argc, char *argv[])
|
||||||
if (app.arguments().length()>=2 && openCount<100) {
|
if (app.arguments().length()>=2 && openCount<100) {
|
||||||
#ifdef Q_OS_WIN
|
#ifdef Q_OS_WIN
|
||||||
if (sendFilesToInstance()) {
|
if (sendFilesToInstance()) {
|
||||||
tempFile.remove();
|
lockFile.unlock();
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
@ -314,7 +321,7 @@ int main(int argc, char *argv[])
|
||||||
QDir::setCurrent(QStandardPaths::standardLocations(QStandardPaths::DocumentsLocation)[0]);
|
QDir::setCurrent(QStandardPaths::standardLocations(QStandardPaths::DocumentsLocation)[0]);
|
||||||
}
|
}
|
||||||
if (settingFilename.isEmpty()) {
|
if (settingFilename.isEmpty()) {
|
||||||
tempFile.remove();
|
lockFile.unlock();
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
QString language;
|
QString language;
|
||||||
|
@ -433,9 +440,8 @@ int main(int argc, char *argv[])
|
||||||
WindowLogoutEventFilter filter;
|
WindowLogoutEventFilter filter;
|
||||||
app.installNativeEventFilter(&filter);
|
app.installNativeEventFilter(&filter);
|
||||||
#endif
|
#endif
|
||||||
if (tempFile.isOpen()) {
|
if (lockFile.isLocked()) {
|
||||||
tempFile.close();
|
lockFile.unlock();
|
||||||
tempFile.remove();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
int retCode = app.exec();
|
int retCode = app.exec();
|
||||||
|
@ -448,7 +454,7 @@ int main(int argc, char *argv[])
|
||||||
}
|
}
|
||||||
return retCode;
|
return retCode;
|
||||||
} catch (BaseError e) {
|
} catch (BaseError e) {
|
||||||
tempFile.remove();
|
lockFile.unlock();
|
||||||
QMessageBox::critical(nullptr,QApplication::tr("Error"),e.reason());
|
QMessageBox::critical(nullptr,QApplication::tr("Error"),e.reason());
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
|
@ -4505,7 +4505,12 @@ void MainWindow::onFilesViewCreateFile()
|
||||||
fileName = QString("untitled%1").arg(count)+suffix;
|
fileName = QString("untitled%1").arg(count)+suffix;
|
||||||
}
|
}
|
||||||
QFile file(dir.filePath(fileName));
|
QFile file(dir.filePath(fileName));
|
||||||
|
#if QT_VERSION >= QT_VERSION_CHECK(5, 11, 0)
|
||||||
file.open(QFile::NewOnly);
|
file.open(QFile::NewOnly);
|
||||||
|
#else
|
||||||
|
// workaround: try create but do not truncate
|
||||||
|
file.open(QFile::ReadWrite);
|
||||||
|
#endif
|
||||||
QModelIndex newIndex = mFileSystemModel.index(fileName);
|
QModelIndex newIndex = mFileSystemModel.index(fileName);
|
||||||
ui->treeFiles->setCurrentIndex(newIndex);
|
ui->treeFiles->setCurrentIndex(newIndex);
|
||||||
}
|
}
|
||||||
|
|
|
@ -326,7 +326,7 @@ QString CppPreprocessor::getNextPreprocessor()
|
||||||
QString result;
|
QString result;
|
||||||
for (int i=preProcFrom;i<=preProcTo;i++) {
|
for (int i=preProcFrom;i<=preProcTo;i++) {
|
||||||
if (mBuffer[i].endsWith('\\')) {
|
if (mBuffer[i].endsWith('\\')) {
|
||||||
result+=mBuffer[i].leftRef(mBuffer[i].size()-1)+' ';
|
result+=mBuffer[i].left(mBuffer[i].size()-1)+' ';
|
||||||
} else {
|
} else {
|
||||||
result+=mBuffer[i]+' ';
|
result+=mBuffer[i]+' ';
|
||||||
}
|
}
|
||||||
|
|
|
@ -21,6 +21,7 @@
|
||||||
#include <QSet>
|
#include <QSet>
|
||||||
#include <QVector>
|
#include <QVector>
|
||||||
#include <memory>
|
#include <memory>
|
||||||
|
#include <functional>
|
||||||
|
|
||||||
using GetFileStreamCallBack = std::function<bool (const QString&, QStringList&)>;
|
using GetFileStreamCallBack = std::function<bool (const QString&, QStringList&)>;
|
||||||
|
|
||||||
|
|
|
@ -21,6 +21,7 @@
|
||||||
|
|
||||||
#include <QMessageBox>
|
#include <QMessageBox>
|
||||||
#include <windows.h>
|
#include <windows.h>
|
||||||
|
#include <shlwapi.h>
|
||||||
|
|
||||||
EnvironmentFileAssociationWidget::EnvironmentFileAssociationWidget(const QString& name, const QString& group, QWidget *parent) :
|
EnvironmentFileAssociationWidget::EnvironmentFileAssociationWidget(const QString& name, const QString& group, QWidget *parent) :
|
||||||
SettingsWidget(name,group,parent),
|
SettingsWidget(name,group,parent),
|
||||||
|
@ -156,33 +157,33 @@ bool FileAssociationModel::checkAssociation(const QString &extension, const QStr
|
||||||
HKEY key;
|
HKEY key;
|
||||||
LONG result;
|
LONG result;
|
||||||
|
|
||||||
result = RegOpenKeyExA(HKEY_CLASSES_ROOT,extension.toLocal8Bit(),0,KEY_READ,&key);
|
result = RegOpenKeyExW(HKEY_CLASSES_ROOT,extension.toStdWString().c_str(),0,KEY_READ,&key);
|
||||||
RegCloseKey(key);
|
RegCloseKey(key);
|
||||||
if (result != ERROR_SUCCESS )
|
if (result != ERROR_SUCCESS )
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
result = RegOpenKeyExA(HKEY_CLASSES_ROOT,filetype.toLocal8Bit(),0,KEY_READ,&key);
|
result = RegOpenKeyExW(HKEY_CLASSES_ROOT,filetype.toStdWString().c_str(),0,KEY_READ,&key);
|
||||||
RegCloseKey(key);
|
RegCloseKey(key);
|
||||||
if (result != ERROR_SUCCESS )
|
if (result != ERROR_SUCCESS )
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
QString keyString = QString("%1\\Shell\\%2\\Command").arg(filetype).arg(verb);
|
QString keyString = QString("%1\\Shell\\%2\\Command").arg(filetype).arg(verb);
|
||||||
QString value1,value2;
|
QString value1,value2;
|
||||||
if (!readRegistry(HKEY_CLASSES_ROOT,keyString.toLocal8Bit(),"",value1))
|
if (!readRegistry(HKEY_CLASSES_ROOT, keyString, "", value1))
|
||||||
return false;
|
return false;
|
||||||
if (!readRegistry(HKEY_CLASSES_ROOT,extension.toLocal8Bit(),"",value2))
|
if (!readRegistry(HKEY_CLASSES_ROOT, extension, "", value2))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
return (value2 == filetype)
|
return (value2 == filetype)
|
||||||
&& (value1.compare(serverApp,PATH_SENSITIVITY)==0);
|
&& (value1.compare(serverApp,PATH_SENSITIVITY)==0);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool writeRegistry(HKEY parentKey, const QByteArray& subKey, const QByteArray& value) {
|
bool writeRegistry(HKEY parentKey, const QString& subKey, const QString& value) {
|
||||||
DWORD disposition;
|
DWORD disposition;
|
||||||
HKEY key;
|
HKEY key;
|
||||||
LONG result = RegCreateKeyExA(
|
LONG result = RegCreateKeyExW(
|
||||||
parentKey,
|
parentKey,
|
||||||
subKey,
|
subKey.toStdWString().c_str(),
|
||||||
0,
|
0,
|
||||||
NULL,
|
NULL,
|
||||||
REG_OPTION_NON_VOLATILE,
|
REG_OPTION_NON_VOLATILE,
|
||||||
|
@ -190,24 +191,23 @@ bool writeRegistry(HKEY parentKey, const QByteArray& subKey, const QByteArray& v
|
||||||
NULL,
|
NULL,
|
||||||
&key,
|
&key,
|
||||||
&disposition);
|
&disposition);
|
||||||
RegCloseKey(key);
|
|
||||||
if (result != ERROR_SUCCESS ) {
|
if (result != ERROR_SUCCESS ) {
|
||||||
|
RegCloseKey(key);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
result = RegSetKeyValueA(
|
result = RegSetValueExW(
|
||||||
HKEY_CLASSES_ROOT,
|
key,
|
||||||
subKey,
|
L"",
|
||||||
"",
|
0,
|
||||||
REG_SZ,
|
REG_SZ,
|
||||||
(const BYTE*)value.data(),
|
(const BYTE*)value.toStdWString().c_str(),
|
||||||
value.length()+1);
|
(value.length() + 1) * sizeof(wchar_t));
|
||||||
|
RegCloseKey(key);
|
||||||
return result == ERROR_SUCCESS;
|
return result == ERROR_SUCCESS;
|
||||||
}
|
}
|
||||||
bool FileAssociationModel::registerAssociation(const QString &extension, const QString &filetype)
|
bool FileAssociationModel::registerAssociation(const QString &extension, const QString &filetype)
|
||||||
{
|
{
|
||||||
if (!writeRegistry(HKEY_CLASSES_ROOT,
|
if (!writeRegistry(HKEY_CLASSES_ROOT, extension, filetype)){
|
||||||
extension.toLocal8Bit(),
|
|
||||||
filetype.toLocal8Bit())){
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
|
@ -217,12 +217,12 @@ bool FileAssociationModel::unregisterAssociation(const QString &extension)
|
||||||
{
|
{
|
||||||
LONG result;
|
LONG result;
|
||||||
HKEY key;
|
HKEY key;
|
||||||
result = RegOpenKeyExA(HKEY_CLASSES_ROOT,extension.toLocal8Bit(),0,KEY_READ,&key);
|
result = RegOpenKeyExW(HKEY_CLASSES_ROOT, extension.toStdWString().c_str(), 0, KEY_READ, &key);
|
||||||
if (result != ERROR_SUCCESS )
|
if (result != ERROR_SUCCESS )
|
||||||
return true;
|
return true;
|
||||||
RegCloseKey(key);
|
RegCloseKey(key);
|
||||||
|
|
||||||
result = RegDeleteTreeA(HKEY_CLASSES_ROOT,extension.toLocal8Bit());
|
result = SHDeleteKeyW(HKEY_CLASSES_ROOT, extension.toStdWString().c_str());
|
||||||
return result == ERROR_SUCCESS;
|
return result == ERROR_SUCCESS;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -231,33 +231,27 @@ bool FileAssociationModel::unregisterFileType(const QString &fileType)
|
||||||
{
|
{
|
||||||
LONG result;
|
LONG result;
|
||||||
HKEY key;
|
HKEY key;
|
||||||
result = RegOpenKeyExA(HKEY_CLASSES_ROOT,fileType.toLocal8Bit(),0,KEY_READ,&key);
|
result = RegOpenKeyExW(HKEY_CLASSES_ROOT, fileType.toStdWString().c_str(), 0, KEY_READ, &key);
|
||||||
if (result != ERROR_SUCCESS )
|
if (result != ERROR_SUCCESS )
|
||||||
return true;
|
return true;
|
||||||
RegCloseKey(key);
|
RegCloseKey(key);
|
||||||
|
|
||||||
result = RegDeleteTreeA(HKEY_CLASSES_ROOT,fileType.toLocal8Bit());
|
result = SHDeleteKeyW(HKEY_CLASSES_ROOT, fileType.toStdWString().c_str());
|
||||||
return result == ERROR_SUCCESS;
|
return result == ERROR_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool FileAssociationModel::registerFileType(const QString &filetype, const QString &description, const QString &verb, const QString &serverApp, int icon)
|
bool FileAssociationModel::registerFileType(const QString &filetype, const QString &description, const QString &verb, const QString &serverApp, int icon)
|
||||||
{
|
{
|
||||||
if (!writeRegistry(HKEY_CLASSES_ROOT,
|
if (!writeRegistry(HKEY_CLASSES_ROOT, filetype, description))
|
||||||
filetype.toLocal8Bit(),
|
|
||||||
description.toLocal8Bit()))
|
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
QString keyString = QString("%1\\DefaultIcon").arg(filetype);
|
QString keyString = QString("%1\\DefaultIcon").arg(filetype);
|
||||||
QString value = QString("%1,%2").arg(serverApp).arg(icon);
|
QString value = QString("%1,%2").arg(serverApp).arg(icon);
|
||||||
if (!writeRegistry(HKEY_CLASSES_ROOT,
|
if (!writeRegistry(HKEY_CLASSES_ROOT, keyString, value))
|
||||||
keyString.toLocal8Bit(),
|
|
||||||
value.toLocal8Bit()))
|
|
||||||
return false;
|
return false;
|
||||||
keyString = QString("%1\\Shell\\%2\\Command").arg(filetype).arg(verb);
|
keyString = QString("%1\\Shell\\%2\\Command").arg(filetype).arg(verb);
|
||||||
value = serverApp+" \"%1\"";
|
value = serverApp+" \"%1\"";
|
||||||
if (!writeRegistry(HKEY_CLASSES_ROOT,
|
if (!writeRegistry(HKEY_CLASSES_ROOT, keyString, value))
|
||||||
keyString.toLocal8Bit(),
|
|
||||||
value.toLocal8Bit()))
|
|
||||||
return false;
|
return false;
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
|
@ -19,6 +19,7 @@
|
||||||
|
|
||||||
#include <QAbstractListModel>
|
#include <QAbstractListModel>
|
||||||
#include <QWidget>
|
#include <QWidget>
|
||||||
|
#include <memory>
|
||||||
#include "settingswidget.h"
|
#include "settingswidget.h"
|
||||||
|
|
||||||
namespace Ui {
|
namespace Ui {
|
||||||
|
|
|
@ -389,9 +389,9 @@ bool isGreenEdition()
|
||||||
if (!gIsGreenEditionInited) {
|
if (!gIsGreenEditionInited) {
|
||||||
QString keyString = QString("Software\\Microsoft\\Windows\\CurrentVersion\\Uninstall\\RedPanda-C++");
|
QString keyString = QString("Software\\Microsoft\\Windows\\CurrentVersion\\Uninstall\\RedPanda-C++");
|
||||||
QString value;
|
QString value;
|
||||||
if (!readRegistry(HKEY_LOCAL_MACHINE,keyString.toLocal8Bit(),"UninstallString",value)) {
|
if (!readRegistry(HKEY_LOCAL_MACHINE, keyString, "UninstallString", value)) {
|
||||||
keyString = "SOFTWARE\\WOW6432Node\\Microsoft\\Windows\\CurrentVersion\\Uninstall\\RedPanda-C++";
|
keyString = "SOFTWARE\\WOW6432Node\\Microsoft\\Windows\\CurrentVersion\\Uninstall\\RedPanda-C++";
|
||||||
if (!readRegistry(HKEY_LOCAL_MACHINE,keyString.toLocal8Bit(),"UninstallString",value)) {
|
if (!readRegistry(HKEY_LOCAL_MACHINE, keyString, "UninstallString", value)) {
|
||||||
value="";
|
value="";
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -465,27 +465,30 @@ void executeFile(const QString &fileName, const QString ¶ms, const QString &
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef Q_OS_WIN
|
#ifdef Q_OS_WIN
|
||||||
bool readRegistry(HKEY key,const QByteArray& subKey, const QByteArray& name, QString& value) {
|
bool readRegistry(HKEY key,const QString& subKey, const QString& name, QString& value) {
|
||||||
DWORD dataSize;
|
|
||||||
LONG result;
|
LONG result;
|
||||||
result = RegGetValueA(key,subKey,
|
HKEY hkey;
|
||||||
name, RRF_RT_REG_SZ | RRF_RT_REG_MULTI_SZ,
|
result = RegOpenKeyExW(key, subKey.toStdWString().c_str(), 0, KEY_READ, &hkey);
|
||||||
NULL,
|
if (result != ERROR_SUCCESS)
|
||||||
NULL,
|
|
||||||
&dataSize);
|
|
||||||
if (result!=ERROR_SUCCESS)
|
|
||||||
return false;
|
return false;
|
||||||
char * buffer = new char[dataSize+10];
|
|
||||||
result = RegGetValueA(key,subKey,
|
DWORD dataType;
|
||||||
name, RRF_RT_REG_SZ | RRF_RT_REG_MULTI_SZ,
|
DWORD dataSize;
|
||||||
NULL,
|
result = RegQueryValueExW(hkey, name.toStdWString().c_str(), NULL, &dataType, NULL, &dataSize);
|
||||||
buffer,
|
if (result != ERROR_SUCCESS || (dataType != REG_SZ && dataType != REG_MULTI_SZ)) {
|
||||||
&dataSize);
|
RegCloseKey(hkey);
|
||||||
if (result!=ERROR_SUCCESS) {
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
wchar_t * buffer = new wchar_t[dataSize / sizeof(wchar_t) + 10];
|
||||||
|
result = RegQueryValueExW(hkey, name.toStdWString().c_str(), NULL, &dataType, (LPBYTE)buffer, &dataSize);
|
||||||
|
RegCloseKey(hkey);
|
||||||
|
if (result != ERROR_SUCCESS) {
|
||||||
delete[] buffer;
|
delete[] buffer;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
value=QString::fromLocal8Bit(buffer);
|
|
||||||
|
value = QString::fromWCharArray(buffer);
|
||||||
delete [] buffer;
|
delete [] buffer;
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
|
@ -145,7 +145,7 @@ void executeFile(const QString& fileName,
|
||||||
bool isGreenEdition();
|
bool isGreenEdition();
|
||||||
|
|
||||||
#ifdef Q_OS_WIN
|
#ifdef Q_OS_WIN
|
||||||
bool readRegistry(HKEY key,const QByteArray& subKey, const QByteArray& name, QString& value);
|
bool readRegistry(HKEY key, const QString& subKey, const QString& name, QString& value);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
qulonglong stringToHex(const QString& str, bool &isOk);
|
qulonglong stringToHex(const QString& str, bool &isOk);
|
||||||
|
|
|
@ -2,7 +2,8 @@ TEMPLATE = lib
|
||||||
QT += core gui
|
QT += core gui
|
||||||
greaterThan(QT_MAJOR_VERSION, 4): QT += widgets
|
greaterThan(QT_MAJOR_VERSION, 4): QT += widgets
|
||||||
|
|
||||||
CONFIG += c++17
|
# without `c++14` old versions of qmake will explicitly set `-std=gnu++98`
|
||||||
|
CONFIG += c++14 c++17
|
||||||
CONFIG += nokey
|
CONFIG += nokey
|
||||||
CONFIG += staticlib
|
CONFIG += staticlib
|
||||||
contains(QMAKE_HOST.arch, x86_64):{
|
contains(QMAKE_HOST.arch, x86_64):{
|
||||||
|
@ -15,7 +16,7 @@ contains(QMAKE_HOST.arch, x86_64):{
|
||||||
|
|
||||||
|
|
||||||
win32: {
|
win32: {
|
||||||
DEFINES += _WIN32_WINNT=0x0601
|
DEFINES += _WIN32_WINNT=0x0501
|
||||||
}
|
}
|
||||||
|
|
||||||
gcc {
|
gcc {
|
||||||
|
|
|
@ -26,6 +26,7 @@
|
||||||
#include <QTextStream>
|
#include <QTextStream>
|
||||||
#include <QVector>
|
#include <QVector>
|
||||||
#include <initializer_list>
|
#include <initializer_list>
|
||||||
|
#include <functional>
|
||||||
//#include <QRect>
|
//#include <QRect>
|
||||||
//#include <QColor>
|
//#include <QColor>
|
||||||
|
|
||||||
|
|
|
@ -3,12 +3,13 @@ QT += core gui
|
||||||
|
|
||||||
greaterThan(QT_MAJOR_VERSION, 4): QT += widgets
|
greaterThan(QT_MAJOR_VERSION, 4): QT += widgets
|
||||||
|
|
||||||
CONFIG += c++17
|
# without `c++14` old versions of qmake will explicitly set `-std=gnu++98`
|
||||||
|
CONFIG += c++14 c++17
|
||||||
CONFIG += nokey
|
CONFIG += nokey
|
||||||
CONFIG += staticlib
|
CONFIG += staticlib
|
||||||
|
|
||||||
win32: {
|
win32: {
|
||||||
DEFINES += _WIN32_WINNT=0x0601
|
DEFINES += _WIN32_WINNT=0x0501
|
||||||
}
|
}
|
||||||
|
|
||||||
gcc {
|
gcc {
|
||||||
|
|
|
@ -0,0 +1,113 @@
|
||||||
|
# for Git Bash
|
||||||
|
|
||||||
|
set -xe
|
||||||
|
|
||||||
|
QT_CONFIGURE_DEBUG_OR_RELEASE="-release"
|
||||||
|
OFFICIAL_QT_DIRECTORY="/c/Qt"
|
||||||
|
QT_INSTALL_PREFIX="/c/Qt/5.6.3"
|
||||||
|
|
||||||
|
qt-module-directory() {
|
||||||
|
moduleName="$1"
|
||||||
|
echo "qt$moduleName-opensource-src-5.6.3"
|
||||||
|
}
|
||||||
|
|
||||||
|
prepare-qt-base-source() {
|
||||||
|
moduleDirectory="$(qt-module-directory base)"
|
||||||
|
fileName="$moduleDirectory.tar.xz"
|
||||||
|
|
||||||
|
if ! [[ -d "$moduleDirectory" ]] ; then
|
||||||
|
patchFileName="qtbase-5.6.3-redpanda.patch"
|
||||||
|
if ! [[ -f "$patchFileName" ]] ; then
|
||||||
|
echo -n "Patch file not found. Please copy it to this directory and press enter to continue..."
|
||||||
|
read -r
|
||||||
|
fi
|
||||||
|
if ! [[ -f "$fileName" ]] ; then
|
||||||
|
downloadUrl="https://download.qt.io/new_archive/qt/5.6/5.6.3/submodules/$fileName"
|
||||||
|
curl -L -o "$fileName" "$downloadUrl"
|
||||||
|
fi
|
||||||
|
tar xf "$fileName"
|
||||||
|
tar xf "$fileName" "$moduleDirectory/configure.exe" # workaround for MSYS2 tar bug: https://github.com/msys2/MSYS2-packages/issues/4103
|
||||||
|
pushd "$moduleDirectory"
|
||||||
|
patch --forward --strip=1 --input="../$patchFileName"
|
||||||
|
popd
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
prepare-qt-module-source() {
|
||||||
|
moduleName="$1"
|
||||||
|
moduleDirectory="$(qt-module-directory $moduleName)"
|
||||||
|
fileName="$moduleDirectory.tar.xz"
|
||||||
|
|
||||||
|
if ! [[ -d "$moduleDirectory" ]] ; then
|
||||||
|
if ! [[ -f "$fileName" ]] ; then
|
||||||
|
downloadUrl="https://download.qt.io/new_archive/qt/5.6/5.6.3/submodules/$fileName"
|
||||||
|
curl -L -o "$fileName" "$downloadUrl"
|
||||||
|
fi
|
||||||
|
tar xf "$fileName"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
prepare-qt-sources() {
|
||||||
|
prepare-qt-base-source
|
||||||
|
prepare-qt-module-source svg
|
||||||
|
prepare-qt-module-source tools
|
||||||
|
}
|
||||||
|
|
||||||
|
build-qt-base() {
|
||||||
|
configuration="$1"
|
||||||
|
|
||||||
|
buildDir="build-qtbase-$configuration"
|
||||||
|
mkdir -p "$buildDir"
|
||||||
|
pushd "$buildDir"
|
||||||
|
|
||||||
|
prefix="$QT_INSTALL_PREFIX/$configuration"
|
||||||
|
"../$(qt-module-directory base)/configure.bat" \
|
||||||
|
-prefix $prefix $QT_CONFIGURE_DEBUG_OR_RELEASE \
|
||||||
|
-opensource -confirm-license \
|
||||||
|
-no-use-gold-linker -static -static-runtime -platform win32-g++ -target xp \
|
||||||
|
-opengl desktop -no-angle -iconv -gnu-iconv -no-icu -qt-zlib -qt-pcre -qt-libpng -qt-libjpeg -qt-freetype -no-fontconfig -qt-harfbuzz -no-ssl -no-openssl \
|
||||||
|
-nomake examples -nomake tests -nomake tools
|
||||||
|
mingw32-make "-j$(nproc)"
|
||||||
|
mingw32-make install
|
||||||
|
export PATH="$prefix/bin:$PATH"
|
||||||
|
|
||||||
|
popd
|
||||||
|
}
|
||||||
|
|
||||||
|
build-qt-module() {
|
||||||
|
configuration="$1"
|
||||||
|
moduleName="$2"
|
||||||
|
|
||||||
|
buildDir="build-qt$moduleName-$configuration"
|
||||||
|
mkdir -p $buildDir
|
||||||
|
pushd $buildDir
|
||||||
|
|
||||||
|
qmake "../$(qt-module-directory $moduleName)"
|
||||||
|
mingw32-make "-j$(nproc)"
|
||||||
|
mingw32-make install
|
||||||
|
|
||||||
|
popd
|
||||||
|
}
|
||||||
|
|
||||||
|
build-qt() {
|
||||||
|
configuration="$1"
|
||||||
|
|
||||||
|
build-qt-base $configuration
|
||||||
|
build-qt-module $configuration svg
|
||||||
|
build-qt-module $configuration tools
|
||||||
|
}
|
||||||
|
|
||||||
|
main() {
|
||||||
|
basePath="$PATH"
|
||||||
|
prepare-qt-sources
|
||||||
|
|
||||||
|
## 32-bit
|
||||||
|
export PATH="$OFFICIAL_QT_DIRECTORY/Tools/mingw810_32/bin:$basePath"
|
||||||
|
build-qt mingw81_32-redpanda
|
||||||
|
|
||||||
|
## 64-bit
|
||||||
|
export PATH="$OFFICIAL_QT_DIRECTORY/Tools/mingw810_64/bin:$basePath"
|
||||||
|
build-qt mingw81_64-redpanda
|
||||||
|
}
|
||||||
|
|
||||||
|
main
|
|
@ -0,0 +1,856 @@
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/corelib/global/qflags.h qtbase-opensource-src-5.6.3/src/corelib/global/qflags.h
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/corelib/global/qflags.h 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/corelib/global/qflags.h 2023-10-17 20:31:37.670315600 +0800
|
||||||
|
@@ -139,6 +139,11 @@
|
||||||
|
Q_DECL_CONSTEXPR inline bool operator!() const Q_DECL_NOTHROW { return !i; }
|
||||||
|
|
||||||
|
Q_DECL_CONSTEXPR inline bool testFlag(Enum f) const Q_DECL_NOTHROW { return (i & Int(f)) == Int(f) && (Int(f) != 0 || i == Int(f) ); }
|
||||||
|
+ Q_DECL_RELAXED_CONSTEXPR inline QFlags &setFlag(Enum f, bool on = true) Q_DECL_NOTHROW
|
||||||
|
+ {
|
||||||
|
+ return on ? (*this |= f) : (*this &= ~Int(f));
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
private:
|
||||||
|
#ifdef Q_COMPILER_INITIALIZER_LISTS
|
||||||
|
Q_DECL_CONSTEXPR static inline Int initializer_list_helper(typename std::initializer_list<Enum>::const_iterator it,
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/corelib/global/qglobal.h qtbase-opensource-src-5.6.3/src/corelib/global/qglobal.h
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/corelib/global/qglobal.h 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/corelib/global/qglobal.h 2023-10-17 14:38:05.801809800 +0800
|
||||||
|
@@ -67,6 +67,9 @@
|
||||||
|
# define QT_NO_UNSHARABLE_CONTAINERS
|
||||||
|
#endif
|
||||||
|
|
||||||
|
+// Red Panda C++: workaround.
|
||||||
|
+#define QT_CONFIG(feature) QT_SUPPORTS(feature)
|
||||||
|
+
|
||||||
|
/* These two macros makes it possible to turn the builtin line expander into a
|
||||||
|
* string literal. */
|
||||||
|
#define QT_STRINGIFY2(x) #x
|
||||||
|
@@ -1054,6 +1057,53 @@
|
||||||
|
|
||||||
|
#endif // QT_NO_TRANSLATION
|
||||||
|
|
||||||
|
+template <typename... Args>
|
||||||
|
+struct QNonConstOverload
|
||||||
|
+{
|
||||||
|
+ template <typename R, typename T>
|
||||||
|
+ Q_DECL_CONSTEXPR auto operator()(R (T::*ptr)(Args...)) const Q_DECL_NOTHROW -> decltype(ptr)
|
||||||
|
+ { return ptr; }
|
||||||
|
+
|
||||||
|
+ template <typename R, typename T>
|
||||||
|
+ static Q_DECL_CONSTEXPR auto of(R (T::*ptr)(Args...)) Q_DECL_NOTHROW -> decltype(ptr)
|
||||||
|
+ { return ptr; }
|
||||||
|
+};
|
||||||
|
+
|
||||||
|
+template <typename... Args>
|
||||||
|
+struct QConstOverload
|
||||||
|
+{
|
||||||
|
+ template <typename R, typename T>
|
||||||
|
+ Q_DECL_CONSTEXPR auto operator()(R (T::*ptr)(Args...) const) const Q_DECL_NOTHROW -> decltype(ptr)
|
||||||
|
+ { return ptr; }
|
||||||
|
+
|
||||||
|
+ template <typename R, typename T>
|
||||||
|
+ static Q_DECL_CONSTEXPR auto of(R (T::*ptr)(Args...) const) Q_DECL_NOTHROW -> decltype(ptr)
|
||||||
|
+ { return ptr; }
|
||||||
|
+};
|
||||||
|
+
|
||||||
|
+template <typename... Args>
|
||||||
|
+struct QOverload : QConstOverload<Args...>, QNonConstOverload<Args...>
|
||||||
|
+{
|
||||||
|
+ using QConstOverload<Args...>::of;
|
||||||
|
+ using QConstOverload<Args...>::operator();
|
||||||
|
+ using QNonConstOverload<Args...>::of;
|
||||||
|
+ using QNonConstOverload<Args...>::operator();
|
||||||
|
+
|
||||||
|
+ template <typename R>
|
||||||
|
+ Q_DECL_CONSTEXPR auto operator()(R (*ptr)(Args...)) const Q_DECL_NOTHROW -> decltype(ptr)
|
||||||
|
+ { return ptr; }
|
||||||
|
+
|
||||||
|
+ template <typename R>
|
||||||
|
+ static Q_DECL_CONSTEXPR auto of(R (*ptr)(Args...)) Q_DECL_NOTHROW -> decltype(ptr)
|
||||||
|
+ { return ptr; }
|
||||||
|
+};
|
||||||
|
+
|
||||||
|
+#if defined(__cpp_variable_templates) && __cpp_variable_templates >= 201304 // C++14
|
||||||
|
+template <typename... Args> Q_CONSTEXPR Q_DECL_UNUSED QOverload<Args...> qOverload = {};
|
||||||
|
+template <typename... Args> Q_CONSTEXPR Q_DECL_UNUSED QConstOverload<Args...> qConstOverload = {};
|
||||||
|
+template <typename... Args> Q_CONSTEXPR Q_DECL_UNUSED QNonConstOverload<Args...> qNonConstOverload = {};
|
||||||
|
+#endif
|
||||||
|
+
|
||||||
|
/*
|
||||||
|
When RTTI is not available, define this macro to force any uses of
|
||||||
|
dynamic_cast to cause a compile failure.
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/corelib/global/qsystemdetection.h qtbase-opensource-src-5.6.3/src/corelib/global/qsystemdetection.h
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/corelib/global/qsystemdetection.h 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/corelib/global/qsystemdetection.h 2023-10-17 22:26:59.822029100 +0800
|
||||||
|
@@ -184,6 +184,7 @@
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if defined(Q_OS_WIN32) || defined(Q_OS_WIN64) || defined(Q_OS_WINCE) || defined(Q_OS_WINRT)
|
||||||
|
+# define Q_OS_WINDOWS
|
||||||
|
# define Q_OS_WIN
|
||||||
|
#endif
|
||||||
|
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/corelib/io/qdir.cpp qtbase-opensource-src-5.6.3/src/corelib/io/qdir.cpp
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/corelib/io/qdir.cpp 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/corelib/io/qdir.cpp 2023-10-17 14:38:05.801809800 +0800
|
||||||
|
@@ -1812,6 +1812,13 @@
|
||||||
|
return QFile::exists(filePath(name));
|
||||||
|
}
|
||||||
|
|
||||||
|
+bool QDir::isEmpty(Filters filters) const
|
||||||
|
+{
|
||||||
|
+ const auto d = d_ptr.constData();
|
||||||
|
+ QDirIterator it(d->dirEntry.filePath(), d->nameFilters, filters);
|
||||||
|
+ return !it.hasNext();
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
/*!
|
||||||
|
Returns a list of the root directories on this system.
|
||||||
|
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/corelib/io/qdir.h qtbase-opensource-src-5.6.3/src/corelib/io/qdir.h
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/corelib/io/qdir.h 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/corelib/io/qdir.h 2023-10-17 14:38:05.801809800 +0800
|
||||||
|
@@ -138,6 +138,8 @@
|
||||||
|
void setSorting(SortFlags sort);
|
||||||
|
|
||||||
|
uint count() const;
|
||||||
|
+ bool isEmpty(Filters filters = Filters(AllEntries | NoDotAndDotDot)) const;
|
||||||
|
+
|
||||||
|
QString operator[](int) const;
|
||||||
|
|
||||||
|
static QStringList nameFiltersFromString(const QString &nameFilter);
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/corelib/io/qprocess.cpp qtbase-opensource-src-5.6.3/src/corelib/io/qprocess.cpp
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/corelib/io/qprocess.cpp 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/corelib/io/qprocess.cpp 2023-10-18 09:11:02.546767400 +0800
|
||||||
|
@@ -1535,6 +1535,18 @@
|
||||||
|
d->nativeArguments = arguments;
|
||||||
|
}
|
||||||
|
|
||||||
|
+QProcess::CreateProcessArgumentModifier QProcess::createProcessArgumentsModifier() const
|
||||||
|
+{
|
||||||
|
+ Q_D(const QProcess);
|
||||||
|
+ return d->modifyCreateProcessArgs;
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+void QProcess::setCreateProcessArgumentsModifier(CreateProcessArgumentModifier modifier)
|
||||||
|
+{
|
||||||
|
+ Q_D(QProcess);
|
||||||
|
+ d->modifyCreateProcessArgs = modifier;
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/*!
|
||||||
|
@@ -2124,6 +2136,20 @@
|
||||||
|
d->start(mode);
|
||||||
|
}
|
||||||
|
|
||||||
|
+bool QProcess::startDetached(qint64 *pid)
|
||||||
|
+{
|
||||||
|
+ Q_D(QProcess);
|
||||||
|
+ if (d->processState != NotRunning) {
|
||||||
|
+ qWarning("QProcess::startDetached: Process is already running");
|
||||||
|
+ return false;
|
||||||
|
+ }
|
||||||
|
+ if (d->program.isEmpty()) {
|
||||||
|
+ d->setErrorAndEmit(QProcess::FailedToStart, tr("No program defined"));
|
||||||
|
+ return false;
|
||||||
|
+ }
|
||||||
|
+ return d->startDetached(pid);
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
/*!
|
||||||
|
Starts the program set by setProgram() with arguments set by setArguments().
|
||||||
|
The OpenMode is set to \a mode.
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/corelib/io/qprocess.h qtbase-opensource-src-5.6.3/src/corelib/io/qprocess.h
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/corelib/io/qprocess.h 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/corelib/io/qprocess.h 2023-10-18 09:09:01.053605200 +0800
|
||||||
|
@@ -38,6 +38,8 @@
|
||||||
|
#include <QtCore/qstringlist.h>
|
||||||
|
#include <QtCore/qshareddata.h>
|
||||||
|
|
||||||
|
+#include <functional>
|
||||||
|
+
|
||||||
|
QT_BEGIN_NAMESPACE
|
||||||
|
|
||||||
|
|
||||||
|
@@ -48,6 +50,8 @@
|
||||||
|
#else
|
||||||
|
QT_END_NAMESPACE
|
||||||
|
typedef struct _PROCESS_INFORMATION *Q_PID;
|
||||||
|
+typedef struct _SECURITY_ATTRIBUTES Q_SECURITY_ATTRIBUTES;
|
||||||
|
+typedef struct _STARTUPINFOW Q_STARTUPINFO;
|
||||||
|
QT_BEGIN_NAMESPACE
|
||||||
|
#endif
|
||||||
|
|
||||||
|
@@ -151,6 +155,7 @@
|
||||||
|
void start(const QString &command, OpenMode mode = ReadWrite);
|
||||||
|
#endif
|
||||||
|
void start(OpenMode mode = ReadWrite);
|
||||||
|
+ bool startDetached(qint64 *pid = nullptr);
|
||||||
|
bool open(OpenMode mode = ReadWrite) Q_DECL_OVERRIDE;
|
||||||
|
|
||||||
|
QString program() const;
|
||||||
|
@@ -180,6 +185,22 @@
|
||||||
|
#if defined(Q_OS_WIN)
|
||||||
|
QString nativeArguments() const;
|
||||||
|
void setNativeArguments(const QString &arguments);
|
||||||
|
+ struct CreateProcessArguments
|
||||||
|
+ {
|
||||||
|
+ const wchar_t *applicationName;
|
||||||
|
+ wchar_t *arguments;
|
||||||
|
+ Q_SECURITY_ATTRIBUTES *processAttributes;
|
||||||
|
+ Q_SECURITY_ATTRIBUTES *threadAttributes;
|
||||||
|
+ bool inheritHandles;
|
||||||
|
+ unsigned long flags;
|
||||||
|
+ void *environment;
|
||||||
|
+ const wchar_t *currentDirectory;
|
||||||
|
+ Q_STARTUPINFO *startupInfo;
|
||||||
|
+ Q_PID processInformation;
|
||||||
|
+ };
|
||||||
|
+ typedef std::function<void(CreateProcessArguments *)> CreateProcessArgumentModifier;
|
||||||
|
+ CreateProcessArgumentModifier createProcessArgumentsModifier() const;
|
||||||
|
+ void setCreateProcessArgumentsModifier(CreateProcessArgumentModifier modifier);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
QString workingDirectory() const;
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/corelib/io/qprocess_p.h qtbase-opensource-src-5.6.3/src/corelib/io/qprocess_p.h
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/corelib/io/qprocess_p.h 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/corelib/io/qprocess_p.h 2023-10-17 14:38:05.822849000 +0800
|
||||||
|
@@ -326,6 +326,7 @@
|
||||||
|
QStringList arguments;
|
||||||
|
#if defined(Q_OS_WIN)
|
||||||
|
QString nativeArguments;
|
||||||
|
+ QProcess::CreateProcessArgumentModifier modifyCreateProcessArgs;
|
||||||
|
#endif
|
||||||
|
QProcessEnvironment environment;
|
||||||
|
|
||||||
|
@@ -355,6 +356,7 @@
|
||||||
|
bool waitForDeadChild();
|
||||||
|
#endif
|
||||||
|
#ifdef Q_OS_WIN
|
||||||
|
+ bool callCreateProcess(QProcess::CreateProcessArguments *cpargs);
|
||||||
|
bool drainOutputPipes();
|
||||||
|
void flushPipeWriter();
|
||||||
|
qint64 pipeWriterBytesToWrite() const;
|
||||||
|
@@ -363,6 +365,8 @@
|
||||||
|
static bool startDetached(const QString &program, const QStringList &arguments, const QString &workingDirectory = QString(),
|
||||||
|
qint64 *pid = 0);
|
||||||
|
|
||||||
|
+ bool startDetached(qint64 *pPid);
|
||||||
|
+
|
||||||
|
int exitCode;
|
||||||
|
QProcess::ExitStatus exitStatus;
|
||||||
|
bool crashed;
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/corelib/io/qprocess_win.cpp qtbase-opensource-src-5.6.3/src/corelib/io/qprocess_win.cpp
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/corelib/io/qprocess_win.cpp 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/corelib/io/qprocess_win.cpp 2023-10-18 09:15:27.039781400 +0800
|
||||||
|
@@ -330,7 +330,8 @@
|
||||||
|
destroyPipe(channel->pipe);
|
||||||
|
}
|
||||||
|
|
||||||
|
-static QString qt_create_commandline(const QString &program, const QStringList &arguments)
|
||||||
|
+static QString qt_create_commandline(const QString &program, const QStringList &arguments,
|
||||||
|
+ const QString &nativeArguments = QString())
|
||||||
|
{
|
||||||
|
QString args;
|
||||||
|
if (!program.isEmpty()) {
|
||||||
|
@@ -359,6 +360,13 @@
|
||||||
|
}
|
||||||
|
args += QLatin1Char(' ') + tmp;
|
||||||
|
}
|
||||||
|
+
|
||||||
|
+ if (!nativeArguments.isEmpty()) {
|
||||||
|
+ if (!args.isEmpty())
|
||||||
|
+ args += QLatin1Char(' ');
|
||||||
|
+ args += nativeArguments;
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
return args;
|
||||||
|
}
|
||||||
|
|
||||||
|
@@ -444,6 +452,30 @@
|
||||||
|
return envlist;
|
||||||
|
}
|
||||||
|
|
||||||
|
+bool QProcessPrivate::callCreateProcess(QProcess::CreateProcessArguments *cpargs)
|
||||||
|
+{
|
||||||
|
+ if (modifyCreateProcessArgs)
|
||||||
|
+ modifyCreateProcessArgs(cpargs);
|
||||||
|
+ bool success = CreateProcess(cpargs->applicationName, cpargs->arguments,
|
||||||
|
+ cpargs->processAttributes, cpargs->threadAttributes,
|
||||||
|
+ cpargs->inheritHandles, cpargs->flags, cpargs->environment,
|
||||||
|
+ cpargs->currentDirectory, cpargs->startupInfo,
|
||||||
|
+ cpargs->processInformation);
|
||||||
|
+ if (stdinChannel.pipe[0] != INVALID_Q_PIPE) {
|
||||||
|
+ CloseHandle(stdinChannel.pipe[0]);
|
||||||
|
+ stdinChannel.pipe[0] = INVALID_Q_PIPE;
|
||||||
|
+ }
|
||||||
|
+ if (stdoutChannel.pipe[1] != INVALID_Q_PIPE) {
|
||||||
|
+ CloseHandle(stdoutChannel.pipe[1]);
|
||||||
|
+ stdoutChannel.pipe[1] = INVALID_Q_PIPE;
|
||||||
|
+ }
|
||||||
|
+ if (stderrChannel.pipe[1] != INVALID_Q_PIPE) {
|
||||||
|
+ CloseHandle(stderrChannel.pipe[1]);
|
||||||
|
+ stderrChannel.pipe[1] = INVALID_Q_PIPE;
|
||||||
|
+ }
|
||||||
|
+ return success;
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
void QProcessPrivate::startProcess()
|
||||||
|
{
|
||||||
|
Q_Q(QProcess);
|
||||||
|
@@ -498,11 +530,22 @@
|
||||||
|
0, 0, 0,
|
||||||
|
stdinChannel.pipe[0], stdoutChannel.pipe[1], stderrChannel.pipe[1]
|
||||||
|
};
|
||||||
|
- success = CreateProcess(0, (wchar_t*)args.utf16(),
|
||||||
|
- 0, 0, TRUE, dwCreationFlags,
|
||||||
|
- environment.isEmpty() ? 0 : envlist.data(),
|
||||||
|
- workingDirectory.isEmpty() ? 0 : (wchar_t*)QDir::toNativeSeparators(workingDirectory).utf16(),
|
||||||
|
- &startupInfo, pid);
|
||||||
|
+
|
||||||
|
+ const QString nativeWorkingDirectory = QDir::toNativeSeparators(workingDirectory);
|
||||||
|
+ QProcess::CreateProcessArguments cpargs = {
|
||||||
|
+ 0, (wchar_t*)args.utf16(),
|
||||||
|
+ 0, 0, TRUE, dwCreationFlags,
|
||||||
|
+ environment.isEmpty() ? 0 : envlist.data(),
|
||||||
|
+ nativeWorkingDirectory.isEmpty() ? Q_NULLPTR : (wchar_t*)nativeWorkingDirectory.utf16(),
|
||||||
|
+ &startupInfo, pid
|
||||||
|
+ };
|
||||||
|
+ if (modifyCreateProcessArgs)
|
||||||
|
+ modifyCreateProcessArgs(&cpargs);
|
||||||
|
+ success = CreateProcess(cpargs.applicationName, cpargs.arguments, cpargs.processAttributes,
|
||||||
|
+ cpargs.threadAttributes, cpargs.inheritHandles, cpargs.flags,
|
||||||
|
+ cpargs.environment, cpargs.currentDirectory, cpargs.startupInfo,
|
||||||
|
+ cpargs.processInformation);
|
||||||
|
+
|
||||||
|
QString errorString;
|
||||||
|
if (!success) {
|
||||||
|
// Capture the error string before we do CloseHandle below
|
||||||
|
@@ -818,6 +861,7 @@
|
||||||
|
// Use ShellExecuteEx() to trigger an UAC prompt when CreateProcess()fails
|
||||||
|
// with ERROR_ELEVATION_REQUIRED.
|
||||||
|
static bool startDetachedUacPrompt(const QString &programIn, const QStringList &arguments,
|
||||||
|
+ const QString &nativeArguments,
|
||||||
|
const QString &workingDir, qint64 *pid)
|
||||||
|
{
|
||||||
|
typedef BOOL (WINAPI *ShellExecuteExType)(SHELLEXECUTEINFOW *);
|
||||||
|
@@ -828,11 +872,13 @@
|
||||||
|
if (!shellExecuteEx)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
- const QString args = qt_create_commandline(QString(), arguments); // needs arguments only
|
||||||
|
+ const QString args = qt_create_commandline(QString(), // needs arguments only
|
||||||
|
+ arguments, nativeArguments);
|
||||||
|
SHELLEXECUTEINFOW shellExecuteExInfo;
|
||||||
|
memset(&shellExecuteExInfo, 0, sizeof(SHELLEXECUTEINFOW));
|
||||||
|
shellExecuteExInfo.cbSize = sizeof(SHELLEXECUTEINFOW);
|
||||||
|
- shellExecuteExInfo.fMask = SEE_MASK_NOCLOSEPROCESS | SEE_MASK_UNICODE | SEE_MASK_FLAG_NO_UI;
|
||||||
|
+ shellExecuteExInfo.fMask = SEE_MASK_NOCLOSEPROCESS | SEE_MASK_UNICODE | SEE_MASK_FLAG_NO_UI | SEE_MASK_CLASSNAME;
|
||||||
|
+ shellExecuteExInfo.lpClass = L"exefile";
|
||||||
|
shellExecuteExInfo.lpVerb = L"runas";
|
||||||
|
const QString program = QDir::toNativeSeparators(programIn);
|
||||||
|
shellExecuteExInfo.lpFile = reinterpret_cast<LPCWSTR>(program.utf16());
|
||||||
|
@@ -850,6 +896,12 @@
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
+static bool startDetachedUacPrompt(const QString &programIn, const QStringList &arguments,
|
||||||
|
+ const QString &workingDir, qint64 *pid)
|
||||||
|
+{
|
||||||
|
+ return startDetachedUacPrompt(programIn, arguments, QString(), workingDir, pid);
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
bool QProcessPrivate::startDetached(const QString &program, const QStringList &arguments, const QString &workingDir, qint64 *pid)
|
||||||
|
{
|
||||||
|
static const DWORD errorElevationRequired = 740;
|
||||||
|
@@ -880,6 +932,75 @@
|
||||||
|
return success;
|
||||||
|
}
|
||||||
|
|
||||||
|
+bool QProcessPrivate::startDetached(qint64 *pid)
|
||||||
|
+{
|
||||||
|
+ static const DWORD errorElevationRequired = 740;
|
||||||
|
+
|
||||||
|
+ if ((stdinChannel.type == Channel::Redirect && !openChannel(stdinChannel))
|
||||||
|
+ || (stdoutChannel.type == Channel::Redirect && !openChannel(stdoutChannel))
|
||||||
|
+ || (stderrChannel.type == Channel::Redirect && !openChannel(stderrChannel))) {
|
||||||
|
+ closeChannel(&stdinChannel);
|
||||||
|
+ closeChannel(&stdoutChannel);
|
||||||
|
+ closeChannel(&stderrChannel);
|
||||||
|
+ return false;
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ QString args = qt_create_commandline(program, arguments, nativeArguments);
|
||||||
|
+ bool success = false;
|
||||||
|
+ PROCESS_INFORMATION pinfo;
|
||||||
|
+
|
||||||
|
+ void *envPtr = nullptr;
|
||||||
|
+ QByteArray envlist;
|
||||||
|
+ if (environment.d.constData()) {
|
||||||
|
+ envlist = qt_create_environment(environment.d.constData()->hash);
|
||||||
|
+ envPtr = envlist.data();
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ DWORD dwCreationFlags = (GetConsoleWindow() ? 0 : CREATE_NO_WINDOW);
|
||||||
|
+ dwCreationFlags |= CREATE_UNICODE_ENVIRONMENT;
|
||||||
|
+ STARTUPINFOW startupInfo = { sizeof( STARTUPINFO ), 0, 0, 0,
|
||||||
|
+ (ulong)CW_USEDEFAULT, (ulong)CW_USEDEFAULT,
|
||||||
|
+ (ulong)CW_USEDEFAULT, (ulong)CW_USEDEFAULT,
|
||||||
|
+ 0, 0, 0,
|
||||||
|
+ STARTF_USESTDHANDLES,
|
||||||
|
+ 0, 0, 0,
|
||||||
|
+ stdinChannel.pipe[0], stdoutChannel.pipe[1], stderrChannel.pipe[1]
|
||||||
|
+ };
|
||||||
|
+
|
||||||
|
+ const bool inheritHandles = stdinChannel.type == Channel::Redirect
|
||||||
|
+ || stdoutChannel.type == Channel::Redirect
|
||||||
|
+ || stderrChannel.type == Channel::Redirect;
|
||||||
|
+ QProcess::CreateProcessArguments cpargs = {
|
||||||
|
+ nullptr, reinterpret_cast<wchar_t *>(const_cast<ushort *>(args.utf16())),
|
||||||
|
+ nullptr, nullptr, inheritHandles, dwCreationFlags, envPtr,
|
||||||
|
+ workingDirectory.isEmpty()
|
||||||
|
+ ? nullptr : reinterpret_cast<const wchar_t *>(workingDirectory.utf16()),
|
||||||
|
+ &startupInfo, &pinfo
|
||||||
|
+ };
|
||||||
|
+ success = callCreateProcess(&cpargs);
|
||||||
|
+
|
||||||
|
+ if (success) {
|
||||||
|
+ CloseHandle(pinfo.hThread);
|
||||||
|
+ CloseHandle(pinfo.hProcess);
|
||||||
|
+ if (pid)
|
||||||
|
+ *pid = pinfo.dwProcessId;
|
||||||
|
+ } else if (GetLastError() == errorElevationRequired) {
|
||||||
|
+ if (envPtr)
|
||||||
|
+ qWarning("QProcess: custom environment will be ignored for detached elevated process.");
|
||||||
|
+ if (!stdinChannel.file.isEmpty() || !stdoutChannel.file.isEmpty()
|
||||||
|
+ || !stderrChannel.file.isEmpty()) {
|
||||||
|
+ qWarning("QProcess: file redirection is unsupported for detached elevated processes.");
|
||||||
|
+ }
|
||||||
|
+ success = startDetachedUacPrompt(program, arguments, nativeArguments,
|
||||||
|
+ workingDirectory, pid);
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ closeChannel(&stdinChannel);
|
||||||
|
+ closeChannel(&stdoutChannel);
|
||||||
|
+ closeChannel(&stderrChannel);
|
||||||
|
+ return success;
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
QT_END_NAMESPACE
|
||||||
|
|
||||||
|
#endif // QT_NO_PROCESS
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/corelib/plugin/quuid.cpp qtbase-opensource-src-5.6.3/src/corelib/plugin/quuid.cpp
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/corelib/plugin/quuid.cpp 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/corelib/plugin/quuid.cpp 2023-10-17 14:38:05.822849000 +0800
|
||||||
|
@@ -43,6 +43,8 @@
|
||||||
|
#endif
|
||||||
|
QT_BEGIN_NAMESPACE
|
||||||
|
|
||||||
|
+enum { MaxStringUuidLength = 38 };
|
||||||
|
+
|
||||||
|
template <class Char, class Integral>
|
||||||
|
void _q_toHex(Char *&dst, Integral value)
|
||||||
|
{
|
||||||
|
@@ -91,6 +93,30 @@
|
||||||
|
*dst = Char('}');
|
||||||
|
}
|
||||||
|
|
||||||
|
+static char *_q_uuidToHex(const QUuid &uuid, char *dst, QUuid::StringFormat mode = QUuid::WithBraces)
|
||||||
|
+{
|
||||||
|
+ if ((mode & QUuid::WithoutBraces) == 0)
|
||||||
|
+ *dst++ = '{';
|
||||||
|
+ _q_toHex(dst, uuid.data1);
|
||||||
|
+ if ((mode & QUuid::Id128) != QUuid::Id128)
|
||||||
|
+ *dst++ = '-';
|
||||||
|
+ _q_toHex(dst, uuid.data2);
|
||||||
|
+ if ((mode & QUuid::Id128) != QUuid::Id128)
|
||||||
|
+ *dst++ = '-';
|
||||||
|
+ _q_toHex(dst, uuid.data3);
|
||||||
|
+ if ((mode & QUuid::Id128) != QUuid::Id128)
|
||||||
|
+ *dst++ = '-';
|
||||||
|
+ for (int i = 0; i < 2; i++)
|
||||||
|
+ _q_toHex(dst, uuid.data4[i]);
|
||||||
|
+ if ((mode & QUuid::Id128) != QUuid::Id128)
|
||||||
|
+ *dst++ = '-';
|
||||||
|
+ for (int i = 2; i < 8; i++)
|
||||||
|
+ _q_toHex(dst, uuid.data4[i]);
|
||||||
|
+ if ((mode & QUuid::WithoutBraces) == 0)
|
||||||
|
+ *dst++ = '}';
|
||||||
|
+ return dst;
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
template <class Char>
|
||||||
|
bool _q_uuidFromHex(const Char *&src, uint &d1, ushort &d2, ushort &d3, uchar (&d4)[8])
|
||||||
|
{
|
||||||
|
@@ -550,6 +576,13 @@
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
+QString QUuid::toString(QUuid::StringFormat mode) const
|
||||||
|
+{
|
||||||
|
+ char latin1[MaxStringUuidLength];
|
||||||
|
+ const auto end = _q_uuidToHex(*this, latin1, mode);
|
||||||
|
+ return QString::fromLatin1(latin1, end - latin1);
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
/*!
|
||||||
|
Returns the binary representation of this QUuid. The byte array is
|
||||||
|
formatted as five hex fields separated by '-' and enclosed in
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/corelib/plugin/quuid.h qtbase-opensource-src-5.6.3/src/corelib/plugin/quuid.h
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/corelib/plugin/quuid.h 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/corelib/plugin/quuid.h 2023-10-17 14:38:05.838486200 +0800
|
||||||
|
@@ -74,6 +74,12 @@
|
||||||
|
Sha1 = 5 // 0 1 0 1
|
||||||
|
};
|
||||||
|
|
||||||
|
+ enum StringFormat {
|
||||||
|
+ WithBraces = 0,
|
||||||
|
+ WithoutBraces = 1,
|
||||||
|
+ Id128 = 3
|
||||||
|
+ };
|
||||||
|
+
|
||||||
|
#if defined(Q_COMPILER_UNIFORM_INIT) && !defined(Q_QDOC)
|
||||||
|
Q_DECL_CONSTEXPR QUuid() Q_DECL_NOTHROW : data1(0), data2(0), data3(0), data4{0,0,0,0,0,0,0,0} {}
|
||||||
|
|
||||||
|
@@ -108,6 +114,7 @@
|
||||||
|
QUuid(const QString &);
|
||||||
|
QUuid(const char *);
|
||||||
|
QString toString() const;
|
||||||
|
+ QString toString(StringFormat mode) const;
|
||||||
|
QUuid(const QByteArray &);
|
||||||
|
QByteArray toByteArray() const;
|
||||||
|
QByteArray toRfc4122() const;
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/corelib/tools/qchar.h qtbase-opensource-src-5.6.3/src/corelib/tools/qchar.h
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/corelib/tools/qchar.h 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/corelib/tools/qchar.h 2023-10-17 14:38:05.838486200 +0800
|
||||||
|
@@ -572,6 +572,21 @@
|
||||||
|
Q_DECL_CONSTEXPR inline bool operator> (QChar c1, QChar c2) { return operator< (c2, c1); }
|
||||||
|
Q_DECL_CONSTEXPR inline bool operator<=(QChar c1, QChar c2) { return !operator< (c2, c1); }
|
||||||
|
|
||||||
|
+Q_DECL_CONSTEXPR inline bool operator==(QChar lhs, std::nullptr_t) Q_DECL_NOTHROW { return lhs.isNull(); }
|
||||||
|
+Q_DECL_CONSTEXPR inline bool operator< (QChar, std::nullptr_t) Q_DECL_NOTHROW { return false; }
|
||||||
|
+Q_DECL_CONSTEXPR inline bool operator==(std::nullptr_t, QChar rhs) Q_DECL_NOTHROW { return rhs.isNull(); }
|
||||||
|
+Q_DECL_CONSTEXPR inline bool operator< (std::nullptr_t, QChar rhs) Q_DECL_NOTHROW { return !rhs.isNull(); }
|
||||||
|
+
|
||||||
|
+Q_DECL_CONSTEXPR inline bool operator!=(QChar lhs, std::nullptr_t) Q_DECL_NOTHROW { return !operator==(lhs, nullptr); }
|
||||||
|
+Q_DECL_CONSTEXPR inline bool operator>=(QChar lhs, std::nullptr_t) Q_DECL_NOTHROW { return !operator< (lhs, nullptr); }
|
||||||
|
+Q_DECL_CONSTEXPR inline bool operator> (QChar lhs, std::nullptr_t) Q_DECL_NOTHROW { return operator< (nullptr, lhs); }
|
||||||
|
+Q_DECL_CONSTEXPR inline bool operator<=(QChar lhs, std::nullptr_t) Q_DECL_NOTHROW { return !operator< (nullptr, lhs); }
|
||||||
|
+
|
||||||
|
+Q_DECL_CONSTEXPR inline bool operator!=(std::nullptr_t, QChar rhs) Q_DECL_NOTHROW { return !operator==(nullptr, rhs); }
|
||||||
|
+Q_DECL_CONSTEXPR inline bool operator>=(std::nullptr_t, QChar rhs) Q_DECL_NOTHROW { return !operator< (nullptr, rhs); }
|
||||||
|
+Q_DECL_CONSTEXPR inline bool operator> (std::nullptr_t, QChar rhs) Q_DECL_NOTHROW { return operator< (rhs, nullptr); }
|
||||||
|
+Q_DECL_CONSTEXPR inline bool operator<=(std::nullptr_t, QChar rhs) Q_DECL_NOTHROW { return !operator< (rhs, nullptr); }
|
||||||
|
+
|
||||||
|
#ifndef QT_NO_DATASTREAM
|
||||||
|
Q_CORE_EXPORT QDataStream &operator<<(QDataStream &, QChar);
|
||||||
|
Q_CORE_EXPORT QDataStream &operator>>(QDataStream &, QChar &);
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/corelib/tools/qdatetime.cpp qtbase-opensource-src-5.6.3/src/corelib/tools/qdatetime.cpp
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/corelib/tools/qdatetime.cpp 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/corelib/tools/qdatetime.cpp 2023-10-17 14:38:05.838486200 +0800
|
||||||
|
@@ -4135,6 +4135,17 @@
|
||||||
|
- julianDayFromDate(1970, 1, 1)) * Q_INT64_C(86400000);
|
||||||
|
}
|
||||||
|
|
||||||
|
+qint64 QDateTime::currentSecsSinceEpoch() Q_DECL_NOTHROW
|
||||||
|
+{
|
||||||
|
+ SYSTEMTIME st;
|
||||||
|
+ memset(&st, 0, sizeof(SYSTEMTIME));
|
||||||
|
+ GetSystemTime(&st);
|
||||||
|
+
|
||||||
|
+ return st.wHour * SECS_PER_HOUR + st.wMinute * SECS_PER_MIN + st.wSecond +
|
||||||
|
+ qint64(julianDayFromDate(st.wYear, st.wMonth, st.wDay)
|
||||||
|
+ - julianDayFromDate(1970, 1, 1)) * Q_INT64_C(86400);
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
#elif defined(Q_OS_UNIX)
|
||||||
|
QDate QDate::currentDate()
|
||||||
|
{
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/corelib/tools/qdatetime.h qtbase-opensource-src-5.6.3/src/corelib/tools/qdatetime.h
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/corelib/tools/qdatetime.h 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/corelib/tools/qdatetime.h 2023-10-17 14:38:05.838486200 +0800
|
||||||
|
@@ -312,6 +312,7 @@
|
||||||
|
static QDateTime fromMSecsSinceEpoch(qint64 msecs, const QTimeZone &timeZone);
|
||||||
|
#endif
|
||||||
|
static qint64 currentMSecsSinceEpoch() Q_DECL_NOTHROW;
|
||||||
|
+ static qint64 currentSecsSinceEpoch() Q_DECL_NOTHROW;
|
||||||
|
|
||||||
|
#if defined(Q_OS_MAC) || defined(Q_QDOC)
|
||||||
|
static QDateTime fromCFDate(CFDateRef date);
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/corelib/tools/qlocale.cpp qtbase-opensource-src-5.6.3/src/corelib/tools/qlocale.cpp
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/corelib/tools/qlocale.cpp 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/corelib/tools/qlocale.cpp 2023-10-17 14:38:05.854106100 +0800
|
||||||
|
@@ -3526,6 +3526,48 @@
|
||||||
|
return format.arg(str, sym);
|
||||||
|
}
|
||||||
|
|
||||||
|
+QString QLocale::formattedDataSize(qint64 bytes, int precision, DataSizeFormats format)
|
||||||
|
+{
|
||||||
|
+ int power, base = 1000;
|
||||||
|
+ if (!bytes) {
|
||||||
|
+ power = 0;
|
||||||
|
+ } else if (format & DataSizeBase1000) {
|
||||||
|
+ power = int(std::log10(qAbs(bytes)) / 3);
|
||||||
|
+ } else { // Compute log2(bytes) / 10:
|
||||||
|
+ power = int((63 - qCountLeadingZeroBits(quint64(qAbs(bytes)))) / 10);
|
||||||
|
+ base = 1024;
|
||||||
|
+ }
|
||||||
|
+ // Only go to doubles if we'll be using a quantifier:
|
||||||
|
+ const QString number = power
|
||||||
|
+ ? toString(bytes / std::pow(double(base), power), 'f', qMin(precision, 3 * power))
|
||||||
|
+ : toString(bytes);
|
||||||
|
+
|
||||||
|
+ // We don't support sizes in units larger than exbibytes because
|
||||||
|
+ // the number of bytes would not fit into qint64.
|
||||||
|
+ Q_ASSERT(power <= 6 && power >= 0);
|
||||||
|
+ // Red Panda C++: use hard-coded unit strings.
|
||||||
|
+ QString unit;
|
||||||
|
+ if (power > 0) {
|
||||||
|
+ if (format & DataSizeSIQuantifiers) {
|
||||||
|
+ static QString siQuantifiers[] {
|
||||||
|
+ QStringLiteral("kB"), QStringLiteral("MB"), QStringLiteral("GB"),
|
||||||
|
+ QStringLiteral("TB"), QStringLiteral("PB"), QStringLiteral("EB")
|
||||||
|
+ };
|
||||||
|
+ unit = siQuantifiers[power - 1];
|
||||||
|
+ } else {
|
||||||
|
+ static QString iecQuantifiers[] {
|
||||||
|
+ QStringLiteral("KiB"), QStringLiteral("MiB"), QStringLiteral("GiB"),
|
||||||
|
+ QStringLiteral("TiB"), QStringLiteral("PiB"), QStringLiteral("EiB")
|
||||||
|
+ };
|
||||||
|
+ unit = iecQuantifiers[power - 1];
|
||||||
|
+ }
|
||||||
|
+ } else {
|
||||||
|
+ unit = QStringLiteral("Bytes");
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ return number + QLatin1Char(' ') + unit;
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
/*!
|
||||||
|
\since 4.8
|
||||||
|
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/corelib/tools/qlocale.h qtbase-opensource-src-5.6.3/src/corelib/tools/qlocale.h
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/corelib/tools/qlocale.h 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/corelib/tools/qlocale.h 2023-10-17 14:38:05.854106100 +0800
|
||||||
|
@@ -854,6 +854,19 @@
|
||||||
|
CurrencyDisplayName
|
||||||
|
};
|
||||||
|
|
||||||
|
+ enum DataSizeFormat {
|
||||||
|
+ // Single-bit values, for internal use.
|
||||||
|
+ DataSizeBase1000 = 1, // use factors of 1000 instead of IEC's 1024;
|
||||||
|
+ DataSizeSIQuantifiers = 2, // use SI quantifiers instead of IEC ones.
|
||||||
|
+
|
||||||
|
+ // Flags values for use in API:
|
||||||
|
+ DataSizeIecFormat = 0, // base 1024, KiB, MiB, GiB, ...
|
||||||
|
+ DataSizeTraditionalFormat = DataSizeSIQuantifiers, // base 1024, kB, MB, GB, ...
|
||||||
|
+ DataSizeSIFormat = DataSizeBase1000 | DataSizeSIQuantifiers // base 1000, kB, MB, GB, ...
|
||||||
|
+ };
|
||||||
|
+ Q_DECLARE_FLAGS(DataSizeFormats, DataSizeFormat)
|
||||||
|
+ Q_FLAG(DataSizeFormats)
|
||||||
|
+
|
||||||
|
QLocale();
|
||||||
|
QLocale(const QString &name);
|
||||||
|
QLocale(Language language, Country country = AnyCountry);
|
||||||
|
@@ -955,6 +968,8 @@
|
||||||
|
QString toCurrencyString(double, const QString &symbol = QString()) const;
|
||||||
|
inline QString toCurrencyString(float, const QString &symbol = QString()) const;
|
||||||
|
|
||||||
|
+ QString formattedDataSize(qint64 bytes, int precision = 2, DataSizeFormats format = DataSizeIecFormat);
|
||||||
|
+
|
||||||
|
QStringList uiLanguages() const;
|
||||||
|
|
||||||
|
bool operator==(const QLocale &other) const;
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/corelib/tools/qstring.h qtbase-opensource-src-5.6.3/src/corelib/tools/qstring.h
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/corelib/tools/qstring.h 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/corelib/tools/qstring.h 2023-10-17 14:38:05.854106100 +0800
|
||||||
|
@@ -258,6 +258,11 @@
|
||||||
|
const QChar operator[](uint i) const;
|
||||||
|
QCharRef operator[](uint i);
|
||||||
|
|
||||||
|
+ Q_REQUIRED_RESULT inline QChar front() const { return at(0); }
|
||||||
|
+ Q_REQUIRED_RESULT inline QCharRef front();
|
||||||
|
+ Q_REQUIRED_RESULT inline QChar back() const { return at(size() - 1); }
|
||||||
|
+ Q_REQUIRED_RESULT inline QCharRef back();
|
||||||
|
+
|
||||||
|
QString arg(qlonglong a, int fieldwidth=0, int base=10,
|
||||||
|
QChar fillChar = QLatin1Char(' ')) const Q_REQUIRED_RESULT;
|
||||||
|
QString arg(qulonglong a, int fieldwidth=0, int base=10,
|
||||||
|
@@ -793,6 +798,10 @@
|
||||||
|
|
||||||
|
Data *d;
|
||||||
|
|
||||||
|
+ friend inline bool operator==(QChar, const QString &) Q_DECL_NOTHROW;
|
||||||
|
+ friend inline bool operator< (QChar, const QString &) Q_DECL_NOTHROW;
|
||||||
|
+ friend inline bool operator> (QChar, const QString &) Q_DECL_NOTHROW;
|
||||||
|
+
|
||||||
|
void reallocData(uint alloc, bool grow = false);
|
||||||
|
void expand(int i);
|
||||||
|
QString multiArg(int numArgs, const QString **args) const;
|
||||||
|
@@ -1094,6 +1103,8 @@
|
||||||
|
{ Q_ASSERT(i >= 0); return QCharRef(*this, i); }
|
||||||
|
inline QCharRef QString::operator[](uint i)
|
||||||
|
{ return QCharRef(*this, i); }
|
||||||
|
+inline QCharRef QString::front() { return operator[](0); }
|
||||||
|
+inline QCharRef QString::back() { return operator[](size() - 1); }
|
||||||
|
inline QString::iterator QString::begin()
|
||||||
|
{ detach(); return reinterpret_cast<QChar*>(d->data()); }
|
||||||
|
inline QString::const_iterator QString::begin() const
|
||||||
|
@@ -1573,6 +1584,25 @@
|
||||||
|
inline int QStringRef::compare(const QStringRef &s1, QLatin1String s2, Qt::CaseSensitivity cs)
|
||||||
|
{ return QString::compare_helper(s1.constData(), s1.length(), s2, cs); }
|
||||||
|
|
||||||
|
+// QChar <> QString
|
||||||
|
+inline bool operator==(QChar lhs, const QString &rhs) Q_DECL_NOTHROW
|
||||||
|
+{ return rhs.size() == 1 && lhs == rhs.front(); }
|
||||||
|
+inline bool operator< (QChar lhs, const QString &rhs) Q_DECL_NOTHROW
|
||||||
|
+{ return QString::compare_helper(&lhs, 1, rhs.data(), rhs.size()) < 0; }
|
||||||
|
+inline bool operator> (QChar lhs, const QString &rhs) Q_DECL_NOTHROW
|
||||||
|
+{ return QString::compare_helper(&lhs, 1, rhs.data(), rhs.size()) > 0; }
|
||||||
|
+
|
||||||
|
+inline bool operator!=(QChar lhs, const QString &rhs) Q_DECL_NOTHROW { return !(lhs == rhs); }
|
||||||
|
+inline bool operator<=(QChar lhs, const QString &rhs) Q_DECL_NOTHROW { return !(lhs > rhs); }
|
||||||
|
+inline bool operator>=(QChar lhs, const QString &rhs) Q_DECL_NOTHROW { return !(lhs < rhs); }
|
||||||
|
+
|
||||||
|
+inline bool operator==(const QString &lhs, QChar rhs) Q_DECL_NOTHROW { return rhs == lhs; }
|
||||||
|
+inline bool operator!=(const QString &lhs, QChar rhs) Q_DECL_NOTHROW { return !(rhs == lhs); }
|
||||||
|
+inline bool operator< (const QString &lhs, QChar rhs) Q_DECL_NOTHROW { return rhs > lhs; }
|
||||||
|
+inline bool operator> (const QString &lhs, QChar rhs) Q_DECL_NOTHROW { return rhs < lhs; }
|
||||||
|
+inline bool operator<=(const QString &lhs, QChar rhs) Q_DECL_NOTHROW { return !(rhs < lhs); }
|
||||||
|
+inline bool operator>=(const QString &lhs, QChar rhs) Q_DECL_NOTHROW { return !(rhs > lhs); }
|
||||||
|
+
|
||||||
|
inline int QString::localeAwareCompare(const QStringRef &s) const
|
||||||
|
{ return localeAwareCompare_helper(constData(), length(), s.constData(), s.length()); }
|
||||||
|
inline int QString::localeAwareCompare(const QString& s1, const QStringRef& s2)
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/gui/kernel/qcursor.cpp qtbase-opensource-src-5.6.3/src/gui/kernel/qcursor.cpp
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/gui/kernel/qcursor.cpp 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/gui/kernel/qcursor.cpp 2023-10-17 14:38:05.869731000 +0800
|
||||||
|
@@ -471,6 +471,27 @@
|
||||||
|
setShape(shape);
|
||||||
|
}
|
||||||
|
|
||||||
|
+bool operator==(const QCursor &lhs, const QCursor &rhs) Q_DECL_NOTHROW
|
||||||
|
+{
|
||||||
|
+ if (lhs.d == rhs.d)
|
||||||
|
+ return true; // Copy or same shape
|
||||||
|
+
|
||||||
|
+ // Check pixmaps or bitmaps cache keys. Notice that having BitmapCursor
|
||||||
|
+ // shape implies either non-null pixmap or non-null bitmap and mask
|
||||||
|
+ if (lhs.shape() == Qt::BitmapCursor && rhs.shape() == Qt::BitmapCursor
|
||||||
|
+ && lhs.hotSpot() == rhs.hotSpot()) {
|
||||||
|
+ if (!lhs.d->pixmap.isNull())
|
||||||
|
+ return lhs.d->pixmap.cacheKey() == rhs.d->pixmap.cacheKey();
|
||||||
|
+
|
||||||
|
+ if (!rhs.d->pixmap.isNull())
|
||||||
|
+ return false;
|
||||||
|
+
|
||||||
|
+ return lhs.d->bm->cacheKey() == rhs.d->bm->cacheKey()
|
||||||
|
+ && lhs.d->bmm->cacheKey() == rhs.d->bmm->cacheKey();
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ return false;
|
||||||
|
+}
|
||||||
|
|
||||||
|
/*!
|
||||||
|
Returns the cursor shape identifier. The return value is one of
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/gui/kernel/qcursor.h qtbase-opensource-src-5.6.3/src/gui/kernel/qcursor.h
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/gui/kernel/qcursor.h 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/gui/kernel/qcursor.h 2023-10-17 14:38:05.869731000 +0800
|
||||||
|
@@ -102,9 +102,13 @@
|
||||||
|
inline static void setPos(QScreen *screen, const QPoint &p) { setPos(screen, p.x(), p.y()); }
|
||||||
|
|
||||||
|
private:
|
||||||
|
+ friend Q_GUI_EXPORT bool operator==(const QCursor &lhs, const QCursor &rhs) Q_DECL_NOTHROW;
|
||||||
|
QCursorData *d;
|
||||||
|
};
|
||||||
|
|
||||||
|
+Q_GUI_EXPORT bool operator==(const QCursor &lhs, const QCursor &rhs) Q_DECL_NOTHROW;
|
||||||
|
+inline bool operator!=(const QCursor &lhs, const QCursor &rhs) Q_DECL_NOTHROW { return !(lhs == rhs); }
|
||||||
|
+
|
||||||
|
/*****************************************************************************
|
||||||
|
QCursor stream functions
|
||||||
|
*****************************************************************************/
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/gui/text/qfontmetrics.cpp qtbase-opensource-src-5.6.3/src/gui/text/qfontmetrics.cpp
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/gui/text/qfontmetrics.cpp 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/gui/text/qfontmetrics.cpp 2023-10-17 14:38:05.869731000 +0800
|
||||||
|
@@ -586,6 +586,17 @@
|
||||||
|
return qRound(advance);
|
||||||
|
}
|
||||||
|
|
||||||
|
+// Rdd Panda C++: forward to `width`.
|
||||||
|
+int QFontMetrics::horizontalAdvance(const QString &text, int len) const
|
||||||
|
+{
|
||||||
|
+ return width(text, len);
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+int QFontMetrics::horizontalAdvance(QChar ch) const
|
||||||
|
+{
|
||||||
|
+ return width(ch);
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
#if QT_VERSION < QT_VERSION_CHECK(6,0,0)
|
||||||
|
/*! \obsolete
|
||||||
|
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/gui/text/qfontmetrics.h qtbase-opensource-src-5.6.3/src/gui/text/qfontmetrics.h
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/gui/text/qfontmetrics.h 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/gui/text/qfontmetrics.h 2023-10-17 14:38:05.869731000 +0800
|
||||||
|
@@ -86,6 +86,10 @@
|
||||||
|
int width(const QString &, int len, int flags) const;
|
||||||
|
|
||||||
|
int width(QChar) const;
|
||||||
|
+
|
||||||
|
+ int horizontalAdvance(const QString &, int len = -1) const;
|
||||||
|
+ int horizontalAdvance(QChar) const;
|
||||||
|
+
|
||||||
|
#if QT_VERSION < QT_VERSION_CHECK(6,0,0)
|
||||||
|
QT_DEPRECATED int charWidth(const QString &str, int pos) const;
|
||||||
|
#endif
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/widgets/kernel/qaction.h qtbase-opensource-src-5.6.3/src/widgets/kernel/qaction.h
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/widgets/kernel/qaction.h 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/widgets/kernel/qaction.h 2023-10-18 08:45:39.996548800 +0800
|
||||||
|
@@ -84,9 +84,9 @@
|
||||||
|
NormalPriority = 128,
|
||||||
|
HighPriority = 256};
|
||||||
|
Q_ENUM(Priority)
|
||||||
|
- explicit QAction(QObject* parent);
|
||||||
|
- QAction(const QString &text, QObject* parent);
|
||||||
|
- QAction(const QIcon &icon, const QString &text, QObject* parent);
|
||||||
|
+ explicit QAction(QObject* parent = nullptr);
|
||||||
|
+ QAction(const QString &text, QObject* parent = nullptr);
|
||||||
|
+ QAction(const QIcon &icon, const QString &text, QObject* parent = nullptr);
|
||||||
|
|
||||||
|
~QAction();
|
||||||
|
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/widgets/kernel/qwidget.cpp qtbase-opensource-src-5.6.3/src/widgets/kernel/qwidget.cpp
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/widgets/kernel/qwidget.cpp 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/widgets/kernel/qwidget.cpp 2023-10-18 07:11:39.982967700 +0800
|
||||||
|
@@ -10337,6 +10337,15 @@
|
||||||
|
d->setWindowFlags(flags);
|
||||||
|
}
|
||||||
|
|
||||||
|
+void QWidget::setWindowFlag(Qt::WindowType flag, bool on)
|
||||||
|
+{
|
||||||
|
+ Q_D(QWidget);
|
||||||
|
+ if (on)
|
||||||
|
+ d->setWindowFlags(data->window_flags | flag);
|
||||||
|
+ else
|
||||||
|
+ d->setWindowFlags(data->window_flags & ~flag);
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
/*! \internal
|
||||||
|
|
||||||
|
Implemented in QWidgetPrivate so that QMdiSubWindowPrivate can reimplement it.
|
||||||
|
diff --unified --recursive --text qtbase-opensource-src-5.6.3.orig/src/widgets/kernel/qwidget.h qtbase-opensource-src-5.6.3/src/widgets/kernel/qwidget.h
|
||||||
|
--- qtbase-opensource-src-5.6.3.orig/src/widgets/kernel/qwidget.h 2017-09-06 20:13:54.000000000 +0800
|
||||||
|
+++ qtbase-opensource-src-5.6.3/src/widgets/kernel/qwidget.h 2023-10-18 07:10:13.033316200 +0800
|
||||||
|
@@ -554,6 +554,7 @@
|
||||||
|
|
||||||
|
void setWindowFlags(Qt::WindowFlags type);
|
||||||
|
inline Qt::WindowFlags windowFlags() const;
|
||||||
|
+ void setWindowFlag(Qt::WindowType, bool on = true);
|
||||||
|
void overrideWindowFlags(Qt::WindowFlags type);
|
||||||
|
|
||||||
|
inline Qt::WindowType windowType() const;
|
|
@ -28,7 +28,8 @@ LIBS+= \
|
||||||
}
|
}
|
||||||
|
|
||||||
win32: {
|
win32: {
|
||||||
DEFINES += _WIN32_WINNT=0x0601
|
DEFINES += _WIN32_WINNT=0x0501
|
||||||
|
LIBS += -lpsapi # GetProcessMemoryInfo
|
||||||
}
|
}
|
||||||
|
|
||||||
CONFIG += lrelease
|
CONFIG += lrelease
|
||||||
|
|
Loading…
Reference in New Issue