Merge remote-tracking branch 'origin/5.11' into dev
Conflicts: src/plugins/platforms/cocoa/qnsview.mm src/plugins/platforms/cocoa/qnsview_mouse.mm src/testlib/testlib.pro Change-Id: Ia0ce4243418fe6a485b0f290c67bd433b3b04ff2
This commit is contained in:
commit
794781e7cf
@ -15,7 +15,8 @@
|
||||
"src/xml",
|
||||
"src/widgets",
|
||||
"src/printsupport",
|
||||
"src/plugins/sqldrivers"
|
||||
"src/plugins/sqldrivers",
|
||||
"src/testlib"
|
||||
],
|
||||
|
||||
"commandline": {
|
||||
|
@ -87,10 +87,12 @@ void PathStrokeControls::createCommonControls(QWidget* parent)
|
||||
m_joinGroup->setSizePolicy(QSizePolicy::Minimum, QSizePolicy::Fixed);
|
||||
QRadioButton *bevelJoin = new QRadioButton(m_joinGroup);
|
||||
QRadioButton *miterJoin = new QRadioButton(m_joinGroup);
|
||||
QRadioButton *svgMiterJoin = new QRadioButton(m_joinGroup);
|
||||
QRadioButton *roundJoin = new QRadioButton(m_joinGroup);
|
||||
m_joinGroup->setTitle(tr("Join Style"));
|
||||
bevelJoin->setText(tr("Bevel"));
|
||||
miterJoin->setText(tr("Miter"));
|
||||
svgMiterJoin->setText(tr("SvgMiter"));
|
||||
roundJoin->setText(tr("Round"));
|
||||
|
||||
m_styleGroup = new QGroupBox(parent);
|
||||
@ -145,6 +147,7 @@ void PathStrokeControls::createCommonControls(QWidget* parent)
|
||||
QVBoxLayout *joinGroupLayout = new QVBoxLayout(m_joinGroup);
|
||||
joinGroupLayout->addWidget(bevelJoin);
|
||||
joinGroupLayout->addWidget(miterJoin);
|
||||
joinGroupLayout->addWidget(svgMiterJoin);
|
||||
joinGroupLayout->addWidget(roundJoin);
|
||||
|
||||
QVBoxLayout *styleGroupLayout = new QVBoxLayout(m_styleGroup);
|
||||
@ -167,6 +170,7 @@ void PathStrokeControls::createCommonControls(QWidget* parent)
|
||||
|
||||
connect(bevelJoin, SIGNAL(clicked()), m_renderer, SLOT(setBevelJoin()));
|
||||
connect(miterJoin, SIGNAL(clicked()), m_renderer, SLOT(setMiterJoin()));
|
||||
connect(svgMiterJoin, SIGNAL(clicked()), m_renderer, SLOT(setSvgMiterJoin()));
|
||||
connect(roundJoin, SIGNAL(clicked()), m_renderer, SLOT(setRoundJoin()));
|
||||
|
||||
connect(curveMode, SIGNAL(clicked()), m_renderer, SLOT(setCurveMode()));
|
||||
|
@ -92,6 +92,7 @@ public slots:
|
||||
|
||||
void setBevelJoin() { m_joinStyle = Qt::BevelJoin; update(); }
|
||||
void setMiterJoin() { m_joinStyle = Qt::MiterJoin; update(); }
|
||||
void setSvgMiterJoin() { m_joinStyle = Qt::SvgMiterJoin; update(); }
|
||||
void setRoundJoin() { m_joinStyle = Qt::RoundJoin; update(); }
|
||||
|
||||
void setCurveMode() { m_pathMode = CurveMode; update(); }
|
||||
|
@ -20,7 +20,7 @@ isEmpty(CTEST_VERSION) {
|
||||
return()
|
||||
}
|
||||
|
||||
!versionAtLeast(CMAKE_VERSION, 2.8.3) {
|
||||
!versionAtLeast(CMAKE_VERSION, 3.1.0) {
|
||||
message("cmake $$CMAKE_VERSION is too old for this test.")
|
||||
return()
|
||||
}
|
||||
|
@ -1,13 +1,7 @@
|
||||
|
||||
!!IF !equals(TEMPLATE, aux)
|
||||
if (CMAKE_VERSION VERSION_LESS 2.8.3)
|
||||
message(FATAL_ERROR \"Qt 5 requires at least CMake version 2.8.3\")
|
||||
if (CMAKE_VERSION VERSION_LESS 3.1.0)
|
||||
message(FATAL_ERROR \"Qt 5 $${CMAKE_MODULE_NAME} module requires at least CMake version 3.1.0\")
|
||||
endif()
|
||||
!!ELSE
|
||||
if (CMAKE_VERSION VERSION_LESS 3.0.0)
|
||||
message(FATAL_ERROR \"Qt 5 $${CMAKE_MODULE_NAME} module requires at least CMake version 3.0.0\")
|
||||
endif()
|
||||
!!ENDIF
|
||||
|
||||
!!IF !isEmpty(CMAKE_USR_MOVE_WORKAROUND)
|
||||
!!IF !isEmpty(CMAKE_LIB_DIR_IS_ABSOLUTE)
|
||||
@ -161,9 +155,7 @@ if (NOT TARGET Qt5::$${CMAKE_MODULE_NAME})
|
||||
set(_Qt5$${CMAKE_MODULE_NAME}_MODULE_DEPENDENCIES \"$${CMAKE_MODULE_DEPS}\")
|
||||
|
||||
!!IF !isEmpty(CMAKE_INTERFACE_MODULE_DEPS)
|
||||
if (NOT CMAKE_VERSION VERSION_LESS 3.0.0)
|
||||
list(APPEND _Qt5$${CMAKE_MODULE_NAME}_MODULE_DEPENDENCIES \"$${CMAKE_INTERFACE_MODULE_DEPS}\")
|
||||
endif()
|
||||
list(APPEND _Qt5$${CMAKE_MODULE_NAME}_MODULE_DEPENDENCIES \"$${CMAKE_INTERFACE_MODULE_DEPS}\")
|
||||
!!ENDIF
|
||||
|
||||
set(Qt5$${CMAKE_MODULE_NAME}_OWN_PRIVATE_INCLUDE_DIRS ${Qt5$${CMAKE_MODULE_NAME}_PRIVATE_INCLUDE_DIRS})
|
||||
@ -219,9 +211,7 @@ if (NOT TARGET Qt5::$${CMAKE_MODULE_NAME})
|
||||
set(_Qt5$${CMAKE_MODULE_NAME}_LIB_DEPENDENCIES \"$${CMAKE_QT5_MODULE_DEPS}\")
|
||||
|
||||
!!IF !isEmpty(CMAKE_INTERFACE_QT5_MODULE_DEPS)
|
||||
if (NOT CMAKE_VERSION VERSION_LESS 3.0.0)
|
||||
list(APPEND _Qt5$${CMAKE_MODULE_NAME}_LIB_DEPENDENCIES \"$${CMAKE_INTERFACE_QT5_MODULE_DEPS}\")
|
||||
endif()
|
||||
list(APPEND _Qt5$${CMAKE_MODULE_NAME}_LIB_DEPENDENCIES \"$${CMAKE_INTERFACE_QT5_MODULE_DEPS}\")
|
||||
!!ENDIF
|
||||
|
||||
!!IF !isEmpty(CMAKE_STATIC_TYPE)
|
||||
@ -252,8 +242,7 @@ if (NOT TARGET Qt5::$${CMAKE_MODULE_NAME})
|
||||
endif()
|
||||
endforeach()
|
||||
|
||||
if (_Qt5$${CMAKE_MODULE_NAME}_PRIVATE_DIRS_EXIST
|
||||
AND NOT CMAKE_VERSION VERSION_LESS 3.0.0 )
|
||||
if (_Qt5$${CMAKE_MODULE_NAME}_PRIVATE_DIRS_EXIST)
|
||||
add_library(Qt5::$${CMAKE_MODULE_NAME}Private INTERFACE IMPORTED)
|
||||
set_property(TARGET Qt5::$${CMAKE_MODULE_NAME}Private PROPERTY
|
||||
INTERFACE_INCLUDE_DIRECTORIES ${Qt5$${CMAKE_MODULE_NAME}_OWN_PRIVATE_INCLUDE_DIRS}
|
||||
|
@ -2913,7 +2913,8 @@
|
||||
Returns the absolute path of \c path.
|
||||
|
||||
If \c base is not specified, uses the current directory as the base
|
||||
directory.
|
||||
directory. If it is a relative path, it is resolved relative to the current
|
||||
directory before use.
|
||||
|
||||
For example, the following call returns the string
|
||||
\c {"/home/johndoe/myproject/readme.txt"}:
|
||||
@ -3152,9 +3153,15 @@
|
||||
|
||||
\section2 relative_path(filePath[, base])
|
||||
|
||||
Returns the path to \c filePath relative to \c base. If \c base is not
|
||||
specified, it is the current project directory. This function is a wrapper
|
||||
around QDir::relativeFilePath.
|
||||
Returns the path to \c filePath relative to \c base.
|
||||
|
||||
If \c base is not specified, it is the current project
|
||||
directory. If it is relative, it is resolved relative to the
|
||||
current project directory before use.
|
||||
|
||||
If \c filePath is relative, it is first resolved against the base
|
||||
directory; in that case, this function effectively acts as
|
||||
$$clean_path().
|
||||
|
||||
See also \l{absolute_path(path[, base])}{absolute_path()},
|
||||
\l{clean_path(path)}{clean_path()}.
|
||||
|
@ -103,7 +103,7 @@ QString IoUtils::resolvePath(const QString &baseDir, const QString &fileName)
|
||||
return QDir::cleanPath(fileName);
|
||||
#ifdef Q_OS_WIN // Add drive to otherwise-absolute path:
|
||||
if (fileName.at(0).unicode() == '/' || fileName.at(0).unicode() == '\\') {
|
||||
Q_ASSERT(isAbsolutePath(baseDir));
|
||||
Q_ASSERT_X(isAbsolutePath(baseDir), "IoUtils::resolvePath", qUtf8Printable(baseDir));
|
||||
return QDir::cleanPath(baseDir.left(2) + fileName);
|
||||
}
|
||||
#endif // Q_OS_WIN
|
||||
|
@ -1178,7 +1178,9 @@ QMakeEvaluator::VisitReturn QMakeEvaluator::evaluateBuiltinExpand(
|
||||
evalError(fL1S("absolute_path(path[, base]) requires one or two arguments."));
|
||||
} else {
|
||||
QString arg = args.at(0).toQString(m_tmp1);
|
||||
QString baseDir = args.count() > 1 ? args.at(1).toQString(m_tmp2) : currentDirectory();
|
||||
QString baseDir = args.count() > 1
|
||||
? IoUtils::resolvePath(currentDirectory(), args.at(1).toQString(m_tmp2))
|
||||
: currentDirectory();
|
||||
QString rstr = arg.isEmpty() ? baseDir : IoUtils::resolvePath(baseDir, arg);
|
||||
ret << (rstr.isSharedWith(m_tmp1)
|
||||
? args.at(0)
|
||||
@ -1192,7 +1194,9 @@ QMakeEvaluator::VisitReturn QMakeEvaluator::evaluateBuiltinExpand(
|
||||
evalError(fL1S("relative_path(path[, base]) requires one or two arguments."));
|
||||
} else {
|
||||
QString arg = args.at(0).toQString(m_tmp1);
|
||||
QString baseDir = args.count() > 1 ? args.at(1).toQString(m_tmp2) : currentDirectory();
|
||||
QString baseDir = args.count() > 1
|
||||
? IoUtils::resolvePath(currentDirectory(), args.at(1).toQString(m_tmp2))
|
||||
: currentDirectory();
|
||||
QString absArg = arg.isEmpty() ? baseDir : IoUtils::resolvePath(baseDir, arg);
|
||||
QString rstr = QDir(baseDir).relativeFilePath(absArg);
|
||||
ret << (rstr.isSharedWith(m_tmp1) ? args.at(0) : ProString(rstr).setSource(args.at(0)));
|
||||
|
@ -1,6 +1,6 @@
|
||||
|
||||
if (CMAKE_VERSION VERSION_LESS 2.8.9)
|
||||
message(FATAL_ERROR \"Qt5 requires at least CMake version 2.8.9\")
|
||||
if (CMAKE_VERSION VERSION_LESS 3.1.0)
|
||||
message(FATAL_ERROR \"Qt5 requires at least CMake version 3.1.0\")
|
||||
endif()
|
||||
|
||||
if (NOT Qt5_FIND_COMPONENTS)
|
||||
|
@ -78,27 +78,10 @@ set(Qt5_POSITION_INDEPENDENT_CODE True)
|
||||
# Applications now need to be compiled with the -fPIC option if the Qt option
|
||||
# \"reduce relocations\" is active. For backward compatibility only, Qt accepts
|
||||
# the use of -fPIE for GCC 4.x versions.
|
||||
if (CMAKE_VERSION VERSION_LESS 2.8.12
|
||||
AND (NOT CMAKE_CXX_COMPILER_ID STREQUAL \"GNU\"
|
||||
OR CMAKE_CXX_COMPILER_VERSION VERSION_LESS 5.0))
|
||||
set_property(TARGET Qt5::Core APPEND PROPERTY INTERFACE_POSITION_INDEPENDENT_CODE \"ON\")
|
||||
else()
|
||||
set_property(TARGET Qt5::Core APPEND PROPERTY INTERFACE_COMPILE_OPTIONS $$QMAKE_CXXFLAGS_APP)
|
||||
endif()
|
||||
set_property(TARGET Qt5::Core APPEND PROPERTY INTERFACE_COMPILE_OPTIONS $$QMAKE_CXXFLAGS_APP)
|
||||
|
||||
# Applications using qmake or cmake >= 2.8.12 as their build system will
|
||||
# adapt automatically. Applications using an older release of cmake in
|
||||
# combination with GCC 5.x need to change their CMakeLists.txt to add
|
||||
# Qt5Core_EXECUTABLE_COMPILE_FLAGS to CMAKE_CXX_FLAGS. In particular,
|
||||
# applications using cmake >= 2.8.9 and < 2.8.11 will continue to build
|
||||
# with the -fPIE option and invoke the special compatibility mode if using
|
||||
# GCC 4.x.
|
||||
# TODO Qt6: Remove
|
||||
set(Qt5Core_EXECUTABLE_COMPILE_FLAGS \"\")
|
||||
if (CMAKE_VERSION VERSION_LESS 2.8.12
|
||||
AND (CMAKE_CXX_COMPILER_ID STREQUAL \"GNU\"
|
||||
AND NOT CMAKE_CXX_COMPILER_VERSION VERSION_LESS 5.0))
|
||||
set(Qt5Core_EXECUTABLE_COMPILE_FLAGS \"-fPIC\")
|
||||
endif()
|
||||
|
||||
!!IF !isEmpty(QT_NAMESPACE)
|
||||
list(APPEND Qt5Core_DEFINITIONS -DQT_NAMESPACE=$$QT_NAMESPACE)
|
||||
@ -157,7 +140,7 @@ if (NOT TARGET Qt5::WinMain)
|
||||
)
|
||||
!!ENDIF
|
||||
|
||||
if (NOT CMAKE_VERSION VERSION_LESS 2.8.11 AND NOT Qt5_NO_LINK_QTMAIN)
|
||||
if (NOT Qt5_NO_LINK_QTMAIN)
|
||||
set(_isExe $<STREQUAL:$<TARGET_PROPERTY:TYPE>,EXECUTABLE>)
|
||||
set(_isWin32 $<BOOL:$<TARGET_PROPERTY:WIN32_EXECUTABLE>>)
|
||||
set(_isNotExcluded $<NOT:$<BOOL:$<TARGET_PROPERTY:Qt5_NO_LINK_QTMAIN>>>)
|
||||
|
@ -152,9 +152,6 @@ function(QT5_GENERATE_MOC infile outfile )
|
||||
set(_outfile "${CMAKE_CURRENT_BINARY_DIR}/${outfile}")
|
||||
endif()
|
||||
if ("x${ARGV2}" STREQUAL "xTARGET")
|
||||
if (CMAKE_VERSION VERSION_LESS 2.8.12)
|
||||
message(FATAL_ERROR "The TARGET parameter to qt5_generate_moc is only available when using CMake 2.8.12 or later.")
|
||||
endif()
|
||||
set(moc_target ${ARGV3})
|
||||
endif()
|
||||
qt5_create_moc_command(${abs_infile} ${_outfile} "${moc_flags}" "" "${moc_target}" "")
|
||||
@ -178,9 +175,6 @@ function(QT5_WRAP_CPP outfiles )
|
||||
set(moc_target ${_WRAP_CPP_TARGET})
|
||||
set(moc_depends ${_WRAP_CPP_DEPENDS})
|
||||
|
||||
if (moc_target AND CMAKE_VERSION VERSION_LESS 2.8.12)
|
||||
message(FATAL_ERROR "The TARGET parameter to qt5_wrap_cpp is only available when using CMake 2.8.12 or later.")
|
||||
endif()
|
||||
foreach(it ${moc_files})
|
||||
get_filename_component(it ${it} ABSOLUTE)
|
||||
qt5_make_output_file(${it} moc_ cpp outfile)
|
||||
@ -300,54 +294,3 @@ function(QT5_ADD_RESOURCES outfiles )
|
||||
endfunction()
|
||||
|
||||
set(_Qt5_COMPONENT_PATH "${CMAKE_CURRENT_LIST_DIR}/..")
|
||||
|
||||
if (NOT CMAKE_VERSION VERSION_LESS 2.8.9)
|
||||
macro(qt5_use_modules _target _link_type)
|
||||
if(NOT CMAKE_MINIMUM_REQUIRED_VERSION VERSION_LESS 2.8.11)
|
||||
if(CMAKE_WARN_DEPRECATED)
|
||||
set(messageType WARNING)
|
||||
endif()
|
||||
if(CMAKE_ERROR_DEPRECATED)
|
||||
set(messageType FATAL_ERROR)
|
||||
endif()
|
||||
if(messageType)
|
||||
message(${messageType} "The qt5_use_modules macro is obsolete. Use target_link_libraries with IMPORTED targets instead.")
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if (NOT TARGET ${_target})
|
||||
message(FATAL_ERROR "The first argument to qt5_use_modules must be an existing target.")
|
||||
endif()
|
||||
if ("${_link_type}" STREQUAL "LINK_PUBLIC" OR "${_link_type}" STREQUAL "LINK_PRIVATE" )
|
||||
set(_qt5_modules ${ARGN})
|
||||
set(_qt5_link_type ${_link_type})
|
||||
else()
|
||||
set(_qt5_modules ${_link_type} ${ARGN})
|
||||
endif()
|
||||
|
||||
if ("${_qt5_modules}" STREQUAL "")
|
||||
message(FATAL_ERROR "qt5_use_modules requires at least one Qt module to use.")
|
||||
endif()
|
||||
|
||||
foreach(_module ${_qt5_modules})
|
||||
if (NOT Qt5${_module}_FOUND)
|
||||
find_package(Qt5${_module} PATHS "${_Qt5_COMPONENT_PATH}" NO_DEFAULT_PATH)
|
||||
if (NOT Qt5${_module}_FOUND)
|
||||
message(FATAL_ERROR "Can not use \"${_module}\" module which has not yet been found.")
|
||||
endif()
|
||||
endif()
|
||||
target_link_libraries(${_target} ${_qt5_link_type} ${Qt5${_module}_LIBRARIES})
|
||||
set_property(TARGET ${_target} APPEND PROPERTY INCLUDE_DIRECTORIES ${Qt5${_module}_INCLUDE_DIRS})
|
||||
set_property(TARGET ${_target} APPEND PROPERTY COMPILE_DEFINITIONS ${Qt5${_module}_COMPILE_DEFINITIONS})
|
||||
set_property(TARGET ${_target} APPEND PROPERTY COMPILE_DEFINITIONS_RELEASE QT_NO_DEBUG)
|
||||
set_property(TARGET ${_target} APPEND PROPERTY COMPILE_DEFINITIONS_RELWITHDEBINFO QT_NO_DEBUG)
|
||||
set_property(TARGET ${_target} APPEND PROPERTY COMPILE_DEFINITIONS_MINSIZEREL QT_NO_DEBUG)
|
||||
if (Qt5_POSITION_INDEPENDENT_CODE
|
||||
AND (CMAKE_VERSION VERSION_LESS 2.8.12
|
||||
AND (NOT CMAKE_CXX_COMPILER_ID STREQUAL "GNU"
|
||||
OR CMAKE_CXX_COMPILER_VERSION VERSION_LESS 5.0)))
|
||||
set_property(TARGET ${_target} PROPERTY POSITION_INDEPENDENT_CODE ${Qt5_POSITION_INDEPENDENT_CODE})
|
||||
endif()
|
||||
endforeach()
|
||||
endmacro()
|
||||
endif()
|
||||
|
@ -87,6 +87,7 @@
|
||||
#define QT_FEATURE_journald -1
|
||||
#define QT_FEATURE_futimens -1
|
||||
#define QT_FEATURE_futimes -1
|
||||
#define QT_FEATURE_itemmodel -1
|
||||
#define QT_FEATURE_library -1
|
||||
#ifdef __linux__
|
||||
# define QT_FEATURE_linkat 1
|
||||
|
@ -676,8 +676,11 @@ QFile::rename(const QString &newName)
|
||||
return !error;
|
||||
}
|
||||
close();
|
||||
d->setError(QFile::RenameError,
|
||||
tr("Cannot open destination file: %1").arg(out.errorString()));
|
||||
} else {
|
||||
d->setError(QFile::RenameError, errorString());
|
||||
}
|
||||
d->setError(QFile::RenameError, out.isOpen() ? errorString() : out.errorString());
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
@ -1,20 +1,46 @@
|
||||
# Qt itemmodels core module
|
||||
|
||||
!qtConfig(itemmodel): return()
|
||||
|
||||
HEADERS += \
|
||||
itemmodels/qabstractitemmodel.h \
|
||||
itemmodels/qabstractitemmodel_p.h \
|
||||
itemmodels/qabstractproxymodel.h \
|
||||
itemmodels/qabstractproxymodel_p.h \
|
||||
itemmodels/qitemselectionmodel.h \
|
||||
itemmodels/qitemselectionmodel_p.h \
|
||||
itemmodels/qidentityproxymodel.h \
|
||||
itemmodels/qsortfilterproxymodel.h \
|
||||
itemmodels/qstringlistmodel.h
|
||||
itemmodels/qitemselectionmodel_p.h
|
||||
|
||||
SOURCES += \
|
||||
itemmodels/qabstractitemmodel.cpp \
|
||||
itemmodels/qabstractproxymodel.cpp \
|
||||
itemmodels/qitemselectionmodel.cpp \
|
||||
itemmodels/qidentityproxymodel.cpp \
|
||||
itemmodels/qsortfilterproxymodel.cpp \
|
||||
itemmodels/qstringlistmodel.cpp
|
||||
itemmodels/qitemselectionmodel.cpp
|
||||
|
||||
qtConfig(proxymodel) {
|
||||
HEADERS += \
|
||||
itemmodels/qabstractproxymodel.h \
|
||||
itemmodels/qabstractproxymodel_p.h
|
||||
|
||||
SOURCES += \
|
||||
itemmodels/qabstractproxymodel.cpp
|
||||
|
||||
qtConfig(identityproxymodel) {
|
||||
HEADERS += \
|
||||
itemmodels/qidentityproxymodel.h
|
||||
|
||||
SOURCES += \
|
||||
itemmodels/qidentityproxymodel.cpp
|
||||
}
|
||||
|
||||
qtConfig(sortfilterproxymodel) {
|
||||
HEADERS += \
|
||||
itemmodels/qsortfilterproxymodel.h
|
||||
|
||||
SOURCES += \
|
||||
itemmodels/qsortfilterproxymodel.cpp
|
||||
}
|
||||
}
|
||||
|
||||
qtConfig(stringlistmodel) {
|
||||
HEADERS += \
|
||||
itemmodels/qstringlistmodel.h
|
||||
|
||||
SOURCES += \
|
||||
itemmodels/qstringlistmodel.cpp
|
||||
}
|
||||
|
@ -45,6 +45,8 @@
|
||||
#include <QtCore/qhash.h>
|
||||
#include <QtCore/qvector.h>
|
||||
|
||||
QT_REQUIRE_CONFIG(itemmodel);
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
|
||||
|
@ -60,6 +60,8 @@
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
QT_REQUIRE_CONFIG(itemmodel);
|
||||
|
||||
class QPersistentModelIndexData
|
||||
{
|
||||
public:
|
||||
|
@ -38,9 +38,6 @@
|
||||
****************************************************************************/
|
||||
|
||||
#include "qabstractproxymodel.h"
|
||||
|
||||
#ifndef QT_NO_PROXYMODEL
|
||||
|
||||
#include "qitemselectionmodel.h"
|
||||
#include <private/qabstractproxymodel_p.h>
|
||||
#include <QtCore/QSize>
|
||||
@ -471,5 +468,3 @@ Qt::DropActions QAbstractProxyModel::supportedDropActions() const
|
||||
QT_END_NAMESPACE
|
||||
|
||||
#include "moc_qabstractproxymodel.cpp"
|
||||
|
||||
#endif // QT_NO_PROXYMODEL
|
||||
|
@ -42,11 +42,10 @@
|
||||
|
||||
#include <QtCore/qabstractitemmodel.h>
|
||||
|
||||
QT_REQUIRE_CONFIG(proxymodel);
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
|
||||
#ifndef QT_NO_PROXYMODEL
|
||||
|
||||
class QAbstractProxyModelPrivate;
|
||||
class QItemSelection;
|
||||
|
||||
@ -112,8 +111,6 @@ private:
|
||||
Q_PRIVATE_SLOT(d_func(), void _q_sourceModelDestroyed())
|
||||
};
|
||||
|
||||
#endif // QT_NO_PROXYMODEL
|
||||
|
||||
QT_END_NAMESPACE
|
||||
|
||||
#endif // QABSTRACTPROXYMODEL_H
|
||||
|
@ -54,7 +54,7 @@
|
||||
|
||||
#include "private/qabstractitemmodel_p.h"
|
||||
|
||||
#ifndef QT_NO_PROXYMODEL
|
||||
QT_REQUIRE_CONFIG(proxymodel);
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
@ -71,6 +71,4 @@ public:
|
||||
|
||||
QT_END_NAMESPACE
|
||||
|
||||
#endif // QT_NO_PROXYMODEL
|
||||
|
||||
#endif // QABSTRACTPROXYMODEL_P_H
|
||||
|
@ -38,9 +38,6 @@
|
||||
****************************************************************************/
|
||||
|
||||
#include "qidentityproxymodel.h"
|
||||
|
||||
#ifndef QT_NO_IDENTITYPROXYMODEL
|
||||
|
||||
#include "qitemselectionmodel.h"
|
||||
#include <private/qabstractproxymodel_p.h>
|
||||
|
||||
@ -616,5 +613,3 @@ void QIdentityProxyModelPrivate::_q_sourceRowsRemoved(const QModelIndex &parent,
|
||||
QT_END_NAMESPACE
|
||||
|
||||
#include "moc_qidentityproxymodel.cpp"
|
||||
|
||||
#endif // QT_NO_IDENTITYPROXYMODEL
|
||||
|
@ -43,7 +43,7 @@
|
||||
|
||||
#include <QtCore/qabstractproxymodel.h>
|
||||
|
||||
#ifndef QT_NO_IDENTITYPROXYMODEL
|
||||
QT_REQUIRE_CONFIG(identityproxymodel);
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
@ -110,7 +110,5 @@ private:
|
||||
|
||||
QT_END_NAMESPACE
|
||||
|
||||
#endif // QT_NO_IDENTITYPROXYMODEL
|
||||
|
||||
#endif // QIDENTITYPROXYMODEL_H
|
||||
|
||||
|
@ -47,6 +47,8 @@
|
||||
#include <QtCore/qlist.h>
|
||||
#include <QtCore/qabstractitemmodel.h>
|
||||
|
||||
QT_REQUIRE_CONFIG(itemmodel);
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
class Q_CORE_EXPORT QItemSelectionRange
|
||||
|
@ -53,6 +53,8 @@
|
||||
|
||||
#include "private/qobject_p.h"
|
||||
|
||||
QT_REQUIRE_CONFIG(itemmodel);
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
class QItemSelectionModelPrivate: public QObjectPrivate
|
||||
|
@ -38,9 +38,6 @@
|
||||
****************************************************************************/
|
||||
|
||||
#include "qsortfilterproxymodel.h"
|
||||
|
||||
#ifndef QT_NO_SORTFILTERPROXYMODEL
|
||||
|
||||
#include "qitemselectionmodel.h"
|
||||
#include <qsize.h>
|
||||
#include <qdebug.h>
|
||||
@ -2896,5 +2893,3 @@ QItemSelection QSortFilterProxyModel::mapSelectionFromSource(const QItemSelectio
|
||||
QT_END_NAMESPACE
|
||||
|
||||
#include "moc_qsortfilterproxymodel.cpp"
|
||||
|
||||
#endif // QT_NO_SORTFILTERPROXYMODEL
|
||||
|
@ -41,11 +41,10 @@
|
||||
#define QSORTFILTERPROXYMODEL_H
|
||||
|
||||
#include <QtCore/qabstractproxymodel.h>
|
||||
|
||||
#ifndef QT_NO_SORTFILTERPROXYMODEL
|
||||
|
||||
#include <QtCore/qregexp.h>
|
||||
|
||||
QT_REQUIRE_CONFIG(sortfilterproxymodel);
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
|
||||
@ -198,6 +197,4 @@ private:
|
||||
|
||||
QT_END_NAMESPACE
|
||||
|
||||
#endif // QT_NO_SORTFILTERPROXYMODEL
|
||||
|
||||
#endif // QSORTFILTERPROXYMODEL_H
|
||||
|
@ -47,8 +47,6 @@
|
||||
|
||||
#include <algorithm>
|
||||
|
||||
#ifndef QT_NO_STRINGLISTMODEL
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
/*!
|
||||
@ -329,5 +327,3 @@ Qt::DropActions QStringListModel::supportedDropActions() const
|
||||
QT_END_NAMESPACE
|
||||
|
||||
#include "moc_qstringlistmodel.cpp"
|
||||
|
||||
#endif // QT_NO_STRINGLISTMODEL
|
||||
|
@ -43,11 +43,10 @@
|
||||
#include <QtCore/qabstractitemmodel.h>
|
||||
#include <QtCore/qstringlist.h>
|
||||
|
||||
QT_REQUIRE_CONFIG(stringlistmodel);
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
|
||||
#ifndef QT_NO_STRINGLISTMODEL
|
||||
|
||||
class Q_CORE_EXPORT QStringListModel : public QAbstractListModel
|
||||
{
|
||||
Q_OBJECT
|
||||
@ -78,8 +77,6 @@ private:
|
||||
QStringList lst;
|
||||
};
|
||||
|
||||
#endif // QT_NO_STRINGLISTMODEL
|
||||
|
||||
QT_END_NAMESPACE
|
||||
|
||||
#endif // QSTRINGLISTMODEL_H
|
||||
|
@ -61,7 +61,6 @@
|
||||
# include "qbitarray.h"
|
||||
# include "qurl.h"
|
||||
# include "qvariant.h"
|
||||
# include "qabstractitemmodel.h"
|
||||
# include "qjsonvalue.h"
|
||||
# include "qjsonobject.h"
|
||||
# include "qjsonarray.h"
|
||||
@ -69,6 +68,10 @@
|
||||
# include "qbytearraylist.h"
|
||||
#endif
|
||||
|
||||
#if QT_CONFIG(itemmodel)
|
||||
# include "qabstractitemmodel.h"
|
||||
#endif
|
||||
|
||||
#ifndef QT_NO_GEOM_VARIANT
|
||||
# include "qsize.h"
|
||||
# include "qpoint.h"
|
||||
@ -1349,8 +1352,10 @@ bool QMetaType::save(QDataStream &stream, int type, const void *data)
|
||||
case QMetaType::Void:
|
||||
case QMetaType::VoidStar:
|
||||
case QMetaType::QObjectStar:
|
||||
#if QT_CONFIG(itemmodel)
|
||||
case QMetaType::QModelIndex:
|
||||
case QMetaType::QPersistentModelIndex:
|
||||
#endif
|
||||
case QMetaType::QJsonValue:
|
||||
case QMetaType::QJsonObject:
|
||||
case QMetaType::QJsonArray:
|
||||
@ -1573,8 +1578,10 @@ bool QMetaType::load(QDataStream &stream, int type, void *data)
|
||||
case QMetaType::Void:
|
||||
case QMetaType::VoidStar:
|
||||
case QMetaType::QObjectStar:
|
||||
#if QT_CONFIG(itemmodel)
|
||||
case QMetaType::QModelIndex:
|
||||
case QMetaType::QPersistentModelIndex:
|
||||
#endif
|
||||
case QMetaType::QJsonValue:
|
||||
case QMetaType::QJsonObject:
|
||||
case QMetaType::QJsonArray:
|
||||
|
@ -89,6 +89,14 @@ inline Q_DECL_CONSTEXPR int qMetaTypeId();
|
||||
#define QT_FOR_EACH_STATIC_PRIMITIVE_POINTER(F)\
|
||||
F(VoidStar, 31, void*) \
|
||||
|
||||
#if QT_CONFIG(itemmodel)
|
||||
#define QT_FOR_EACH_STATIC_ITEMMODEL_CLASS(F)\
|
||||
F(QModelIndex, 42, QModelIndex) \
|
||||
F(QPersistentModelIndex, 50, QPersistentModelIndex)
|
||||
#else
|
||||
#define QT_FOR_EACH_STATIC_ITEMMODEL_CLASS(F)
|
||||
#endif
|
||||
|
||||
#define QT_FOR_EACH_STATIC_CORE_CLASS(F)\
|
||||
F(QChar, 7, QChar) \
|
||||
F(QString, 10, QString) \
|
||||
@ -112,13 +120,12 @@ inline Q_DECL_CONSTEXPR int qMetaTypeId();
|
||||
F(QEasingCurve, 29, QEasingCurve) \
|
||||
F(QUuid, 30, QUuid) \
|
||||
F(QVariant, 41, QVariant) \
|
||||
F(QModelIndex, 42, QModelIndex) \
|
||||
F(QRegularExpression, 44, QRegularExpression) \
|
||||
F(QJsonValue, 45, QJsonValue) \
|
||||
F(QJsonObject, 46, QJsonObject) \
|
||||
F(QJsonArray, 47, QJsonArray) \
|
||||
F(QJsonDocument, 48, QJsonDocument) \
|
||||
F(QPersistentModelIndex, 50, QPersistentModelIndex) \
|
||||
QT_FOR_EACH_STATIC_ITEMMODEL_CLASS(F)
|
||||
|
||||
#define QT_FOR_EACH_STATIC_CORE_POINTER(F)\
|
||||
F(QObjectStar, 39, QObject*)
|
||||
|
@ -201,8 +201,6 @@ template<> struct TypeDefinition<QJsonArray> { static const bool IsAvailable = f
|
||||
template<> struct TypeDefinition<QJsonDocument> { static const bool IsAvailable = false; };
|
||||
template<> struct TypeDefinition<QJsonObject> { static const bool IsAvailable = false; };
|
||||
template<> struct TypeDefinition<QJsonValue> { static const bool IsAvailable = false; };
|
||||
template<> struct TypeDefinition<QModelIndex> { static const bool IsAvailable = false; };
|
||||
template<> struct TypeDefinition<QPersistentModelIndex> { static const bool IsAvailable = false; };
|
||||
template<> struct TypeDefinition<QUrl> { static const bool IsAvailable = false; };
|
||||
template<> struct TypeDefinition<QByteArrayList> { static const bool IsAvailable = false; };
|
||||
#endif
|
||||
|
@ -56,8 +56,10 @@
|
||||
#include "qurl.h"
|
||||
#include "qlocale.h"
|
||||
#include "quuid.h"
|
||||
#ifndef QT_BOOTSTRAPPED
|
||||
#if QT_CONFIG(itemmodel)
|
||||
#include "qabstractitemmodel.h"
|
||||
#endif
|
||||
#ifndef QT_BOOTSTRAPPED
|
||||
#include "qjsonvalue.h"
|
||||
#include "qjsonobject.h"
|
||||
#include "qjsonarray.h"
|
||||
@ -393,6 +395,8 @@ static bool convert(const QVariant::Private *d, int t, void *result, bool *ok)
|
||||
return false;
|
||||
}
|
||||
break;
|
||||
#endif // QT_BOOTSTRAPPED
|
||||
#if QT_CONFIG(itemmodel)
|
||||
case QVariant::ModelIndex:
|
||||
switch (d->type) {
|
||||
case QVariant::PersistentModelIndex:
|
||||
@ -411,7 +415,7 @@ static bool convert(const QVariant::Private *d, int t, void *result, bool *ok)
|
||||
return false;
|
||||
}
|
||||
break;
|
||||
#endif // QT_BOOTSTRAPPED
|
||||
#endif // QT_CONFIG(itemmodel)
|
||||
case QVariant::String: {
|
||||
QString *str = static_cast<QString *>(result);
|
||||
switch (d->type) {
|
||||
@ -1952,12 +1956,6 @@ QVariant::QVariant(const QRegularExpression &re)
|
||||
QVariant::QVariant(const QUuid &uuid)
|
||||
: d(Uuid)
|
||||
{ v_construct<QUuid>(&d, uuid); }
|
||||
QVariant::QVariant(const QModelIndex &modelIndex)
|
||||
: d(ModelIndex)
|
||||
{ v_construct<QModelIndex>(&d, modelIndex); }
|
||||
QVariant::QVariant(const QPersistentModelIndex &modelIndex)
|
||||
: d(PersistentModelIndex)
|
||||
{ v_construct<QPersistentModelIndex>(&d, modelIndex); }
|
||||
QVariant::QVariant(const QJsonValue &jsonValue)
|
||||
: d(QMetaType::QJsonValue)
|
||||
{ v_construct<QJsonValue>(&d, jsonValue); }
|
||||
@ -1971,6 +1969,14 @@ QVariant::QVariant(const QJsonDocument &jsonDocument)
|
||||
: d(QMetaType::QJsonDocument)
|
||||
{ v_construct<QJsonDocument>(&d, jsonDocument); }
|
||||
#endif // QT_BOOTSTRAPPED
|
||||
#if QT_CONFIG(itemmodel)
|
||||
QVariant::QVariant(const QModelIndex &modelIndex)
|
||||
: d(ModelIndex)
|
||||
{ v_construct<QModelIndex>(&d, modelIndex); }
|
||||
QVariant::QVariant(const QPersistentModelIndex &modelIndex)
|
||||
: d(PersistentModelIndex)
|
||||
{ v_construct<QPersistentModelIndex>(&d, modelIndex); }
|
||||
#endif
|
||||
|
||||
/*!
|
||||
Returns the storage type of the value stored in the variant.
|
||||
@ -2668,21 +2674,7 @@ QRegularExpression QVariant::toRegularExpression() const
|
||||
}
|
||||
#endif // QT_CONFIG(regularexpression)
|
||||
|
||||
#ifndef QT_BOOTSTRAPPED
|
||||
/*!
|
||||
\since 5.0
|
||||
|
||||
Returns the variant as a QUuid if the variant has type()
|
||||
\l QMetaType::QUuid, \l QMetaType::QByteArray or \l QMetaType::QString;
|
||||
otherwise returns a default-constructed QUuid.
|
||||
|
||||
\sa canConvert(), convert()
|
||||
*/
|
||||
QUuid QVariant::toUuid() const
|
||||
{
|
||||
return qVariantToHelper<QUuid>(d, handlerManager);
|
||||
}
|
||||
|
||||
#if QT_CONFIG(itemmodel)
|
||||
/*!
|
||||
\since 5.0
|
||||
|
||||
@ -2708,6 +2700,22 @@ QPersistentModelIndex QVariant::toPersistentModelIndex() const
|
||||
{
|
||||
return qVariantToHelper<QPersistentModelIndex>(d, handlerManager);
|
||||
}
|
||||
#endif // QT_CONFIG(itemmodel)
|
||||
|
||||
#ifndef QT_BOOTSTRAPPED
|
||||
/*!
|
||||
\since 5.0
|
||||
|
||||
Returns the variant as a QUuid if the variant has type()
|
||||
\l QMetaType::QUuid, \l QMetaType::QByteArray or \l QMetaType::QString;
|
||||
otherwise returns a default-constructed QUuid.
|
||||
|
||||
\sa canConvert(), convert()
|
||||
*/
|
||||
QUuid QVariant::toUuid() const
|
||||
{
|
||||
return qVariantToHelper<QUuid>(d, handlerManager);
|
||||
}
|
||||
|
||||
/*!
|
||||
\since 5.0
|
||||
@ -3182,9 +3190,11 @@ bool QVariant::canConvert(int targetTypeId) const
|
||||
if (d.type == targetTypeId)
|
||||
return true;
|
||||
|
||||
#if QT_CONFIG(itemmodel)
|
||||
if ((targetTypeId == QMetaType::QModelIndex && d.type == QMetaType::QPersistentModelIndex)
|
||||
|| (targetTypeId == QMetaType::QPersistentModelIndex && d.type == QMetaType::QModelIndex))
|
||||
return true;
|
||||
#endif
|
||||
|
||||
if (targetTypeId == QMetaType::QVariantList
|
||||
&& (d.type == QMetaType::QVariantList
|
||||
|
@ -165,8 +165,10 @@ class Q_CORE_EXPORT QVariant
|
||||
Hash = QMetaType::QVariantHash,
|
||||
EasingCurve = QMetaType::QEasingCurve,
|
||||
Uuid = QMetaType::QUuid,
|
||||
#if QT_CONFIG(itemmodel)
|
||||
ModelIndex = QMetaType::QModelIndex,
|
||||
PersistentModelIndex = QMetaType::QPersistentModelIndex,
|
||||
#endif
|
||||
LastCoreType = QMetaType::LastCoreType,
|
||||
|
||||
Font = QMetaType::QFont,
|
||||
@ -255,13 +257,15 @@ class Q_CORE_EXPORT QVariant
|
||||
QVariant(const QUrl &url);
|
||||
QVariant(const QEasingCurve &easing);
|
||||
QVariant(const QUuid &uuid);
|
||||
QVariant(const QModelIndex &modelIndex);
|
||||
QVariant(const QPersistentModelIndex &modelIndex);
|
||||
QVariant(const QJsonValue &jsonValue);
|
||||
QVariant(const QJsonObject &jsonObject);
|
||||
QVariant(const QJsonArray &jsonArray);
|
||||
QVariant(const QJsonDocument &jsonDocument);
|
||||
#endif // QT_BOOTSTRAPPED
|
||||
#if QT_CONFIG(itemmodel)
|
||||
QVariant(const QModelIndex &modelIndex);
|
||||
QVariant(const QPersistentModelIndex &modelIndex);
|
||||
#endif
|
||||
|
||||
QVariant& operator=(const QVariant &other);
|
||||
#ifdef Q_COMPILER_RVALUE_REFS
|
||||
@ -329,13 +333,15 @@ class Q_CORE_EXPORT QVariant
|
||||
QUrl toUrl() const;
|
||||
QEasingCurve toEasingCurve() const;
|
||||
QUuid toUuid() const;
|
||||
QModelIndex toModelIndex() const;
|
||||
QPersistentModelIndex toPersistentModelIndex() const;
|
||||
QJsonValue toJsonValue() const;
|
||||
QJsonObject toJsonObject() const;
|
||||
QJsonArray toJsonArray() const;
|
||||
QJsonDocument toJsonDocument() const;
|
||||
#endif // QT_BOOTSTRAPPED
|
||||
#if QT_CONFIG(itemmodel)
|
||||
QModelIndex toModelIndex() const;
|
||||
QPersistentModelIndex toPersistentModelIndex() const;
|
||||
#endif
|
||||
|
||||
#ifndef QT_NO_DATASTREAM
|
||||
void load(QDataStream &ds);
|
||||
|
@ -797,27 +797,60 @@ struct BezierEase : public QEasingCurveFunction
|
||||
return t3;
|
||||
}
|
||||
|
||||
qreal static inline findTForX(const SingleCubicBezier &singleCubicBezier, qreal x)
|
||||
{
|
||||
const qreal p0 = singleCubicBezier.p0x;
|
||||
const qreal p1 = singleCubicBezier.p1x;
|
||||
const qreal p2 = singleCubicBezier.p2x;
|
||||
const qreal p3 = singleCubicBezier.p3x;
|
||||
bool static inline almostZero(qreal value)
|
||||
{
|
||||
// 1e-3 might seem excessively fuzzy, but any smaller value will make the
|
||||
// factors a, b, and c large enough to knock out the cubic solver.
|
||||
return value > -1e-3 && value < 1e-3;
|
||||
}
|
||||
|
||||
const qreal factorT3 = p3 - p0 + 3 * p1 - 3 * p2;
|
||||
const qreal factorT2 = 3 * p0 - 6 * p1 + 3 * p2;
|
||||
const qreal factorT1 = -3 * p0 + 3 * p1;
|
||||
const qreal factorT0 = p0 - x;
|
||||
qreal static inline findTForX(const SingleCubicBezier &singleCubicBezier, qreal x)
|
||||
{
|
||||
const qreal p0 = singleCubicBezier.p0x;
|
||||
const qreal p1 = singleCubicBezier.p1x;
|
||||
const qreal p2 = singleCubicBezier.p2x;
|
||||
const qreal p3 = singleCubicBezier.p3x;
|
||||
|
||||
const qreal a = factorT2 / factorT3;
|
||||
const qreal b = factorT1 / factorT3;
|
||||
const qreal c = factorT0 / factorT3;
|
||||
const qreal factorT3 = p3 - p0 + 3 * p1 - 3 * p2;
|
||||
const qreal factorT2 = 3 * p0 - 6 * p1 + 3 * p2;
|
||||
const qreal factorT1 = -3 * p0 + 3 * p1;
|
||||
const qreal factorT0 = p0 - x;
|
||||
|
||||
return singleRealSolutionForCubic(a, b, c);
|
||||
// Cases for quadratic, linear and invalid equations
|
||||
if (almostZero(factorT3)) {
|
||||
if (almostZero(factorT2)) {
|
||||
if (almostZero(factorT1))
|
||||
return 0.0;
|
||||
|
||||
//one new iteration to increase numeric stability
|
||||
//return newtonIteration(singleCubicBezier, t, x);
|
||||
}
|
||||
return -factorT0 / factorT1;
|
||||
}
|
||||
const qreal discriminant = factorT1 * factorT1 - 4.0 * factorT2 * factorT0;
|
||||
if (discriminant < 0.0)
|
||||
return 0.0;
|
||||
|
||||
if (discriminant == 0.0)
|
||||
return -factorT1 / (2.0 * factorT2);
|
||||
|
||||
const qreal solution1 = (-factorT1 + std::sqrt(discriminant)) / (2.0 * factorT2);
|
||||
if (solution1 >= 0.0 && solution1 <= 1.0)
|
||||
return solution1;
|
||||
|
||||
const qreal solution2 = (-factorT1 - std::sqrt(discriminant)) / (2.0 * factorT2);
|
||||
if (solution2 >= 0.0 && solution2 <= 1.0)
|
||||
return solution2;
|
||||
|
||||
return 0.0;
|
||||
}
|
||||
|
||||
const qreal a = factorT2 / factorT3;
|
||||
const qreal b = factorT1 / factorT3;
|
||||
const qreal c = factorT0 / factorT3;
|
||||
|
||||
return singleRealSolutionForCubic(a, b, c);
|
||||
|
||||
//one new iteration to increase numeric stability
|
||||
//return newtonIteration(singleCubicBezier, t, x);
|
||||
}
|
||||
};
|
||||
|
||||
struct TCBEase : public BezierEase
|
||||
|
@ -176,11 +176,11 @@ public:
|
||||
inline QVarLengthArray<T, Prealloc> &operator<<(const T &t)
|
||||
{ append(t); return *this; }
|
||||
inline QVarLengthArray<T, Prealloc> &operator<<(T &&t)
|
||||
{ append(t); return *this; }
|
||||
{ append(std::move(t)); return *this; }
|
||||
inline QVarLengthArray<T, Prealloc> &operator+=(const T &t)
|
||||
{ append(t); return *this; }
|
||||
inline QVarLengthArray<T, Prealloc> &operator+=(T &&t)
|
||||
{ append(t); return *this; }
|
||||
{ append(std::move(t)); return *this; }
|
||||
|
||||
void prepend(T &&t);
|
||||
void prepend(const T &t);
|
||||
|
@ -284,9 +284,9 @@ public:
|
||||
inline QVector<T> &operator<<(const QVector<T> &l)
|
||||
{ *this += l; return *this; }
|
||||
inline QVector<T> &operator+=(T &&t)
|
||||
{ append(t); return *this; }
|
||||
{ append(std::move(t)); return *this; }
|
||||
inline QVector<T> &operator<<(T &&t)
|
||||
{ append(t); return *this; }
|
||||
{ append(std::move(t)); return *this; }
|
||||
|
||||
QList<T> toList() const;
|
||||
|
||||
|
@ -61,8 +61,7 @@ function(QT5_ADD_DBUS_INTERFACE _sources _interface _basename)
|
||||
COMMAND ${Qt5DBus_QDBUSXML2CPP_EXECUTABLE} ${_params} -p ${_basename} ${_infile}
|
||||
DEPENDS ${_infile} VERBATIM)
|
||||
|
||||
set_source_files_properties("${_impl}" PROPERTIES SKIP_AUTOMOC TRUE)
|
||||
set_source_files_properties("${_header}" PROPERTIES SKIP_AUTOMOC TRUE)
|
||||
set_source_files_properties("${_impl}" "${_header}" PROPERTIES SKIP_AUTOMOC TRUE)
|
||||
|
||||
qt5_generate_moc("${_header}" "${_moc}")
|
||||
|
||||
@ -147,8 +146,7 @@ function(QT5_ADD_DBUS_ADAPTOR _sources _xml_file _include _parentClass) # _optio
|
||||
endif()
|
||||
|
||||
qt5_generate_moc("${_header}" "${_moc}")
|
||||
set_source_files_properties("${_impl}" PROPERTIES SKIP_AUTOMOC TRUE)
|
||||
set_source_files_properties("${_header}" PROPERTIES SKIP_AUTOMOC TRUE)
|
||||
set_source_files_properties("${_impl}" "${_header}" PROPERTIES SKIP_AUTOMOC TRUE)
|
||||
macro_add_file_dependencies("${_impl}" "${_moc}")
|
||||
|
||||
list(APPEND ${_sources} "${_impl}" "${_header}" "${_moc}")
|
||||
|
@ -137,6 +137,16 @@ void qt_scale_image_16bit(uchar *destPixels, int dbpl,
|
||||
|
||||
// this bounds check here is required as floating point rounding above might in some cases lead to
|
||||
// w/h values that are one pixel too large, falling outside of the valid image area.
|
||||
const int ystart = srcy >> 16;
|
||||
if (ystart >= srch && iy < 0) {
|
||||
srcy += iy;
|
||||
--h;
|
||||
}
|
||||
const int xstart = basex >> 16;
|
||||
if (xstart >= (int)(sbpl/sizeof(SRC)) && ix < 0) {
|
||||
basex += ix;
|
||||
--w;
|
||||
}
|
||||
int yend = (srcy + iy * (h - 1)) >> 16;
|
||||
if (yend < 0 || yend >= srch)
|
||||
--h;
|
||||
@ -248,6 +258,16 @@ template <typename T> void qt_scale_image_32bit(uchar *destPixels, int dbpl,
|
||||
|
||||
// this bounds check here is required as floating point rounding above might in some cases lead to
|
||||
// w/h values that are one pixel too large, falling outside of the valid image area.
|
||||
const int ystart = srcy >> 16;
|
||||
if (ystart >= srch && iy < 0) {
|
||||
srcy += iy;
|
||||
--h;
|
||||
}
|
||||
const int xstart = basex >> 16;
|
||||
if (xstart >= (int)(sbpl/sizeof(quint32)) && ix < 0) {
|
||||
basex += ix;
|
||||
--w;
|
||||
}
|
||||
int yend = (srcy + iy * (h - 1)) >> 16;
|
||||
if (yend < 0 || yend >= srch)
|
||||
--h;
|
||||
|
@ -558,6 +558,16 @@ void qt_scale_image_argb32_on_argb32_sse2(uchar *destPixels, int dbpl,
|
||||
|
||||
// this bounds check here is required as floating point rounding above might in some cases lead to
|
||||
// w/h values that are one pixel too large, falling outside of the valid image area.
|
||||
const int ystart = srcy >> 16;
|
||||
if (ystart >= srch && iy < 0) {
|
||||
srcy += iy;
|
||||
--h;
|
||||
}
|
||||
const int xstart = basex >> 16;
|
||||
if (xstart >= (int)(sbpl/sizeof(quint32)) && ix < 0) {
|
||||
basex += ix;
|
||||
--w;
|
||||
}
|
||||
int yend = (srcy + iy * (h - 1)) >> 16;
|
||||
if (yend < 0 || yend >= srch)
|
||||
--h;
|
||||
|
@ -698,6 +698,11 @@ void QRasterPaintEngine::setState(QPainterState *s)
|
||||
{
|
||||
Q_D(QRasterPaintEngine);
|
||||
QPaintEngineEx::setState(s);
|
||||
QRasterPaintEngineState *t = state();
|
||||
if (t->clip && t->clip->enabled != t->clipEnabled) {
|
||||
// Since we do not "detach" clipdata when changing only enabled state, we need to resync state here
|
||||
t->clip->enabled = t->clipEnabled;
|
||||
}
|
||||
d->rasterBuffer->compositionMode = s->composition_mode;
|
||||
}
|
||||
|
||||
|
@ -1033,7 +1033,6 @@ void QPainterPath::addRect(const QRectF &r)
|
||||
|
||||
bool first = d_func()->elements.size() < 2;
|
||||
|
||||
d_func()->elements.reserve(d_func()->elements.size() + 5);
|
||||
moveTo(r.x(), r.y());
|
||||
|
||||
Element l1 = { r.x() + r.width(), r.y(), LineToElement };
|
||||
@ -1071,8 +1070,6 @@ void QPainterPath::addPolygon(const QPolygonF &polygon)
|
||||
ensureData();
|
||||
detach();
|
||||
|
||||
d_func()->elements.reserve(d_func()->elements.size() + polygon.size());
|
||||
|
||||
moveTo(polygon.constFirst());
|
||||
for (int i=1; i<polygon.size(); ++i) {
|
||||
Element elm = { polygon.at(i).x(), polygon.at(i).y(), LineToElement };
|
||||
@ -1115,9 +1112,7 @@ void QPainterPath::addEllipse(const QRectF &boundingRect)
|
||||
ensureData();
|
||||
detach();
|
||||
|
||||
Q_D(QPainterPath);
|
||||
bool first = d_func()->elements.size() < 2;
|
||||
d->elements.reserve(d->elements.size() + 13);
|
||||
|
||||
QPointF pts[12];
|
||||
int point_count;
|
||||
@ -1294,7 +1289,6 @@ void QPainterPath::addRegion(const QRegion ®ion)
|
||||
ensureData();
|
||||
detach();
|
||||
|
||||
d_func()->elements.reserve(region.rectCount() * 5);
|
||||
for (const QRect &rect : region)
|
||||
addRect(rect);
|
||||
}
|
||||
@ -2463,7 +2457,6 @@ QDataStream &operator>>(QDataStream &s, QPainterPath &p)
|
||||
Q_ASSERT(p.d_func()->elements.at(0).type == QPainterPath::MoveToElement);
|
||||
p.d_func()->elements.clear();
|
||||
}
|
||||
p.d_func()->elements.reserve(p.d_func()->elements.size() + size);
|
||||
for (int i=0; i<size; ++i) {
|
||||
int type;
|
||||
double x, y;
|
||||
|
@ -382,7 +382,14 @@ static void getAddresses(int sock, char *buf, QList<QNetworkInterfacePrivate *>
|
||||
auto payloadPtr = reinterpret_cast<uchar *>(RTA_DATA(rta));
|
||||
|
||||
switch (rta->rta_type) {
|
||||
case IFA_ADDRESS: // address
|
||||
case IFA_ADDRESS:
|
||||
// Local address (all interfaces except for point-to-point)
|
||||
if (entry.ip().isNull())
|
||||
entry.setIp(makeAddress(payloadPtr, payloadLen));
|
||||
break;
|
||||
|
||||
case IFA_LOCAL:
|
||||
// Override the local address (point-to-point interfaces)
|
||||
entry.setIp(makeAddress(payloadPtr, payloadLen));
|
||||
break;
|
||||
|
||||
|
@ -87,6 +87,9 @@ typedef IAsyncOperationWithProgress<IBuffer *, UINT32> IAsyncBufferOperation;
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
Q_LOGGING_CATEGORY(lcNetworkSocket, "qt.network.socket");
|
||||
Q_LOGGING_CATEGORY(lcNetworkSocketVerbose, "qt.network.socket.verbose");
|
||||
|
||||
#if _MSC_VER >= 1900
|
||||
static HRESULT qt_winrt_try_create_thread_network_context(QString host, ComPtr<IThreadNetworkContext> &context)
|
||||
{
|
||||
@ -167,11 +170,14 @@ public:
|
||||
SocketEngineWorker(QNativeSocketEnginePrivate *engine)
|
||||
: enginePrivate(engine)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << engine;
|
||||
}
|
||||
|
||||
~SocketEngineWorker()
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO;
|
||||
if (Q_UNLIKELY(initialReadOp)) {
|
||||
qCDebug(lcNetworkSocket) << Q_FUNC_INFO << "Closing initial read operation";
|
||||
ComPtr<IAsyncInfo> info;
|
||||
HRESULT hr = initialReadOp.As(&info);
|
||||
Q_ASSERT_SUCCEEDED(hr);
|
||||
@ -184,6 +190,7 @@ public:
|
||||
}
|
||||
|
||||
if (readOp) {
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << "Closing read operation";
|
||||
ComPtr<IAsyncInfo> info;
|
||||
HRESULT hr = readOp.As(&info);
|
||||
Q_ASSERT_SUCCEEDED(hr);
|
||||
@ -196,6 +203,7 @@ public:
|
||||
}
|
||||
|
||||
if (connectOp) {
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << "Closing connect operation";
|
||||
ComPtr<IAsyncInfo> info;
|
||||
HRESULT hr = connectOp.As(&info);
|
||||
Q_ASSERT_SUCCEEDED(hr);
|
||||
@ -210,30 +218,13 @@ public:
|
||||
|
||||
signals:
|
||||
void connectOpFinished(bool success, QAbstractSocket::SocketError error, WinRTSocketEngine::ErrorString errorString);
|
||||
void newDatagramsReceived(const QList<WinRtDatagram> &datagram);
|
||||
void newDataReceived(const QVector<QByteArray> &data);
|
||||
void newDataReceived();
|
||||
void socketErrorOccured(QAbstractSocket::SocketError error);
|
||||
|
||||
public slots:
|
||||
Q_INVOKABLE void notifyAboutNewDatagrams()
|
||||
{
|
||||
QMutexLocker locker(&mutex);
|
||||
QList<WinRtDatagram> datagrams = pendingDatagrams;
|
||||
pendingDatagrams.clear();
|
||||
emit newDatagramsReceived(datagrams);
|
||||
}
|
||||
|
||||
Q_INVOKABLE void notifyAboutNewData()
|
||||
{
|
||||
QMutexLocker locker(&mutex);
|
||||
const QVector<QByteArray> newData = std::move(pendingData);
|
||||
pendingData.clear();
|
||||
emit newDataReceived(newData);
|
||||
}
|
||||
|
||||
public:
|
||||
void startReading()
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO;
|
||||
ComPtr<IBuffer> buffer;
|
||||
HRESULT hr = g->bufferFactory->Create(READ_BUFFER_SIZE, &buffer);
|
||||
Q_ASSERT_SUCCEEDED(hr);
|
||||
@ -249,6 +240,7 @@ public:
|
||||
|
||||
HRESULT onConnectOpFinished(IAsyncAction *action, AsyncStatus)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO;
|
||||
HRESULT hr = action->GetResults();
|
||||
if (FAILED(hr)) {
|
||||
if (hr == HRESULT_FROM_WIN32(WSAETIMEDOUT)) {
|
||||
@ -287,6 +279,7 @@ public:
|
||||
|
||||
HRESULT OnNewDatagramReceived(IDatagramSocket *, IDatagramSocketMessageReceivedEventArgs *args)
|
||||
{
|
||||
qCDebug(lcNetworkSocketVerbose) << this << Q_FUNC_INFO;
|
||||
WinRtDatagram datagram;
|
||||
QHostAddress returnAddress;
|
||||
ComPtr<IHostName> remoteHost;
|
||||
@ -311,10 +304,11 @@ public:
|
||||
datagram.data.resize(length);
|
||||
hr = reader->ReadBytes(length, reinterpret_cast<BYTE *>(datagram.data.data()));
|
||||
RETURN_OK_IF_FAILED("Could not read datagram");
|
||||
|
||||
QMutexLocker locker(&mutex);
|
||||
// Notify the engine about new datagrams being present at the next event loop iteration
|
||||
if (pendingDatagrams.isEmpty())
|
||||
QMetaObject::invokeMethod(this, "notifyAboutNewDatagrams", Qt::QueuedConnection);
|
||||
if (emitDataReceived)
|
||||
emit newDataReceived();
|
||||
pendingDatagrams << datagram;
|
||||
|
||||
return S_OK;
|
||||
@ -322,6 +316,7 @@ public:
|
||||
|
||||
HRESULT onReadyRead(IAsyncBufferOperation *asyncInfo, AsyncStatus status)
|
||||
{
|
||||
qCDebug(lcNetworkSocketVerbose) << this << Q_FUNC_INFO;
|
||||
if (asyncInfo == initialReadOp.Get()) {
|
||||
initialReadOp.Reset();
|
||||
} else if (asyncInfo == readOp.Get()) {
|
||||
@ -334,6 +329,7 @@ public:
|
||||
// that the connection was closed. The socket cannot be closed here, as the subsequent read
|
||||
// might fail then.
|
||||
if (status == Error || status == Canceled) {
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << "Remote host closed";
|
||||
emit socketErrorOccured(QAbstractSocket::RemoteHostClosedError);
|
||||
return S_OK;
|
||||
}
|
||||
@ -358,6 +354,7 @@ public:
|
||||
// the closing of the socket won't be communicated to the caller. So only the error is set. The
|
||||
// actual socket close happens inside of read.
|
||||
if (!bufferLength) {
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << "Remote host closed";
|
||||
emit socketErrorOccured(QAbstractSocket::RemoteHostClosedError);
|
||||
return S_OK;
|
||||
}
|
||||
@ -378,10 +375,10 @@ public:
|
||||
}
|
||||
|
||||
QByteArray newData(reinterpret_cast<const char*>(data), qint64(bufferLength));
|
||||
|
||||
QMutexLocker readLocker(&mutex);
|
||||
if (pendingData.isEmpty())
|
||||
QMetaObject::invokeMethod(this, "notifyAboutNewData", Qt::QueuedConnection);
|
||||
pendingData << newData;
|
||||
emit newDataReceived();
|
||||
pendingData.append(newData);
|
||||
readLocker.unlock();
|
||||
|
||||
hr = QEventDispatcherWinRT::runOnXamlThread([buffer, this]() {
|
||||
@ -433,7 +430,8 @@ private:
|
||||
ComPtr<IStreamSocket> tcpSocket;
|
||||
|
||||
QList<WinRtDatagram> pendingDatagrams;
|
||||
QVector<QByteArray> pendingData;
|
||||
bool emitDataReceived = true;
|
||||
QByteArray pendingData;
|
||||
|
||||
// Protects pendingData/pendingDatagrams which are accessed from native callbacks
|
||||
QMutex mutex;
|
||||
@ -487,6 +485,12 @@ static QByteArray socketDescription(const QAbstractSocketEngine *s)
|
||||
" not in "#state1" or "#state2); \
|
||||
return (returnValue); \
|
||||
} } while (0)
|
||||
#define Q_CHECK_STATES3(function, state1, state2, state3, returnValue) do { \
|
||||
if (d->socketState != (state1) && d->socketState != (state2) && d->socketState != (state3)) { \
|
||||
qWarning(""#function" was called" \
|
||||
" not in "#state1", "#state2" or "#state3); \
|
||||
return (returnValue); \
|
||||
} } while (0)
|
||||
#define Q_CHECK_TYPE(function, type, returnValue) do { \
|
||||
if (d->socketType != (type)) { \
|
||||
qWarning(#function" was called by a" \
|
||||
@ -509,6 +513,7 @@ static AsyncStatus opStatus(const ComPtr<T> &op)
|
||||
|
||||
static qint64 writeIOStream(ComPtr<IOutputStream> stream, const char *data, qint64 len)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << Q_FUNC_INFO << data << len;
|
||||
ComPtr<IBuffer> buffer;
|
||||
HRESULT hr = g->bufferFactory->Create(len, &buffer);
|
||||
Q_ASSERT_SUCCEEDED(hr);
|
||||
@ -533,6 +538,7 @@ static qint64 writeIOStream(ComPtr<IOutputStream> stream, const char *data, qint
|
||||
QNativeSocketEngine::QNativeSocketEngine(QObject *parent)
|
||||
: QAbstractSocketEngine(*new QNativeSocketEnginePrivate(), parent)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << parent;
|
||||
qRegisterMetaType<WinRtDatagram>();
|
||||
qRegisterMetaType<WinRTSocketEngine::ErrorString>();
|
||||
Q_D(QNativeSocketEngine);
|
||||
@ -546,20 +552,20 @@ QNativeSocketEngine::QNativeSocketEngine(QObject *parent)
|
||||
connect(this, SIGNAL(writeReady()), SLOT(writeNotification()), Qt::QueuedConnection);
|
||||
connect(d->worker, &SocketEngineWorker::connectOpFinished,
|
||||
this, &QNativeSocketEngine::handleConnectOpFinished, Qt::QueuedConnection);
|
||||
connect(d->worker, &SocketEngineWorker::newDatagramsReceived, this, &QNativeSocketEngine::handleNewDatagrams, Qt::QueuedConnection);
|
||||
connect(d->worker, &SocketEngineWorker::newDataReceived,
|
||||
this, &QNativeSocketEngine::handleNewData, Qt::QueuedConnection);
|
||||
connect(d->worker, &SocketEngineWorker::newDataReceived, this, &QNativeSocketEngine::handleNewData, Qt::QueuedConnection);
|
||||
connect(d->worker, &SocketEngineWorker::socketErrorOccured,
|
||||
this, &QNativeSocketEngine::handleTcpError, Qt::QueuedConnection);
|
||||
}
|
||||
|
||||
QNativeSocketEngine::~QNativeSocketEngine()
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO;
|
||||
close();
|
||||
}
|
||||
|
||||
bool QNativeSocketEngine::initialize(QAbstractSocket::SocketType type, QAbstractSocket::NetworkLayerProtocol protocol)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << type << protocol;
|
||||
Q_D(QNativeSocketEngine);
|
||||
if (isValid())
|
||||
close();
|
||||
@ -568,6 +574,28 @@ bool QNativeSocketEngine::initialize(QAbstractSocket::SocketType type, QAbstract
|
||||
if (!d->createNewSocket(type, protocol))
|
||||
return false;
|
||||
|
||||
if (type == QAbstractSocket::UdpSocket) {
|
||||
// Set the broadcasting flag if it's a UDP socket.
|
||||
if (!setOption(BroadcastSocketOption, 1)) {
|
||||
d->setError(QAbstractSocket::UnsupportedSocketOperationError,
|
||||
WinRTSocketEngine::BroadcastingInitFailedErrorString);
|
||||
close();
|
||||
return false;
|
||||
}
|
||||
|
||||
// Set some extra flags that are interesting to us, but accept failure
|
||||
setOption(ReceivePacketInformation, 1);
|
||||
setOption(ReceiveHopLimit, 1);
|
||||
}
|
||||
|
||||
|
||||
// Make sure we receive out-of-band data
|
||||
if (type == QAbstractSocket::TcpSocket
|
||||
&& !setOption(ReceiveOutOfBandData, 1)) {
|
||||
qWarning("QNativeSocketEngine::initialize unable to inline out-of-band data");
|
||||
}
|
||||
|
||||
|
||||
d->socketType = type;
|
||||
d->socketProtocol = protocol;
|
||||
return true;
|
||||
@ -575,6 +603,7 @@ bool QNativeSocketEngine::initialize(QAbstractSocket::SocketType type, QAbstract
|
||||
|
||||
bool QNativeSocketEngine::initialize(qintptr socketDescriptor, QAbstractSocket::SocketState socketState)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << socketDescriptor << socketState;
|
||||
Q_D(QNativeSocketEngine);
|
||||
|
||||
if (isValid())
|
||||
@ -622,18 +651,28 @@ bool QNativeSocketEngine::isValid() const
|
||||
|
||||
bool QNativeSocketEngine::connectToHost(const QHostAddress &address, quint16 port)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << address << port;
|
||||
Q_D(QNativeSocketEngine);
|
||||
Q_CHECK_VALID_SOCKETLAYER(QNativeSocketEngine::connectToHost(), false);
|
||||
Q_CHECK_STATES3(QNativeSocketEngine::connectToHost(), QAbstractSocket::BoundState,
|
||||
QAbstractSocket::UnconnectedState, QAbstractSocket::ConnectingState, false);
|
||||
const QString addressString = address.toString();
|
||||
return connectToHostByName(addressString, port);
|
||||
}
|
||||
|
||||
bool QNativeSocketEngine::connectToHostByName(const QString &name, quint16 port)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << name << port;
|
||||
Q_D(QNativeSocketEngine);
|
||||
Q_CHECK_VALID_SOCKETLAYER(QNativeSocketEngine::connectToHostByName(), false);
|
||||
Q_CHECK_STATES3(QNativeSocketEngine::connectToHostByName(), QAbstractSocket::BoundState,
|
||||
QAbstractSocket::UnconnectedState, QAbstractSocket::ConnectingState, false);
|
||||
HRESULT hr;
|
||||
|
||||
#if _MSC_VER >= 1900
|
||||
ComPtr<IThreadNetworkContext> networkContext;
|
||||
if (!qEnvironmentVariableIsEmpty("QT_WINRT_USE_THREAD_NETWORK_CONTEXT")) {
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << "Creating network context";
|
||||
hr = qt_winrt_try_create_thread_network_context(name, networkContext);
|
||||
if (FAILED(hr)) {
|
||||
setError(QAbstractSocket::ConnectionRefusedError, QLatin1String("Could not create thread network context."));
|
||||
@ -668,6 +707,7 @@ bool QNativeSocketEngine::connectToHostByName(const QString &name, quint16 port)
|
||||
|
||||
#if _MSC_VER >= 1900
|
||||
if (networkContext != nullptr) {
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << "Closing network context";
|
||||
ComPtr<IClosable> networkContextCloser;
|
||||
hr = networkContext.As(&networkContextCloser);
|
||||
Q_ASSERT_SUCCEEDED(hr);
|
||||
@ -691,7 +731,11 @@ bool QNativeSocketEngine::connectToHostByName(const QString &name, quint16 port)
|
||||
|
||||
bool QNativeSocketEngine::bind(const QHostAddress &address, quint16 port)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << address << port;
|
||||
Q_D(QNativeSocketEngine);
|
||||
Q_CHECK_VALID_SOCKETLAYER(QNativeSocketEngine::bind(), false);
|
||||
Q_CHECK_STATE(QNativeSocketEngine::bind(), QAbstractSocket::UnconnectedState, false);
|
||||
|
||||
HRESULT hr;
|
||||
// runOnXamlThread may only return S_OK (will assert otherwise) so no need to check its result.
|
||||
// hr is set inside the lambda though. If an error occurred hr will point that out.
|
||||
@ -773,10 +817,16 @@ bool QNativeSocketEngine::bind(const QHostAddress &address, quint16 port)
|
||||
|
||||
bool QNativeSocketEngine::listen()
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO;
|
||||
Q_D(QNativeSocketEngine);
|
||||
Q_CHECK_VALID_SOCKETLAYER(QNativeSocketEngine::listen(), false);
|
||||
Q_CHECK_STATE(QNativeSocketEngine::listen(), QAbstractSocket::BoundState, false);
|
||||
#if QT_CONFIG(sctp)
|
||||
Q_CHECK_TYPES(QNativeSocketEngine::listen(), QAbstractSocket::TcpSocket,
|
||||
QAbstractSocket::SctpSocket, false);
|
||||
#else
|
||||
Q_CHECK_TYPE(QNativeSocketEngine::listen(), QAbstractSocket::TcpSocket, false);
|
||||
#endif
|
||||
|
||||
if (d->tcpListener && d->socketDescriptor != -1) {
|
||||
d->socketState = QAbstractSocket::ListeningState;
|
||||
@ -787,10 +837,16 @@ bool QNativeSocketEngine::listen()
|
||||
|
||||
int QNativeSocketEngine::accept()
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO;
|
||||
Q_D(QNativeSocketEngine);
|
||||
Q_CHECK_VALID_SOCKETLAYER(QNativeSocketEngine::accept(), -1);
|
||||
Q_CHECK_STATE(QNativeSocketEngine::accept(), QAbstractSocket::ListeningState, -1);
|
||||
#if QT_CONFIG(sctp)
|
||||
Q_CHECK_TYPES(QNativeSocketEngine::accept(), QAbstractSocket::TcpSocket,
|
||||
QAbstractSocket::SctpSocket, -1);
|
||||
#else
|
||||
Q_CHECK_TYPE(QNativeSocketEngine::accept(), QAbstractSocket::TcpSocket, -1);
|
||||
#endif
|
||||
|
||||
if (d->socketDescriptor == -1 || d->pendingConnections.isEmpty()) {
|
||||
d->setError(QAbstractSocket::TemporaryError, WinRTSocketEngine::TemporaryErrorString);
|
||||
@ -810,6 +866,7 @@ int QNativeSocketEngine::accept()
|
||||
|
||||
void QNativeSocketEngine::close()
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO;
|
||||
Q_D(QNativeSocketEngine);
|
||||
|
||||
if (d->closingDown)
|
||||
@ -878,29 +935,41 @@ void QNativeSocketEngine::close()
|
||||
|
||||
bool QNativeSocketEngine::joinMulticastGroup(const QHostAddress &groupAddress, const QNetworkInterface &iface)
|
||||
{
|
||||
Q_UNUSED(groupAddress);
|
||||
Q_UNUSED(iface);
|
||||
Q_D(QNativeSocketEngine);
|
||||
Q_CHECK_VALID_SOCKETLAYER(QNativeSocketEngine::joinMulticastGroup(), false);
|
||||
Q_CHECK_STATE(QNativeSocketEngine::joinMulticastGroup(), QAbstractSocket::BoundState, false);
|
||||
Q_CHECK_TYPE(QNativeSocketEngine::joinMulticastGroup(), QAbstractSocket::UdpSocket, false);
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << groupAddress << iface;
|
||||
Q_UNIMPLEMENTED();
|
||||
return false;
|
||||
}
|
||||
|
||||
bool QNativeSocketEngine::leaveMulticastGroup(const QHostAddress &groupAddress, const QNetworkInterface &iface)
|
||||
{
|
||||
Q_UNUSED(groupAddress);
|
||||
Q_UNUSED(iface);
|
||||
Q_D(QNativeSocketEngine);
|
||||
Q_CHECK_VALID_SOCKETLAYER(QNativeSocketEngine::leaveMulticastGroup(), false);
|
||||
Q_CHECK_STATE(QNativeSocketEngine::leaveMulticastGroup(), QAbstractSocket::BoundState, false);
|
||||
Q_CHECK_TYPE(QNativeSocketEngine::leaveMulticastGroup(), QAbstractSocket::UdpSocket, false);
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << groupAddress << iface;
|
||||
Q_UNIMPLEMENTED();
|
||||
return false;
|
||||
}
|
||||
|
||||
QNetworkInterface QNativeSocketEngine::multicastInterface() const
|
||||
{
|
||||
Q_D(const QNativeSocketEngine);
|
||||
Q_CHECK_VALID_SOCKETLAYER(QNativeSocketEngine::multicastInterface(), QNetworkInterface());
|
||||
Q_CHECK_TYPE(QNativeSocketEngine::multicastInterface(), QAbstractSocket::UdpSocket, QNetworkInterface());
|
||||
Q_UNIMPLEMENTED();
|
||||
return QNetworkInterface();
|
||||
}
|
||||
|
||||
bool QNativeSocketEngine::setMulticastInterface(const QNetworkInterface &iface)
|
||||
{
|
||||
Q_UNUSED(iface);
|
||||
Q_D(QNativeSocketEngine);
|
||||
Q_CHECK_VALID_SOCKETLAYER(QNativeSocketEngine::setMulticastInterface(), false);
|
||||
Q_CHECK_TYPE(QNativeSocketEngine::setMulticastInterface(), QAbstractSocket::UdpSocket, false);
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << iface;
|
||||
Q_UNIMPLEMENTED();
|
||||
return false;
|
||||
}
|
||||
@ -908,55 +977,64 @@ bool QNativeSocketEngine::setMulticastInterface(const QNetworkInterface &iface)
|
||||
qint64 QNativeSocketEngine::bytesAvailable() const
|
||||
{
|
||||
Q_D(const QNativeSocketEngine);
|
||||
Q_CHECK_VALID_SOCKETLAYER(QNativeSocketEngine::bytesAvailable(), -1);
|
||||
Q_CHECK_NOT_STATE(QNativeSocketEngine::bytesAvailable(), QAbstractSocket::UnconnectedState, -1);
|
||||
if (d->socketType != QAbstractSocket::TcpSocket)
|
||||
return -1;
|
||||
|
||||
return d->bytesAvailable;
|
||||
QMutexLocker locker(&d->worker->mutex);
|
||||
const qint64 bytesAvailable = d->worker->pendingData.length();
|
||||
|
||||
qCDebug(lcNetworkSocketVerbose) << this << Q_FUNC_INFO << bytesAvailable;
|
||||
return bytesAvailable;
|
||||
}
|
||||
|
||||
qint64 QNativeSocketEngine::read(char *data, qint64 maxlen)
|
||||
{
|
||||
qCDebug(lcNetworkSocketVerbose) << this << Q_FUNC_INFO << maxlen;
|
||||
Q_D(QNativeSocketEngine);
|
||||
Q_CHECK_VALID_SOCKETLAYER(QNativeSocketEngine::read(), -1);
|
||||
Q_CHECK_STATES(QNativeSocketEngine::read(), QAbstractSocket::ConnectedState, QAbstractSocket::BoundState, -1);
|
||||
if (d->socketType != QAbstractSocket::TcpSocket)
|
||||
return -1;
|
||||
|
||||
// There will be a read notification when the socket was closed by the remote host. If that
|
||||
// happens and there isn't anything left in the buffer, we have to return -1 in order to signal
|
||||
// the closing of the socket.
|
||||
QMutexLocker mutexLocker(&d->readMutex);
|
||||
if (d->pendingData.isEmpty() && d->socketState != QAbstractSocket::ConnectedState) {
|
||||
QMutexLocker mutexLocker(&d->worker->mutex);
|
||||
if (d->worker->pendingData.isEmpty() && d->socketState != QAbstractSocket::ConnectedState) {
|
||||
close();
|
||||
return -1;
|
||||
}
|
||||
|
||||
QByteArray readData;
|
||||
qint64 leftToMaxLen = maxlen;
|
||||
while (leftToMaxLen > 0 && !d->pendingData.isEmpty()) {
|
||||
QByteArray pendingData = d->pendingData.takeFirst();
|
||||
// Do not read the whole data. Put the rest of it back into the "queue"
|
||||
if (leftToMaxLen < pendingData.length()) {
|
||||
readData += pendingData.left(leftToMaxLen);
|
||||
pendingData = pendingData.remove(0, maxlen);
|
||||
d->pendingData.prepend(pendingData);
|
||||
break;
|
||||
} else {
|
||||
readData += pendingData;
|
||||
leftToMaxLen -= pendingData.length();
|
||||
}
|
||||
const int copyLength = qMin(maxlen, qint64(d->worker->pendingData.length()));
|
||||
if (maxlen >= d->worker->pendingData.length()) {
|
||||
qCDebug(lcNetworkSocketVerbose) << this << Q_FUNC_INFO << "Reading full buffer";
|
||||
readData = d->worker->pendingData;
|
||||
d->worker->pendingData.clear();
|
||||
d->emitReadReady = true;
|
||||
} else {
|
||||
qCDebug(lcNetworkSocketVerbose) << this << Q_FUNC_INFO << "Reading part of the buffer ("
|
||||
<< copyLength << "of" << d->worker->pendingData.length() << "bytes";
|
||||
readData = d->worker->pendingData.left(maxlen);
|
||||
d->worker->pendingData.remove(0, maxlen);
|
||||
if (d->notifyOnRead)
|
||||
emit readReady();
|
||||
}
|
||||
const int copyLength = qMin(maxlen, qint64(readData.length()));
|
||||
d->bytesAvailable -= copyLength;
|
||||
mutexLocker.unlock();
|
||||
|
||||
memcpy(data, readData, copyLength);
|
||||
qCDebug(lcNetworkSocketVerbose) << this << Q_FUNC_INFO << "Read" << copyLength << "bytes";
|
||||
return copyLength;
|
||||
}
|
||||
|
||||
qint64 QNativeSocketEngine::write(const char *data, qint64 len)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << data << len;
|
||||
Q_D(QNativeSocketEngine);
|
||||
if (!isValid())
|
||||
return -1;
|
||||
Q_CHECK_VALID_SOCKETLAYER(QNativeSocketEngine::write(), -1);
|
||||
Q_CHECK_STATE(QNativeSocketEngine::write(), QAbstractSocket::ConnectedState, -1);
|
||||
|
||||
HRESULT hr = E_FAIL;
|
||||
ComPtr<IOutputStream> stream;
|
||||
@ -978,28 +1056,35 @@ qint64 QNativeSocketEngine::write(const char *data, qint64 len)
|
||||
qint64 QNativeSocketEngine::readDatagram(char *data, qint64 maxlen, QIpPacketHeader *header,
|
||||
PacketHeaderOptions)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << maxlen;
|
||||
#ifndef QT_NO_UDPSOCKET
|
||||
Q_D(QNativeSocketEngine);
|
||||
QMutexLocker locker(&d->readMutex);
|
||||
if (d->socketType != QAbstractSocket::UdpSocket || d->pendingDatagrams.isEmpty()) {
|
||||
Q_CHECK_VALID_SOCKETLAYER(QNativeSocketEngine::readDatagram(), -1);
|
||||
Q_CHECK_STATES(QNativeSocketEngine::readDatagram(), QAbstractSocket::BoundState,
|
||||
QAbstractSocket::ConnectedState, -1);
|
||||
|
||||
QMutexLocker locker(&d->worker->mutex);
|
||||
if (d->socketType != QAbstractSocket::UdpSocket || d->worker->pendingDatagrams.isEmpty()) {
|
||||
if (header)
|
||||
header->clear();
|
||||
return -1;
|
||||
}
|
||||
|
||||
WinRtDatagram datagram = d->pendingDatagrams.takeFirst();
|
||||
WinRtDatagram datagram = d->worker->pendingDatagrams.takeFirst();
|
||||
if (header)
|
||||
*header = datagram.header;
|
||||
|
||||
QByteArray readOrigin;
|
||||
// Do not read the whole datagram. Put the rest of it back into the "queue"
|
||||
if (maxlen < datagram.data.length()) {
|
||||
if (maxlen < datagram.data.length())
|
||||
readOrigin = datagram.data.left(maxlen);
|
||||
datagram.data = datagram.data.remove(0, maxlen);
|
||||
d->pendingDatagrams.prepend(datagram);
|
||||
} else {
|
||||
else
|
||||
readOrigin = datagram.data;
|
||||
if (d->worker->pendingDatagrams.isEmpty()) {
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << "That's all folks";
|
||||
d->worker->emitDataReceived = true;
|
||||
d->emitReadReady = true;
|
||||
}
|
||||
|
||||
locker.unlock();
|
||||
memcpy(data, readOrigin, qMin(maxlen, qint64(datagram.data.length())));
|
||||
return readOrigin.length();
|
||||
@ -1013,8 +1098,13 @@ qint64 QNativeSocketEngine::readDatagram(char *data, qint64 maxlen, QIpPacketHea
|
||||
|
||||
qint64 QNativeSocketEngine::writeDatagram(const char *data, qint64 len, const QIpPacketHeader &header)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << data << len;
|
||||
#ifndef QT_NO_UDPSOCKET
|
||||
Q_D(QNativeSocketEngine);
|
||||
Q_CHECK_VALID_SOCKETLAYER(QNativeSocketEngine::writeDatagram(), -1);
|
||||
Q_CHECK_STATES(QNativeSocketEngine::writeDatagram(), QAbstractSocket::BoundState,
|
||||
QAbstractSocket::ConnectedState, -1);
|
||||
|
||||
if (d->socketType != QAbstractSocket::UdpSocket)
|
||||
return -1;
|
||||
|
||||
@ -1051,18 +1141,25 @@ qint64 QNativeSocketEngine::writeDatagram(const char *data, qint64 len, const QI
|
||||
bool QNativeSocketEngine::hasPendingDatagrams() const
|
||||
{
|
||||
Q_D(const QNativeSocketEngine);
|
||||
QMutexLocker locker(&d->readMutex);
|
||||
return d->pendingDatagrams.length() > 0;
|
||||
Q_CHECK_VALID_SOCKETLAYER(QNativeSocketEngine::hasPendingDatagrams(), false);
|
||||
Q_CHECK_NOT_STATE(QNativeSocketEngine::hasPendingDatagrams(), QAbstractSocket::UnconnectedState, false);
|
||||
Q_CHECK_TYPE(QNativeSocketEngine::hasPendingDatagrams(), QAbstractSocket::UdpSocket, false);
|
||||
|
||||
QMutexLocker locker(&d->worker->mutex);
|
||||
return d->worker->pendingDatagrams.length() > 0;
|
||||
}
|
||||
|
||||
qint64 QNativeSocketEngine::pendingDatagramSize() const
|
||||
{
|
||||
Q_D(const QNativeSocketEngine);
|
||||
QMutexLocker locker(&d->readMutex);
|
||||
if (d->pendingDatagrams.isEmpty())
|
||||
Q_CHECK_VALID_SOCKETLAYER(QNativeSocketEngine::pendingDatagramSize(), -1);
|
||||
Q_CHECK_TYPE(QNativeSocketEngine::pendingDatagramSize(), QAbstractSocket::UdpSocket, -1);
|
||||
|
||||
QMutexLocker locker(&d->worker->mutex);
|
||||
if (d->worker->pendingDatagrams.isEmpty())
|
||||
return -1;
|
||||
|
||||
return d->pendingDatagrams.at(0).data.length();
|
||||
return d->worker->pendingDatagrams.at(0).data.length();
|
||||
}
|
||||
|
||||
qint64 QNativeSocketEngine::bytesToWrite() const
|
||||
@ -1078,6 +1175,7 @@ qint64 QNativeSocketEngine::receiveBufferSize() const
|
||||
|
||||
void QNativeSocketEngine::setReceiveBufferSize(qint64 bufferSize)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << bufferSize;
|
||||
Q_D(QNativeSocketEngine);
|
||||
d->setOption(QAbstractSocketEngine::ReceiveBufferSocketOption, bufferSize);
|
||||
}
|
||||
@ -1090,6 +1188,7 @@ qint64 QNativeSocketEngine::sendBufferSize() const
|
||||
|
||||
void QNativeSocketEngine::setSendBufferSize(qint64 bufferSize)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << bufferSize;
|
||||
Q_D(QNativeSocketEngine);
|
||||
d->setOption(QAbstractSocketEngine::SendBufferSocketOption, bufferSize);
|
||||
}
|
||||
@ -1102,12 +1201,14 @@ int QNativeSocketEngine::option(QAbstractSocketEngine::SocketOption option) cons
|
||||
|
||||
bool QNativeSocketEngine::setOption(QAbstractSocketEngine::SocketOption option, int value)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << option << value;
|
||||
Q_D(QNativeSocketEngine);
|
||||
return d->setOption(option, value);
|
||||
}
|
||||
|
||||
bool QNativeSocketEngine::waitForRead(int msecs, bool *timedOut)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << msecs;
|
||||
Q_D(QNativeSocketEngine);
|
||||
Q_CHECK_VALID_SOCKETLAYER(QNativeSocketEngine::waitForRead(), false);
|
||||
Q_CHECK_NOT_STATE(QNativeSocketEngine::waitForRead(),
|
||||
@ -1124,8 +1225,8 @@ bool QNativeSocketEngine::waitForRead(int msecs, bool *timedOut)
|
||||
return true;
|
||||
|
||||
// If we are a client, we are ready to read if our buffer has data
|
||||
QMutexLocker locker(&d->readMutex);
|
||||
if (!d->pendingData.isEmpty())
|
||||
QMutexLocker locker(&d->worker->mutex);
|
||||
if (!d->worker->pendingData.isEmpty())
|
||||
return true;
|
||||
|
||||
// Nothing to do, wait for more events
|
||||
@ -1142,9 +1243,13 @@ bool QNativeSocketEngine::waitForRead(int msecs, bool *timedOut)
|
||||
|
||||
bool QNativeSocketEngine::waitForWrite(int msecs, bool *timedOut)
|
||||
{
|
||||
Q_UNUSED(msecs);
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << msecs;
|
||||
Q_UNUSED(timedOut);
|
||||
Q_D(QNativeSocketEngine);
|
||||
Q_CHECK_VALID_SOCKETLAYER(QNativeSocketEngine::waitForWrite(), false);
|
||||
Q_CHECK_NOT_STATE(QNativeSocketEngine::waitForWrite(),
|
||||
QAbstractSocket::UnconnectedState, false);
|
||||
|
||||
if (d->socketState == QAbstractSocket::ConnectingState) {
|
||||
HRESULT hr = QWinRTFunctions::await(d->worker->connectOp, QWinRTFunctions::ProcessMainThreadEvents);
|
||||
if (SUCCEEDED(hr)) {
|
||||
@ -1157,11 +1262,14 @@ bool QNativeSocketEngine::waitForWrite(int msecs, bool *timedOut)
|
||||
|
||||
bool QNativeSocketEngine::waitForReadOrWrite(bool *readyToRead, bool *readyToWrite, bool checkRead, bool checkWrite, int msecs, bool *timedOut)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << checkRead << checkWrite << msecs;
|
||||
Q_D(QNativeSocketEngine);
|
||||
Q_CHECK_VALID_SOCKETLAYER(QNativeSocketEngine::waitForReadOrWrite(), false);
|
||||
Q_CHECK_NOT_STATE(QNativeSocketEngine::waitForReadOrWrite(),
|
||||
QAbstractSocket::UnconnectedState, false);
|
||||
|
||||
Q_UNUSED(readyToRead);
|
||||
Q_UNUSED(readyToWrite);
|
||||
Q_UNUSED(checkRead);
|
||||
Q_UNUSED(checkWrite);
|
||||
Q_UNUSED(msecs);
|
||||
Q_UNUSED(timedOut);
|
||||
return false;
|
||||
}
|
||||
@ -1174,6 +1282,7 @@ bool QNativeSocketEngine::isReadNotificationEnabled() const
|
||||
|
||||
void QNativeSocketEngine::setReadNotificationEnabled(bool enable)
|
||||
{
|
||||
qCDebug(lcNetworkSocketVerbose) << this << Q_FUNC_INFO << enable;
|
||||
Q_D(QNativeSocketEngine);
|
||||
d->notifyOnRead = enable;
|
||||
}
|
||||
@ -1186,6 +1295,7 @@ bool QNativeSocketEngine::isWriteNotificationEnabled() const
|
||||
|
||||
void QNativeSocketEngine::setWriteNotificationEnabled(bool enable)
|
||||
{
|
||||
qCDebug(lcNetworkSocketVerbose) << this << Q_FUNC_INFO << enable;
|
||||
Q_D(QNativeSocketEngine);
|
||||
d->notifyOnWrite = enable;
|
||||
if (enable && d->socketState == QAbstractSocket::ConnectedState) {
|
||||
@ -1203,12 +1313,14 @@ bool QNativeSocketEngine::isExceptionNotificationEnabled() const
|
||||
|
||||
void QNativeSocketEngine::setExceptionNotificationEnabled(bool enable)
|
||||
{
|
||||
qCDebug(lcNetworkSocketVerbose) << this << Q_FUNC_INFO << enable;
|
||||
Q_D(QNativeSocketEngine);
|
||||
d->notifyOnException = enable;
|
||||
}
|
||||
|
||||
void QNativeSocketEngine::establishRead()
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO;
|
||||
Q_D(QNativeSocketEngine);
|
||||
|
||||
HRESULT hr;
|
||||
@ -1222,6 +1334,7 @@ void QNativeSocketEngine::establishRead()
|
||||
|
||||
void QNativeSocketEngine::handleConnectOpFinished(bool success, QAbstractSocket::SocketError error, WinRTSocketEngine::ErrorString errorString)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << success << error << errorString;
|
||||
Q_D(QNativeSocketEngine);
|
||||
disconnect(d->worker, &SocketEngineWorker::connectOpFinished,
|
||||
this, &QNativeSocketEngine::handleConnectOpFinished);
|
||||
@ -1232,6 +1345,7 @@ void QNativeSocketEngine::handleConnectOpFinished(bool success, QAbstractSocket:
|
||||
}
|
||||
|
||||
d->socketState = QAbstractSocket::ConnectedState;
|
||||
d->fetchConnectionParameters();
|
||||
emit connectionReady();
|
||||
|
||||
if (d->socketType != QAbstractSocket::TcpSocket)
|
||||
@ -1246,29 +1360,24 @@ void QNativeSocketEngine::handleConnectOpFinished(bool success, QAbstractSocket:
|
||||
establishRead();
|
||||
}
|
||||
|
||||
void QNativeSocketEngine::handleNewDatagrams(const QList<WinRtDatagram> &datagrams)
|
||||
void QNativeSocketEngine::handleNewData()
|
||||
{
|
||||
qCDebug(lcNetworkSocketVerbose) << this << Q_FUNC_INFO;
|
||||
Q_D(QNativeSocketEngine);
|
||||
QMutexLocker locker(&d->readMutex);
|
||||
d->pendingDatagrams.append(datagrams);
|
||||
if (d->notifyOnRead)
|
||||
emit readReady();
|
||||
}
|
||||
|
||||
void QNativeSocketEngine::handleNewData(const QVector<QByteArray> &data)
|
||||
{
|
||||
Q_D(QNativeSocketEngine);
|
||||
QMutexLocker locker(&d->readMutex);
|
||||
d->pendingData.append(data);
|
||||
for (const QByteArray &newData : data)
|
||||
d->bytesAvailable += newData.length();
|
||||
locker.unlock();
|
||||
if (d->notifyOnRead)
|
||||
readNotification();
|
||||
if (d->notifyOnRead && d->emitReadReady) {
|
||||
if (d->socketType == QAbstractSocket::UdpSocket && !d->worker->emitDataReceived)
|
||||
return;
|
||||
qCDebug(lcNetworkSocketVerbose) << this << Q_FUNC_INFO << "Emitting readReady";
|
||||
emit readReady();
|
||||
d->worker->emitDataReceived = false;
|
||||
d->emitReadReady = false;
|
||||
}
|
||||
}
|
||||
|
||||
void QNativeSocketEngine::handleTcpError(QAbstractSocket::SocketError error)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << error;
|
||||
Q_D(QNativeSocketEngine);
|
||||
WinRTSocketEngine::ErrorString errorString;
|
||||
switch (error) {
|
||||
@ -1287,6 +1396,7 @@ void QNativeSocketEngine::handleTcpError(QAbstractSocket::SocketError error)
|
||||
|
||||
bool QNativeSocketEnginePrivate::createNewSocket(QAbstractSocket::SocketType socketType, QAbstractSocket::NetworkLayerProtocol &socketProtocol)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << socketType << socketProtocol;
|
||||
Q_UNUSED(socketProtocol);
|
||||
HRESULT hr;
|
||||
|
||||
@ -1343,10 +1453,12 @@ QNativeSocketEnginePrivate::QNativeSocketEnginePrivate()
|
||||
, sslSocket(nullptr)
|
||||
, connectionToken( { -1 } )
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO;
|
||||
}
|
||||
|
||||
QNativeSocketEnginePrivate::~QNativeSocketEnginePrivate()
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO;
|
||||
if (socketDescriptor == -1 || connectionToken.value == -1)
|
||||
return;
|
||||
|
||||
@ -1362,6 +1474,7 @@ QNativeSocketEnginePrivate::~QNativeSocketEnginePrivate()
|
||||
|
||||
void QNativeSocketEnginePrivate::setError(QAbstractSocket::SocketError error, WinRTSocketEngine::ErrorString errorString) const
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << error << errorString;
|
||||
if (hasSetSocketError) {
|
||||
// Only set socket errors once for one engine; expect the
|
||||
// socket to recreate its engine after an error. Note: There's
|
||||
@ -1523,6 +1636,7 @@ int QNativeSocketEnginePrivate::option(QAbstractSocketEngine::SocketOption opt)
|
||||
|
||||
bool QNativeSocketEnginePrivate::setOption(QAbstractSocketEngine::SocketOption opt, int v)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO << opt << v;
|
||||
ComPtr<IStreamSocketControl> control;
|
||||
if (socketType == QAbstractSocket::TcpSocket) {
|
||||
if (FAILED(tcpSocket()->get_Control(&control))) {
|
||||
@ -1583,6 +1697,7 @@ bool QNativeSocketEnginePrivate::setOption(QAbstractSocketEngine::SocketOption o
|
||||
|
||||
bool QNativeSocketEnginePrivate::fetchConnectionParameters()
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO;
|
||||
localPort = 0;
|
||||
localAddress.clear();
|
||||
peerPort = 0;
|
||||
@ -1659,6 +1774,7 @@ bool QNativeSocketEnginePrivate::fetchConnectionParameters()
|
||||
|
||||
HRESULT QNativeSocketEnginePrivate::handleClientConnection(IStreamSocketListener *listener, IStreamSocketListenerConnectionReceivedEventArgs *args)
|
||||
{
|
||||
qCDebug(lcNetworkSocket) << this << Q_FUNC_INFO;
|
||||
Q_Q(QNativeSocketEngine);
|
||||
Q_UNUSED(listener)
|
||||
IStreamSocket *socket;
|
||||
@ -1670,40 +1786,6 @@ HRESULT QNativeSocketEnginePrivate::handleClientConnection(IStreamSocketListener
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
HRESULT QNativeSocketEnginePrivate::handleNewDatagram(IDatagramSocket *socket, IDatagramSocketMessageReceivedEventArgs *args)
|
||||
{
|
||||
Q_Q(QNativeSocketEngine);
|
||||
Q_UNUSED(socket);
|
||||
|
||||
WinRtDatagram datagram;
|
||||
QHostAddress returnAddress;
|
||||
ComPtr<IHostName> remoteHost;
|
||||
HRESULT hr = args->get_RemoteAddress(&remoteHost);
|
||||
RETURN_OK_IF_FAILED("Could not obtain remote host");
|
||||
HString remoteHostString;
|
||||
remoteHost->get_CanonicalName(remoteHostString.GetAddressOf());
|
||||
RETURN_OK_IF_FAILED("Could not obtain remote host's canonical name");
|
||||
returnAddress.setAddress(qt_QStringFromHString(remoteHostString));
|
||||
datagram.header.senderAddress = returnAddress;
|
||||
HString remotePort;
|
||||
hr = args->get_RemotePort(remotePort.GetAddressOf());
|
||||
RETURN_OK_IF_FAILED("Could not obtain remote port");
|
||||
datagram.header.senderPort = qt_QStringFromHString(remotePort).toInt();
|
||||
|
||||
ComPtr<IDataReader> reader;
|
||||
hr = args->GetDataReader(&reader);
|
||||
RETURN_OK_IF_FAILED("Could not obtain data reader");
|
||||
quint32 length;
|
||||
hr = reader->get_UnconsumedBufferLength(&length);
|
||||
RETURN_OK_IF_FAILED("Could not obtain unconsumed buffer length");
|
||||
datagram.data.resize(length);
|
||||
hr = reader->ReadBytes(length, reinterpret_cast<BYTE *>(datagram.data.data()));
|
||||
RETURN_OK_IF_FAILED("Could not read datagram");
|
||||
emit q->newDatagramReceived(datagram);
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
QT_END_NAMESPACE
|
||||
|
||||
#include "qnativesocketengine_winrt.moc"
|
||||
|
@ -54,6 +54,7 @@
|
||||
#include <QtNetwork/private/qtnetworkglobal_p.h>
|
||||
#include <QtCore/QEventLoop>
|
||||
#include <QtCore/QBuffer>
|
||||
#include <QtCore/QLoggingCategory>
|
||||
#include <QtCore/QMutex>
|
||||
#include <QtCore/QAtomicInteger>
|
||||
#include "QtNetwork/qhostaddress.h"
|
||||
@ -63,6 +64,9 @@
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
Q_DECLARE_LOGGING_CATEGORY(lcNetworkSocket)
|
||||
Q_DECLARE_LOGGING_CATEGORY(lcNetworkSocketVerbose)
|
||||
|
||||
namespace WinRTSocketEngine {
|
||||
enum ErrorString {
|
||||
NonBlockingInitFailedErrorString,
|
||||
@ -178,8 +182,7 @@ private slots:
|
||||
void establishRead();
|
||||
void handleConnectOpFinished(bool success, QAbstractSocket::SocketError error,
|
||||
WinRTSocketEngine::ErrorString errorString);
|
||||
void handleNewDatagrams(const QList<WinRtDatagram> &datagram);
|
||||
void handleNewData(const QVector<QByteArray> &data);
|
||||
void handleNewData();
|
||||
void handleTcpError(QAbstractSocket::SocketError error);
|
||||
|
||||
private:
|
||||
@ -218,28 +221,14 @@ private:
|
||||
{ return reinterpret_cast<ABI::Windows::Networking::Sockets::IDatagramSocket *>(socketDescriptor); }
|
||||
Microsoft::WRL::ComPtr<ABI::Windows::Networking::Sockets::IStreamSocketListener> tcpListener;
|
||||
|
||||
// In case of TCP readMutex protects readBytes and bytesAvailable. In case of UDP it is
|
||||
// pendingDatagrams. They are written inside native callbacks (handleReadyRead and
|
||||
// handleNewDatagrams/putIntoPendingDatagramsList)
|
||||
mutable QMutex readMutex;
|
||||
|
||||
// Protected by readMutex. Written in handleReadyRead (native callback)
|
||||
QAtomicInteger<int> bytesAvailable;
|
||||
|
||||
// Protected by readMutex. Written in handleNewData/putIntoPendingData (native callback)
|
||||
QVector<QByteArray> pendingData;
|
||||
|
||||
// Protected by readMutex. Written in handleNewDatagrams/putIntoPendingDatagramsList
|
||||
QList<WinRtDatagram> pendingDatagrams;
|
||||
|
||||
QList<ABI::Windows::Networking::Sockets::IStreamSocket *> pendingConnections;
|
||||
QList<ABI::Windows::Networking::Sockets::IStreamSocket *> currentConnections;
|
||||
QEventLoop eventLoop;
|
||||
QAbstractSocket *sslSocket;
|
||||
EventRegistrationToken connectionToken;
|
||||
|
||||
HRESULT handleNewDatagram(ABI::Windows::Networking::Sockets::IDatagramSocket *socket,
|
||||
ABI::Windows::Networking::Sockets::IDatagramSocketMessageReceivedEventArgs *args);
|
||||
bool emitReadReady = true;
|
||||
|
||||
HRESULT handleClientConnection(ABI::Windows::Networking::Sockets::IStreamSocketListener *tcpListener,
|
||||
ABI::Windows::Networking::Sockets::IStreamSocketListenerConnectionReceivedEventArgs *args);
|
||||
};
|
||||
|
@ -116,14 +116,14 @@ Q_LOGGING_CATEGORY(lcSsl, "qt.network.ssl");
|
||||
|
||||
Describes the protocol of the cipher.
|
||||
|
||||
\value SslV3 SSLv3
|
||||
\value SslV3 SSLv3. When using the WinRT backend this option will also enable TLSv1.0
|
||||
\value SslV2 SSLv2
|
||||
\value TlsV1_0 TLSv1.0
|
||||
\value TlsV1_0OrLater TLSv1.0 and later versions. This option is not available when using the WinRT backend due to platform limitations.
|
||||
\value TlsV1 Obsolete, means the same as TlsV1_0
|
||||
\value TlsV1_1 TLSv1.1
|
||||
\value TlsV1_1 TLSv1.1. When using the WinRT backend this option will also enable TLSv1.0.
|
||||
\value TlsV1_1OrLater TLSv1.1 and later versions. This option is not available when using the WinRT backend due to platform limitations.
|
||||
\value TlsV1_2 TLSv1.2
|
||||
\value TlsV1_2 TLSv1.2. When using the WinRT backend this option will also enable TLSv1.0 and TLSv1.1.
|
||||
\value TlsV1_2OrLater TLSv1.2 and later versions. This option is not available when using the WinRT backend due to platform limitations.
|
||||
\value UnknownProtocol The cipher's protocol cannot be determined.
|
||||
\value AnyProtocol The socket understands SSLv2, SSLv3, and TLSv1.0. This
|
||||
|
@ -128,10 +128,10 @@ QList<QSslCertificate> QSslSocketPrivate::systemCaCertificates()
|
||||
QList<QSslCertificate> systemCerts;
|
||||
// SecTrustSettingsCopyCertificates is not defined on iOS.
|
||||
#ifdef Q_OS_OSX
|
||||
QCFType<CFArrayRef> cfCerts;
|
||||
// iterate through all enum members, order:
|
||||
// kSecTrustSettingsDomainUser, kSecTrustSettingsDomainAdmin, kSecTrustSettingsDomainSystem
|
||||
for (int dom = kSecTrustSettingsDomainUser; dom <= int(kSecTrustSettingsDomainSystem); dom++) {
|
||||
QCFType<CFArrayRef> cfCerts;
|
||||
OSStatus status = SecTrustSettingsCopyCertificates(SecTrustSettingsDomain(dom), &cfCerts);
|
||||
if (status == noErr) {
|
||||
const CFIndex size = CFArrayGetCount(cfCerts);
|
||||
|
@ -238,7 +238,6 @@ void QSslSocketBackendPrivate::startClientEncryption()
|
||||
case QSsl::SslV3:
|
||||
protectionLevel = SocketProtectionLevel_Ssl; // Only use this value if weak cipher support is required
|
||||
break;
|
||||
case QSsl::SecureProtocols:
|
||||
case QSsl::TlsV1SslV3:
|
||||
case QSsl::TlsV1_0:
|
||||
protectionLevel = SocketProtectionLevel_Tls10;
|
||||
@ -257,6 +256,11 @@ void QSslSocketBackendPrivate::startClientEncryption()
|
||||
setErrorAndEmit(QAbstractSocket::SslInvalidUserDataError,
|
||||
QStringLiteral("unsupported protocol"));
|
||||
return;
|
||||
case QSsl::SecureProtocols:
|
||||
// SocketProtectionLevel_Tls12 actually means "use TLS1.0, 1.1 or 1.2"
|
||||
// https://docs.microsoft.com/en-us/uwp/api/windows.networking.sockets.socketprotectionlevel
|
||||
protectionLevel = SocketProtectionLevel_Tls12;
|
||||
break;
|
||||
default:
|
||||
protectionLevel = SocketProtectionLevel_Tls12; // default to highest
|
||||
protocol = QSsl::TlsV1_2;
|
||||
|
@ -493,7 +493,7 @@ NSUInteger QCocoaWindow::windowStyleMask(Qt::WindowFlags flags)
|
||||
{
|
||||
const Qt::WindowType type = static_cast<Qt::WindowType>(int(flags & Qt::WindowType_Mask));
|
||||
const bool frameless = (flags & Qt::FramelessWindowHint) || windowIsPopupType(type);
|
||||
const bool resizeable = type != Qt::Dialog; // Dialogs: remove zoom button by disabling resize
|
||||
const bool resizeable = !(flags & Qt::CustomizeWindowHint); // Remove zoom button by disabling resize
|
||||
|
||||
// Select base window type. Note that the value of NSBorderlessWindowMask is 0.
|
||||
NSUInteger styleMask = (frameless || !resizeable) ? NSBorderlessWindowMask : NSResizableWindowMask;
|
||||
|
@ -155,8 +155,12 @@
|
||||
NSPoint screenPoint;
|
||||
if (theEvent) {
|
||||
NSPoint windowPoint = [theEvent locationInWindow];
|
||||
NSRect screenRect = [[theEvent window] convertRectToScreen:NSMakeRect(windowPoint.x, windowPoint.y, 1, 1)];
|
||||
screenPoint = screenRect.origin;
|
||||
if (qIsNaN(windowPoint.x) || qIsNaN(windowPoint.y)) {
|
||||
screenPoint = [NSEvent mouseLocation];
|
||||
} else {
|
||||
NSRect screenRect = [[theEvent window] convertRectToScreen:NSMakeRect(windowPoint.x, windowPoint.y, 1, 1)];
|
||||
screenPoint = screenRect.origin;
|
||||
}
|
||||
} else {
|
||||
screenPoint = [NSEvent mouseLocation];
|
||||
}
|
||||
|
@ -63,6 +63,18 @@
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
#define DECLARE_DEBUG_VAR(variable) \
|
||||
static bool debug_ ## variable() \
|
||||
{ static bool value = qgetenv("QNX_SCREEN_DEBUG").contains(QT_STRINGIFY(variable)); return value; }
|
||||
DECLARE_DEBUG_VAR(fps)
|
||||
DECLARE_DEBUG_VAR(posts)
|
||||
DECLARE_DEBUG_VAR(blits)
|
||||
DECLARE_DEBUG_VAR(updates)
|
||||
DECLARE_DEBUG_VAR(cpu_time)
|
||||
DECLARE_DEBUG_VAR(gpu_time)
|
||||
DECLARE_DEBUG_VAR(statistics)
|
||||
#undef DECLARE_DEBUG_VAR
|
||||
|
||||
/*!
|
||||
\class QQnxWindow
|
||||
\brief The QQnxWindow is the base class of the various classes used as instances of
|
||||
@ -211,6 +223,35 @@ QQnxWindow::QQnxWindow(QWindow *window, screen_context_t context, bool needRootW
|
||||
// it'll cause us not to join a group (the app will presumably join at some future time).
|
||||
if (windowGroup.isValid() && windowGroup.canConvert<QByteArray>())
|
||||
joinWindowGroup(windowGroup.toByteArray());
|
||||
|
||||
int debug = 0;
|
||||
if (Q_UNLIKELY(debug_fps())) {
|
||||
debug |= SCREEN_DEBUG_GRAPH_FPS;
|
||||
}
|
||||
if (Q_UNLIKELY(debug_posts())) {
|
||||
debug |= SCREEN_DEBUG_GRAPH_POSTS;
|
||||
}
|
||||
if (Q_UNLIKELY(debug_blits())) {
|
||||
debug |= SCREEN_DEBUG_GRAPH_BLITS;
|
||||
}
|
||||
if (Q_UNLIKELY(debug_updates())) {
|
||||
debug |= SCREEN_DEBUG_GRAPH_UPDATES;
|
||||
}
|
||||
if (Q_UNLIKELY(debug_cpu_time())) {
|
||||
debug |= SCREEN_DEBUG_GRAPH_CPU_TIME;
|
||||
}
|
||||
if (Q_UNLIKELY(debug_gpu_time())) {
|
||||
debug |= SCREEN_DEBUG_GRAPH_GPU_TIME;
|
||||
}
|
||||
if (Q_UNLIKELY(debug_statistics())) {
|
||||
debug = SCREEN_DEBUG_STATISTICS;
|
||||
}
|
||||
|
||||
if (debug > 0) {
|
||||
Q_SCREEN_CHECKERROR(screen_set_window_property_iv(nativeHandle(), SCREEN_PROPERTY_DEBUG, &debug),
|
||||
"Could not set SCREEN_PROPERTY_DEBUG");
|
||||
qWindowDebug() << "window SCREEN_PROPERTY_DEBUG= " << debug;
|
||||
}
|
||||
}
|
||||
|
||||
QQnxWindow::~QQnxWindow()
|
||||
|
@ -86,6 +86,22 @@ typedef GLXContext (*glXCreateContextAttribsARBProc)(Display*, GLXFBConfig, GLXC
|
||||
#define GL_CONTEXT_FLAG_DEBUG_BIT 0x00000002
|
||||
#endif
|
||||
|
||||
#ifndef GLX_CONTEXT_ROBUST_ACCESS_BIT_ARB
|
||||
#define GLX_CONTEXT_ROBUST_ACCESS_BIT_ARB 0x00000004
|
||||
#endif
|
||||
|
||||
#ifndef GLX_CONTEXT_RESET_NOTIFICATION_STRATEGY_ARB
|
||||
#define GLX_CONTEXT_RESET_NOTIFICATION_STRATEGY_ARB 0x8256
|
||||
#endif
|
||||
|
||||
#ifndef GLX_LOSE_CONTEXT_ON_RESET_ARB
|
||||
#define GLX_LOSE_CONTEXT_ON_RESET_ARB 0x8252
|
||||
#endif
|
||||
|
||||
#ifndef GLX_GENERATE_RESET_ON_VIDEO_MEMORY_PURGE_NV
|
||||
#define GLX_GENERATE_RESET_ON_VIDEO_MEMORY_PURGE_NV 0x20F7
|
||||
#endif
|
||||
|
||||
static Window createDummyWindow(Display *dpy, XVisualInfo *visualInfo, int screenNumber, Window rootWin)
|
||||
{
|
||||
Colormap cmap = XCreateColormap(dpy, rootWin, visualInfo->visual, AllocNone);
|
||||
@ -179,6 +195,8 @@ QGLXContext::QGLXContext(QXcbScreen *screen, const QSurfaceFormat &format, QPlat
|
||||
, m_isPBufferCurrent(false)
|
||||
, m_swapInterval(-1)
|
||||
, m_ownsContext(nativeHandle.isNull())
|
||||
, m_getGraphicsResetStatus(0)
|
||||
, m_lost(false)
|
||||
{
|
||||
if (nativeHandle.isNull())
|
||||
init(screen, share);
|
||||
@ -214,6 +232,8 @@ void QGLXContext::init(QXcbScreen *screen, QPlatformOpenGLContext *share)
|
||||
glXCreateContextAttribsARB = (glXCreateContextAttribsARBProc) glXGetProcAddress((const GLubyte*)"glXCreateContextAttribsARB");
|
||||
|
||||
const bool supportsProfiles = glxExt.contains("GLX_ARB_create_context_profile");
|
||||
const bool supportsRobustness = glxExt.contains("GLX_ARB_create_context_robustness");
|
||||
const bool supportsVideoMemoryPurge = glxExt.contains("GLX_NV_robustness_video_memory_purge");
|
||||
|
||||
// Use glXCreateContextAttribsARB if available
|
||||
// Also, GL ES context creation requires GLX_EXT_create_context_es2_profile
|
||||
@ -266,6 +286,9 @@ void QGLXContext::init(QXcbScreen *screen, QPlatformOpenGLContext *share)
|
||||
|
||||
int flags = 0;
|
||||
|
||||
if (supportsRobustness)
|
||||
flags |= GLX_CONTEXT_ROBUST_ACCESS_BIT_ARB;
|
||||
|
||||
if (m_format.testOption(QSurfaceFormat::DebugContext))
|
||||
flags |= GLX_CONTEXT_DEBUG_BIT_ARB;
|
||||
|
||||
@ -279,14 +302,33 @@ void QGLXContext::init(QXcbScreen *screen, QPlatformOpenGLContext *share)
|
||||
contextAttributes << GLX_CONTEXT_PROFILE_MASK_ARB << GLX_CONTEXT_ES2_PROFILE_BIT_EXT;
|
||||
}
|
||||
|
||||
contextAttributes << None;
|
||||
if (supportsRobustness && supportsVideoMemoryPurge) {
|
||||
QVector<int> contextAttributesWithNvidiaReset = contextAttributes;
|
||||
|
||||
m_context = glXCreateContextAttribsARB(m_display, config, m_shareContext, true, contextAttributes.data());
|
||||
if (!m_context && m_shareContext) {
|
||||
// re-try without a shared glx context
|
||||
m_context = glXCreateContextAttribsARB(m_display, config, 0, true, contextAttributes.data());
|
||||
if (m_context)
|
||||
m_shareContext = 0;
|
||||
contextAttributesWithNvidiaReset << GLX_CONTEXT_RESET_NOTIFICATION_STRATEGY_ARB << GLX_LOSE_CONTEXT_ON_RESET_ARB;
|
||||
contextAttributesWithNvidiaReset << GLX_GENERATE_RESET_ON_VIDEO_MEMORY_PURGE_NV << GL_TRUE;
|
||||
|
||||
contextAttributesWithNvidiaReset << None;
|
||||
m_context = glXCreateContextAttribsARB(m_display, config, m_shareContext, true, contextAttributesWithNvidiaReset.data());
|
||||
if (!m_context && m_shareContext) {
|
||||
// re-try without a shared glx context
|
||||
m_context = glXCreateContextAttribsARB(m_display, config, 0, true, contextAttributesWithNvidiaReset.data());
|
||||
if (m_context)
|
||||
m_shareContext = 0;
|
||||
}
|
||||
}
|
||||
|
||||
if (m_context) {
|
||||
m_getGraphicsResetStatus = reinterpret_cast<GLenum (QOPENGLF_APIENTRYP)()>(getProcAddress("glGetGraphicsResetStatusARB"));
|
||||
} else {
|
||||
contextAttributes << None;
|
||||
m_context = glXCreateContextAttribsARB(m_display, config, m_shareContext, true, contextAttributes.data());
|
||||
if (!m_context && m_shareContext) {
|
||||
// re-try without a shared glx context
|
||||
m_context = glXCreateContextAttribsARB(m_display, config, 0, true, contextAttributes.data());
|
||||
if (m_context)
|
||||
m_shareContext = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -494,6 +536,12 @@ bool QGLXContext::makeCurrent(QPlatformSurface *surface)
|
||||
QXcbWindow *window = static_cast<QXcbWindow *>(surface);
|
||||
glxDrawable = window->xcb_window();
|
||||
success = glXMakeCurrent(m_display, glxDrawable, m_context);
|
||||
m_lost = false;
|
||||
if (m_getGraphicsResetStatus && m_getGraphicsResetStatus() != GL_NO_ERROR) {
|
||||
m_lost = true;
|
||||
// Drop the surface. Will recreate on the next makeCurrent.
|
||||
window->invalidateSurface();
|
||||
}
|
||||
} else if (surfaceClass == QSurface::Offscreen) {
|
||||
m_isPBufferCurrent = true;
|
||||
QGLXPbuffer *pbuffer = static_cast<QGLXPbuffer *>(surface);
|
||||
@ -609,7 +657,7 @@ bool QGLXContext::isSharing() const
|
||||
|
||||
bool QGLXContext::isValid() const
|
||||
{
|
||||
return m_context != 0;
|
||||
return m_context != 0 && !m_lost;
|
||||
}
|
||||
|
||||
bool QGLXContext::m_queriedDummyContext = false;
|
||||
|
@ -89,6 +89,8 @@ private:
|
||||
bool m_isPBufferCurrent;
|
||||
int m_swapInterval;
|
||||
bool m_ownsContext;
|
||||
GLenum (APIENTRY * m_getGraphicsResetStatus)();
|
||||
bool m_lost;
|
||||
static bool m_queriedDummyContext;
|
||||
static bool m_supportsThreading;
|
||||
};
|
||||
|
@ -462,8 +462,10 @@ void QPSQLResult::cleanup()
|
||||
d->result = nullptr;
|
||||
while (!d->nextResultSets.isEmpty())
|
||||
PQclear(d->nextResultSets.takeFirst());
|
||||
if (d->stmtId != InvalidStatementId)
|
||||
d->drv_d_func()->finishQuery(d->stmtId);
|
||||
if (d->stmtId != InvalidStatementId) {
|
||||
if (d->drv_d_func())
|
||||
d->drv_d_func()->finishQuery(d->stmtId);
|
||||
}
|
||||
d->stmtId = InvalidStatementId;
|
||||
setAt(QSql::BeforeFirstRow);
|
||||
d->currentSize = -1;
|
||||
|
@ -56,6 +56,7 @@
|
||||
#include <qregularexpression.h>
|
||||
#endif
|
||||
#include <QTimeZone>
|
||||
#include <QScopedValueRollback>
|
||||
|
||||
#if defined Q_OS_WIN
|
||||
# include <qt_windows.h>
|
||||
@ -129,6 +130,7 @@ protected:
|
||||
bool gotoNext(QSqlCachedResult::ValueCache& row, int idx) override;
|
||||
bool reset(const QString &query) override;
|
||||
bool prepare(const QString &query) override;
|
||||
bool execBatch(bool arrayBind) override;
|
||||
bool exec() override;
|
||||
int size() override;
|
||||
int numRowsAffected() override;
|
||||
@ -443,6 +445,29 @@ static QString timespecToString(const QDateTime &dateTime)
|
||||
}
|
||||
}
|
||||
|
||||
bool QSQLiteResult::execBatch(bool arrayBind)
|
||||
{
|
||||
Q_UNUSED(arrayBind);
|
||||
Q_D(QSqlResult);
|
||||
QScopedValueRollback<QVector<QVariant>> valuesScope(d->values);
|
||||
QVector<QVariant> values = d->values;
|
||||
if (values.count() == 0)
|
||||
return false;
|
||||
|
||||
for (int i = 0; i < values.at(0).toList().count(); ++i) {
|
||||
d->values.clear();
|
||||
QScopedValueRollback<QHash<QString, QVector<int>>> indexesScope(d->indexes);
|
||||
QHash<QString, QVector<int>>::const_iterator it = d->indexes.constBegin();
|
||||
while (it != d->indexes.constEnd()) {
|
||||
bindValue(it.key(), values.at(it.value().first()).toList().at(i), QSql::In);
|
||||
++it;
|
||||
}
|
||||
if (!exec())
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool QSQLiteResult::exec()
|
||||
{
|
||||
Q_D(QSQLiteResult);
|
||||
@ -471,7 +496,7 @@ bool QSQLiteResult::exec()
|
||||
// can end up in a case where for virtual tables it returns 0 even though it
|
||||
// has parameters
|
||||
if (paramCount > 1 && paramCount < values.count()) {
|
||||
const auto countIndexes = [](int counter, const QList<int>& indexList) {
|
||||
const auto countIndexes = [](int counter, const QVector<int> &indexList) {
|
||||
return counter + indexList.length();
|
||||
};
|
||||
|
||||
@ -485,13 +510,14 @@ bool QSQLiteResult::exec()
|
||||
// placeholders. So we need to ensure the QVector has only one instance of
|
||||
// each value as SQLite will do the rest for us.
|
||||
QVector<QVariant> prunedValues;
|
||||
QList<int> handledIndexes;
|
||||
QVector<int> handledIndexes;
|
||||
for (int i = 0, currentIndex = 0; i < values.size(); ++i) {
|
||||
if (handledIndexes.contains(i))
|
||||
continue;
|
||||
const auto placeHolder = QString::fromUtf8(sqlite3_bind_parameter_name(d->stmt, currentIndex + 1));
|
||||
handledIndexes << d->indexes[placeHolder];
|
||||
prunedValues << values.at(d->indexes[placeHolder].first());
|
||||
const auto &indexes = d->indexes.value(placeHolder);
|
||||
handledIndexes << indexes;
|
||||
prunedValues << values.at(indexes.first());
|
||||
++currentIndex;
|
||||
}
|
||||
values = prunedValues;
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -190,6 +190,7 @@ public:
|
||||
Button_PullDown, // QPushButton with menu
|
||||
Button_PushButton,
|
||||
Button_RadioButton,
|
||||
Button_SquareButton, // Oversized QPushButton
|
||||
Button_WindowClose,
|
||||
Button_WindowMiniaturize,
|
||||
Button_WindowZoom,
|
||||
@ -206,7 +207,23 @@ public:
|
||||
TextField
|
||||
};
|
||||
|
||||
typedef QPair<CocoaControlType, QStyleHelper::WidgetSizePolicy> CocoaControl;
|
||||
|
||||
struct CocoaControl {
|
||||
CocoaControl();
|
||||
CocoaControl(CocoaControlType t, QStyleHelper::WidgetSizePolicy s);
|
||||
|
||||
CocoaControlType type;
|
||||
QStyleHelper::WidgetSizePolicy size;
|
||||
|
||||
bool operator==(const CocoaControl &other) const;
|
||||
|
||||
QSizeF defaultFrameSize() const;
|
||||
QRectF adjustedControlFrame(const QRectF &rect) const;
|
||||
QMarginsF titleMargins() const;
|
||||
|
||||
bool getCocoaButtonTypeAndBezelStyle(NSButtonType *buttonType, NSBezelStyle *bezelStyle) const;
|
||||
};
|
||||
|
||||
|
||||
typedef void (^DrawRectBlock)(CGContextRef, const CGRect &);
|
||||
|
||||
@ -273,11 +290,13 @@ public:
|
||||
|
||||
void setupVerticalInvertedXform(CGContextRef cg, bool reverse, bool vertical, const CGRect &rect) const;
|
||||
|
||||
void drawNSViewInRect(CocoaControl widget, NSView *view, const QRect &rect, QPainter *p, bool isQWidget = true, __attribute__((noescape)) DrawRectBlock drawRectBlock = nil) const;
|
||||
void drawNSViewInRect(CocoaControl widget, NSView *view, const QRectF &rect, QPainter *p, bool isQWidget = true, __attribute__((noescape)) DrawRectBlock drawRectBlock = nil) const;
|
||||
void resolveCurrentNSView(QWindow *window) const;
|
||||
|
||||
void drawFocusRing(QPainter *p, const QRect &targetRect, int hMargin, int vMargin, qreal radius = 0) const;
|
||||
void drawFocusRing(QPainter *p, const QRect &targetRect, int hMargin, int vMargin, const CocoaControl &cw) const;
|
||||
void drawFocusRing(QPainter *p, const QRectF &targetRect, int hMargin, int vMargin, const CocoaControl &cw) const;
|
||||
|
||||
void drawToolbarButtonArrow(const QStyleOption *opt, QPainter *p) const;
|
||||
|
||||
QPainterPath windowPanelPath(const QRectF &r) const;
|
||||
|
||||
|
@ -122,7 +122,8 @@ static inline HDC hdcForWidgetBackingStore(const QWidget *widget)
|
||||
{
|
||||
if (QBackingStore *backingStore = backingStoreForWidget(widget)) {
|
||||
QPlatformNativeInterface *nativeInterface = QGuiApplication::platformNativeInterface();
|
||||
return static_cast<HDC>(nativeInterface->nativeResourceForBackingStore(QByteArrayLiteral("getDC"), backingStore));
|
||||
if (nativeInterface)
|
||||
return static_cast<HDC>(nativeInterface->nativeResourceForBackingStore(QByteArrayLiteral("getDC"), backingStore));
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -690,7 +690,7 @@ void QSqlResult::bindValue(int index, const QVariant& val, QSql::ParamType param
|
||||
{
|
||||
Q_D(QSqlResult);
|
||||
d->binds = PositionalBinding;
|
||||
QList<int>& indexes = d->indexes[d->fieldSerial(index)];
|
||||
QVector<int> &indexes = d->indexes[d->fieldSerial(index)];
|
||||
if (!indexes.contains(index))
|
||||
indexes.append(index);
|
||||
if (d->values.count() <= index)
|
||||
@ -717,7 +717,7 @@ void QSqlResult::bindValue(const QString& placeholder, const QVariant& val,
|
||||
d->binds = NamedBinding;
|
||||
// if the index has already been set when doing emulated named
|
||||
// bindings - don't reset it
|
||||
const QList<int> indexes = d->indexes.value(placeholder);
|
||||
const QVector<int> indexes = d->indexes.value(placeholder);
|
||||
for (int idx : indexes) {
|
||||
if (d->values.count() <= idx)
|
||||
d->values.resize(idx + 1);
|
||||
@ -764,7 +764,7 @@ QVariant QSqlResult::boundValue(int index) const
|
||||
QVariant QSqlResult::boundValue(const QString& placeholder) const
|
||||
{
|
||||
Q_D(const QSqlResult);
|
||||
QList<int> indexes = d->indexes.value(placeholder);
|
||||
const QVector<int> indexes = d->indexes.value(placeholder);
|
||||
return d->values.value(indexes.value(0,-1));
|
||||
}
|
||||
|
||||
|
@ -135,7 +135,7 @@ public:
|
||||
QString executedQuery;
|
||||
QHash<int, QSql::ParamType> types;
|
||||
QVector<QVariant> values;
|
||||
typedef QHash<QString, QList<int> > IndexMap;
|
||||
typedef QHash<QString, QVector<int> > IndexMap;
|
||||
IndexMap indexes;
|
||||
|
||||
typedef QVector<QHolder> QHolderVector;
|
||||
|
22
src/testlib/configure.json
Normal file
22
src/testlib/configure.json
Normal file
@ -0,0 +1,22 @@
|
||||
{
|
||||
"module": "testlib",
|
||||
"depends": [
|
||||
"core"
|
||||
],
|
||||
|
||||
"features": {
|
||||
"itemmodeltester": {
|
||||
"label": "Tester for item models",
|
||||
"purpose": "Provides a utility to test item models.",
|
||||
"condition": "features.itemmodel",
|
||||
"output": [ "publicFeature" ]
|
||||
}
|
||||
},
|
||||
|
||||
"summary": [
|
||||
{
|
||||
"section": "Qt Testlib",
|
||||
"entries": [ "itemmodeltester" ]
|
||||
}
|
||||
]
|
||||
}
|
@ -30,7 +30,7 @@
|
||||
#define QABSTRACTITEMMODELTESTER_H
|
||||
|
||||
#include <QtCore/QObject>
|
||||
#include <QtTest/qtest_global.h>
|
||||
#include <QtTest/qttestglobal.h>
|
||||
|
||||
#ifdef QT_GUI_LIB
|
||||
#include <QtGui/QFont>
|
||||
@ -41,6 +41,8 @@
|
||||
#include <QtGui/QIcon>
|
||||
#endif
|
||||
|
||||
QT_REQUIRE_CONFIG(itemmodeltester);
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
class QAbstractItemModel;
|
||||
|
@ -40,7 +40,7 @@
|
||||
#ifndef QBENCHMARK_H
|
||||
#define QBENCHMARK_H
|
||||
|
||||
#include <QtTest/qtest_global.h>
|
||||
#include <QtTest/qttestglobal.h>
|
||||
#include <QtTest/qbenchmarkmetric.h>
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
@ -69,7 +69,7 @@
|
||||
|
||||
#include <QtTest/private/qbenchmarkmeasurement_p.h>
|
||||
#include <QtCore/QMap>
|
||||
#include <QtTest/qtest_global.h>
|
||||
#include <QtTest/qttestglobal.h>
|
||||
#ifdef QTESTLIB_USE_VALGRIND
|
||||
#include <QtTest/private/qbenchmarkvalgrind_p.h>
|
||||
#endif
|
||||
|
@ -41,7 +41,7 @@
|
||||
#ifndef QBENCHMARKMETRIC_H
|
||||
#define QBENCHMARKMETRIC_H
|
||||
|
||||
#include <QtTest/qtest_global.h>
|
||||
#include <QtTest/qttestglobal.h>
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
|
@ -51,7 +51,7 @@
|
||||
// We mean it.
|
||||
//
|
||||
|
||||
#include <QtTest/qtest_global.h>
|
||||
#include <QtTest/qttestglobal.h>
|
||||
#include <QtTest/qbenchmarkmetric.h>
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
@ -41,7 +41,7 @@
|
||||
#ifndef QTEST_H
|
||||
#define QTEST_H
|
||||
|
||||
#include <QtTest/qtest_global.h>
|
||||
#include <QtTest/qttestglobal.h>
|
||||
#include <QtTest/qtestcase.h>
|
||||
#include <QtTest/qtestdata.h>
|
||||
#include <QtTest/qbenchmark.h>
|
||||
|
@ -54,7 +54,7 @@
|
||||
#include <QtCore/qdebug.h>
|
||||
#include <QtGui/qaccessible.h>
|
||||
#include <QtGui/qguiapplication.h>
|
||||
#include <QtTest/qtest_global.h>
|
||||
#include <QtTest/qttestglobal.h>
|
||||
#include <QtTest/qtestsystem.h>
|
||||
|
||||
#if QT_CONFIG(accessibility)
|
||||
|
@ -51,7 +51,7 @@
|
||||
// We mean it.
|
||||
//
|
||||
|
||||
#include <QtTest/qtest_global.h>
|
||||
#include <QtTest/qttestglobal.h>
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
|
@ -75,6 +75,7 @@
|
||||
#include <QtTest/private/qtestutil_macos_p.h>
|
||||
#endif
|
||||
|
||||
#include <cmath>
|
||||
#include <numeric>
|
||||
#include <algorithm>
|
||||
|
||||
@ -208,8 +209,13 @@ static void stackTrace()
|
||||
if (debuggerPresent())
|
||||
return;
|
||||
|
||||
#if defined(Q_OS_LINUX) || defined(Q_OS_MACOS)
|
||||
const int msecsFunctionTime = qRound(QTestLog::msecsFunctionTime());
|
||||
const int msecsTotalTime = qRound(QTestLog::msecsTotalTime());
|
||||
fprintf(stderr, "\n=== Received signal at function time: %dms, total time: %dms, dumping stack ===\n",
|
||||
msecsFunctionTime, msecsTotalTime);
|
||||
#endif
|
||||
#ifdef Q_OS_LINUX
|
||||
fprintf(stderr, "\n========= Received signal, dumping stack ==============\n");
|
||||
char cmd[512];
|
||||
qsnprintf(cmd, 512, "gdb --pid %d 2>/dev/null <<EOF\n"
|
||||
"set prompt\n"
|
||||
@ -221,9 +227,8 @@ static void stackTrace()
|
||||
(int)getpid());
|
||||
if (system(cmd) == -1)
|
||||
fprintf(stderr, "calling gdb failed\n");
|
||||
fprintf(stderr, "========= End of stack trace ==============\n");
|
||||
fprintf(stderr, "=== End of stack trace ===\n");
|
||||
#elif defined(Q_OS_OSX)
|
||||
fprintf(stderr, "\n========= Received signal, dumping stack ==============\n");
|
||||
char cmd[512];
|
||||
qsnprintf(cmd, 512, "lldb -p %d 2>/dev/null <<EOF\n"
|
||||
"bt all\n"
|
||||
@ -232,7 +237,7 @@ static void stackTrace()
|
||||
(int)getpid());
|
||||
if (system(cmd) == -1)
|
||||
fprintf(stderr, "calling lldb failed\n");
|
||||
fprintf(stderr, "========= End of stack trace ==============\n");
|
||||
fprintf(stderr, "=== End of stack trace ===\n");
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -2445,7 +2450,16 @@ bool QTest::qCompare(float const &t1, float const &t2, const char *actual, const
|
||||
bool QTest::qCompare(double const &t1, double const &t2, const char *actual, const char *expected,
|
||||
const char *file, int line)
|
||||
{
|
||||
return compare_helper(qFuzzyCompare(t1, t2), "Compared doubles are not the same (fuzzy compare)",
|
||||
bool equal = false;
|
||||
int cl1 = std::fpclassify(t1);
|
||||
int cl2 = std::fpclassify(t2);
|
||||
if (cl1 == FP_INFINITE)
|
||||
equal = ((t1 < 0) == (t2 < 0)) && cl2 == FP_INFINITE;
|
||||
else if (cl1 == FP_NAN)
|
||||
equal = (cl2 == FP_NAN);
|
||||
else
|
||||
equal = qFuzzyCompare(t1, t2);
|
||||
return compare_helper(equal, "Compared doubles are not the same (fuzzy compare)",
|
||||
toString(t1), toString(t2), actual, expected, file, line);
|
||||
}
|
||||
|
||||
|
@ -40,7 +40,7 @@
|
||||
#ifndef QTESTCASE_H
|
||||
#define QTESTCASE_H
|
||||
|
||||
#include <QtTest/qtest_global.h>
|
||||
#include <QtTest/qttestglobal.h>
|
||||
|
||||
#include <QtCore/qstring.h>
|
||||
#include <QtCore/qnamespace.h>
|
||||
|
@ -40,7 +40,7 @@
|
||||
#ifndef QTESTDATA_H
|
||||
#define QTESTDATA_H
|
||||
|
||||
#include <QtTest/qtest_global.h>
|
||||
#include <QtTest/qttestglobal.h>
|
||||
|
||||
#include <QtCore/qmetatype.h>
|
||||
#include <QtCore/qstring.h>
|
||||
|
@ -45,7 +45,7 @@
|
||||
#pragma qt_no_master_include
|
||||
#endif
|
||||
|
||||
#include <QtTest/qtest_global.h>
|
||||
#include <QtTest/qttestglobal.h>
|
||||
#ifdef QT_GUI_LIB
|
||||
#include <QtTest/qtestkeyboard.h>
|
||||
#include <QtTest/qtestmouse.h>
|
||||
@ -103,7 +103,10 @@ class QTestKeyClicksEvent: public QTestEvent
|
||||
{
|
||||
public:
|
||||
inline QTestKeyClicksEvent(const QString &keys, Qt::KeyboardModifiers modifiers, int delay)
|
||||
: _keys(keys), _modifiers(modifiers), _delay(delay) {}
|
||||
: _keys(keys), _modifiers(modifiers), _delay(delay)
|
||||
{
|
||||
Q_UNUSED(_delay) // Silence -Werror,-Wunused-private-field
|
||||
}
|
||||
inline QTestEvent *clone() const override { return new QTestKeyClicksEvent(*this); }
|
||||
|
||||
#ifdef QT_WIDGETS_LIB
|
||||
@ -124,7 +127,12 @@ class QTestMouseEvent: public QTestEvent
|
||||
public:
|
||||
inline QTestMouseEvent(QTest::MouseAction action, Qt::MouseButton button,
|
||||
Qt::KeyboardModifiers modifiers, QPoint position, int delay)
|
||||
: _action(action), _button(button), _modifiers(modifiers), _pos(position), _delay(delay) {}
|
||||
: _action(action), _button(button), _modifiers(modifiers), _pos(position), _delay(delay)
|
||||
{
|
||||
Q_UNUSED(_action)
|
||||
Q_UNUSED(_button)
|
||||
Q_UNUSED(_delay)
|
||||
}
|
||||
inline QTestEvent *clone() const override { return new QTestMouseEvent(*this); }
|
||||
|
||||
#ifdef QT_WIDGETS_LIB
|
||||
@ -147,7 +155,10 @@ private:
|
||||
class QTestDelayEvent: public QTestEvent
|
||||
{
|
||||
public:
|
||||
inline QTestDelayEvent(int msecs): _delay(msecs) {}
|
||||
inline QTestDelayEvent(int msecs): _delay(msecs)
|
||||
{
|
||||
Q_UNUSED(_delay)
|
||||
}
|
||||
inline QTestEvent *clone() const override { return new QTestDelayEvent(*this); }
|
||||
|
||||
#ifdef QT_WIDGETS_LIB
|
||||
|
@ -40,7 +40,7 @@
|
||||
#ifndef QTESTEVENTLOOP_H
|
||||
#define QTESTEVENTLOOP_H
|
||||
|
||||
#include <QtTest/qtest_global.h>
|
||||
#include <QtTest/qttestglobal.h>
|
||||
|
||||
#include <QtCore/qcoreapplication.h>
|
||||
#include <QtCore/qeventloop.h>
|
||||
|
@ -46,7 +46,7 @@
|
||||
#endif
|
||||
|
||||
#include <QtTest/qtestassert.h>
|
||||
#include <QtTest/qtest_global.h>
|
||||
#include <QtTest/qttestglobal.h>
|
||||
#include <QtTest/qtestsystem.h>
|
||||
#include <QtTest/qtestspontaneevent.h>
|
||||
|
||||
|
@ -51,7 +51,7 @@
|
||||
// We mean it.
|
||||
//
|
||||
|
||||
#include <QtTest/qtest_global.h>
|
||||
#include <QtTest/qttestglobal.h>
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
|
@ -39,7 +39,7 @@
|
||||
|
||||
#include <QtCore/QtGlobal>
|
||||
#include <QtCore/qnamespace.h>
|
||||
#include <QtTest/qtest_global.h>
|
||||
#include <QtTest/qttestglobal.h>
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
|
@ -45,7 +45,7 @@
|
||||
#pragma qt_no_master_include
|
||||
#endif
|
||||
|
||||
#include <QtTest/qtest_global.h>
|
||||
#include <QtTest/qttestglobal.h>
|
||||
#include <QtTest/qtestassert.h>
|
||||
#include <QtTest/qtestsystem.h>
|
||||
#include <QtTest/qtestspontaneevent.h>
|
||||
|
@ -51,7 +51,7 @@
|
||||
// We mean it.
|
||||
//
|
||||
|
||||
#include <QtTest/qtest_global.h>
|
||||
#include <QtTest/qttestglobal.h>
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
|
@ -51,7 +51,7 @@
|
||||
// We mean it.
|
||||
//
|
||||
|
||||
#include <QtTest/qtest_global.h>
|
||||
#include <QtTest/qttestglobal.h>
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
|
@ -45,7 +45,7 @@
|
||||
#pragma qt_no_master_include
|
||||
#endif
|
||||
|
||||
#include <QtTest/qtest_global.h>
|
||||
#include <QtTest/qttestglobal.h>
|
||||
#include <QtTest/qtestassert.h>
|
||||
#include <QtTest/qtestsystem.h>
|
||||
#include <QtTest/qtestspontaneevent.h>
|
||||
|
@ -37,14 +37,14 @@
|
||||
**
|
||||
****************************************************************************/
|
||||
|
||||
#ifndef QTEST_GLOBAL_H
|
||||
#define QTEST_GLOBAL_H
|
||||
#ifndef QTTESTGLOBAL_H
|
||||
#define QTTESTGLOBAL_H
|
||||
|
||||
#include <QtCore/qglobal.h>
|
||||
#include <QtTest/qttestlib-config.h>
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
|
||||
#if defined(QT_STATIC)
|
||||
# define Q_TESTLIB_EXPORT
|
||||
#else
|
@ -12,7 +12,6 @@ unix:!embedded:QMAKE_PKGCONFIG_DESCRIPTION = Qt \
|
||||
QMAKE_DOCS = $$PWD/doc/qttestlib.qdocconf
|
||||
|
||||
HEADERS = \
|
||||
qabstractitemmodeltester.h \
|
||||
qbenchmark.h \
|
||||
qbenchmark_p.h \
|
||||
qbenchmarkmeasurement_p.h \
|
||||
@ -29,7 +28,6 @@ HEADERS = \
|
||||
qtestdata.h \
|
||||
qtestevent.h \
|
||||
qtesteventloop.h \
|
||||
qtest_global.h \
|
||||
qtest_gui.h \
|
||||
qtest_network.h \
|
||||
qtest_widgets.h \
|
||||
@ -41,10 +39,10 @@ HEADERS = \
|
||||
qtesttouch.h \
|
||||
qtestblacklist_p.h \
|
||||
qtesthelpers_p.h \
|
||||
qttestglobal.h \
|
||||
qtaptestlogger_p.h
|
||||
|
||||
SOURCES = \
|
||||
qabstractitemmodeltester.cpp \
|
||||
qtestcase.cpp \
|
||||
qtestlog.cpp \
|
||||
qtesttable.cpp \
|
||||
@ -71,6 +69,14 @@ SOURCES = \
|
||||
qtestblacklist.cpp \
|
||||
qtaptestlogger.cpp
|
||||
|
||||
qtConfig(itemmodeltester) {
|
||||
HEADERS += \
|
||||
qabstractitemmodeltester.h
|
||||
|
||||
SOURCES += \
|
||||
qabstractitemmodeltester.cpp
|
||||
}
|
||||
|
||||
DEFINES *= QT_NO_CAST_TO_ASCII \
|
||||
QT_NO_CAST_FROM_ASCII \
|
||||
QT_NO_FOREACH \
|
||||
|
@ -1525,7 +1525,7 @@ QTableWidgetItem &QTableWidgetItem::operator=(const QTableWidgetItem &other)
|
||||
\snippet qtablewidget-resizing/mainwindow.cpp 0
|
||||
\snippet qtablewidget-resizing/mainwindow.cpp 1
|
||||
|
||||
Items are created ouside the table (with no parent widget) and inserted
|
||||
Items are created outside the table (with no parent widget) and inserted
|
||||
into the table with setItem():
|
||||
|
||||
\snippet qtablewidget-resizing/mainwindow.cpp 2
|
||||
|
@ -242,7 +242,7 @@ public:
|
||||
static HWND getHWNDForWidget(const QWidget *widget)
|
||||
{
|
||||
if (QWindow *window = windowForWidget(widget))
|
||||
if (window->handle())
|
||||
if (window->handle() && QGuiApplication::platformNativeInterface())
|
||||
return static_cast<HWND> (QGuiApplication::platformNativeInterface()->
|
||||
nativeResourceForWindow(QByteArrayLiteral("handle"), window));
|
||||
return 0;
|
||||
|
@ -73,6 +73,9 @@
|
||||
},
|
||||
"QtDBus" => {
|
||||
"qdbusmacros.h" => "QtDbus/qtdbusglobal.h"
|
||||
},
|
||||
"QtTest" => {
|
||||
"qtest_global.h" => "QtTest/qttestglobal.h"
|
||||
}
|
||||
);
|
||||
|
||||
|
@ -47,17 +47,7 @@ find_package(Qt5Core REQUIRED)
|
||||
|
||||
include("${_Qt5CTestMacros}")
|
||||
|
||||
if(NOT ${CMAKE_VERSION} VERSION_LESS 2.8.9)
|
||||
# Requires INCLUDE_DIRECTORIES target property in CMake 2.8.8
|
||||
# and POSITION_INDEPENDENT_CODE target property in 2.8.9
|
||||
if (NOT NO_GUI)
|
||||
expect_pass(test_use_modules_function)
|
||||
endif()
|
||||
expect_pass(test_umbrella_config)
|
||||
else()
|
||||
message("CMake version older than 2.8.9 (Found ${CMAKE_VERSION}). Not running test \"test_use_modules_function\" or \"test_umbrella_config\"")
|
||||
endif()
|
||||
|
||||
expect_pass(test_umbrella_config)
|
||||
expect_pass(test_wrap_cpp_and_resources)
|
||||
if (NOT NO_WIDGETS)
|
||||
expect_pass(test_dependent_modules)
|
||||
@ -90,12 +80,8 @@ if (NOT NO_DBUS)
|
||||
expect_pass(test_dbus_module)
|
||||
endif()
|
||||
expect_pass(test_multiple_find_package)
|
||||
if (NOT WIN32 OR (WIN32 AND NOT CMAKE_VERSION VERSION_LESS 2.8.11))
|
||||
# Broken on windows on earlier CMake versions.
|
||||
# http://public.kitware.com/Bug/view.php?id=13392
|
||||
expect_pass(test_add_resources_delayed_file)
|
||||
expect_pass(test_add_binary_resources_delayed_file BINARY test_add_binary_resources_delayed_file)
|
||||
endif()
|
||||
expect_pass(test_add_resources_delayed_file)
|
||||
expect_pass(test_add_binary_resources_delayed_file BINARY test_add_binary_resources_delayed_file)
|
||||
expect_pass(test_private_includes)
|
||||
expect_pass(test_private_targets)
|
||||
expect_pass(test_testlib_definitions)
|
||||
@ -153,7 +139,7 @@ if (QT_WITH_ANGLE OR (NOT WIN32 AND NOT APPLE AND NOT NO_EGL))
|
||||
endif()
|
||||
expect_pass(test_opengl_lib)
|
||||
|
||||
if (NOT CMAKE_VERSION VERSION_LESS 2.8.11 AND NOT NO_WIDGETS)
|
||||
if (NOT NO_WIDGETS)
|
||||
expect_pass(test_interface)
|
||||
endif()
|
||||
|
||||
@ -166,4 +152,3 @@ if (NOT CMAKE_VERSION VERSION_LESS 3.8)
|
||||
# /usr/bin/ld: CMakeFiles/mywidget.dir/moc_mywidget.cpp.o: previous definition here
|
||||
# Reason: SKIP_* properties were added in CMake 3.8 only
|
||||
expect_pass(test_QTBUG-63422)
|
||||
endif()
|
||||
|
@ -1,18 +0,0 @@
|
||||
|
||||
cmake_minimum_required(VERSION 2.8)
|
||||
|
||||
project(test_use_modules_function)
|
||||
|
||||
set(CMAKE_AUTOMOC ON)
|
||||
|
||||
set(CMAKE_INCLUDE_CURRENT_DIR ON)
|
||||
|
||||
add_executable(two two.cpp)
|
||||
add_executable(three three.cpp)
|
||||
|
||||
find_package(Qt5Core)
|
||||
|
||||
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${Qt5Core_EXECUTABLE_COMPILE_FLAGS}")
|
||||
|
||||
qt5_use_modules(two Test)
|
||||
qt5_use_modules(three Gui Test)
|
@ -1,45 +0,0 @@
|
||||
/****************************************************************************
|
||||
**
|
||||
** Copyright (C) 2011 Klarälvdalens Datakonsult AB, a KDAB Group company, info@kdab.com, author Stephen Kelly <stephen.kelly@kdab.com>
|
||||
** Contact: https://www.qt.io/licensing/
|
||||
**
|
||||
** This file is part of the test suite of the Qt Toolkit.
|
||||
**
|
||||
** $QT_BEGIN_LICENSE:GPL-EXCEPT$
|
||||
** Commercial License Usage
|
||||
** Licensees holding valid commercial Qt licenses may use this file in
|
||||
** accordance with the commercial license agreement provided with the
|
||||
** Software or, alternatively, in accordance with the terms contained in
|
||||
** a written agreement between you and The Qt Company. For licensing terms
|
||||
** and conditions see https://www.qt.io/terms-conditions. For further
|
||||
** information use the contact form at https://www.qt.io/contact-us.
|
||||
**
|
||||
** GNU General Public License Usage
|
||||
** Alternatively, this file may be used under the terms of the GNU
|
||||
** General Public License version 3 as published by the Free Software
|
||||
** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
|
||||
** included in the packaging of this file. Please review the following
|
||||
** information to ensure the GNU General Public License requirements will
|
||||
** be met: https://www.gnu.org/licenses/gpl-3.0.html.
|
||||
**
|
||||
** $QT_END_LICENSE$
|
||||
**
|
||||
****************************************************************************/
|
||||
|
||||
#include <QtTest>
|
||||
#include <QWindow>
|
||||
|
||||
class Three : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
public:
|
||||
Three(QObject *parent = 0)
|
||||
{
|
||||
QWindow *w = new QWindow;
|
||||
w->show();
|
||||
}
|
||||
};
|
||||
|
||||
QTEST_MAIN(Three)
|
||||
|
||||
#include "three.moc"
|
@ -1,43 +0,0 @@
|
||||
/****************************************************************************
|
||||
**
|
||||
** Copyright (C) 2011 Klarälvdalens Datakonsult AB, a KDAB Group company, info@kdab.com, author Stephen Kelly <stephen.kelly@kdab.com>
|
||||
** Contact: https://www.qt.io/licensing/
|
||||
**
|
||||
** This file is part of the test suite of the Qt Toolkit.
|
||||
**
|
||||
** $QT_BEGIN_LICENSE:GPL-EXCEPT$
|
||||
** Commercial License Usage
|
||||
** Licensees holding valid commercial Qt licenses may use this file in
|
||||
** accordance with the commercial license agreement provided with the
|
||||
** Software or, alternatively, in accordance with the terms contained in
|
||||
** a written agreement between you and The Qt Company. For licensing terms
|
||||
** and conditions see https://www.qt.io/terms-conditions. For further
|
||||
** information use the contact form at https://www.qt.io/contact-us.
|
||||
**
|
||||
** GNU General Public License Usage
|
||||
** Alternatively, this file may be used under the terms of the GNU
|
||||
** General Public License version 3 as published by the Free Software
|
||||
** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
|
||||
** included in the packaging of this file. Please review the following
|
||||
** information to ensure the GNU General Public License requirements will
|
||||
** be met: https://www.gnu.org/licenses/gpl-3.0.html.
|
||||
**
|
||||
** $QT_END_LICENSE$
|
||||
**
|
||||
****************************************************************************/
|
||||
|
||||
#include <QtTest>
|
||||
|
||||
class Two : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
public:
|
||||
Two(QObject *parent = 0)
|
||||
{
|
||||
|
||||
}
|
||||
};
|
||||
|
||||
QTEST_MAIN(Two)
|
||||
|
||||
#include "two.moc"
|
@ -4,3 +4,6 @@ redhatenterpriselinuxworkstation-6.6
|
||||
[fileWriterProcess]
|
||||
msvc-2015 ci
|
||||
msvc-2017 ci
|
||||
[softExitInSlots]
|
||||
# QTBUG-66903
|
||||
windows
|
||||
|
@ -146,6 +146,7 @@ public:
|
||||
HANDLE eventHandle() const { return notifier.handle(); }
|
||||
int numberOfTimesActivated() const { return activatedCount; }
|
||||
void setEnabled(bool b) { notifier.setEnabled(b); }
|
||||
bool isEnabled() const { return notifier.isEnabled(); }
|
||||
|
||||
signals:
|
||||
void activated();
|
||||
@ -239,8 +240,9 @@ void tst_QWinEventNotifier::disableNotifiersInActivatedSlot()
|
||||
for (int i = 0; i < count; ++i)
|
||||
events[i].reset(new EventWithNotifier);
|
||||
|
||||
auto isActivatedOrNull = [&events](int i) {
|
||||
return !events.at(i) || events.at(i)->numberOfTimesActivated() > 0;
|
||||
auto isActivatedOrDisabled = [&events](int i) {
|
||||
return !events.at(i) || !events.at(i)->isEnabled()
|
||||
|| events.at(i)->numberOfTimesActivated() > 0;
|
||||
};
|
||||
|
||||
for (auto &e : events) {
|
||||
@ -251,8 +253,10 @@ void tst_QWinEventNotifier::disableNotifiersInActivatedSlot()
|
||||
else
|
||||
events.at(i)->setEnabled(false);
|
||||
}
|
||||
if (std::all_of(notifiersToSignal.begin(), notifiersToSignal.end(), isActivatedOrNull))
|
||||
if (std::all_of(notifiersToSignal.begin(), notifiersToSignal.end(),
|
||||
isActivatedOrDisabled)) {
|
||||
QTimer::singleShot(0, &QTestEventLoop::instance(), SLOT(exitLoop()));
|
||||
}
|
||||
});
|
||||
}
|
||||
for (int i : notifiersToSignal)
|
||||
|
@ -54,6 +54,7 @@ private slots:
|
||||
void testCbrtDouble();
|
||||
void testCbrtFloat();
|
||||
void cpp11();
|
||||
void quadraticEquation();
|
||||
};
|
||||
|
||||
void tst_QEasingCurve::type()
|
||||
@ -804,5 +805,74 @@ void tst_QEasingCurve::cpp11()
|
||||
#endif
|
||||
}
|
||||
|
||||
void tst_QEasingCurve::quadraticEquation() {
|
||||
// We find the value for a given time by solving a cubic equation.
|
||||
// ax^3 + bx^2 + cx + d = 0
|
||||
// However, the solver also needs to take care of cases where a = 0,
|
||||
// b = 0 or c = 0, and the equation becomes quadratic, linear or invalid.
|
||||
// A naive cubic solver might divide by zero and return nan, even
|
||||
// when the solution is a real number.
|
||||
// This test should triggers those cases.
|
||||
|
||||
{
|
||||
// If the control points are spaced 1/3 apart of the distance of the
|
||||
// start- and endpoint, the equation becomes linear.
|
||||
QEasingCurve test(QEasingCurve::BezierSpline);
|
||||
const qreal p1 = 1.0 / 3.0;
|
||||
const qreal p2 = 1.0 - 1.0 / 3.0;
|
||||
const qreal p3 = 1.0;
|
||||
|
||||
test.addCubicBezierSegment(QPointF(p1, 0.0), QPointF(p2, 1.0), QPointF(p3, 1.0));
|
||||
QVERIFY(qAbs(test.valueForProgress(0.25) - 0.15625) < 1e-6);
|
||||
QVERIFY(qAbs(test.valueForProgress(0.5) - 0.5) < 1e-6);
|
||||
QVERIFY(qAbs(test.valueForProgress(0.75) - 0.84375) < 1e-6);
|
||||
}
|
||||
|
||||
{
|
||||
// If both the start point and the first control point
|
||||
// are placed a 0.0, and the second control point is
|
||||
// placed at 1/3, we get a case where a = 0 and b != 0
|
||||
// i.e. a quadratic equation.
|
||||
QEasingCurve test(QEasingCurve::BezierSpline);
|
||||
const qreal p1 = 0.0;
|
||||
const qreal p2 = 1.0 / 3.0;
|
||||
const qreal p3 = 1.0;
|
||||
test.addCubicBezierSegment(QPointF(p1, 0.0), QPointF(p2, 1.0), QPointF(p3, 1.0));
|
||||
QVERIFY(qAbs(test.valueForProgress(0.25) - 0.5) < 1e-6);
|
||||
QVERIFY(qAbs(test.valueForProgress(0.5) - 0.792893) < 1e-6);
|
||||
QVERIFY(qAbs(test.valueForProgress(0.75) - 0.950962) < 1e-6);
|
||||
}
|
||||
|
||||
{
|
||||
// If both the start point and the first control point
|
||||
// are placed a 0.0, and the second control point is
|
||||
// placed close to 1/3, we get a case where a = ~0 and b != 0.
|
||||
// It's not truly a quadratic equation, but should be treated
|
||||
// as one, because it causes some cubic solvers to fail.
|
||||
QEasingCurve test(QEasingCurve::BezierSpline);
|
||||
const qreal p1 = 0.0;
|
||||
const qreal p2 = 1.0 / 3.0 + 1e-6;
|
||||
const qreal p3 = 1.0;
|
||||
test.addCubicBezierSegment(QPointF(p1, 0.0), QPointF(p2, 1.0), QPointF(p3, 1.0));
|
||||
QVERIFY(qAbs(test.valueForProgress(0.25) - 0.499999) < 1e-6);
|
||||
QVERIFY(qAbs(test.valueForProgress(0.5) - 0.792892) < 1e-6);
|
||||
QVERIFY(qAbs(test.valueForProgress(0.75) - 0.950961) < 1e-6);
|
||||
}
|
||||
|
||||
{
|
||||
// A bad case, where the segment is of zero length.
|
||||
// However, it might still happen in user code,
|
||||
// and we should return a sensible answer.
|
||||
QEasingCurve test(QEasingCurve::BezierSpline);
|
||||
const qreal p0 = 0.0;
|
||||
const qreal p1 = p0;
|
||||
const qreal p2 = p0;
|
||||
const qreal p3 = p0;
|
||||
test.addCubicBezierSegment(QPointF(p1, 0.0), QPointF(p2, 1.0), QPointF(p3, 1.0));
|
||||
test.addCubicBezierSegment(QPointF(p3, 1.0), QPointF(1.0, 1.0), QPointF(1.0, 1.0));
|
||||
QCOMPARE(test.valueForProgress(0.0), 0.0);
|
||||
}
|
||||
}
|
||||
|
||||
QTEST_MAIN(tst_QEasingCurve)
|
||||
#include "tst_qeasingcurve.moc"
|
||||
|
@ -957,19 +957,21 @@ void tst_QVarLengthArray::insertMove()
|
||||
QCOMPARE(MyBase::copyCount, 0);
|
||||
|
||||
{
|
||||
QVarLengthArray<MyMovable, 4> vec;
|
||||
QVarLengthArray<MyMovable, 6> vec;
|
||||
MyMovable m1;
|
||||
MyMovable m2;
|
||||
MyMovable m3;
|
||||
MyMovable m4;
|
||||
MyMovable m5;
|
||||
MyMovable m6;
|
||||
QCOMPARE(MyBase::copyCount, 0);
|
||||
QCOMPARE(MyBase::liveCount, 4);
|
||||
QCOMPARE(MyBase::liveCount, 6);
|
||||
|
||||
vec.append(std::move(m3));
|
||||
QVERIFY(m3.wasConstructedAt(nullptr));
|
||||
QVERIFY(vec.at(0).wasConstructedAt(&m3));
|
||||
QCOMPARE(MyBase::errorCount, 0);
|
||||
QCOMPARE(MyBase::liveCount, 4);
|
||||
QCOMPARE(MyBase::liveCount, 6);
|
||||
QCOMPARE(MyBase::movedCount, 1);
|
||||
|
||||
vec.push_back(std::move(m4));
|
||||
@ -977,7 +979,7 @@ void tst_QVarLengthArray::insertMove()
|
||||
QVERIFY(vec.at(0).wasConstructedAt(&m3));
|
||||
QVERIFY(vec.at(1).wasConstructedAt(&m4));
|
||||
QCOMPARE(MyBase::errorCount, 0);
|
||||
QCOMPARE(MyBase::liveCount, 4);
|
||||
QCOMPARE(MyBase::liveCount, 6);
|
||||
QCOMPARE(MyBase::movedCount, 2);
|
||||
|
||||
vec.prepend(std::move(m1));
|
||||
@ -986,7 +988,7 @@ void tst_QVarLengthArray::insertMove()
|
||||
QVERIFY(vec.at(1).wasConstructedAt(&m3));
|
||||
QVERIFY(vec.at(2).wasConstructedAt(&m4));
|
||||
QCOMPARE(MyBase::errorCount, 0);
|
||||
QCOMPARE(MyBase::liveCount, 4);
|
||||
QCOMPARE(MyBase::liveCount, 6);
|
||||
QCOMPARE(MyBase::movedCount, 3);
|
||||
|
||||
vec.insert(1, std::move(m2));
|
||||
@ -995,11 +997,34 @@ void tst_QVarLengthArray::insertMove()
|
||||
QVERIFY(vec.at(1).wasConstructedAt(&m2));
|
||||
QVERIFY(vec.at(2).wasConstructedAt(&m3));
|
||||
QVERIFY(vec.at(3).wasConstructedAt(&m4));
|
||||
QCOMPARE(MyBase::errorCount, 0);
|
||||
QCOMPARE(MyBase::liveCount, 6);
|
||||
QCOMPARE(MyBase::movedCount, 4);
|
||||
|
||||
vec += std::move(m5);
|
||||
QVERIFY(m5.wasConstructedAt(nullptr));
|
||||
QVERIFY(vec.at(0).wasConstructedAt(&m1));
|
||||
QVERIFY(vec.at(1).wasConstructedAt(&m2));
|
||||
QVERIFY(vec.at(2).wasConstructedAt(&m3));
|
||||
QVERIFY(vec.at(3).wasConstructedAt(&m4));
|
||||
QVERIFY(vec.at(4).wasConstructedAt(&m5));
|
||||
QCOMPARE(MyBase::errorCount, 0);
|
||||
QCOMPARE(MyBase::liveCount, 6);
|
||||
QCOMPARE(MyBase::movedCount, 5);
|
||||
|
||||
vec << std::move(m6);
|
||||
QVERIFY(m6.wasConstructedAt(nullptr));
|
||||
QVERIFY(vec.at(0).wasConstructedAt(&m1));
|
||||
QVERIFY(vec.at(1).wasConstructedAt(&m2));
|
||||
QVERIFY(vec.at(2).wasConstructedAt(&m3));
|
||||
QVERIFY(vec.at(3).wasConstructedAt(&m4));
|
||||
QVERIFY(vec.at(4).wasConstructedAt(&m5));
|
||||
QVERIFY(vec.at(5).wasConstructedAt(&m6));
|
||||
|
||||
QCOMPARE(MyBase::copyCount, 0);
|
||||
QCOMPARE(MyBase::liveCount, 4);
|
||||
QCOMPARE(MyBase::liveCount, 6);
|
||||
QCOMPARE(MyBase::errorCount, 0);
|
||||
QCOMPARE(MyBase::movedCount, 4);
|
||||
QCOMPARE(MyBase::movedCount, 6);
|
||||
}
|
||||
QCOMPARE(MyBase::liveCount, 0);
|
||||
QCOMPARE(MyBase::errorCount, 0);
|
||||
@ -1013,10 +1038,14 @@ void tst_QVarLengthArray::nonCopyable()
|
||||
std::unique_ptr<int> val2(new int(2));
|
||||
std::unique_ptr<int> val3(new int(3));
|
||||
std::unique_ptr<int> val4(new int(4));
|
||||
std::unique_ptr<int> val5(new int(5));
|
||||
std::unique_ptr<int> val6(new int(6));
|
||||
int *const ptr1 = val1.get();
|
||||
int *const ptr2 = val2.get();
|
||||
int *const ptr3 = val3.get();
|
||||
int *const ptr4 = val4.get();
|
||||
int *const ptr5 = val5.get();
|
||||
int *const ptr6 = val6.get();
|
||||
|
||||
vec.append(std::move(val3));
|
||||
QVERIFY(!val3);
|
||||
@ -1035,6 +1064,22 @@ void tst_QVarLengthArray::nonCopyable()
|
||||
QVERIFY(ptr1 == vec.at(0).get());
|
||||
QVERIFY(ptr2 == vec.at(1).get());
|
||||
QVERIFY(ptr3 == vec.at(2).get());
|
||||
QVERIFY(ptr4 == vec.at(3).get());
|
||||
vec += std::move(val5);
|
||||
QVERIFY(!val5);
|
||||
QVERIFY(ptr1 == vec.at(0).get());
|
||||
QVERIFY(ptr2 == vec.at(1).get());
|
||||
QVERIFY(ptr3 == vec.at(2).get());
|
||||
QVERIFY(ptr4 == vec.at(3).get());
|
||||
QVERIFY(ptr5 == vec.at(4).get());
|
||||
vec << std::move(val6);
|
||||
QVERIFY(!val6);
|
||||
QVERIFY(ptr1 == vec.at(0).get());
|
||||
QVERIFY(ptr2 == vec.at(1).get());
|
||||
QVERIFY(ptr3 == vec.at(2).get());
|
||||
QVERIFY(ptr4 == vec.at(3).get());
|
||||
QVERIFY(ptr5 == vec.at(4).get());
|
||||
QVERIFY(ptr6 == vec.at(5).get());
|
||||
}
|
||||
|
||||
QTEST_APPLESS_MAIN(tst_QVarLengthArray)
|
||||
|
@ -2895,12 +2895,14 @@ void tst_QVector::insertMove() const
|
||||
const int instancesCount = Movable::counter.loadAcquire();
|
||||
{
|
||||
QVector<Movable> vec;
|
||||
vec.reserve(5);
|
||||
vec.reserve(7);
|
||||
Movable m0;
|
||||
Movable m1;
|
||||
Movable m2;
|
||||
Movable m3;
|
||||
Movable m4;
|
||||
Movable m5;
|
||||
Movable m6;
|
||||
|
||||
vec.append(std::move(m3));
|
||||
QVERIFY(m3.wasConstructedAt(nullptr));
|
||||
@ -2920,6 +2922,21 @@ void tst_QVector::insertMove() const
|
||||
QVERIFY(vec.at(1).wasConstructedAt(&m2));
|
||||
QVERIFY(vec.at(2).wasConstructedAt(&m3));
|
||||
QVERIFY(vec.at(3).wasConstructedAt(&m4));
|
||||
vec += std::move(m5);
|
||||
QVERIFY(m5.wasConstructedAt(nullptr));
|
||||
QVERIFY(vec.at(0).wasConstructedAt(&m1));
|
||||
QVERIFY(vec.at(1).wasConstructedAt(&m2));
|
||||
QVERIFY(vec.at(2).wasConstructedAt(&m3));
|
||||
QVERIFY(vec.at(3).wasConstructedAt(&m4));
|
||||
QVERIFY(vec.at(4).wasConstructedAt(&m5));
|
||||
vec << std::move(m6);
|
||||
QVERIFY(m6.wasConstructedAt(nullptr));
|
||||
QVERIFY(vec.at(0).wasConstructedAt(&m1));
|
||||
QVERIFY(vec.at(1).wasConstructedAt(&m2));
|
||||
QVERIFY(vec.at(2).wasConstructedAt(&m3));
|
||||
QVERIFY(vec.at(3).wasConstructedAt(&m4));
|
||||
QVERIFY(vec.at(4).wasConstructedAt(&m5));
|
||||
QVERIFY(vec.at(5).wasConstructedAt(&m6));
|
||||
vec.push_front(std::move(m0));
|
||||
QVERIFY(m0.wasConstructedAt(nullptr));
|
||||
QVERIFY(vec.at(0).wasConstructedAt(&m0));
|
||||
@ -2927,8 +2944,10 @@ void tst_QVector::insertMove() const
|
||||
QVERIFY(vec.at(2).wasConstructedAt(&m2));
|
||||
QVERIFY(vec.at(3).wasConstructedAt(&m3));
|
||||
QVERIFY(vec.at(4).wasConstructedAt(&m4));
|
||||
QVERIFY(vec.at(5).wasConstructedAt(&m5));
|
||||
QVERIFY(vec.at(6).wasConstructedAt(&m6));
|
||||
|
||||
QCOMPARE(Movable::counter.loadAcquire(), instancesCount + 10);
|
||||
QCOMPARE(Movable::counter.loadAcquire(), instancesCount + 14);
|
||||
}
|
||||
QCOMPARE(Movable::counter.loadAcquire(), instancesCount);
|
||||
}
|
||||
|
@ -153,6 +153,7 @@ private slots:
|
||||
void setEqualClipRegionAndPath();
|
||||
|
||||
void clipRectSaveRestore();
|
||||
void clipStateSaveRestore();
|
||||
|
||||
void clippedFillPath_data();
|
||||
void clippedFillPath();
|
||||
@ -3425,6 +3426,35 @@ void tst_QPainter::clipRectSaveRestore()
|
||||
QCOMPARE(img.pixel(0, 0), QColor(Qt::black).rgba());
|
||||
}
|
||||
|
||||
void tst_QPainter::clipStateSaveRestore()
|
||||
{
|
||||
QImage img(16, 16, QImage::Format_RGB32);
|
||||
img.fill(Qt::blue);
|
||||
{
|
||||
QPainter p(&img);
|
||||
p.setClipRect(QRect(5, 5, 10, 10));
|
||||
p.save();
|
||||
p.setClipping(false);
|
||||
p.restore();
|
||||
p.fillRect(0, 0, 16, 16, Qt::red);
|
||||
p.end();
|
||||
QCOMPARE(img.pixel(0, 0), QColor(Qt::blue).rgb());
|
||||
}
|
||||
|
||||
img.fill(Qt::blue);
|
||||
{
|
||||
QPainter p(&img);
|
||||
p.setClipRect(QRect(5, 5, 10, 10));
|
||||
p.setClipping(false);
|
||||
p.save();
|
||||
p.setClipping(true);
|
||||
p.restore();
|
||||
p.fillRect(0, 0, 16, 16, Qt::red);
|
||||
p.end();
|
||||
QCOMPARE(img.pixel(0, 0), QColor(Qt::red).rgb());
|
||||
}
|
||||
}
|
||||
|
||||
void tst_QPainter::clippedImage()
|
||||
{
|
||||
QImage img(16, 16, QImage::Format_ARGB32_Premultiplied);
|
||||
|
@ -359,7 +359,6 @@ void tst_QSqlQuery::dropTestTables( QSqlDatabase db )
|
||||
<< qTableName("more_results", __FILE__, db)
|
||||
<< qTableName("blobstest", __FILE__, db)
|
||||
<< qTableName("oraRowId", __FILE__, db)
|
||||
<< qTableName("qtest_batch", __FILE__, db)
|
||||
<< qTableName("bug43874", __FILE__, db)
|
||||
<< qTableName("bug6421", __FILE__, db).toUpper()
|
||||
<< qTableName("bug5765", __FILE__, db)
|
||||
@ -2439,76 +2438,103 @@ void tst_QSqlQuery::batchExec()
|
||||
QSqlDatabase db = QSqlDatabase::database( dbName );
|
||||
CHECK_DATABASE( db );
|
||||
|
||||
if ( !db.driver()->hasFeature( QSqlDriver::BatchOperations ) )
|
||||
QSKIP( "Database can't do BatchOperations");
|
||||
|
||||
QSqlQuery q( db );
|
||||
const QString tableName = qTableName("qtest_batch", __FILE__, db);
|
||||
tst_Databases::safeDropTable(db, tableName);
|
||||
QVERIFY_SQL(q, exec(QStringLiteral("create table ") + tableName +
|
||||
QStringLiteral(" (id int, name varchar(20), dt date, num numeric(8, 4), "
|
||||
"dtstamp TIMESTAMP(3), extraId int, extraName varchar(20))")));
|
||||
|
||||
QVERIFY_SQL(q, exec("create table " + tableName + " (id int, name varchar(20), dt date, num numeric(8, 4), dtstamp TIMESTAMP(3))"));
|
||||
QVERIFY_SQL(q, prepare("insert into " + tableName + " (id, name, dt, num, dtstamp) values (?, ?, ?, ?, ?)"));
|
||||
|
||||
QVariantList intCol;
|
||||
intCol << 1 << 2 << QVariant( QVariant::Int );
|
||||
|
||||
QVariantList charCol;
|
||||
charCol << QLatin1String( "harald" ) << QLatin1String( "boris" ) << QVariant( QVariant::String );
|
||||
|
||||
QVariantList dateCol;
|
||||
QDateTime dt = QDateTime( QDate::currentDate(), QTime( 1, 2, 3 ) );
|
||||
dateCol << dt << dt.addDays( -1 ) << QVariant( QVariant::DateTime );
|
||||
|
||||
QVariantList numCol;
|
||||
numCol << 2.3 << 3.4 << QVariant( QVariant::Double );
|
||||
|
||||
QVariantList timeStampCol;
|
||||
const QDateTime dtStamp = QDateTime(QDate::currentDate(), QTime(1, 2, 3, 4));
|
||||
timeStampCol << dtStamp << dtStamp.addDays(-1) << QVariant(QVariant::DateTime);
|
||||
const QVariantList intCol = { 1, 2, QVariant(QVariant::Int) };
|
||||
const QVariantList charCol = { QStringLiteral("harald"), QStringLiteral("boris"),
|
||||
QVariant(QVariant::String) };
|
||||
const QDateTime currentDateTime = QDateTime(QDateTime::currentDateTime());
|
||||
const QVariantList dateCol = { currentDateTime.date(), currentDateTime.date().addDays(-1),
|
||||
QVariant(QVariant::Date) };
|
||||
const QVariantList numCol = { 2.3, 3.4, QVariant(QVariant::Double) };
|
||||
const QVariantList timeStampCol = { currentDateTime, currentDateTime.addDays(-1),
|
||||
QVariant(QVariant::DateTime) };
|
||||
|
||||
// Test with positional placeholders
|
||||
QVERIFY_SQL(q, prepare(QStringLiteral("insert into ") + tableName +
|
||||
QStringLiteral(" (id, name, dt, num, dtstamp, extraId, extraName) values "
|
||||
"(?, ?, ?, ?, ?, ?, ?)")));
|
||||
q.addBindValue(intCol);
|
||||
q.addBindValue( charCol );
|
||||
q.addBindValue( dateCol );
|
||||
q.addBindValue( numCol );
|
||||
q.addBindValue(timeStampCol);
|
||||
q.addBindValue(intCol);
|
||||
q.addBindValue(charCol);
|
||||
|
||||
QVERIFY_SQL( q, execBatch() );
|
||||
QVERIFY_SQL(q, exec("select id, name, dt, num, dtstamp from " + tableName + " order by id"));
|
||||
QVERIFY_SQL(q, exec(QStringLiteral("select id, name, dt, num, dtstamp, "
|
||||
"extraId, extraName from ") + tableName));
|
||||
|
||||
QVERIFY( q.next() );
|
||||
QCOMPARE( q.value( 0 ).toInt(), 1 );
|
||||
QCOMPARE( q.value( 1 ).toString(), QString( "harald" ) );
|
||||
QCOMPARE( q.value( 2 ).toDateTime(), dt );
|
||||
QCOMPARE( q.value( 3 ).toDouble(), 2.3 );
|
||||
QCOMPARE(q.value(4).toDateTime(), dtStamp);
|
||||
for (int i = 0; i < intCol.size(); ++i) {
|
||||
QVERIFY(q.next());
|
||||
QCOMPARE(q.value(0).toInt(), intCol.at(i));
|
||||
QCOMPARE(q.value(1).toString(), charCol.at(i));
|
||||
QCOMPARE(q.value(2).toDate(), dateCol.at(i));
|
||||
QCOMPARE(q.value(3).toDouble(), numCol.at(i));
|
||||
if (tst_Databases::getDatabaseType(db) == QSqlDriver::MySqlServer && timeStampCol.at(i).isNull()) {
|
||||
QEXPECT_FAIL("", "This appears to be a bug in MySQL as it converts null datetimes to the "
|
||||
"current datetime for a timestamp field", Continue);
|
||||
}
|
||||
QCOMPARE(q.value(4).toDateTime(), timeStampCol.at(i));
|
||||
QCOMPARE(q.value(5).toInt(), intCol.at(i));
|
||||
QCOMPARE(q.value(6).toString(), charCol.at(i));
|
||||
}
|
||||
|
||||
QVERIFY( q.next() );
|
||||
QCOMPARE( q.value( 0 ).toInt(), 2 );
|
||||
QCOMPARE( q.value( 1 ).toString(), QString( "boris" ) );
|
||||
QCOMPARE( q.value( 2 ).toDateTime(), dt.addDays( -1 ) );
|
||||
QCOMPARE( q.value( 3 ).toDouble(), 3.4 );
|
||||
QCOMPARE(q.value(4).toDateTime(), dtStamp.addDays(-1));
|
||||
// Empty table ready for retesting with duplicated named placeholders
|
||||
QVERIFY_SQL(q, exec(QStringLiteral("delete from ") + tableName));
|
||||
QVERIFY_SQL(q, prepare(QStringLiteral("insert into ") + tableName +
|
||||
QStringLiteral(" (id, name, dt, num, dtstamp, extraId, extraName) "
|
||||
"values (:id, :name, :dt, :num, :dtstamp, :id, :name)")));
|
||||
q.bindValue(":id", intCol);
|
||||
q.bindValue(":name", charCol);
|
||||
q.bindValue(":dt", dateCol);
|
||||
q.bindValue(":num", numCol);
|
||||
q.bindValue(":dtstamp", timeStampCol);
|
||||
|
||||
QVERIFY( q.next() );
|
||||
QVERIFY( q.value( 0 ).isNull() );
|
||||
QVERIFY( q.value( 1 ).isNull() );
|
||||
QVERIFY( q.value( 2 ).isNull() );
|
||||
QVERIFY( q.value( 3 ).isNull() );
|
||||
QVERIFY(q.value(4).isNull());
|
||||
|
||||
const QString procName = qTableName("qtest_batch_proc", __FILE__, db);
|
||||
QVERIFY_SQL(q, exec("create or replace procedure " + procName + " (x in timestamp, y out timestamp) is\n"
|
||||
"begin\n"
|
||||
" y := x;\n"
|
||||
"end;\n"));
|
||||
QVERIFY(q.prepare("call " + procName + "(?, ?)"));
|
||||
q.addBindValue(timeStampCol, QSql::In);
|
||||
QVariantList emptyDateTimes;
|
||||
emptyDateTimes.reserve(timeStampCol.size());
|
||||
for (int i = 0; i < timeStampCol.size(); i++)
|
||||
emptyDateTimes << QVariant(QDateTime());
|
||||
q.addBindValue(emptyDateTimes, QSql::Out);
|
||||
QVERIFY_SQL(q, execBatch());
|
||||
QCOMPARE(q.boundValue(1).toList(), timeStampCol);
|
||||
QVERIFY_SQL(q, exec(QStringLiteral("select id, name, dt, num, dtstamp, extraId, extraName from ") +
|
||||
tableName));
|
||||
|
||||
for (int i = 0; i < intCol.size(); ++i) {
|
||||
QVERIFY(q.next());
|
||||
QCOMPARE(q.value(0).toInt(), intCol.at(i));
|
||||
QCOMPARE(q.value(1).toString(), charCol.at(i));
|
||||
QCOMPARE(q.value(2).toDate(), dateCol.at(i));
|
||||
QCOMPARE(q.value(3).toDouble(), numCol.at(i));
|
||||
if (tst_Databases::getDatabaseType(db) == QSqlDriver::MySqlServer && timeStampCol.at(i).isNull()) {
|
||||
QEXPECT_FAIL("", "This appears to be a bug in MySQL as it converts null datetimes to the "
|
||||
"current datetime for a timestamp field", Continue);
|
||||
}
|
||||
QCOMPARE(q.value(4).toDateTime(), timeStampCol.at(i));
|
||||
QCOMPARE(q.value(5).toInt(), intCol.at(i));
|
||||
QCOMPARE(q.value(6).toString(), charCol.at(i));
|
||||
}
|
||||
|
||||
// Only test the prepared stored procedure approach where the driver has support
|
||||
// for batch operations as this will not work without it
|
||||
if (db.driver()->hasFeature(QSqlDriver::BatchOperations)) {
|
||||
const QString procName = qTableName("qtest_batch_proc", __FILE__, db);
|
||||
QVERIFY_SQL(q, exec("create or replace procedure " + procName +
|
||||
" (x in timestamp, y out timestamp) is\n"
|
||||
"begin\n"
|
||||
" y := x;\n"
|
||||
"end;\n"));
|
||||
QVERIFY(q.prepare("call " + procName + "(?, ?)"));
|
||||
q.addBindValue(timeStampCol, QSql::In);
|
||||
QVariantList emptyDateTimes;
|
||||
emptyDateTimes.reserve(timeStampCol.size());
|
||||
for (int i = 0; i < timeStampCol.size(); i++)
|
||||
emptyDateTimes << QVariant(QDateTime());
|
||||
q.addBindValue(emptyDateTimes, QSql::Out);
|
||||
QVERIFY_SQL(q, execBatch());
|
||||
QCOMPARE(q.boundValue(1).toList(), timeStampCol);
|
||||
}
|
||||
}
|
||||
|
||||
void tst_QSqlQuery::QTBUG_43874()
|
||||
|
@ -36,11 +36,11 @@ if(*-g++*|*-icc*|*-clang*|*-llvm):!win32-*: HEADERS += os9-newlines.h win-newlin
|
||||
if(*-g++*|*-clang*): HEADERS += dollars.h
|
||||
SOURCES += tst_moc.cpp
|
||||
|
||||
QT = core sql network testlib
|
||||
qtHaveModule(dbus) {
|
||||
DEFINES += WITH_DBUS
|
||||
QT += dbus
|
||||
}
|
||||
QT = core testlib
|
||||
qtHaveModule(dbus): QT += dbus
|
||||
qtHaveModule(concurrent): QT += concurrent
|
||||
qtHaveModule(network): QT += network
|
||||
qtHaveModule(sql): QT += sql
|
||||
|
||||
# tst_Moc::specifyMetaTagsFromCmdline()
|
||||
# Ensure that plugin_metadata.h are moc-ed with some extra -M arguments:
|
||||
|
@ -37,16 +37,19 @@
|
||||
#define slots Baz
|
||||
#define emit Yoyodyne
|
||||
|
||||
#include <QtCore/QtCore>
|
||||
|
||||
#ifdef QT_CONCURRENT_LIB
|
||||
#include <QtConcurrent/QtConcurrent>
|
||||
#include <QtCore>
|
||||
#include <QtNetwork/QtNetwork>
|
||||
#include <QtSql/QtSql>
|
||||
//#include <QtSvg>
|
||||
#if defined(WITH_DBUS)
|
||||
#include <QtDBus>
|
||||
#endif
|
||||
#ifdef QT_SCRIPT_LIB
|
||||
#include <QtScript>
|
||||
#ifdef QT_NETWORK_LIB
|
||||
#include <QtNetwork/QtNetwork>
|
||||
#endif
|
||||
#ifdef QT_SQL_LIB
|
||||
#include <QtSql/QtSql>
|
||||
#endif
|
||||
#ifdef QT_DBUS_LIB
|
||||
#include <QtDBus/QtDBus>
|
||||
#endif
|
||||
|
||||
#undef signals
|
||||
|
@ -1604,6 +1604,12 @@ void tst_qmakelib::addReplaceFunctions(const QString &qindir)
|
||||
<< ""
|
||||
<< true;
|
||||
|
||||
QTest::newRow("$$absolute_path(): relative file & relative path")
|
||||
<< "VAR = $$absolute_path(dir/file.ext, some/where)"
|
||||
<< "VAR = " + qindir + "/some/where/dir/file.ext"
|
||||
<< ""
|
||||
<< true;
|
||||
|
||||
QTest::newRow("$$absolute_path(): file & path")
|
||||
<< "VAR = $$absolute_path(dir/file.ext, " EVAL_DRIVE "/root/sub)"
|
||||
<< "VAR = " EVAL_DRIVE "/root/sub/dir/file.ext"
|
||||
@ -1642,6 +1648,12 @@ void tst_qmakelib::addReplaceFunctions(const QString &qindir)
|
||||
<< ""
|
||||
<< true;
|
||||
|
||||
QTest::newRow("$$relative_path(): relative file & relative path")
|
||||
<< "VAR = $$relative_path(dir/file.ext, some/where)"
|
||||
<< "VAR = dir/file.ext"
|
||||
<< ""
|
||||
<< true;
|
||||
|
||||
QTest::newRow("$$relative_path(): relative file to empty")
|
||||
<< "VAR = $$relative_path(dir/..)"
|
||||
<< "VAR = ."
|
||||
@ -2752,9 +2764,9 @@ void tst_qmakelib::proEval_data()
|
||||
|
||||
// Raw data leak with empty file name. Verify with Valgrind or asan.
|
||||
QTest::newRow("QTBUG-54550")
|
||||
<< "FULL = /there/is\n"
|
||||
<< "FULL = " EVAL_DRIVE "/there/is\n"
|
||||
"VAR = $$absolute_path(, $$FULL/nothing/here/really)"
|
||||
<< "VAR = /there/is/nothing/here/really"
|
||||
<< "VAR = " EVAL_DRIVE "/there/is/nothing/here/really"
|
||||
<< ""
|
||||
<< true;
|
||||
}
|
||||
|
@ -2992,19 +2992,14 @@ void tst_QGraphicsView::acceptMousePressEvent()
|
||||
view.show();
|
||||
QVERIFY(QTest::qWaitForWindowExposed(&view));
|
||||
|
||||
QMouseEvent event(QEvent::MouseButtonPress,
|
||||
view.viewport()->rect().center(),
|
||||
view.viewport()->mapToGlobal(view.viewport()->rect().center()),
|
||||
Qt::LeftButton, 0, 0);
|
||||
event.setAccepted(false);
|
||||
QApplication::sendEvent(view.viewport(), &event);
|
||||
QTest::mouseClick(view.viewport(), Qt::LeftButton);
|
||||
QVERIFY(!view.pressAccepted);
|
||||
|
||||
QSignalSpy spy(&scene, &QGraphicsScene::changed);
|
||||
scene.addRect(0, 0, 2000, 2000)->setFlag(QGraphicsItem::ItemIsMovable);
|
||||
QVERIFY(spy.wait());
|
||||
|
||||
qApp->processEvents(); // ensure scene rect is updated
|
||||
|
||||
QApplication::sendEvent(view.viewport(), &event);
|
||||
QTest::mouseClick(view.viewport(), Qt::LeftButton);
|
||||
QVERIFY(view.pressAccepted);
|
||||
}
|
||||
|
||||
@ -3016,19 +3011,14 @@ void tst_QGraphicsView::acceptMouseDoubleClickEvent()
|
||||
view.show();
|
||||
QVERIFY(QTest::qWaitForWindowExposed(&view));
|
||||
|
||||
QMouseEvent event(QEvent::MouseButtonDblClick,
|
||||
view.viewport()->rect().center(),
|
||||
view.viewport()->mapToGlobal(view.viewport()->rect().center()),
|
||||
Qt::LeftButton, 0, 0);
|
||||
event.setAccepted(false);
|
||||
QApplication::sendEvent(view.viewport(), &event);
|
||||
QTest::mouseDClick(view.viewport(), Qt::LeftButton);
|
||||
QVERIFY(!view.doubleClickAccepted);
|
||||
|
||||
QSignalSpy spy(&scene, &QGraphicsScene::changed);
|
||||
scene.addRect(0, 0, 2000, 2000)->setFlag(QGraphicsItem::ItemIsMovable);
|
||||
QVERIFY(spy.wait());
|
||||
|
||||
qApp->processEvents(); // ensure scene rect is updated
|
||||
|
||||
QApplication::sendEvent(view.viewport(), &event);
|
||||
QTest::mouseDClick(view.viewport(), Qt::LeftButton);
|
||||
QVERIFY(view.doubleClickAccepted);
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user