From 35fd077c803b7465325a94f02da3c4e10cb55bee Mon Sep 17 00:00:00 2001 From: Leonard Lee Date: Mon, 19 Aug 2013 11:29:32 +0200 Subject: Specify maximum array size for QByteArray. Task-number: QTBUG-33037 Change-Id: I3f39b1498fc70614402fca2281ffbd1a6ec4cf3f Reviewed-by: Thiago Macieira --- src/corelib/tools/qbytearray.cpp | 2 ++ 1 file changed, 2 insertions(+) (limited to 'src') diff --git a/src/corelib/tools/qbytearray.cpp b/src/corelib/tools/qbytearray.cpp index 6ce17e5e13..e993855e7e 100644 --- a/src/corelib/tools/qbytearray.cpp +++ b/src/corelib/tools/qbytearray.cpp @@ -645,6 +645,8 @@ static inline char qToLower(char c) store raw binary data, and when memory conservation is critical (e.g., with Qt for Embedded Linux). + The maximum array size of a QByteArray is under 2^30. + One way to initialize a QByteArray is simply to pass a \c{const char *} to its constructor. For example, the following code creates a byte array of size 5 containing the data "Hello": -- cgit v1.2.3 From 9d0b190f4b27e64d0e5d532c6a819dae076c3274 Mon Sep 17 00:00:00 2001 From: Mitch Curtis Date: Wed, 21 Aug 2013 14:25:55 +0200 Subject: Construct a valid QTime when creating timestamps for iBase SQL driver. 0e62fc73c905d1f476f3c1493db1bde8096ac609 requires this. Task-number: QTBUG-29261 Change-Id: Idd8b630c72d0fd1c255695a8c2c22f9fe32767ee Reviewed-by: John Layt --- src/sql/drivers/ibase/qsql_ibase.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src') diff --git a/src/sql/drivers/ibase/qsql_ibase.cpp b/src/sql/drivers/ibase/qsql_ibase.cpp index bd97db189c..e4979e54a4 100644 --- a/src/sql/drivers/ibase/qsql_ibase.cpp +++ b/src/sql/drivers/ibase/qsql_ibase.cpp @@ -240,7 +240,7 @@ static ISC_TIMESTAMP toTimeStamp(const QDateTime &dt) static QDateTime fromTimeStamp(char *buffer) { static const QDate bd(1858, 11, 17); - QTime t; + QTime t(0, 0); QDate d; // have to demangle the structure ourselves because isc_decode_time -- cgit v1.2.3 From 5680484476d7d60b85ac64b017edd97116048525 Mon Sep 17 00:00:00 2001 From: Andreas Holzammer Date: Tue, 20 Aug 2013 09:35:21 +0200 Subject: [QNX]Fix transparencies It is not guaranteed that buffers are cleared when they are allocated. So don't use a buffer for the root window, and clear buffers for the actual content. Change-Id: I42939baec03fa05968c83bbf2739ab8d1d70c8be Reviewed-by: Matt Hoosier Reviewed-by: Rafael Roquetto --- src/plugins/platforms/qnx/qqnxrootwindow.cpp | 31 ++-------------------------- src/plugins/platforms/qnx/qqnxwindow.cpp | 16 ++++++++++++-- 2 files changed, 16 insertions(+), 31 deletions(-) (limited to 'src') diff --git a/src/plugins/platforms/qnx/qqnxrootwindow.cpp b/src/plugins/platforms/qnx/qqnxrootwindow.cpp index ff5866d1b7..b3f5c87176 100644 --- a/src/plugins/platforms/qnx/qqnxrootwindow.cpp +++ b/src/plugins/platforms/qnx/qqnxrootwindow.cpp @@ -188,35 +188,8 @@ void QQnxRootWindow::makeTranslucent() int result; errno = 0; - result = screen_destroy_window_buffers(m_window); - if (result != 0) { - qFatal("QQnxRootWindow: failed to destroy window buffer, errno=%d", errno); - } - - QRect geometry = m_screen->geometry(); - errno = 0; - int val[2]; - val[0] = geometry.width(); - val[1] = geometry.height(); - result = screen_set_window_property_iv(m_window, SCREEN_PROPERTY_BUFFER_SIZE, val); - if (result != 0) { - qFatal("QQnxRootWindow: failed to set window buffer size, errno=%d", errno); - } - - errno = 0; - result = screen_create_window_buffers(m_window, 1); - if (result != 0) { - qFatal("QQNX: failed to create window buffer, errno=%d", errno); - } - - // Install an alpha channel on the root window. - // - // This is necessary in order to avoid interfering with any particular - // toplevel widget's QQnxWindow window instance from showing transparent - // if it desires. - errno = 0; - val[0] = SCREEN_TRANSPARENCY_SOURCE_OVER; - result = screen_set_window_property_iv(m_window, SCREEN_PROPERTY_TRANSPARENCY, val); + const int val = SCREEN_TRANSPARENCY_DISCARD; + result = screen_set_window_property_iv(m_window, SCREEN_PROPERTY_TRANSPARENCY, &val); if (result != 0) { qFatal("QQnxRootWindow: failed to set window transparency, errno=%d", errno); } diff --git a/src/plugins/platforms/qnx/qqnxwindow.cpp b/src/plugins/platforms/qnx/qqnxwindow.cpp index 5aa1c970fd..fb8e8075ad 100644 --- a/src/plugins/platforms/qnx/qqnxwindow.cpp +++ b/src/plugins/platforms/qnx/qqnxwindow.cpp @@ -418,15 +418,27 @@ QQnxBuffer &QQnxWindow::renderBuffer() // Get all buffers available for rendering errno = 0; screen_buffer_t buffers[MAX_BUFFER_COUNT]; - const int result = screen_get_window_property_pv(m_window, SCREEN_PROPERTY_RENDER_BUFFERS, (void **)buffers); + int result = screen_get_window_property_pv(m_window, SCREEN_PROPERTY_RENDER_BUFFERS, (void **)buffers); if (result != 0) qFatal("QQnxWindow: failed to query window buffers, errno=%d", errno); - // Wrap each buffer + // Wrap each buffer and clear for (int i = 0; i < MAX_BUFFER_COUNT; ++i) { m_buffers[i] = QQnxBuffer(buffers[i]); + + // Clear Buffer + errno = 0; + int bg[] = { SCREEN_BLIT_COLOR, 0x00000000, SCREEN_BLIT_END }; + result = screen_fill(m_screen->nativeContext(), buffers[i], bg); + if (result != 0) + qFatal("QQnxWindow: failed to clear window buffer, errno=%d", errno); } + errno = 0; + result = screen_flush_blits(m_screen->nativeContext(), 0); + if (result != 0) + qFatal("QQnxWindow: failed to flush blits, errno=%d", errno); + // Use the first available render buffer m_currentBufferIndex = 0; m_previousBufferIndex = -1; -- cgit v1.2.3 From ecbd3a70e4cd7322dd4fe07c4e46d06afa3e952b Mon Sep 17 00:00:00 2001 From: Eskil Abrahamsen Blomfeldt Date: Thu, 15 Aug 2013 11:41:19 +0200 Subject: Android: Remove EGL_BAD_SURFACE warning on suspension When suspending the app we would destroy the surface twice, causing libEGL to output a warning on the second attempt. We would also destroy the surface before all references were released which is not 100% nice. We don't need to call the super class implementation at all, since we are managing the EGL surface ourselves. Change-Id: Ie1ab2ea8561d0018b5f16ac8cdf3296313a0a92c Reviewed-by: Christian Stromme --- .../platforms/android/src/opengl/qandroidopenglplatformwindow.cpp | 1 - 1 file changed, 1 deletion(-) (limited to 'src') diff --git a/src/plugins/platforms/android/src/opengl/qandroidopenglplatformwindow.cpp b/src/plugins/platforms/android/src/opengl/qandroidopenglplatformwindow.cpp index 5362906e0e..24a7debd1f 100644 --- a/src/plugins/platforms/android/src/opengl/qandroidopenglplatformwindow.cpp +++ b/src/plugins/platforms/android/src/opengl/qandroidopenglplatformwindow.cpp @@ -69,7 +69,6 @@ void QAndroidOpenGLPlatformWindow::invalidateSurface() { QWindowSystemInterface::handleExposeEvent(window(), QRegion()); // Obscure event QWindowSystemInterface::flushWindowSystemEvents(); - QEglFSWindow::invalidateSurface(); m_window = 0; m_surface = 0; -- cgit v1.2.3 From bd9a023a41209a216eec28bd25a20372a5172b6a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tor=20Arne=20Vestb=C3=B8?= Date: Wed, 21 Aug 2013 15:05:19 +0200 Subject: Don't use qt_mac_get_fixed_pitch() to resolve fixed pitch fonts on OSX The call was resulting in inifinite recursion on OSX 10.9 when Qt was built against the 10.7 SDK, as qt_mac_get_fixed_pitch uses QFontMetrics to resolve the pitch, and we would end up in the font resolver again when asking for the metrics. The CoreText font-database already takes care of resolving whether or not a font family is fixed-pitch, so the code is likely a leftover from the ATSUI-days, and can be removed. Task-number: QTBUG-31803 Change-Id: I37c90fa637927eb4adc16c0fd556c4c46c456034 Reviewed-by: Gabriel de Dietrich --- src/gui/text/qfontdatabase.cpp | 24 ------------------------ 1 file changed, 24 deletions(-) (limited to 'src') diff --git a/src/gui/text/qfontdatabase.cpp b/src/gui/text/qfontdatabase.cpp index 62379cd592..54b4629ca0 100644 --- a/src/gui/text/qfontdatabase.cpp +++ b/src/gui/text/qfontdatabase.cpp @@ -314,9 +314,6 @@ struct QtFontFamily QtFontFamily(const QString &n) : fixedPitch(false), -#if !defined(QWS) && defined(Q_OS_MAC) - fixedPitchComputed(false), -#endif name(n), count(0), foundries(0) , bogusWritingSystems(false) , askedForFallback(false) @@ -330,9 +327,6 @@ struct QtFontFamily } bool fixedPitch : 1; -#if !defined(QWS) && defined(Q_OS_MAC) - bool fixedPitchComputed : 1; -#endif QString name; QStringList aliases; @@ -348,18 +342,6 @@ struct QtFontFamily QtFontFoundry *foundry(const QString &f, bool = false); }; -#if !defined(QWS) && defined(Q_OS_MAC) -inline static void qt_mac_get_fixed_pitch(QtFontFamily *f) -{ - if(f && !f->fixedPitchComputed) { - QFontMetrics fm(f->name); - f->fixedPitch = fm.width(QLatin1Char('i')) == fm.width(QLatin1Char('m')); - f->fixedPitchComputed = true; - } -} -#endif - - QtFontFoundry *QtFontFamily::foundry(const QString &f, bool create) { if (f.isNull() && count == 1) @@ -823,9 +805,6 @@ unsigned int bestFoundry(int script, unsigned int score, int styleStrategy, EncodingMismatch = 0x0002 }; if (pitch != '*') { -#if !defined(QWS) && defined(Q_OS_MAC) - qt_mac_get_fixed_pitch(const_cast(family)); -#endif if ((pitch == 'm' && !family->fixedPitch) || (pitch == 'p' && family->fixedPitch)) this_score += PitchMismatch; @@ -1263,9 +1242,6 @@ bool QFontDatabase::isFixedPitch(const QString &family, QT_PREPEND_NAMESPACE(load)(familyName); QtFontFamily *f = d->family(familyName); -#if !defined(QWS) && defined(Q_OS_MAC) - qt_mac_get_fixed_pitch(f); -#endif return (f && f->fixedPitch); } -- cgit v1.2.3 From f7ebb8d4c64030a0569f8f2af98dad665a6866a7 Mon Sep 17 00:00:00 2001 From: Shawn Rutledge Date: Tue, 20 Aug 2013 11:41:15 +0200 Subject: QXcbBackingStore: don't crash in flush() if no platformWindow Task-number: QTBUG-32681 Change-Id: Iec7204985867a8d65cea393ba6ab66d328a5e7b2 Reviewed-by: Friedemann Kleint --- src/plugins/platforms/xcb/qxcbbackingstore.cpp | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'src') diff --git a/src/plugins/platforms/xcb/qxcbbackingstore.cpp b/src/plugins/platforms/xcb/qxcbbackingstore.cpp index 1f2485db0d..dc677cd3be 100644 --- a/src/plugins/platforms/xcb/qxcbbackingstore.cpp +++ b/src/plugins/platforms/xcb/qxcbbackingstore.cpp @@ -306,6 +306,10 @@ void QXcbBackingStore::flush(QWindow *window, const QRegion ®ion, const QPoin Q_XCB_NOOP(connection()); QXcbWindow *platformWindow = static_cast(window->handle()); + if (!platformWindow) { + qWarning("QXcbBackingStore::flush: QWindow has no platform window (QTBUG-32681)"); + return; + } QVector rects = clipped.rects(); for (int i = 0; i < rects.size(); ++i) -- cgit v1.2.3 From 4ef8144dd6a7a4e493c901c3d1d4bbb7735c161c Mon Sep 17 00:00:00 2001 From: Friedemann Kleint Date: Wed, 21 Aug 2013 13:52:48 +0200 Subject: QWidget: Apply window opacity set before show. Task-number: QTBUG-33078 Change-Id: Id9111f223a9dc58c88b072c52e36d42db450573a Reviewed-by: Shawn Rutledge --- src/widgets/kernel/qwidget_qpa.cpp | 2 ++ 1 file changed, 2 insertions(+) (limited to 'src') diff --git a/src/widgets/kernel/qwidget_qpa.cpp b/src/widgets/kernel/qwidget_qpa.cpp index f0846bea6b..665aa4b17a 100644 --- a/src/widgets/kernel/qwidget_qpa.cpp +++ b/src/widgets/kernel/qwidget_qpa.cpp @@ -900,6 +900,8 @@ void QWidgetPrivate::createTLSysExtra() extra->topextra->window->setMinimumSize(QSize(extra->minw, extra->minh)); if (extra->maxw != QWIDGETSIZE_MAX || extra->maxh != QWIDGETSIZE_MAX) extra->topextra->window->setMaximumSize(QSize(extra->maxw, extra->maxh)); + if (extra->topextra->opacity != 255 && q->isWindow()) + extra->topextra->window->setOpacity(qreal(extra->topextra->opacity) / qreal(255)); #ifdef Q_OS_WIN // Pass on native parent handle for Widget embedded into Active X. const QVariant activeXNativeParentHandle = q->property(activeXNativeParentHandleProperty); -- cgit v1.2.3 From ee50096830f7915db2078ad66d83283e3c97f5d9 Mon Sep 17 00:00:00 2001 From: Stephen Kelly Date: Mon, 8 Jul 2013 12:17:35 +0200 Subject: Populate INTERFACE_LINK_LIBRARIES property in the cmake files. This is new in CMake 2.8.12 and replaces the old properties matching IMPORTED_INTERFACE_LINK_LIBRARIES_. Change-Id: I5d4c454972f2535f6792e95718c73d80c56ac24c Reviewed-by: Stephen Kelly --- src/corelib/Qt5CoreConfigExtras.cmake.in | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'src') diff --git a/src/corelib/Qt5CoreConfigExtras.cmake.in b/src/corelib/Qt5CoreConfigExtras.cmake.in index e01b448351..db482fa9e6 100644 --- a/src/corelib/Qt5CoreConfigExtras.cmake.in +++ b/src/corelib/Qt5CoreConfigExtras.cmake.in @@ -133,6 +133,11 @@ if (NOT TARGET Qt5::WinMain) set(_isPolicyNEW $) get_target_property(_configs Qt5::Core IMPORTED_CONFIGURATIONS) foreach(_config ${_configs}) + set_property(TARGET Qt5::Core APPEND PROPERTY + INTERFACE_LINK_LIBRARIES + $<$:Qt5::WinMain> + ) + # For backward compatibility with CMake < 2.8.12 set_property(TARGET Qt5::Core APPEND PROPERTY IMPORTED_LINK_INTERFACE_LIBRARIES_${_config} $<$:Qt5::WinMain> -- cgit v1.2.3 From 8074693425e06d2c4a8f130124658fe72f3e5ab9 Mon Sep 17 00:00:00 2001 From: Stephen Kelly Date: Wed, 19 Jun 2013 17:56:04 +0200 Subject: CMake: Allow specifying a TARGET in invocations of macros. Forward-port of 9ce60ff509c4ff27fe861fc5b2080f50897a68c4 (Qt4Macros: Allow specifying a TARGET in invokations of macros., 2013-02-26) from cmake.git. This causes the INCLUDE_DIRECTORIES and COMPILE_DEFINITIONS to be used from the specified target when running moc. Change-Id: I868a35ade3c6b059e64d226291cf2046709d86d4 Reviewed-by: Stephen Kelly --- src/corelib/Qt5CoreMacros.cmake | 80 ++++++++++++++++++++++++++--------------- 1 file changed, 51 insertions(+), 29 deletions(-) (limited to 'src') diff --git a/src/corelib/Qt5CoreMacros.cmake b/src/corelib/Qt5CoreMacros.cmake index 6630885257..dca257f080 100644 --- a/src/corelib/Qt5CoreMacros.cmake +++ b/src/corelib/Qt5CoreMacros.cmake @@ -94,34 +94,45 @@ endmacro() # helper macro to set up a moc rule -macro(QT5_CREATE_MOC_COMMAND infile outfile moc_flags moc_options) - # For Windows, create a parameters file to work around command line length limit - if(WIN32) - # Pass the parameters in a file. Set the working directory to - # be that containing the parameters file and reference it by - # just the file name. This is necessary because the moc tool on - # MinGW builds does not seem to handle spaces in the path to the - # file given with the @ syntax. - get_filename_component(_moc_outfile_name "${outfile}" NAME) - get_filename_component(_moc_outfile_dir "${outfile}" PATH) - if(_moc_outfile_dir) - set(_moc_working_dir WORKING_DIRECTORY ${_moc_outfile_dir}) - endif() - set(_moc_parameters_file ${outfile}_parameters) - set(_moc_parameters ${moc_flags} ${moc_options} -o "${outfile}" "${infile}") - string(REPLACE ";" "\n" _moc_parameters "${_moc_parameters}") - file(WRITE ${_moc_parameters_file} "${_moc_parameters}") - add_custom_command(OUTPUT ${outfile} - COMMAND ${Qt5Core_MOC_EXECUTABLE} @${_moc_outfile_name}_parameters - DEPENDS ${infile} - ${_moc_working_dir} - VERBATIM) +macro(QT5_CREATE_MOC_COMMAND infile outfile moc_flags moc_options moc_target) + # Pass the parameters in a file. Set the working directory to + # be that containing the parameters file and reference it by + # just the file name. This is necessary because the moc tool on + # MinGW builds does not seem to handle spaces in the path to the + # file given with the @ syntax. + get_filename_component(_moc_outfile_name "${outfile}" NAME) + get_filename_component(_moc_outfile_dir "${outfile}" PATH) + if(_moc_outfile_dir) + set(_moc_working_dir WORKING_DIRECTORY ${_moc_outfile_dir}) + endif() + set (_moc_parameters_file ${outfile}_parameters) + set (_moc_parameters ${moc_flags} ${moc_options} -o "${outfile}" "${infile}") + string (REPLACE ";" "\n" _moc_parameters "${_moc_parameters}") + + if(moc_target) + set(targetincludes "$") + set(targetdefines "$") + + set(targetincludes "$<$:-I$\n>") + set(targetdefines "$<$:-D$\n>") + + file (GENERATE + OUTPUT ${_moc_parameters_file} + CONTENT "${targetdefines}${targetincludes}${_moc_parameters}\n" + ) + + set(targetincludes) + set(targetdefines) else() - add_custom_command(OUTPUT ${outfile} - COMMAND ${Qt5Core_MOC_EXECUTABLE} - ARGS ${moc_flags} ${moc_options} -o ${outfile} ${infile} - DEPENDS ${infile} VERBATIM) + file(WRITE ${_moc_parameters_file} "${_moc_parameters}\n") endif() + + set(_moc_extra_parameters_file @${_moc_parameters_file}) + add_custom_command(OUTPUT ${outfile} + COMMAND ${Qt5Core_MOC_EXECUTABLE} ${_moc_extra_parameters_file} + DEPENDS ${infile} + ${_moc_working_dir} + VERBATIM) endmacro() @@ -133,7 +144,13 @@ function(QT5_GENERATE_MOC infile outfile ) if(NOT IS_ABSOLUTE "${outfile}") set(_outfile "${CMAKE_CURRENT_BINARY_DIR}/${outfile}") endif() - qt5_create_moc_command(${abs_infile} ${_outfile} "${moc_flags}" "") + 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}") set_source_files_properties(${outfile} PROPERTIES SKIP_AUTOMOC TRUE) # dont run automoc on this file endfunction() @@ -145,17 +162,22 @@ function(QT5_WRAP_CPP outfiles ) qt5_get_moc_flags(moc_flags) set(options) - set(oneValueArgs) + set(oneValueArgs TARGET) set(multiValueArgs OPTIONS) cmake_parse_arguments(_WRAP_CPP "${options}" "${oneValueArgs}" "${multiValueArgs}" ${ARGN}) set(moc_files ${_WRAP_CPP_UNPARSED_ARGUMENTS}) set(moc_options ${_WRAP_CPP_OPTIONS}) + set(moc_target ${_WRAP_CPP_TARGET}) + + 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) - qt5_create_moc_command(${it} ${outfile} "${moc_flags}" "${moc_options}") + qt5_create_moc_command(${it} ${outfile} "${moc_flags}" "${moc_options}" "${moc_target}") list(APPEND ${outfiles} ${outfile}) endforeach() set(${outfiles} ${${outfiles}} PARENT_SCOPE) -- cgit v1.2.3 From bc4ce284ade4e3584370a74a0cc6aadc40301231 Mon Sep 17 00:00:00 2001 From: Friedemann Kleint Date: Wed, 21 Aug 2013 10:36:19 +0200 Subject: Windows: Generate expose events for layered transient children. Layered (translucent/non-opaque) windows do not receive WM_PAINT, expose events need to be generated. Improve 6800728d091e5122e6d93675db84ee028221d161 to handle transient children as well. Task-number: QTBUG-17548 Change-Id: Id113604512692dfbea1f2b10d0db3068213cf599 Reviewed-by: Joerg Bornemann --- src/plugins/platforms/windows/qwindowswindow.cpp | 25 ++++++++++++++++++------ src/plugins/platforms/windows/qwindowswindow.h | 10 ++++++++++ 2 files changed, 29 insertions(+), 6 deletions(-) (limited to 'src') diff --git a/src/plugins/platforms/windows/qwindowswindow.cpp b/src/plugins/platforms/windows/qwindowswindow.cpp index 8ec10294a2..401fa67c4b 100644 --- a/src/plugins/platforms/windows/qwindowswindow.cpp +++ b/src/plugins/platforms/windows/qwindowswindow.cpp @@ -1408,14 +1408,27 @@ void QWindowsWindow::handleWindowStateChange(Qt::WindowState state) handleHidden(); QWindowSystemInterface::flushWindowSystemEvents(); // Tell QQuickWindow to stop rendering now. break; - case Qt::WindowNoState: + case Qt::WindowNoState: { // QTBUG-17548: We send expose events when receiving WM_Paint, but for - // layered windows, we won't receive any WM_Paint. - if (GetWindowLongPtr(m_data.hwnd, GWL_EXSTYLE) & WS_EX_LAYERED) { - fireExpose(QRegion(0, 0, window()->width(), window()->height())); - if (!QWindowsContext::instance()->asyncExpose()) - QWindowSystemInterface::flushWindowSystemEvents(); + // layered windows and transient children, we won't receive any WM_Paint. + QWindow *w = window(); + bool exposeEventsSent = false; + if (isLayered()) { + fireExpose(QRegion(0, 0, w->width(), w->height())); + exposeEventsSent = true; } + foreach (QWindow *child, QGuiApplication::allWindows()) { + if (child != w && child->isVisible() && child->transientParent() == w) { + QWindowsWindow *platformWindow = QWindowsWindow::baseWindowOf(child); + if (platformWindow->isLayered()) { + platformWindow->fireExpose(QRegion(0, 0, child->width(), child->height())); + exposeEventsSent = true; + } + } + } + if (exposeEventsSent && !QWindowsContext::instance()->asyncExpose()) + QWindowSystemInterface::flushWindowSystemEvents(); + } break; default: break; diff --git a/src/plugins/platforms/windows/qwindowswindow.h b/src/plugins/platforms/windows/qwindowswindow.h index f7d142fc36..afcfa8b821 100644 --- a/src/plugins/platforms/windows/qwindowswindow.h +++ b/src/plugins/platforms/windows/qwindowswindow.h @@ -229,6 +229,7 @@ public: static inline void setUserDataOf(HWND hwnd, void *ud); static bool setWindowLayered(HWND hwnd, Qt::WindowFlags flags, bool hasAlpha, qreal opacity); + bool isLayered() const; HDC getDC(); void releaseDC(); @@ -375,6 +376,15 @@ inline void QWindowsWindow::destroyIcon() } } +inline bool QWindowsWindow::isLayered() const +{ +#ifndef Q_OS_WINCE + return GetWindowLongPtr(m_data.hwnd, GWL_EXSTYLE) & WS_EX_LAYERED; +#else + return false; +#endif +} + QT_END_NAMESPACE Q_DECLARE_METATYPE(QMargins) -- cgit v1.2.3 From 95e880bd9dd0244983acebb1d7c3bce620e93c26 Mon Sep 17 00:00:00 2001 From: Friedemann Kleint Date: Tue, 20 Aug 2013 16:01:43 +0200 Subject: Windows: Handle Qt::ForeignWindow. Task-number: QTBUG-33079 Change-Id: Iec2ddfe07b07b3a921098c7147f26aff316bf6e6 Reviewed-by: Joerg Bornemann --- src/plugins/platforms/windows/qwindowsintegration.cpp | 2 ++ src/plugins/platforms/windows/qwindowswindow.cpp | 14 +++++++++++++- 2 files changed, 15 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/plugins/platforms/windows/qwindowsintegration.cpp b/src/plugins/platforms/windows/qwindowsintegration.cpp index fc2ba454df..754d7a0288 100644 --- a/src/plugins/platforms/windows/qwindowsintegration.cpp +++ b/src/plugins/platforms/windows/qwindowsintegration.cpp @@ -395,6 +395,8 @@ bool QWindowsIntegration::hasCapability(QPlatformIntegration::Capability cap) co return true; case MultipleWindows: return true; + case ForeignWindows: + return true; default: return QPlatformIntegration::hasCapability(cap); } diff --git a/src/plugins/platforms/windows/qwindowswindow.cpp b/src/plugins/platforms/windows/qwindowswindow.cpp index 401fa67c4b..ace18ddf5b 100644 --- a/src/plugins/platforms/windows/qwindowswindow.cpp +++ b/src/plugins/platforms/windows/qwindowswindow.cpp @@ -485,6 +485,18 @@ QWindowsWindow::WindowData qDebug().nospace() << "Created desktop window " << w << result.hwnd; return result; } + if ((flags & Qt::WindowType_Mask) == Qt::ForeignWindow) { + result.hwnd = reinterpret_cast(w->winId()); + Q_ASSERT(result.hwnd); + const LONG_PTR style = GetWindowLongPtr(result.hwnd, GWL_STYLE); + const LONG_PTR exStyle = GetWindowLongPtr(result.hwnd, GWL_EXSTYLE); + result.geometry = frameGeometry(result.hwnd, !GetParent(result.hwnd)); + result.frame = QWindowsGeometryHint::frame(style, exStyle); + result.embedded = false; + if (QWindowsContext::verboseWindows) + qDebug() << "Foreign window: " << w << result.hwnd << result.geometry << result.frame; + return result; + } const HINSTANCE appinst = (HINSTANCE)GetModuleHandle(0); @@ -894,7 +906,7 @@ void QWindowsWindow::destroyWindow() } } #endif // !Q_OS_WINCE - if (m_data.hwnd != GetDesktopWindow()) + if (m_data.hwnd != GetDesktopWindow() && window()->type() != Qt::ForeignWindow) DestroyWindow(m_data.hwnd); context->removeWindow(m_data.hwnd); m_data.hwnd = 0; -- cgit v1.2.3 From c20b3587038c8834e439057c791684c5f636cd07 Mon Sep 17 00:00:00 2001 From: Olivier Goffart Date: Mon, 22 Jul 2013 13:01:59 +0200 Subject: moc: Issue a warning instead of an error when macro argument mismatch moc's C++ is not 100% accurate, so better process the invalid macro with a warning rather than an error. Such errors occurred in the QSKIP macro with variadic arguments since that macro is defined conditionally. It is also causing problem in boost header (cf task QTBUG-29331) Task-number: QTBUG-29331 Change-Id: Ice6a01b675286540d6470c8e36920b7efd39b540 Reviewed-by: Lars Knoll --- src/tools/moc/preprocessor.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'src') diff --git a/src/tools/moc/preprocessor.cpp b/src/tools/moc/preprocessor.cpp index 8f4b84a9c8..06758e67bd 100644 --- a/src/tools/moc/preprocessor.cpp +++ b/src/tools/moc/preprocessor.cpp @@ -645,7 +645,7 @@ Symbols Preprocessor::macroExpandIdentifier(Preprocessor *that, SymbolStack &sym // 0 argument macros are a bit special. They are ok if the // argument is pure whitespace or empty (macro.arguments.size() != 0 || arguments.size() != 1 || !arguments.at(0).isEmpty())) - that->error("Macro argument mismatch."); + that->warning("Macro argument mismatch."); // now replace the macro arguments with the expanded arguments enum Mode { @@ -662,7 +662,7 @@ Symbols Preprocessor::macroExpandIdentifier(Preprocessor *that, SymbolStack &sym } int index = macro.arguments.indexOf(s); if (mode == Normal) { - if (index >= 0) { + if (index >= 0 && index < arguments.size()) { // each argument undoergoes macro expansion if it's not used as part of a # or ## if (i == macro.symbols.size() - 1 || macro.symbols.at(i + 1).token != PP_HASHHASH) { Symbols arg = arguments.at(index); -- cgit v1.2.3 From 2bd40c53ef54ff2c11ddb3b3acbd443a6429a8db Mon Sep 17 00:00:00 2001 From: Olivier Goffart Date: Wed, 21 Aug 2013 11:29:14 +0200 Subject: moc: Fix related objects containing itself This may happen when we have namespaces and the qualified name is used to scope an enum. Task-number: QTBUG-32933 Change-Id: Ic4923bbfb138387bae1e3694172661ace8342089 Reviewed-by: Alan Alpert Reviewed-by: Thiago Macieira --- src/tools/moc/generator.cpp | 16 ++++++++++++++-- 1 file changed, 14 insertions(+), 2 deletions(-) (limited to 'src') diff --git a/src/tools/moc/generator.cpp b/src/tools/moc/generator.cpp index 4757fdad93..3302d23ad4 100644 --- a/src/tools/moc/generator.cpp +++ b/src/tools/moc/generator.cpp @@ -184,6 +184,18 @@ bool Generator::registerableMetaType(const QByteArray &propertyType) return false; } +/* returns true if name and qualifiedName refers to the same name. + * If qualified name is "A::B::C", it returns true for "C", "B::C" or "A::B::C" */ +static bool qualifiedNameEquals(const QByteArray &qualifiedName, const QByteArray &name) +{ + if (qualifiedName == name) + return true; + int index = qualifiedName.indexOf("::"); + if (index == -1) + return false; + return qualifiedNameEquals(qualifiedName.mid(index+2), name); +} + void Generator::generateCode() { bool isQt = (cdef->classname == "Qt"); @@ -431,7 +443,7 @@ void Generator::generateCode() int s = p.type.lastIndexOf("::"); if (s > 0) { QByteArray scope = p.type.left(s); - if (scope != "Qt" && scope != cdef->classname && !extraList.contains(scope)) + if (scope != "Qt" && !qualifiedNameEquals(cdef->qualified, scope) && !extraList.contains(scope)) extraList += scope; } } @@ -446,7 +458,7 @@ void Generator::generateCode() int s = enumKey.lastIndexOf("::"); if (s > 0) { QByteArray scope = enumKey.left(s); - if (scope != "Qt" && scope != cdef->classname && !extraList.contains(scope)) + if (scope != "Qt" && !qualifiedNameEquals(cdef->qualified, scope) && !extraList.contains(scope)) extraList += scope; } } -- cgit v1.2.3 From 8a96679493bcb5e508cf438d6d6f18d0db7a43cc Mon Sep 17 00:00:00 2001 From: Olivier Goffart Date: Wed, 21 Aug 2013 09:32:16 +0200 Subject: moc generated code should compile with QT_NO_KEYWORDS Don't use the 'emit' keyword in the moc generated code for properties with MEMBER Task-number: QTBUG-33094 Change-Id: I5a0950e9c7a0dee347a6a6c79098e3e7d4776014 Reviewed-by: Thiago Macieira --- src/tools/moc/generator.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'src') diff --git a/src/tools/moc/generator.cpp b/src/tools/moc/generator.cpp index 3302d23ad4..50da6d2e54 100644 --- a/src/tools/moc/generator.cpp +++ b/src/tools/moc/generator.cpp @@ -984,9 +984,9 @@ void Generator::generateMetacall() if (!p.notify.isEmpty() && p.notifyId != -1) { const FunctionDef &f = cdef->signalList.at(p.notifyId); if (f.arguments.size() == 0) - fprintf(out, " emit %s();\n", p.notify.constData()); + fprintf(out, " Q_EMIT %s();\n", p.notify.constData()); else if (f.arguments.size() == 1 && f.arguments.at(0).normalizedType == p.type) - fprintf(out, " emit %s(%s%s);\n", + fprintf(out, " Q_EMIT %s(%s%s);\n", p.notify.constData(), prefix.constData(), p.member.constData()); } fprintf(out, " }\n"); -- cgit v1.2.3 From 4e043026725b1dfd201bf432bdd0b28ba8867196 Mon Sep 17 00:00:00 2001 From: Friedemann Kleint Date: Thu, 22 Aug 2013 10:06:33 +0200 Subject: Check for window handle in QBackingStore::flush(). Task-number: QTBUG-33062 Change-Id: Iab4ccc3a2a855ee7f6964659b53b3401af436212 Reviewed-by: Andy Shaw --- src/gui/painting/qbackingstore.cpp | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'src') diff --git a/src/gui/painting/qbackingstore.cpp b/src/gui/painting/qbackingstore.cpp index edb5f66c5b..c1f7c6c738 100644 --- a/src/gui/painting/qbackingstore.cpp +++ b/src/gui/painting/qbackingstore.cpp @@ -97,6 +97,11 @@ void QBackingStore::flush(const QRegion ®ion, QWindow *win, const QPoint &off { if (!win) win = window(); + if (!win->handle()) { + qWarning() << "QBackingStore::flush() called for " + << win << " which does not have a handle."; + return; + } #ifdef QBACKINGSTORE_DEBUG if (win && win->isTopLevel() && !qt_window_private(win)->receivedExpose) { -- cgit v1.2.3 From c7c3a78075eb05db6714b21c61aad722b275ec8c Mon Sep 17 00:00:00 2001 From: Mitch Curtis Date: Mon, 19 Aug 2013 16:29:29 +0200 Subject: Add json/savegame example. There wasn't any example documentation besides json.html, which doesn't actually describe usage of the various QJson* classes. This also makes each QJson* class page link back to json.html. Change-Id: If5ad6493d2728df0cec7bdbbc5790f0b755f816c Reviewed-by: Friedemann Kleint Reviewed-by: Jerome Pasion Reviewed-by: Lars Knoll --- src/corelib/doc/qtcore.qdocconf | 3 ++- src/corelib/doc/src/datastreamformat.qdoc | 2 ++ src/corelib/doc/src/json.qdoc | 2 ++ src/corelib/json/qjsonarray.cpp | 2 ++ src/corelib/json/qjsondocument.cpp | 2 ++ src/corelib/json/qjsonobject.cpp | 6 ++++-- src/corelib/json/qjsonparser.cpp | 2 ++ src/corelib/json/qjsonvalue.cpp | 2 ++ 8 files changed, 18 insertions(+), 3 deletions(-) (limited to 'src') diff --git a/src/corelib/doc/qtcore.qdocconf b/src/corelib/doc/qtcore.qdocconf index 0e275ee8d4..752e8eb946 100644 --- a/src/corelib/doc/qtcore.qdocconf +++ b/src/corelib/doc/qtcore.qdocconf @@ -36,6 +36,7 @@ exampledirs += \ ../ \ snippets \ ../../../examples/threads/ \ - ../../../examples/tools/ + ../../../examples/tools/ \ + ../../../examples/json/ imagedirs += images diff --git a/src/corelib/doc/src/datastreamformat.qdoc b/src/corelib/doc/src/datastreamformat.qdoc index 99a0a077cd..b6efe6aa33 100644 --- a/src/corelib/doc/src/datastreamformat.qdoc +++ b/src/corelib/doc/src/datastreamformat.qdoc @@ -369,4 +369,6 @@ \li The items (T) \endlist \endtable + + \sa {JSON Support in Qt} */ diff --git a/src/corelib/doc/src/json.qdoc b/src/corelib/doc/src/json.qdoc index 89e1bcac34..5bffe98ae5 100644 --- a/src/corelib/doc/src/json.qdoc +++ b/src/corelib/doc/src/json.qdoc @@ -99,6 +99,8 @@ A valid JSON document is either an array or an object, so a document always starts with a square or curly bracket. + \sa {JSON Save Game Example} + \section1 The JSON Classes diff --git a/src/corelib/json/qjsonarray.cpp b/src/corelib/json/qjsonarray.cpp index fb8d2e83ff..8dd7f6092f 100644 --- a/src/corelib/json/qjsonarray.cpp +++ b/src/corelib/json/qjsonarray.cpp @@ -71,6 +71,8 @@ QT_BEGIN_NAMESPACE it has been created from as long as it is not being modified. You can convert the array to and from text based JSON through QJsonDocument. + + \sa {JSON Support in Qt}, {JSON Save Game Example} */ /*! diff --git a/src/corelib/json/qjsondocument.cpp b/src/corelib/json/qjsondocument.cpp index bdb46528d3..05d57e2ab9 100644 --- a/src/corelib/json/qjsondocument.cpp +++ b/src/corelib/json/qjsondocument.cpp @@ -76,6 +76,8 @@ QT_BEGIN_NAMESPACE A document can also be created from a stored binary representation using fromBinaryData() or fromRawData(). + + \sa {JSON Support in Qt}, {JSON Save Game Example} */ /*! diff --git a/src/corelib/json/qjsonobject.cpp b/src/corelib/json/qjsonobject.cpp index 43336de2e7..362d01384e 100644 --- a/src/corelib/json/qjsonobject.cpp +++ b/src/corelib/json/qjsonobject.cpp @@ -70,6 +70,8 @@ QT_BEGIN_NAMESPACE it has been created from as long as it is not being modified. You can convert the object to and from text based JSON through QJsonDocument. + + \sa {JSON Support in Qt}, {JSON Save Game Example} */ /*! @@ -604,7 +606,7 @@ QJsonObject::const_iterator QJsonObject::constFind(const QString &key) const Multiple iterators can be used on the same object. Existing iterators will however become dangling once the object gets modified. - \sa QJsonObject::const_iterator + \sa QJsonObject::const_iterator, {JSON Support in Qt}, {JSON Save Game Example} */ /*! \typedef QJsonObject::iterator::difference_type @@ -799,7 +801,7 @@ QJsonObject::const_iterator QJsonObject::constFind(const QString &key) const Multiple iterators can be used on the same object. Existing iterators will however become dangling if the object gets modified. - \sa QJsonObject::iterator + \sa QJsonObject::iterator, {JSON Support in Qt}, {JSON Save Game Example} */ /*! \typedef QJsonObject::const_iterator::difference_type diff --git a/src/corelib/json/qjsonparser.cpp b/src/corelib/json/qjsonparser.cpp index b151af7955..8721f06064 100644 --- a/src/corelib/json/qjsonparser.cpp +++ b/src/corelib/json/qjsonparser.cpp @@ -86,6 +86,8 @@ QT_BEGIN_NAMESPACE \since 5.0 \brief The QJsonParseError class is used to report errors during JSON parsing. + + \sa {JSON Support in Qt}, {JSON Save Game Example} */ /*! diff --git a/src/corelib/json/qjsonvalue.cpp b/src/corelib/json/qjsonvalue.cpp index 3fbc811948..9dd9a9cab9 100644 --- a/src/corelib/json/qjsonvalue.cpp +++ b/src/corelib/json/qjsonvalue.cpp @@ -81,6 +81,8 @@ QT_BEGIN_NAMESPACE Values are strictly typed internally and contrary to QVariant will not attempt to do any implicit type conversions. This implies that converting to a type that is not stored in the value will return a default constructed return value. + + \sa {JSON Support in Qt}, {JSON Save Game Example} */ /*! -- cgit v1.2.3 From 61948f84da12432b9b8b178875a86f54fef12e32 Mon Sep 17 00:00:00 2001 From: J-P Nurmi Date: Thu, 22 Aug 2013 17:43:54 +0300 Subject: Fix scrollbar appearance on Win8 Task-number: QTBUG-26503 Change-Id: Id74821e005483d05450467fcaea672bbf35113bc Reviewed-by: Jens Bache-Wiig --- src/widgets/styles/qwindowsvistastyle.cpp | 46 ++++++++++++++++--------------- 1 file changed, 24 insertions(+), 22 deletions(-) (limited to 'src') diff --git a/src/widgets/styles/qwindowsvistastyle.cpp b/src/widgets/styles/qwindowsvistastyle.cpp index e442e53bde..22458eb96f 100644 --- a/src/widgets/styles/qwindowsvistastyle.cpp +++ b/src/widgets/styles/qwindowsvistastyle.cpp @@ -1830,29 +1830,31 @@ void QWindowsVistaStyle::drawComplexControl(ComplexControl control, const QStyle int gw = size.cx, gh = size.cy; - QRect gripperBounds; - if (flags & State_Horizontal && ((swidth - contentsMargin.cxLeftWidth - contentsMargin.cxRightWidth) > gw)) { - gripperBounds.setLeft(theme.rect.left() + swidth/2 - gw/2); - gripperBounds.setTop(theme.rect.top() + sheight/2 - gh/2); - gripperBounds.setWidth(gw); - gripperBounds.setHeight(gh); - } else if ((sheight - contentsMargin.cyTopHeight - contentsMargin.cyBottomHeight) > gh) { - gripperBounds.setLeft(theme.rect.left() + swidth/2 - gw/2); - gripperBounds.setTop(theme.rect.top() + sheight/2 - gh/2); - gripperBounds.setWidth(gw); - gripperBounds.setHeight(gh); - } + if (QSysInfo::WindowsVersion < QSysInfo::WV_WINDOWS8) { + QRect gripperBounds; + if (flags & State_Horizontal && ((swidth - contentsMargin.cxLeftWidth - contentsMargin.cxRightWidth) > gw)) { + gripperBounds.setLeft(theme.rect.left() + swidth/2 - gw/2); + gripperBounds.setTop(theme.rect.top() + sheight/2 - gh/2); + gripperBounds.setWidth(gw); + gripperBounds.setHeight(gh); + } else if ((sheight - contentsMargin.cyTopHeight - contentsMargin.cyBottomHeight) > gh) { + gripperBounds.setLeft(theme.rect.left() + swidth/2 - gw/2); + gripperBounds.setTop(theme.rect.top() + sheight/2 - gh/2); + gripperBounds.setWidth(gw); + gripperBounds.setHeight(gh); + } - // Draw gripper if there is enough space - if (!gripperBounds.isEmpty() && flags & State_Enabled) { - painter->save(); - XPThemeData grippBackground = theme; - grippBackground.partId = flags & State_Horizontal ? SBP_LOWERTRACKHORZ : SBP_LOWERTRACKVERT; - theme.rect = gripperBounds; - painter->setClipRegion(d->region(theme));// Only change inside the region of the gripper - d->drawBackground(grippBackground);// The gutter is the grippers background - d->drawBackground(theme); // Transparent gripper ontop of background - painter->restore(); + // Draw gripper if there is enough space + if (!gripperBounds.isEmpty() && flags & State_Enabled) { + painter->save(); + XPThemeData grippBackground = theme; + grippBackground.partId = flags & State_Horizontal ? SBP_LOWERTRACKHORZ : SBP_LOWERTRACKVERT; + theme.rect = gripperBounds; + painter->setClipRegion(d->region(theme));// Only change inside the region of the gripper + d->drawBackground(grippBackground);// The gutter is the grippers background + d->drawBackground(theme); // Transparent gripper ontop of background + painter->restore(); + } } } } -- cgit v1.2.3 From 2af8feee929c8b07f4243d99f6a539e6d17ced85 Mon Sep 17 00:00:00 2001 From: Gabriel de Dietrich Date: Wed, 21 Aug 2013 17:04:58 +0200 Subject: Cocoa: Bring back old exposure behavior on Mac OS X 10.6 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Task-number: QTBUG-31864 Change-Id: Ife2429b2d6b845e5ccca31a03e66351a3ff5ba4b Reviewed-by: Morten Johan Sørvig --- src/plugins/platforms/cocoa/qnsview.mm | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'src') diff --git a/src/plugins/platforms/cocoa/qnsview.mm b/src/plugins/platforms/cocoa/qnsview.mm index a949bb3ea5..4505f8b8cf 100644 --- a/src/plugins/platforms/cocoa/qnsview.mm +++ b/src/plugins/platforms/cocoa/qnsview.mm @@ -285,6 +285,10 @@ static QTouchDevice *touchDevice = 0; Qt::WindowState newState = notificationName == NSWindowDidMiniaturizeNotification ? Qt::WindowMinimized : Qt::WindowNoState; [self notifyWindowStateChanged:newState]; + // NSWindowDidOrderOnScreenAndFinishAnimatingNotification is private API, and not + // emitted in 10.6, so we bring back the old behavior for that case alone. + if (newState == Qt::WindowNoState && QSysInfo::QSysInfo::MacintoshVersion == QSysInfo::MV_10_6) + m_platformWindow->exposeWindow(); } else if ([notificationName isEqualToString: @"NSWindowDidOrderOffScreenNotification"]) { m_platformWindow->obscureWindow(); } else if ([notificationName isEqualToString: @"NSWindowDidOrderOnScreenAndFinishAnimatingNotification"]) { -- cgit v1.2.3 From 10e23c84d5cbd40ca054a2040e0fac38c248b34d Mon Sep 17 00:00:00 2001 From: Gabriel de Dietrich Date: Wed, 14 Aug 2013 19:06:34 +0200 Subject: Style: Remove useless background paint for menu scroller This would also cause an extra paint in QQuickStyleItem, resulting in the frame being erased for those styles not having a frame width set (e.g., fusion and GTK). Change-Id: I7a9371c540cd31fd9f1400a51c4ec57582996dd2 Reviewed-by: Jens Bache-Wiig --- src/widgets/styles/qcommonstyle.cpp | 1 - 1 file changed, 1 deletion(-) (limited to 'src') diff --git a/src/widgets/styles/qcommonstyle.cpp b/src/widgets/styles/qcommonstyle.cpp index 936eb76dad..ba6c222820 100644 --- a/src/widgets/styles/qcommonstyle.cpp +++ b/src/widgets/styles/qcommonstyle.cpp @@ -1329,7 +1329,6 @@ void QCommonStyle::drawControl(ControlElement element, const QStyleOption *opt, break; #ifndef QT_NO_MENU case CE_MenuScroller: { - p->fillRect(opt->rect, opt->palette.background()); QStyleOption arrowOpt = *opt; arrowOpt.state |= State_Enabled; proxy()->drawPrimitive(((opt->state & State_DownArrow) ? PE_IndicatorArrowDown : PE_IndicatorArrowUp), -- cgit v1.2.3 From 68563cdabd3b9ff1f9ebba98f700ea70e085ded8 Mon Sep 17 00:00:00 2001 From: Gabriel de Dietrich Date: Mon, 19 Aug 2013 12:53:41 +0200 Subject: Cocoa: Fix memory leak in event dispatcher MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit We retain each modal NSWindow as long as its modal session is running, and we should release it every time that modal session ends. Task-number: QTBUG-32728 Change-Id: Ia30c9c2d15be1350e7150a0d3c2f530a2fe4f38b Reviewed-by: Morten Johan Sørvig --- src/plugins/platforms/cocoa/qcocoaeventdispatcher.mm | 1 + 1 file changed, 1 insertion(+) (limited to 'src') diff --git a/src/plugins/platforms/cocoa/qcocoaeventdispatcher.mm b/src/plugins/platforms/cocoa/qcocoaeventdispatcher.mm index 2ac9a5dac9..9a661ffe5a 100644 --- a/src/plugins/platforms/cocoa/qcocoaeventdispatcher.mm +++ b/src/plugins/platforms/cocoa/qcocoaeventdispatcher.mm @@ -594,6 +594,7 @@ void QCocoaEventDispatcherPrivate::temporarilyStopAllModalSessions() if (info.session) { [NSApp endModalSession:info.session]; info.session = 0; + [(NSWindow*) info.nswindow release]; } } currentModalSessionCached = 0; -- cgit v1.2.3 From b4252802b3a537268b83855d2e13390bd5aedf5c Mon Sep 17 00:00:00 2001 From: BogDan Vatra Date: Wed, 14 Aug 2013 14:22:25 +0300 Subject: Switch back to thumb for android armeabi. Add workaround for gcc 4.8 compile bug. Change-Id: Ie7a81ec25a79764989bbd9eb43dd5a8fbf442dfc Reviewed-by: Eskil Abrahamsen Blomfeldt Reviewed-by: Oswald Buddenhagen --- src/gui/text/qcssparser.cpp | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'src') diff --git a/src/gui/text/qcssparser.cpp b/src/gui/text/qcssparser.cpp index 1264330873..b486ec05fa 100644 --- a/src/gui/text/qcssparser.cpp +++ b/src/gui/text/qcssparser.cpp @@ -583,7 +583,11 @@ bool ValueExtractor::extractBorder(int *borders, QBrush *colors, BorderStyle *st case BorderRightStyle: styles[RightEdge] = decl.styleValue(); break; case BorderStyles: decl.styleValues(styles); break; +#ifndef QT_OS_ANDROID_GCC_48_WORKAROUND case BorderTopLeftRadius: radii[0] = sizeValue(decl); break; +#else + case BorderTopLeftRadius: new(radii)QSize(sizeValue(decl)); break; +#endif case BorderTopRightRadius: radii[1] = sizeValue(decl); break; case BorderBottomLeftRadius: radii[2] = sizeValue(decl); break; case BorderBottomRightRadius: radii[3] = sizeValue(decl); break; -- cgit v1.2.3 From 4994300fe7c7ba9dd391b2453b4c5297f9d7a6ba Mon Sep 17 00:00:00 2001 From: Rafael Roquetto Date: Wed, 31 Jul 2013 15:27:07 -0300 Subject: Playbook: Fix rendering when thumbnailed/minimized On Playbook, rendering should happen when the application is thumbnailed, therefore we need to send a window activated event to resume rendering once the thumbnail is restored from the minimized state. Change-Id: I0fa5da483dc101e25f718e52859a66edfe5c66c7 Reviewed-by: Bernd Weimer Reviewed-by: Fabian Bumberger Reviewed-by: Nicolas Arnaud-Cormos --- src/plugins/platforms/qnx/qqnxbpseventfilter.cpp | 3 +++ 1 file changed, 3 insertions(+) (limited to 'src') diff --git a/src/plugins/platforms/qnx/qqnxbpseventfilter.cpp b/src/plugins/platforms/qnx/qqnxbpseventfilter.cpp index d94d3c092a..aadefec8d1 100644 --- a/src/plugins/platforms/qnx/qqnxbpseventfilter.cpp +++ b/src/plugins/platforms/qnx/qqnxbpseventfilter.cpp @@ -221,6 +221,9 @@ bool QQnxBpsEventFilter::handleNavigatorEvent(bps_event_t *event) break; case NAVIGATOR_WINDOW_THUMBNAIL: m_navigatorEventHandler->handleWindowGroupStateChanged(id, Qt::WindowMinimized); +#if defined(Q_OS_BLACKBERRY_TABLET) + m_navigatorEventHandler->handleWindowGroupActivated(id); +#endif break; case NAVIGATOR_WINDOW_INVISIBLE: m_navigatorEventHandler->handleWindowGroupDeactivated(id); -- cgit v1.2.3 From 9de6d1a74ff1f172f164a3c916424a1cc4eb4ade Mon Sep 17 00:00:00 2001 From: Rafael Roquetto Date: Wed, 31 Jul 2013 15:43:33 -0300 Subject: BB10: Do not send deactivate event twice On BB10, NAVIGATOR_WINDOW_INACTIVE is called before NAVIGATOR_WINDOW_INVISIBLE, already triggering handleWindowGroupDeactivated() Change-Id: I7d82c0220fe8dc8e87bfa2b31af6085c7d1d6cee Reviewed-by: Kevin Krammer Reviewed-by: Bernd Weimer Reviewed-by: Nicolas Arnaud-Cormos --- src/plugins/platforms/qnx/qqnxbpseventfilter.cpp | 2 ++ 1 file changed, 2 insertions(+) (limited to 'src') diff --git a/src/plugins/platforms/qnx/qqnxbpseventfilter.cpp b/src/plugins/platforms/qnx/qqnxbpseventfilter.cpp index aadefec8d1..e723e32301 100644 --- a/src/plugins/platforms/qnx/qqnxbpseventfilter.cpp +++ b/src/plugins/platforms/qnx/qqnxbpseventfilter.cpp @@ -226,7 +226,9 @@ bool QQnxBpsEventFilter::handleNavigatorEvent(bps_event_t *event) #endif break; case NAVIGATOR_WINDOW_INVISIBLE: +#if defined(Q_OS_BLACKBERRY_TABLET) m_navigatorEventHandler->handleWindowGroupDeactivated(id); +#endif break; } -- cgit v1.2.3 From 1f8c179c6cd6d6c79e5bbd1a85e3d4252eeafa79 Mon Sep 17 00:00:00 2001 From: Takumi Asaki Date: Wed, 21 Aug 2013 18:04:44 +0900 Subject: Doc: Add Q_OS_ANDROID macro Change-Id: If428f0b7c1540e809f756f426a6d222acea5d310 Reviewed-by: Eskil Abrahamsen Blomfeldt --- src/corelib/global/qglobal.cpp | 7 +++++++ 1 file changed, 7 insertions(+) (limited to 'src') diff --git a/src/corelib/global/qglobal.cpp b/src/corelib/global/qglobal.cpp index 85cb698afc..6e5de68b01 100644 --- a/src/corelib/global/qglobal.cpp +++ b/src/corelib/global/qglobal.cpp @@ -1165,6 +1165,13 @@ bool qSharedBuild() Q_DECL_NOTHROW Defined on Linux. */ +/*! + \macro Q_OS_ANDROID + \relates + + Defined on Android. +*/ + /*! \macro Q_OS_FREEBSD \relates -- cgit v1.2.3 From bd00b51c47f986dd2f8b7696b09f10f19321a99e Mon Sep 17 00:00:00 2001 From: Uli Schlachter Date: Thu, 22 Aug 2013 14:31:10 +0200 Subject: XCB: Fix race with the event thread The XCB backend runs a thread which gets events out of the XCB event queue and feeds it to the main thread via another queue. This queue is protected by a mutex. However, when the event thread exits, it cleans up after itself and frees all remaining entries in the queue. This code messed with the event queue without acquiring the needed mutex and left behind a list full of stale pointers. Fix this and protect the freeing with the correct mutex and clear the event queue afterwards. Change-Id: Ie49cf6241b76be86d8cebbc931f7226a3f6a14e5 Signed-off-by: Uli Schlachter Reviewed-by: Friedemann Kleint Reviewed-by: Shawn Rutledge --- src/plugins/platforms/xcb/qxcbconnection.cpp | 3 +++ 1 file changed, 3 insertions(+) (limited to 'src') diff --git a/src/plugins/platforms/xcb/qxcbconnection.cpp b/src/plugins/platforms/xcb/qxcbconnection.cpp index 01af23377e..2ce34ea8f2 100644 --- a/src/plugins/platforms/xcb/qxcbconnection.cpp +++ b/src/plugins/platforms/xcb/qxcbconnection.cpp @@ -989,8 +989,11 @@ void QXcbEventReader::run() emit eventPending(); } + m_mutex.lock(); for (int i = 0; i < m_events.size(); ++i) free(m_events.at(i)); + m_events.clear(); + m_mutex.unlock(); } void QXcbEventReader::addEvent(xcb_generic_event_t *event) -- cgit v1.2.3 From 3e7c77cfaeab06d20945fcaba2fe25cdaa5a74be Mon Sep 17 00:00:00 2001 From: Nico Vertriest Date: Wed, 21 Aug 2013 17:12:37 +0200 Subject: Doc: minimal qdocconf file with comments Task-number: QTBUG-31801 Change-Id: Ia94989b066ab2cd4d6dbf64261b5d9b4207db12a Reviewed-by: Martin Smith --- src/tools/qdoc/doc/qdoc-minimum-qdocconf.qdoc | 86 +++++++++++++++++++++++++++ 1 file changed, 86 insertions(+) create mode 100644 src/tools/qdoc/doc/qdoc-minimum-qdocconf.qdoc (limited to 'src') diff --git a/src/tools/qdoc/doc/qdoc-minimum-qdocconf.qdoc b/src/tools/qdoc/doc/qdoc-minimum-qdocconf.qdoc new file mode 100644 index 0000000000..4289f357e9 --- /dev/null +++ b/src/tools/qdoc/doc/qdoc-minimum-qdocconf.qdoc @@ -0,0 +1,86 @@ +/**************************************************************************** +** +** Copyright (C) 2013 Digia Plc and/or its subsidiary(-ies). +** Contact: http://www.qt-project.org/legal +** +** This file is part of the documentation of the Qt Toolkit. +** +** $QT_BEGIN_LICENSE:FDL$ +** 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 Digia. For licensing terms and +** conditions see http://qt.digia.com/licensing. For further information +** use the contact form at http://qt.digia.com/contact-us. +** +** GNU Free Documentation License Usage +** Alternatively, this file may be used under the terms of the GNU Free +** Documentation License version 1.3 as published by the Free Software +** Foundation and appearing in the file included in the packaging of +** this file. Please review the following information to ensure +** the GNU Free Documentation License version 1.3 requirements +** will be met: http://www.gnu.org/copyleft/fdl.html. +** $QT_END_LICENSE$ +** +****************************************************************************/ +/*! +\page qdoc-minimum-qdocconf.html +\title A minimal qdocconf file with comments + +\brief Describes a minimal .qdocconf file + +Below you will find the full contents of qtgui.qdocconf. The subsequent section will discuss +every statement in the qdocconf file. + +\code + #include(compat.qdocconf) + outputdir = html + headerdirs = . + sourcedirs = . + exampledirs = . + imagedirs = ./images +\endcode + +\title Notes + +\code + #include(compat.qdocconf) +\endcode + +For compatibility with older versions of Qt, it is recommended +to include compat.qdocconf. + +\code + outputdir = html +\endcode + +QDoc will put the documentation generated in the html directory. + +\code + headerdirs = . +\endcode + +The header file associated with the \e .cpp source files can be found in the +current directory. + +\code + sourcedirs = . +\endcode + +The current directory is the directory containing the source files: the \e .cpp +and \e .qdoc files used in the documentation. + +\code + exampledirs = . +\endcode + +The source code of the example files can be found in the current directory. + +\code + imagedirs = ./images +\endcode + +The image files can be found in the underlying directory "images". + +*/ -- cgit v1.2.3 From 6d0d5a2adeff94fa483c8d6b370493e604f77ccd Mon Sep 17 00:00:00 2001 From: Nico Vertriest Date: Thu, 22 Aug 2013 10:28:36 +0200 Subject: Doc: added excludedirs to qdocconf example. Corrected style issues pointed out in review. Task-number: QTBUG-31801 Change-Id: Ibbc4e5f8dcd8ca129ae945b5e62b15daed47d86d Reviewed-by: Martin Smith --- src/tools/qdoc/doc/qtgui-qdocconf.qdoc | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) (limited to 'src') diff --git a/src/tools/qdoc/doc/qtgui-qdocconf.qdoc b/src/tools/qdoc/doc/qtgui-qdocconf.qdoc index 7e6da0feb5..767934986f 100644 --- a/src/tools/qdoc/doc/qtgui-qdocconf.qdoc +++ b/src/tools/qdoc/doc/qtgui-qdocconf.qdoc @@ -83,6 +83,8 @@ every statement in the qdocconf file. sourcedirs += .. \ ../../../examples/gui/doc/src + excludedirs = ../../../examples/gui/doc/src/tmp + exampledirs += ../../../examples/gui \ snippets @@ -272,15 +274,31 @@ associated with the \e .cpp source files. Add the specified directories to the list of directories containing the \e .cpp and \e .qdoc files used in the documentation. +\code + excludedirs = ../../../examples/gui/doc/src/tmp +\endcode + +The \c excludedirs variable is for listing directories that should not be processed +by qdoc, even if the same directories are included by the \c sourcedirs or \c headerdirs +variables. + +When executed, QDoc will ignore the directories listed. +\sa excludefiles + \code exampledirs += ../../../examples/gui \ snippets \endcode +\sa examples \sa examplesinstallpath Add the two directories specified to the list of directories containing the source code of the example files. +If QDoc encounters both \c exampledirs and \c examples, it will look first in the +\c examples directory. QDoc will accept the first matching file it finds. QDoc will +search in the directories specified, not in their subdirectories. + \code imagedirs += images \ ../../../examples/gui/doc/images \ -- cgit v1.2.3 From 9194fc00a61379fa9ccd4b05c480f67b2fb739bc Mon Sep 17 00:00:00 2001 From: Friedemann Kleint Date: Thu, 22 Aug 2013 16:06:51 +0200 Subject: Windows: Keep monitors when system is locked. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Prevent windows from being recreated due to screen changes which can cause GL widgets to stop updating among other things. EnumMonitors returns only one temporary monitor named "WinDisc" when locked. Do not remove monitors when that happens. Task-number: QTBUG-33062 Change-Id: Ia2247bb04b3e10f99f594245f84238b5f9044f70 Reviewed-by: Jan Arve Sæther Reviewed-by: Shawn Rutledge --- src/plugins/platforms/windows/qwindowsscreen.cpp | 68 ++++++++++++++---------- src/plugins/platforms/windows/qwindowsscreen.h | 3 +- 2 files changed, 41 insertions(+), 30 deletions(-) (limited to 'src') diff --git a/src/plugins/platforms/windows/qwindowsscreen.cpp b/src/plugins/platforms/windows/qwindowsscreen.cpp index f616972aa0..530ebc38b7 100644 --- a/src/plugins/platforms/windows/qwindowsscreen.cpp +++ b/src/plugins/platforms/windows/qwindowsscreen.cpp @@ -98,35 +98,39 @@ BOOL QT_WIN_CALLBACK monitorEnumCallback(HMONITOR hMonitor, HDC, LPRECT, LPARAM WindowsScreenDataList *result = reinterpret_cast(p); QWindowsScreenData data; data.geometry = QRect(QPoint(info.rcMonitor.left, info.rcMonitor.top), QPoint(info.rcMonitor.right - 1, info.rcMonitor.bottom - 1)); + data.name = QString::fromWCharArray(info.szDevice); + if (data.name == QLatin1String("WinDisc")) { + data.flags |= QWindowsScreenData::LockScreen; + } else { #ifdef Q_OS_WINCE - //Windows CE, just supports one Display and expects to get only DISPLAY, - //instead of DISPLAY0 and so on, which are passed by info.szDevice - HDC hdc = CreateDC(TEXT("DISPLAY"), NULL, NULL, NULL); + //Windows CE, just supports one Display and expects to get only DISPLAY, + //instead of DISPLAY0 and so on, which are passed by info.szDevice + HDC hdc = CreateDC(TEXT("DISPLAY"), NULL, NULL, NULL); #else - HDC hdc = CreateDC(info.szDevice, NULL, NULL, NULL); + HDC hdc = CreateDC(info.szDevice, NULL, NULL, NULL); #endif - if (hdc) { - data.dpi = deviceDPI(hdc); - data.depth = GetDeviceCaps(hdc, BITSPIXEL); - data.format = data.depth == 16 ? QImage::Format_RGB16 : QImage::Format_RGB32; - data.physicalSizeMM = QSizeF(GetDeviceCaps(hdc, HORZSIZE), GetDeviceCaps(hdc, VERTSIZE)); - const int refreshRate = GetDeviceCaps(hdc, VREFRESH); - if (refreshRate > 1) // 0,1 means heardware default. - data.refreshRateHz = refreshRate; - DeleteDC(hdc); - } else { - qWarning("%s: Unable to obtain handle for monitor '%s', defaulting to %g DPI.", - __FUNCTION__, qPrintable(QString::fromWCharArray(info.szDevice)), - data.dpi.first); - } + if (hdc) { + data.dpi = deviceDPI(hdc); + data.depth = GetDeviceCaps(hdc, BITSPIXEL); + data.format = data.depth == 16 ? QImage::Format_RGB16 : QImage::Format_RGB32; + data.physicalSizeMM = QSizeF(GetDeviceCaps(hdc, HORZSIZE), GetDeviceCaps(hdc, VERTSIZE)); + const int refreshRate = GetDeviceCaps(hdc, VREFRESH); + if (refreshRate > 1) // 0,1 means hardware default. + data.refreshRateHz = refreshRate; + DeleteDC(hdc); + } else { + qWarning("%s: Unable to obtain handle for monitor '%s', defaulting to %g DPI.", + __FUNCTION__, qPrintable(QString::fromWCharArray(info.szDevice)), + data.dpi.first); + } // CreateDC() failed + } // not lock screen data.geometry = QRect(QPoint(info.rcMonitor.left, info.rcMonitor.top), QPoint(info.rcMonitor.right - 1, info.rcMonitor.bottom - 1)); data.availableGeometry = QRect(QPoint(info.rcWork.left, info.rcWork.top), QPoint(info.rcWork.right - 1, info.rcWork.bottom - 1)); data.orientation = data.geometry.height() > data.geometry.width() ? Qt::PortraitOrientation : Qt::LandscapeOrientation; // EnumDisplayMonitors (as opposed to EnumDisplayDevices) enumerates only // virtual desktop screens. - data.name = QString::fromWCharArray(info.szDevice); - data.flags = QWindowsScreenData::VirtualDesktop; + data.flags |= QWindowsScreenData::VirtualDesktop; if (info.dwFlags & MONITORINFOF_PRIMARY) { data.flags |= QWindowsScreenData::PrimaryScreen; // QPlatformIntegration::screenAdded() documentation specifies that first @@ -162,6 +166,8 @@ static QDebug operator<<(QDebug dbg, const QWindowsScreenData &d) nospace << " primary"; if (d.flags & QWindowsScreenData::VirtualDesktop) nospace << " virtual desktop"; + if (d.flags & QWindowsScreenData::LockScreen) + nospace << " lock screen"; return dbg; } @@ -392,7 +398,8 @@ static inline int indexOfMonitor(const QList &screenData, bool QWindowsScreenManager::handleScreenChanges() { // Look for changed monitors, add new ones - const WindowsScreenDataList newDataList = monitorData(); + WindowsScreenDataList newDataList = monitorData(); + const bool lockScreen = newDataList.size() == 1 && (newDataList.front().flags & QWindowsScreenData::LockScreen); foreach (const QWindowsScreenData &newData, newDataList) { const int existingIndex = indexOfMonitor(m_screens, newData.name); if (existingIndex != -1) { @@ -405,14 +412,17 @@ bool QWindowsScreenManager::handleScreenChanges() qDebug() << "New Monitor: " << newData; } // exists } // for new screens. - // Remove deleted ones. - for (int i = m_screens.size() - 1; i >= 0; --i) { - if (indexOfMonitor(newDataList, m_screens.at(i)->data().name) == -1) { - if (QWindowsContext::verboseWindows) - qDebug() << "Removing Monitor: " << m_screens.at(i) ->data(); - delete m_screens.takeAt(i); - } // not found - } // for existing screens + // Remove deleted ones but keep main monitors if we get only the + // temporary lock screen to avoid window recreation (QTBUG-33062). + if (!lockScreen) { + for (int i = m_screens.size() - 1; i >= 0; --i) { + if (indexOfMonitor(newDataList, m_screens.at(i)->data().name) == -1) { + if (QWindowsContext::verboseWindows) + qDebug() << "Removing Monitor: " << m_screens.at(i) ->data(); + delete m_screens.takeAt(i); + } // not found + } // for existing screens + } // not lock screen return true; } diff --git a/src/plugins/platforms/windows/qwindowsscreen.h b/src/plugins/platforms/windows/qwindowsscreen.h index 216973125b..930814a17d 100644 --- a/src/plugins/platforms/windows/qwindowsscreen.h +++ b/src/plugins/platforms/windows/qwindowsscreen.h @@ -59,7 +59,8 @@ struct QWindowsScreenData enum Flags { PrimaryScreen = 0x1, - VirtualDesktop = 0x2 + VirtualDesktop = 0x2, + LockScreen = 0x4 // Temporary screen existing during user change, etc. }; QWindowsScreenData(); -- cgit v1.2.3 From 79570157e3f2d49a016a63fbf3a2e6e00da08fe9 Mon Sep 17 00:00:00 2001 From: Daiwei Li Date: Tue, 13 Aug 2013 15:41:04 -0700 Subject: Return 1.0 for devicePixelRatio in QCocoaWindow if no valid window MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit If m_window is invalid, devicePixelRatio returns 0, which leads to adverse effects in other parts of the code. For example, qquickshadereffectsource.cpp will get stuck in an infinite loop trying to multiply 0 by 2. Task-number: QTBUG-32975 Change-Id: Ie3db86f1f459df018ebce67bcb4226f6cffe854e Reviewed-by: Morten Johan Sørvig --- src/plugins/platforms/cocoa/qcocoawindow.mm | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/plugins/platforms/cocoa/qcocoawindow.mm b/src/plugins/platforms/cocoa/qcocoawindow.mm index 26869d4b5f..86f12e0e5f 100644 --- a/src/plugins/platforms/cocoa/qcocoawindow.mm +++ b/src/plugins/platforms/cocoa/qcocoawindow.mm @@ -1007,7 +1007,12 @@ qreal QCocoaWindow::devicePixelRatio() const { #if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_7 if (QSysInfo::MacintoshVersion >= QSysInfo::MV_10_7) { - return qreal([[m_contentView window] backingScaleFactor]); + NSWindow* window = [m_contentView window]; + if (window) { + return qreal([window backingScaleFactor]); + } else { + return 1.0; + } } else #endif { -- cgit v1.2.3 From f738a4a5d5f62c1136b5820a89c9b47080d150a4 Mon Sep 17 00:00:00 2001 From: Friedemann Kleint Date: Thu, 22 Aug 2013 11:40:58 +0200 Subject: Do not recreate window if it is moved to a virtual sibling screen. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Task-number: QTBUG-32681 Task-number: QTBUG-33062 Change-Id: Id37627231b7a129c398d90d3f01ded6bd5171088 Reviewed-by: Jan Arve Sæther Reviewed-by: Shawn Rutledge --- src/gui/kernel/qwindow.cpp | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) (limited to 'src') diff --git a/src/gui/kernel/qwindow.cpp b/src/gui/kernel/qwindow.cpp index 9ef19715ed..490cf0c110 100644 --- a/src/gui/kernel/qwindow.cpp +++ b/src/gui/kernel/qwindow.cpp @@ -348,8 +348,9 @@ void QWindowPrivate::updateVisibility() void QWindowPrivate::setScreen(QScreen *newScreen, bool recreate) { Q_Q(QWindow); - if (newScreen != q->screen()) { - const bool shouldRecreate = recreate && platformWindow != 0; + if (newScreen != screen) { + const bool shouldRecreate = recreate && platformWindow != 0 + && !(screen && screen->virtualSiblings().contains(newScreen)); if (shouldRecreate) q->destroy(); if (screen) -- cgit v1.2.3 From ca772b2f2f5a8981d0c44dfb278e84f546d53cb2 Mon Sep 17 00:00:00 2001 From: Thiago Macieira Date: Thu, 22 Aug 2013 18:21:23 -0700 Subject: Ensure the docs for QOpenGLFunctions_ES2 are generated qdoc runs the preprocessor, so it probably skipped the definition for this class. Change-Id: I10933134d0c20131dd25e15bee914ebfac358b10 Reviewed-by: Robin Burchell Reviewed-by: James Turner Reviewed-by: Sean Harmer --- src/gui/opengl/qopenglfunctions_es2.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src') diff --git a/src/gui/opengl/qopenglfunctions_es2.h b/src/gui/opengl/qopenglfunctions_es2.h index 9c14567723..21ed6bec93 100644 --- a/src/gui/opengl/qopenglfunctions_es2.h +++ b/src/gui/opengl/qopenglfunctions_es2.h @@ -44,7 +44,7 @@ #include -#if defined(QT_OPENGL_ES_2) +#if defined(QT_OPENGL_ES_2) || defined(Q_QDOC) #include #include -- cgit v1.2.3 From 362ea2dedeeca351ae36fcf860cc47b2f12830cf Mon Sep 17 00:00:00 2001 From: Thiago Macieira Date: Tue, 20 Aug 2013 11:30:11 -0700 Subject: Soft-deprecate obscure feature on property getters returning pointers moc actually generates the right code for getters returning a pointer to the type in question, or a reference to the type (a reference, one would assume, does not require code changes). However, the same extension is not valid for the setter: it can't receive the new value by pointer. Therefore, let's soft-deprecate the feature by removing its existence from the documentation. Task-number: QTBUG-33091 Change-Id: I27844213e051ec7fafeb4744089a0653aea6f1f3 Reviewed-by: Olivier Goffart Reviewed-by: Jerome Pasion --- src/corelib/doc/src/objectmodel/properties.qdoc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src') diff --git a/src/corelib/doc/src/objectmodel/properties.qdoc b/src/corelib/doc/src/objectmodel/properties.qdoc index d1690c5908..70f0b88e06 100644 --- a/src/corelib/doc/src/objectmodel/properties.qdoc +++ b/src/corelib/doc/src/objectmodel/properties.qdoc @@ -67,7 +67,7 @@ \li A \c READ accessor function is required if no \c MEMBER variable was specified. It is for reading the property value. Ideally, a const function is used for this purpose, and it must return either the property's type or a - pointer or reference to that type. e.g., QWidget::focus is a read-only + const reference to that type. e.g., QWidget::focus is a read-only property with \c READ function, QWidget::hasFocus(). \li A \c WRITE accessor function is optional. It is for setting the -- cgit v1.2.3 From 64a1448d87727878d9789906b2f4f5b9e3d74e38 Mon Sep 17 00:00:00 2001 From: Thiago Macieira Date: Tue, 9 Jul 2013 00:10:35 -0700 Subject: Update Linux interface getting to make fewer syscalls Each time we call if_nametoindex, if_indextoname or somesuch, the libc needs to open a socket, make an ioctl, and close the socket. Since we've got most of the information we need anyway in the data from getifaddrs(3), let's just use it Change-Id: I572c212a27c4b9ffe57980b36f75bb04e6d5cf29 Reviewed-by: Jonas Gastal Reviewed-by: Richard J. Moore --- src/network/kernel/qnetworkinterface_unix.cpp | 58 +++++++++++++-------------- 1 file changed, 29 insertions(+), 29 deletions(-) (limited to 'src') diff --git a/src/network/kernel/qnetworkinterface_unix.cpp b/src/network/kernel/qnetworkinterface_unix.cpp index b090213861..01c082059f 100644 --- a/src/network/kernel/qnetworkinterface_unix.cpp +++ b/src/network/kernel/qnetworkinterface_unix.cpp @@ -312,38 +312,38 @@ QT_END_INCLUDE_NAMESPACE static QList createInterfaces(ifaddrs *rawList) { QList interfaces; + QSet seenInterfaces; + // on Linux, AF_PACKET addresses carry the hardware address and interface index; + // scan for them first (they're usually first, but we have no guarantee this + // will be the case forever) for (ifaddrs *ptr = rawList; ptr; ptr = ptr->ifa_next) { - if ( !ptr->ifa_addr ) - continue; - - // Get the interface index - int ifindex = if_nametoindex(ptr->ifa_name); + if (ptr->ifa_addr && ptr->ifa_addr->sa_family == AF_PACKET) { + sockaddr_ll *sll = (sockaddr_ll *)ptr->ifa_addr; + QNetworkInterfacePrivate *iface = new QNetworkInterfacePrivate; + interfaces << iface; + iface->index = sll->sll_ifindex; + iface->name = QString::fromLatin1(ptr->ifa_name); + iface->flags = convertFlags(ptr->ifa_flags); + iface->hardwareAddress = iface->makeHwAddress(sll->sll_halen, (uchar*)sll->sll_addr); - // on Linux we use AF_PACKET and sockaddr_ll to obtain hHwAddress - QList::Iterator if_it = interfaces.begin(); - for ( ; if_it != interfaces.end(); ++if_it) - if ((*if_it)->index == ifindex) { - // this one has been added already - if ( ptr->ifa_addr->sa_family == AF_PACKET - && (*if_it)->hardwareAddress.isEmpty()) { - sockaddr_ll *sll = (sockaddr_ll *)ptr->ifa_addr; - (*if_it)->hardwareAddress = (*if_it)->makeHwAddress(sll->sll_halen, (uchar*)sll->sll_addr); - } - break; - } - if ( if_it != interfaces.end() ) - continue; + seenInterfaces.insert(iface->name); + } + } - QNetworkInterfacePrivate *iface = new QNetworkInterfacePrivate; - interfaces << iface; - iface->index = ifindex; - iface->name = QString::fromLatin1(ptr->ifa_name); - iface->flags = convertFlags(ptr->ifa_flags); + // see if we missed anything: + // virtual interfaces with no HW address have no AF_PACKET + for (ifaddrs *ptr = rawList; ptr; ptr = ptr->ifa_next) { + if (ptr->ifa_addr && ptr->ifa_addr->sa_family != AF_PACKET) { + QString name = QString::fromLatin1(ptr->ifa_name); + if (seenInterfaces.contains(name)) + continue; - if ( ptr->ifa_addr->sa_family == AF_PACKET ) { - sockaddr_ll *sll = (sockaddr_ll *)ptr->ifa_addr; - iface->hardwareAddress = iface->makeHwAddress(sll->sll_halen, (uchar*)sll->sll_addr); + QNetworkInterfacePrivate *iface = new QNetworkInterfacePrivate; + interfaces << iface; + iface->name = name; + iface->flags = convertFlags(ptr->ifa_flags); + iface->index = if_nametoindex(ptr->ifa_name); } } @@ -423,11 +423,11 @@ static QList interfaceListing() interfaces = createInterfaces(interfaceListing); for (ifaddrs *ptr = interfaceListing; ptr; ptr = ptr->ifa_next) { // Get the interface index - int ifindex = if_nametoindex(ptr->ifa_name); + QString name = QString::fromLatin1(ptr->ifa_name); QNetworkInterfacePrivate *iface = 0; QList::Iterator if_it = interfaces.begin(); for ( ; if_it != interfaces.end(); ++if_it) - if ((*if_it)->index == ifindex) { + if ((*if_it)->name == name) { // found this interface already iface = *if_it; break; -- cgit v1.2.3 From fa8786c3971ba1614d7b6357a2dcb87fc9cdc91d Mon Sep 17 00:00:00 2001 From: Eskil Abrahamsen Blomfeldt Date: Wed, 21 Aug 2013 14:10:29 +0200 Subject: Android: Fix crash when hitting Back button to quit On Android, it's possible to reach the condition when window == 0 if you hit the Back key, since the previous bail-out is disabled for this case. To avoid a null-pointer dereference, an extra check is required. Change-Id: Ic898cd82dd6e52c24505dd2248c98efcefc15b1c Reviewed-by: Paul Olav Tvete --- src/gui/kernel/qguiapplication.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src') diff --git a/src/gui/kernel/qguiapplication.cpp b/src/gui/kernel/qguiapplication.cpp index 7d2c710c52..6653d5a207 100644 --- a/src/gui/kernel/qguiapplication.cpp +++ b/src/gui/kernel/qguiapplication.cpp @@ -1557,7 +1557,7 @@ void QGuiApplicationPrivate::processKeyEvent(QWindowSystemInterfacePrivate::KeyE ) { return; } - if (window->d_func()->blockedByModalWindow) { + if (window && window->d_func()->blockedByModalWindow) { // a modal window is blocking this window, don't allow key events through return; } -- cgit v1.2.3 From 0ccb75b5fc043820d0759c0559e44be2b620df93 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Christian=20Str=C3=B8mme?= Date: Wed, 10 Jul 2013 14:33:46 +0200 Subject: JNI Convenience: Use isSameObject() when comparing jobjects. Comparing the value of two jobjects are not safe, as it's not guaranteed that two jobjects that is referencing the same object, will have the same value. To make things worse two jobjects might have the same value even though they reference two different objects... Change-Id: I997ea8abfb8c687c342b261bba3848cbbd741633 Reviewed-by: Yoann Lopes --- src/platformsupport/jniconvenience/qjnihelpers_p.h | 18 ++++++++++++------ 1 file changed, 12 insertions(+), 6 deletions(-) (limited to 'src') diff --git a/src/platformsupport/jniconvenience/qjnihelpers_p.h b/src/platformsupport/jniconvenience/qjnihelpers_p.h index fb44d156bd..437a0d039a 100644 --- a/src/platformsupport/jniconvenience/qjnihelpers_p.h +++ b/src/platformsupport/jniconvenience/qjnihelpers_p.h @@ -157,33 +157,39 @@ private: template bool operator==(const QJNILocalRef &ptr1, const QJNILocalRef &ptr2) { - return ptr1.m_obj == ptr2.m_obj; + QAttachedJNIEnv env; + return env->IsSameObject(ptr1.m_obj, ptr2.m_obj); } template bool operator!=(const QJNILocalRef &ptr1, const QJNILocalRef &ptr2) { - return ptr1.m_obj != ptr2.m_obj; + QAttachedJNIEnv env; + return !env->IsSameObject(ptr1.m_obj, ptr2.m_obj); } template bool operator==(const QJNILocalRef &ptr1, X ptr2) { - return ptr1.m_obj == ptr2; + QAttachedJNIEnv env; + return env->IsSameObject(ptr1.m_obj, ptr2); } template bool operator==(T ptr1, const QJNILocalRef &ptr2) { - return ptr1 == ptr2.m_obj; + QAttachedJNIEnv env; + return env->IsSameObject(ptr1, ptr2.m_obj); } template bool operator!=(const QJNILocalRef &ptr1, X ptr2) { - return !(ptr1 == ptr2); + QAttachedJNIEnv env; + return !env->IsSameObject(ptr1.m_obj, ptr2); } template bool operator!=(const T *ptr1, const QJNILocalRef &ptr2) { - return !(ptr2 == ptr1); + QAttachedJNIEnv env; + return !env->IsSameObject(ptr1, ptr2.m_obj); } QT_END_NAMESPACE -- cgit v1.2.3 From 1db13907d938c8e1f4e5c47f009030a69f793127 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Christian=20Str=C3=B8mme?= Date: Wed, 10 Jul 2013 14:53:06 +0200 Subject: JNI Convenience: Make it possible to copy QJNIObjects. Change-Id: I692242147d5f908381ea9d3b393b3c591385efd4 Reviewed-by: Yoann Lopes --- src/platformsupport/jniconvenience/qjniobject.cpp | 267 +++++++++++----------- src/platformsupport/jniconvenience/qjniobject_p.h | 39 +++- 2 files changed, 168 insertions(+), 138 deletions(-) (limited to 'src') diff --git a/src/platformsupport/jniconvenience/qjniobject.cpp b/src/platformsupport/jniconvenience/qjniobject.cpp index 515e82b2f0..1d0bb435aa 100644 --- a/src/platformsupport/jniconvenience/qjniobject.cpp +++ b/src/platformsupport/jniconvenience/qjniobject.cpp @@ -127,7 +127,7 @@ static jfieldID getCachedFieldID(JNIEnv *env, return id; } -QJNIObject::QJNIObject(const char *className) +QJNIObjectPrivate::QJNIObjectPrivate(const char *className) : m_jobject(0) , m_jclass(0) , m_own_jclass(false) @@ -147,7 +147,7 @@ QJNIObject::QJNIObject(const char *className) } } -QJNIObject::QJNIObject(const char *className, const char *sig, ...) +QJNIObjectPrivate::QJNIObjectPrivate(const char *className, const char *sig, va_list args) : m_jobject(0) , m_jclass(0) , m_own_jclass(false) @@ -157,10 +157,7 @@ QJNIObject::QJNIObject(const char *className, const char *sig, ...) if (m_jclass) { jmethodID constructorId = getCachedMethodID(env, m_jclass, "", sig); if (constructorId) { - va_list args; - va_start(args, sig); jobject obj = env->NewObjectV(m_jclass, constructorId, args); - va_end(args); if (obj) { m_jobject = env->NewGlobalRef(obj); env->DeleteLocalRef(obj); @@ -169,7 +166,7 @@ QJNIObject::QJNIObject(const char *className, const char *sig, ...) } } -QJNIObject::QJNIObject(jclass clazz) +QJNIObjectPrivate::QJNIObjectPrivate(jclass clazz) : m_jobject(0) , m_jclass(0) , m_own_jclass(true) @@ -189,7 +186,7 @@ QJNIObject::QJNIObject(jclass clazz) } } -QJNIObject::QJNIObject(jclass clazz, const char *sig, ...) +QJNIObjectPrivate::QJNIObjectPrivate(jclass clazz, const char *sig, va_list args) : m_jobject(0) , m_jclass(0) , m_own_jclass(true) @@ -200,10 +197,7 @@ QJNIObject::QJNIObject(jclass clazz, const char *sig, ...) if (m_jclass) { jmethodID constructorId = getCachedMethodID(env, m_jclass, "", sig); if (constructorId) { - va_list args; - va_start(args, sig); jobject obj = env->NewObjectV(m_jclass, constructorId, args); - va_end(args); if (obj) { m_jobject = env->NewGlobalRef(obj); env->DeleteLocalRef(obj); @@ -213,7 +207,7 @@ QJNIObject::QJNIObject(jclass clazz, const char *sig, ...) } } -QJNIObject::QJNIObject(jobject obj) +QJNIObjectPrivate::QJNIObjectPrivate(jobject obj) : m_jobject(0) , m_jclass(0) , m_own_jclass(true) @@ -223,7 +217,7 @@ QJNIObject::QJNIObject(jobject obj) m_jclass = static_cast(env->NewGlobalRef(env->GetObjectClass(m_jobject))); } -QJNIObject::~QJNIObject() +QJNIObjectPrivate::~QJNIObjectPrivate() { QAttachedJNIEnv env; if (m_jobject) @@ -232,6 +226,23 @@ QJNIObject::~QJNIObject() env->DeleteGlobalRef(m_jclass); } +QJNIObject::QJNIObject(const char *className, const char *sig, ...) +{ + va_list args; + va_start(args, sig); + d = QSharedPointer(new QJNIObjectPrivate(className, sig, args)); + va_end(args); +} + +QJNIObject::QJNIObject(jclass clazz, const char *sig, ...) +{ + va_list args; + va_start(args, sig); + d = QSharedPointer(new QJNIObjectPrivate(clazz, sig, args)); + va_end(args); +} + + bool QJNIObject::isClassAvailable(const char *className) { QAttachedJNIEnv env; @@ -248,11 +259,11 @@ template <> void QJNIObject::callMethod(const char *methodName, const char *sig, ...) { QAttachedJNIEnv env; - jmethodID id = getCachedMethodID(env, m_jclass, methodName, sig); + jmethodID id = getCachedMethodID(env, d->m_jclass, methodName, sig); if (id) { va_list args; va_start(args, sig); - env->CallVoidMethodV(m_jobject, id, args); + env->CallVoidMethodV(d->m_jobject, id, args); va_end(args); } } @@ -262,11 +273,11 @@ jboolean QJNIObject::callMethod(const char *methodName, const char *si { QAttachedJNIEnv env; jboolean res = 0; - jmethodID id = getCachedMethodID(env, m_jclass, methodName, sig); + jmethodID id = getCachedMethodID(env, d->m_jclass, methodName, sig); if (id) { va_list args; va_start(args, sig); - res = env->CallBooleanMethodV(m_jobject, id, args); + res = env->CallBooleanMethodV(d->m_jobject, id, args); va_end(args); } return res; @@ -277,11 +288,11 @@ jbyte QJNIObject::callMethod(const char *methodName, const char *sig, ... { QAttachedJNIEnv env; jbyte res = 0; - jmethodID id = getCachedMethodID(env, m_jclass, methodName, sig); + jmethodID id = getCachedMethodID(env, d->m_jclass, methodName, sig); if (id) { va_list args; va_start(args, sig); - res = env->CallByteMethodV(m_jobject, id, args); + res = env->CallByteMethodV(d->m_jobject, id, args); va_end(args); } return res; @@ -292,11 +303,11 @@ jchar QJNIObject::callMethod(const char *methodName, const char *sig, ... { QAttachedJNIEnv env; jchar res = 0; - jmethodID id = getCachedMethodID(env, m_jclass, methodName, sig); + jmethodID id = getCachedMethodID(env, d->m_jclass, methodName, sig); if (id) { va_list args; va_start(args, sig); - res = env->CallCharMethodV(m_jobject, id, args); + res = env->CallCharMethodV(d->m_jobject, id, args); va_end(args); } return res; @@ -307,11 +318,11 @@ jshort QJNIObject::callMethod(const char *methodName, const char *sig, . { QAttachedJNIEnv env; jshort res = 0; - jmethodID id = getCachedMethodID(env, m_jclass, methodName, sig); + jmethodID id = getCachedMethodID(env, d->m_jclass, methodName, sig); if (id) { va_list args; va_start(args, sig); - res = env->CallShortMethodV(m_jobject, id, args); + res = env->CallShortMethodV(d->m_jobject, id, args); va_end(args); } return res; @@ -322,11 +333,11 @@ jint QJNIObject::callMethod(const char *methodName, const char *sig, ...) { QAttachedJNIEnv env; jint res = 0; - jmethodID id = getCachedMethodID(env, m_jclass, methodName, sig); + jmethodID id = getCachedMethodID(env, d->m_jclass, methodName, sig); if (id) { va_list args; va_start(args, sig); - res = env->CallIntMethodV(m_jobject, id, args); + res = env->CallIntMethodV(d->m_jobject, id, args); va_end(args); } return res; @@ -337,11 +348,11 @@ jlong QJNIObject::callMethod(const char *methodName, const char *sig, ... { QAttachedJNIEnv env; jlong res = 0; - jmethodID id = getCachedMethodID(env, m_jclass, methodName, sig); + jmethodID id = getCachedMethodID(env, d->m_jclass, methodName, sig); if (id) { va_list args; va_start(args, sig); - res = env->CallLongMethodV(m_jobject, id, args); + res = env->CallLongMethodV(d->m_jobject, id, args); va_end(args); } return res; @@ -352,11 +363,11 @@ jfloat QJNIObject::callMethod(const char *methodName, const char *sig, . { QAttachedJNIEnv env; jfloat res = 0.f; - jmethodID id = getCachedMethodID(env, m_jclass, methodName, sig); + jmethodID id = getCachedMethodID(env, d->m_jclass, methodName, sig); if (id) { va_list args; va_start(args, sig); - res = env->CallFloatMethodV(m_jobject, id, args); + res = env->CallFloatMethodV(d->m_jobject, id, args); va_end(args); } return res; @@ -367,11 +378,11 @@ jdouble QJNIObject::callMethod(const char *methodName, const char *sig, { QAttachedJNIEnv env; jdouble res = 0.; - jmethodID id = getCachedMethodID(env, m_jclass, methodName, sig); + jmethodID id = getCachedMethodID(env, d->m_jclass, methodName, sig); if (id) { va_list args; va_start(args, sig); - res = env->CallDoubleMethodV(m_jobject, id, args); + res = env->CallDoubleMethodV(d->m_jobject, id, args); va_end(args); } return res; @@ -384,11 +395,11 @@ QJNILocalRef QJNIObject::callObjectMethod(const char *methodNa { QAttachedJNIEnv env; jobject res = 0; - jmethodID id = getCachedMethodID(env, m_jclass, methodName, sig); + jmethodID id = getCachedMethodID(env, d->m_jclass, methodName, sig); if (id) { va_list args; va_start(args, sig); - res = env->CallObjectMethodV(m_jobject, id, args); + res = env->CallObjectMethodV(d->m_jobject, id, args); va_end(args); } return QJNILocalRef(res); @@ -401,11 +412,11 @@ QJNILocalRef QJNIObject::callObjectMethod(const char *methodNa { QAttachedJNIEnv env; jstring res = 0; - jmethodID id = getCachedMethodID(env, m_jclass, methodName, sig); + jmethodID id = getCachedMethodID(env, d->m_jclass, methodName, sig); if (id) { va_list args; va_start(args, sig); - res = static_cast(env->CallObjectMethodV(m_jobject, id, args)); + res = static_cast(env->CallObjectMethodV(d->m_jobject, id, args)); va_end(args); } return QJNILocalRef(res); @@ -418,11 +429,11 @@ QJNILocalRef QJNIObject::callObjectMethod(const char { QAttachedJNIEnv env; jobjectArray res = 0; - jmethodID id = getCachedMethodID(env, m_jclass, methodName, sig); + jmethodID id = getCachedMethodID(env, d->m_jclass, methodName, sig); if (id) { va_list args; va_start(args, sig); - res = static_cast(env->CallObjectMethodV(m_jobject, id, args)); + res = static_cast(env->CallObjectMethodV(d->m_jobject, id, args)); va_end(args); } return QJNILocalRef(res); @@ -435,11 +446,11 @@ QJNILocalRef QJNIObject::callObjectMethod(const ch { QAttachedJNIEnv env; jbooleanArray res = 0; - jmethodID id = getCachedMethodID(env, m_jclass, methodName, sig); + jmethodID id = getCachedMethodID(env, d->m_jclass, methodName, sig); if (id) { va_list args; va_start(args, sig); - res = static_cast(env->CallObjectMethodV(m_jobject, id, args)); + res = static_cast(env->CallObjectMethodV(d->m_jobject, id, args)); va_end(args); } return QJNILocalRef(res); @@ -452,11 +463,11 @@ QJNILocalRef QJNIObject::callObjectMethod(const char *me { QAttachedJNIEnv env; jbyteArray res = 0; - jmethodID id = getCachedMethodID(env, m_jclass, methodName, sig); + jmethodID id = getCachedMethodID(env, d->m_jclass, methodName, sig); if (id) { va_list args; va_start(args, sig); - res = static_cast(env->CallObjectMethodV(m_jobject, id, args)); + res = static_cast(env->CallObjectMethodV(d->m_jobject, id, args)); va_end(args); } return QJNILocalRef(res); @@ -469,11 +480,11 @@ QJNILocalRef QJNIObject::callObjectMethod(const char *me { QAttachedJNIEnv env; jcharArray res = 0; - jmethodID id = getCachedMethodID(env, m_jclass, methodName, sig); + jmethodID id = getCachedMethodID(env, d->m_jclass, methodName, sig); if (id) { va_list args; va_start(args, sig); - res = static_cast(env->CallObjectMethodV(m_jobject, id, args)); + res = static_cast(env->CallObjectMethodV(d->m_jobject, id, args)); va_end(args); } return QJNILocalRef(res); @@ -486,11 +497,11 @@ QJNILocalRef QJNIObject::callObjectMethod(const char * { QAttachedJNIEnv env; jshortArray res = 0; - jmethodID id = getCachedMethodID(env, m_jclass, methodName, sig); + jmethodID id = getCachedMethodID(env, d->m_jclass, methodName, sig); if (id) { va_list args; va_start(args, sig); - res = static_cast(env->CallObjectMethodV(m_jobject, id, args)); + res = static_cast(env->CallObjectMethodV(d->m_jobject, id, args)); va_end(args); } return QJNILocalRef(res); @@ -503,11 +514,11 @@ QJNILocalRef QJNIObject::callObjectMethod(const char *meth { QAttachedJNIEnv env; jintArray res = 0; - jmethodID id = getCachedMethodID(env, m_jclass, methodName, sig); + jmethodID id = getCachedMethodID(env, d->m_jclass, methodName, sig); if (id) { va_list args; va_start(args, sig); - res = static_cast(env->CallObjectMethodV(m_jobject, id, args)); + res = static_cast(env->CallObjectMethodV(d->m_jobject, id, args)); va_end(args); } return QJNILocalRef(res); @@ -520,11 +531,11 @@ QJNILocalRef QJNIObject::callObjectMethod(const char *me { QAttachedJNIEnv env; jlongArray res = 0; - jmethodID id = getCachedMethodID(env, m_jclass, methodName, sig); + jmethodID id = getCachedMethodID(env, d->m_jclass, methodName, sig); if (id) { va_list args; va_start(args, sig); - res = static_cast(env->CallObjectMethodV(m_jobject, id, args)); + res = static_cast(env->CallObjectMethodV(d->m_jobject, id, args)); va_end(args); } return QJNILocalRef(res); @@ -537,11 +548,11 @@ QJNILocalRef QJNIObject::callObjectMethod(const char * { QAttachedJNIEnv env; jfloatArray res = 0; - jmethodID id = getCachedMethodID(env, m_jclass, methodName, sig); + jmethodID id = getCachedMethodID(env, d->m_jclass, methodName, sig); if (id) { va_list args; va_start(args, sig); - res = static_cast(env->CallObjectMethodV(m_jobject, id, args)); + res = static_cast(env->CallObjectMethodV(d->m_jobject, id, args)); va_end(args); } return QJNILocalRef(res); @@ -554,11 +565,11 @@ QJNILocalRef QJNIObject::callObjectMethod(const char { QAttachedJNIEnv env; jdoubleArray res = 0; - jmethodID id = getCachedMethodID(env, m_jclass, methodName, sig); + jmethodID id = getCachedMethodID(env, d->m_jclass, methodName, sig); if (id) { va_list args; va_start(args, sig); - res = static_cast(env->CallObjectMethodV(m_jobject, id, args)); + res = static_cast(env->CallObjectMethodV(d->m_jobject, id, args)); va_end(args); } return QJNILocalRef(res); @@ -1796,9 +1807,9 @@ jboolean QJNIObject::getField(const char *fieldName) { QAttachedJNIEnv env; jboolean res = 0; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "Z"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "Z"); if (id) - res = env->GetBooleanField(m_jobject, id); + res = env->GetBooleanField(d->m_jobject, id); return res; } @@ -1808,9 +1819,9 @@ jbyte QJNIObject::getField(const char *fieldName) { QAttachedJNIEnv env; jbyte res = 0; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "B"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "B"); if (id) - res = env->GetByteField(m_jobject, id); + res = env->GetByteField(d->m_jobject, id); return res; } @@ -1820,9 +1831,9 @@ jchar QJNIObject::getField(const char *fieldName) { QAttachedJNIEnv env; jchar res = 0; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "C"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "C"); if (id) - res = env->GetCharField(m_jobject, id); + res = env->GetCharField(d->m_jobject, id); return res; } @@ -1832,9 +1843,9 @@ jshort QJNIObject::getField(const char *fieldName) { QAttachedJNIEnv env; jshort res = 0; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "S"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "S"); if (id) - res = env->GetShortField(m_jobject, id); + res = env->GetShortField(d->m_jobject, id); return res; } @@ -1844,9 +1855,9 @@ jint QJNIObject::getField(const char *fieldName) { QAttachedJNIEnv env; jint res = 0; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "I"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "I"); if (id) - res = env->GetIntField(m_jobject, id); + res = env->GetIntField(d->m_jobject, id); return res; } @@ -1856,9 +1867,9 @@ jlong QJNIObject::getField(const char *fieldName) { QAttachedJNIEnv env; jlong res = 0; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "J"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "J"); if (id) - res = env->GetLongField(m_jobject, id); + res = env->GetLongField(d->m_jobject, id); return res; } @@ -1868,9 +1879,9 @@ jfloat QJNIObject::getField(const char *fieldName) { QAttachedJNIEnv env; jfloat res = 0.f; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "F"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "F"); if (id) - res = env->GetFloatField(m_jobject, id); + res = env->GetFloatField(d->m_jobject, id); return res; } @@ -1880,9 +1891,9 @@ jdouble QJNIObject::getField(const char *fieldName) { QAttachedJNIEnv env; jdouble res = 0.; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "D"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "D"); if (id) - res = env->GetDoubleField(m_jobject, id); + res = env->GetDoubleField(d->m_jobject, id); return res; } @@ -1892,9 +1903,9 @@ QJNILocalRef QJNIObject::getObjectField(const char *fieldName, { QAttachedJNIEnv env; jobject res = 0; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, sig); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, sig); if (id) - res = env->GetObjectField(m_jobject, id); + res = env->GetObjectField(d->m_jobject, id); return QJNILocalRef(res); } @@ -1904,9 +1915,9 @@ QJNILocalRef QJNIObject::getObjectField(const char { QAttachedJNIEnv env; jbooleanArray res = 0; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "[Z"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "[Z"); if (id) - res = static_cast(env->GetObjectField(m_jobject, id)); + res = static_cast(env->GetObjectField(d->m_jobject, id)); return QJNILocalRef(res); } @@ -1916,9 +1927,9 @@ QJNILocalRef QJNIObject::getObjectField(const char *fiel { QAttachedJNIEnv env; jbyteArray res = 0; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "[B"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "[B"); if (id) - res = static_cast(env->GetObjectField(m_jobject, id)); + res = static_cast(env->GetObjectField(d->m_jobject, id)); return QJNILocalRef(res); } @@ -1928,9 +1939,9 @@ QJNILocalRef QJNIObject::getObjectField(const char *fiel { QAttachedJNIEnv env; jcharArray res = 0; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "[C"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "[C"); if (id) - res = static_cast(env->GetObjectField(m_jobject, id)); + res = static_cast(env->GetObjectField(d->m_jobject, id)); return QJNILocalRef(res); } @@ -1940,9 +1951,9 @@ QJNILocalRef QJNIObject::getObjectField(const char *fi { QAttachedJNIEnv env; jshortArray res = 0; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "[S"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "[S"); if (id) - res = static_cast(env->GetObjectField(m_jobject, id)); + res = static_cast(env->GetObjectField(d->m_jobject, id)); return QJNILocalRef(res); } @@ -1952,9 +1963,9 @@ QJNILocalRef QJNIObject::getObjectField(const char *fieldN { QAttachedJNIEnv env; jintArray res = 0; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "[I"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "[I"); if (id) - res = static_cast(env->GetObjectField(m_jobject, id)); + res = static_cast(env->GetObjectField(d->m_jobject, id)); return QJNILocalRef(res); } @@ -1964,9 +1975,9 @@ QJNILocalRef QJNIObject::getObjectField(const char *fiel { QAttachedJNIEnv env; jlongArray res = 0; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "[J"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "[J"); if (id) - res = static_cast(env->GetObjectField(m_jobject, id)); + res = static_cast(env->GetObjectField(d->m_jobject, id)); return QJNILocalRef(res); } @@ -1976,9 +1987,9 @@ QJNILocalRef QJNIObject::getObjectField(const char *fi { QAttachedJNIEnv env; jfloatArray res = 0; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "[F"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "[F"); if (id) - res = static_cast(env->GetObjectField(m_jobject, id)); + res = static_cast(env->GetObjectField(d->m_jobject, id)); return QJNILocalRef(res); } @@ -1988,9 +1999,9 @@ QJNILocalRef QJNIObject::getObjectField(const char * { QAttachedJNIEnv env; jdoubleArray res = 0; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "[D"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "[D"); if (id) - res = static_cast(env->GetObjectField(m_jobject, id)); + res = static_cast(env->GetObjectField(d->m_jobject, id)); return QJNILocalRef(res); } @@ -2000,9 +2011,9 @@ QJNILocalRef QJNIObject::getObjectField(const char *fieldName) { QAttachedJNIEnv env; jstring res = 0; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "Ljava/lang/String;"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "Ljava/lang/String;"); if (id) - res = static_cast(env->GetObjectField(m_jobject, id)); + res = static_cast(env->GetObjectField(d->m_jobject, id)); return QJNILocalRef(res); } @@ -2013,9 +2024,9 @@ QJNILocalRef QJNIObject::getObjectField(const char * { QAttachedJNIEnv env; jobjectArray res = 0; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, sig); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, sig); if (id) - res = static_cast(env->GetObjectField(m_jobject, id)); + res = static_cast(env->GetObjectField(d->m_jobject, id)); return QJNILocalRef(res); } @@ -2024,9 +2035,9 @@ template <> void QJNIObject::setField(const char *fieldName, jboolean value) { QAttachedJNIEnv env; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "Z"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "Z"); if (id) - env->SetBooleanField(m_jobject, id, value); + env->SetBooleanField(d->m_jobject, id, value); } @@ -2034,9 +2045,9 @@ template <> void QJNIObject::setField(const char *fieldName, jbyte value) { QAttachedJNIEnv env; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "B"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "B"); if (id) - env->SetByteField(m_jobject, id, value); + env->SetByteField(d->m_jobject, id, value); } @@ -2044,9 +2055,9 @@ template <> void QJNIObject::setField(const char *fieldName, jchar value) { QAttachedJNIEnv env; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "C"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "C"); if (id) - env->SetCharField(m_jobject, id, value); + env->SetCharField(d->m_jobject, id, value); } @@ -2054,9 +2065,9 @@ template <> void QJNIObject::setField(const char *fieldName, jshort value) { QAttachedJNIEnv env; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "S"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "S"); if (id) - env->SetShortField(m_jobject, id, value); + env->SetShortField(d->m_jobject, id, value); } @@ -2064,9 +2075,9 @@ template <> void QJNIObject::setField(const char *fieldName, jint value) { QAttachedJNIEnv env; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "I"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "I"); if (id) - env->SetIntField(m_jobject, id, value); + env->SetIntField(d->m_jobject, id, value); } @@ -2074,9 +2085,9 @@ template <> void QJNIObject::setField(const char *fieldName, jlong value) { QAttachedJNIEnv env; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "J"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "J"); if (id) - env->SetLongField(m_jobject, id, value); + env->SetLongField(d->m_jobject, id, value); } @@ -2084,9 +2095,9 @@ template <> void QJNIObject::setField(const char *fieldName, jfloat value) { QAttachedJNIEnv env; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "F"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "F"); if (id) - env->SetFloatField(m_jobject, id, value); + env->SetFloatField(d->m_jobject, id, value); } @@ -2094,9 +2105,9 @@ template <> void QJNIObject::setField(const char *fieldName, jdouble value) { QAttachedJNIEnv env; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "D"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "D"); if (id) - env->SetDoubleField(m_jobject, id, value); + env->SetDoubleField(d->m_jobject, id, value); } @@ -2104,9 +2115,9 @@ template <> void QJNIObject::setField(const char *fieldName, jbooleanArray value) { QAttachedJNIEnv env; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "[Z"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "[Z"); if (id) - env->SetObjectField(m_jobject, id, value); + env->SetObjectField(d->m_jobject, id, value); } @@ -2114,9 +2125,9 @@ template <> void QJNIObject::setField(const char *fieldName, jbyteArray value) { QAttachedJNIEnv env; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "[B"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "[B"); if (id) - env->SetObjectField(m_jobject, id, value); + env->SetObjectField(d->m_jobject, id, value); } @@ -2124,9 +2135,9 @@ template <> void QJNIObject::setField(const char *fieldName, jcharArray value) { QAttachedJNIEnv env; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "[C"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "[C"); if (id) - env->SetObjectField(m_jobject, id, value); + env->SetObjectField(d->m_jobject, id, value); } @@ -2134,9 +2145,9 @@ template <> void QJNIObject::setField(const char *fieldName, jshortArray value) { QAttachedJNIEnv env; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "[S"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "[S"); if (id) - env->SetObjectField(m_jobject, id, value); + env->SetObjectField(d->m_jobject, id, value); } @@ -2144,9 +2155,9 @@ template <> void QJNIObject::setField(const char *fieldName, jintArray value) { QAttachedJNIEnv env; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "[I"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "[I"); if (id) - env->SetObjectField(m_jobject, id, value); + env->SetObjectField(d->m_jobject, id, value); } @@ -2154,9 +2165,9 @@ template <> void QJNIObject::setField(const char *fieldName, jlongArray value) { QAttachedJNIEnv env; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "[J"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "[J"); if (id) - env->SetObjectField(m_jobject, id, value); + env->SetObjectField(d->m_jobject, id, value); } @@ -2164,9 +2175,9 @@ template <> void QJNIObject::setField(const char *fieldName, jfloatArray value) { QAttachedJNIEnv env; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "[F"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "[F"); if (id) - env->SetObjectField(m_jobject, id, value); + env->SetObjectField(d->m_jobject, id, value); } @@ -2174,9 +2185,9 @@ template <> void QJNIObject::setField(const char *fieldName, jdoubleArray value) { QAttachedJNIEnv env; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "[D"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "[D"); if (id) - env->SetObjectField(m_jobject, id, value); + env->SetObjectField(d->m_jobject, id, value); } @@ -2184,9 +2195,9 @@ template <> void QJNIObject::setField(const char *fieldName, jstring value) { QAttachedJNIEnv env; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, "Ljava/lang/String;"); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, "Ljava/lang/String;"); if (id) - env->SetObjectField(m_jobject, id, value); + env->SetObjectField(d->m_jobject, id, value); } @@ -2194,9 +2205,9 @@ template <> void QJNIObject::setField(const char *fieldName, const char *sig, jobject value) { QAttachedJNIEnv env; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, sig); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, sig); if (id) - env->SetObjectField(m_jobject, id, value); + env->SetObjectField(d->m_jobject, id, value); } @@ -2206,9 +2217,9 @@ void QJNIObject::setField(const char *fieldName, jobjectArray value) { QAttachedJNIEnv env; - jfieldID id = getCachedFieldID(env, m_jclass, fieldName, sig); + jfieldID id = getCachedFieldID(env, d->m_jclass, fieldName, sig); if (id) - env->SetObjectField(m_jobject, id, value); + env->SetObjectField(d->m_jobject, id, value); } diff --git a/src/platformsupport/jniconvenience/qjniobject_p.h b/src/platformsupport/jniconvenience/qjniobject_p.h index 6874765f06..f8c2842433 100644 --- a/src/platformsupport/jniconvenience/qjniobject_p.h +++ b/src/platformsupport/jniconvenience/qjniobject_p.h @@ -43,6 +43,7 @@ #define QJNIOBJECT_H #include +#include #include QT_BEGIN_NAMESPACE @@ -72,20 +73,40 @@ class QJNILocalRef; * someObject.setField("fieldName", 10); * someObject.callMethod("doStuff"); */ + +class QJNIObjectPrivate +{ +public: + QJNIObjectPrivate(const char *className); + QJNIObjectPrivate(const char *className, const char *sig, va_list args); + QJNIObjectPrivate(jclass clazz); + QJNIObjectPrivate(jclass clazz, const char *sig, va_list args); + QJNIObjectPrivate(jobject obj); + ~QJNIObjectPrivate(); + +private: + Q_DISABLE_COPY(QJNIObjectPrivate) + friend class QJNIObject; + jobject m_jobject; + jclass m_jclass; + bool m_own_jclass; +}; + class QJNIObject { public: - QJNIObject(const char *className); + QJNIObject(const char *className) : d(new QJNIObjectPrivate(className)) { } QJNIObject(const char *className, const char *sig, ...); - QJNIObject(jclass clazz); + QJNIObject(jclass clazz) : d(new QJNIObjectPrivate(clazz)) { } QJNIObject(jclass clazz, const char *sig, ...); - QJNIObject(jobject obj); - virtual ~QJNIObject(); + QJNIObject(jobject obj) : d(new QJNIObjectPrivate(obj)) { } + + virtual ~QJNIObject() { } static bool isClassAvailable(const char *className); - bool isValid() const { return m_jobject != 0; } - jobject object() const { return m_jobject; } + bool isValid() const { return d->m_jobject != 0; } + jobject object() const { return d->m_jobject; } template T callMethod(const char *methodName); @@ -158,10 +179,8 @@ public: template static void setStaticField(jclass clazz, const char *fieldName, T value); -protected: - jobject m_jobject; - jclass m_jclass; - bool m_own_jclass; +private: + QSharedPointer d; }; QT_END_NAMESPACE -- cgit v1.2.3 From ca0ec4043f20e2e2c687cdf83ca5df5608c1b066 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Christian=20Str=C3=B8mme?= Date: Fri, 16 Aug 2013 11:31:26 +0200 Subject: JNI Convenience: Print exceptions in debug mode. The exception message might contain valuable information about what went wrong, so we should print the message. Change-Id: I50c986d4c18cf6115017fcc92363c946be45024d Reviewed-by: Yoann Lopes --- src/platformsupport/jniconvenience/qjniobject.cpp | 9 +++++++++ 1 file changed, 9 insertions(+) (limited to 'src') diff --git a/src/platformsupport/jniconvenience/qjniobject.cpp b/src/platformsupport/jniconvenience/qjniobject.cpp index 1d0bb435aa..ecf247aabf 100644 --- a/src/platformsupport/jniconvenience/qjniobject.cpp +++ b/src/platformsupport/jniconvenience/qjniobject.cpp @@ -57,6 +57,9 @@ static jclass getCachedClass(JNIEnv *env, const char *className) jclass c = env->FindClass(className); if (env->ExceptionCheck()) { c = 0; +#ifdef QT_DEBUG + env->ExceptionDescribe(); +#endif // QT_DEBUG env->ExceptionClear(); } if (c) @@ -88,6 +91,9 @@ static jmethodID getCachedMethodID(JNIEnv *env, if (env->ExceptionCheck()) { id = 0; +#ifdef QT_DEBUG + env->ExceptionDescribe(); +#endif // QT_DEBUG env->ExceptionClear(); } @@ -117,6 +123,9 @@ static jfieldID getCachedFieldID(JNIEnv *env, if (env->ExceptionCheck()) { id = 0; +#ifdef QT_DEBUG + env->ExceptionDescribe(); +#endif // QT_DEBUG env->ExceptionClear(); } -- cgit v1.2.3 From ac611399fe1f059b00b3939b78b8ef1666102e68 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Christian=20Str=C3=B8mme?= Date: Fri, 16 Aug 2013 17:27:42 +0200 Subject: JNI Convenience: Make single argument ctors explicit. Change-Id: I330e4acf9b944fc72066b608653edd4686620b7e Reviewed-by: Yoann Lopes --- src/platformsupport/jniconvenience/qjniobject_p.h | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'src') diff --git a/src/platformsupport/jniconvenience/qjniobject_p.h b/src/platformsupport/jniconvenience/qjniobject_p.h index f8c2842433..8721ec3a6a 100644 --- a/src/platformsupport/jniconvenience/qjniobject_p.h +++ b/src/platformsupport/jniconvenience/qjniobject_p.h @@ -95,11 +95,11 @@ private: class QJNIObject { public: - QJNIObject(const char *className) : d(new QJNIObjectPrivate(className)) { } + explicit QJNIObject(const char *className) : d(new QJNIObjectPrivate(className)) { } QJNIObject(const char *className, const char *sig, ...); - QJNIObject(jclass clazz) : d(new QJNIObjectPrivate(clazz)) { } + explicit QJNIObject(jclass clazz) : d(new QJNIObjectPrivate(clazz)) { } QJNIObject(jclass clazz, const char *sig, ...); - QJNIObject(jobject obj) : d(new QJNIObjectPrivate(obj)) { } + explicit QJNIObject(jobject obj) : d(new QJNIObjectPrivate(obj)) { } virtual ~QJNIObject() { } -- cgit v1.2.3 From f3a53eae80bda8bb9364e5caa6b0e1cf0dd9ce87 Mon Sep 17 00:00:00 2001 From: Eskil Abrahamsen Blomfeldt Date: Tue, 27 Aug 2013 11:52:56 +0200 Subject: Revert "Fix compilation for Android ARMv5" This reverts commit 9fa1bdeeb2bca6f9ba370fce594a47a066a7e81a which is no longer needed because the Android NDK now contains a toolchain without the bug for which it was a work-around. Task-number: QTBUG-31051 Change-Id: I601ba2fccb927ee7e818644de4474700e2eec8f1 Reviewed-by: BogDan Vatra --- src/corelib/global/qglobal.h | 4 ---- 1 file changed, 4 deletions(-) (limited to 'src') diff --git a/src/corelib/global/qglobal.h b/src/corelib/global/qglobal.h index cde3e96ed1..a70dc52e9f 100644 --- a/src/corelib/global/qglobal.h +++ b/src/corelib/global/qglobal.h @@ -203,11 +203,7 @@ typedef quint64 qulonglong; QT_BEGIN_INCLUDE_NAMESPACE typedef unsigned char uchar; typedef unsigned short ushort; -#if defined(Q_QDOC) || !defined(Q_OS_ANDROID) typedef unsigned int uint; -#else -# include -#endif typedef unsigned long ulong; QT_END_INCLUDE_NAMESPACE -- cgit v1.2.3 From 5971e0918757737425151c39a5f81a238663a17a Mon Sep 17 00:00:00 2001 From: Yoann Lopes Date: Wed, 21 Aug 2013 13:54:07 +0200 Subject: Use custom class for storing distance fields instead of QImage. Distance fields are stored using a one-byte alpha component per pixel, a format that QImage doesn't currently support. The Indexed8 format was used instead, limiting what could be done with the QImage. This patch introduces a new private class, QDistanceField, with a similar API to QImage and using the Alpha8 pixel format. Unlike QImage which aligns scanlines on a 4-byte boundary, QDistanceField tightly packs scanlines together. Task-number: QTBUG-30908 Task-number: QTBUG-32861 Change-Id: Ic273259ea07dfbd2b81a6358c0ca11a2330eb749 Reviewed-by: Eskil Abrahamsen Blomfeldt --- src/gui/text/qdistancefield.cpp | 270 ++++++++++++++++++++++++++++++++++++---- src/gui/text/qdistancefield_p.h | 65 +++++++++- 2 files changed, 306 insertions(+), 29 deletions(-) (limited to 'src') diff --git a/src/gui/text/qdistancefield.cpp b/src/gui/text/qdistancefield.cpp index f4274a2c19..e584b66a25 100644 --- a/src/gui/text/qdistancefield.cpp +++ b/src/gui/text/qdistancefield.cpp @@ -487,15 +487,19 @@ static void drawPolygons(qint32 *bits, int width, int height, const QPoint *vert } } -static QImage makeDistanceField(int imgWidth, int imgHeight, const QPainterPath &path, int dfScale, int offs) +static void makeDistanceField(QDistanceFieldData *data, const QPainterPath &path, int dfScale, int offs) { - QImage image(imgWidth, imgHeight, QImage::Format_Indexed8); + if (!data || !data->data) + return; if (path.isEmpty()) { - image.fill(0); - return image; + memset(data->data, 0, data->nbytes); + return; } + int imgWidth = data->width; + int imgHeight = data->height; + QTransform transform; transform.translate(offs, offs); transform.scale(qreal(1) / dfScale, qreal(1) / dfScale); @@ -521,8 +525,8 @@ static QImage makeDistanceField(int imgWidth, int imgHeight, const QPainterPath QVarLengthArray isConvex; QVarLengthArray needsClipping; - drawPolygons(bits.data(), imgWidth, imgHeight, pathVertices.data(), indices, pathIndices.size(), - interiorColor); + drawPolygons(bits.data(), imgWidth, imgHeight, pathVertices.data(), + indices, pathIndices.size(), interiorColor); int index = 0; @@ -681,15 +685,11 @@ static QImage makeDistanceField(int imgWidth, int imgHeight, const QPainterPath } const qint32 *inLine = bits.data(); - uchar *outLine = image.bits(); - int padding = image.bytesPerLine() - image.width(); + uchar *outLine = data->data; for (int y = 0; y < imgHeight; ++y) { for (int x = 0; x < imgWidth; ++x, ++inLine, ++outLine) *outLine = uchar((0x7f80 - *inLine) >> 8); - outLine += padding; } - - return image; } static bool imageHasNarrowOutlines(const QImage &im) @@ -769,31 +769,96 @@ bool qt_fontHasNarrowOutlines(const QRawFont &f) QRawFont::PixelAntialiasing)); } -static QImage renderDistanceFieldPath(const QPainterPath &path, bool doubleResolution) + +QDistanceFieldData::QDistanceFieldData(const QDistanceFieldData &other) + : QSharedData(other) + , glyph(other.glyph) + , width(other.width) + , height(other.height) + , nbytes(other.nbytes) +{ + if (nbytes && other.data) + data = (uchar *)memcpy(malloc(nbytes), other.data, nbytes); + else + data = 0; +} + +QDistanceFieldData::~QDistanceFieldData() +{ + free(data); +} + +QDistanceFieldData *QDistanceFieldData::create(const QSize &size) +{ + QDistanceFieldData *data = new QDistanceFieldData; + + if (size.isValid()) { + data->width = size.width(); + data->height = size.height(); + // pixel data stored as a 1-byte alpha value + data->nbytes = data->width * data->height; // tightly packed + data->data = (uchar *)malloc(data->nbytes); + } + + return data; +} + +QDistanceFieldData *QDistanceFieldData::create(const QPainterPath &path, bool doubleResolution) { int dfMargin = QT_DISTANCEFIELD_RADIUS(doubleResolution) / QT_DISTANCEFIELD_SCALE(doubleResolution); int glyphWidth = qCeil(path.boundingRect().width() / QT_DISTANCEFIELD_SCALE(doubleResolution)) + dfMargin * 2; - QImage im = makeDistanceField(glyphWidth, - QT_DISTANCEFIELD_TILESIZE(doubleResolution), - path, - QT_DISTANCEFIELD_SCALE(doubleResolution), - QT_DISTANCEFIELD_RADIUS(doubleResolution) / QT_DISTANCEFIELD_SCALE(doubleResolution)); - return im; + QDistanceFieldData *data = create(QSize(glyphWidth, QT_DISTANCEFIELD_TILESIZE(doubleResolution))); + + makeDistanceField(data, + path, + QT_DISTANCEFIELD_SCALE(doubleResolution), + QT_DISTANCEFIELD_RADIUS(doubleResolution) / QT_DISTANCEFIELD_SCALE(doubleResolution)); + return data; } -QImage qt_renderDistanceFieldGlyph(QFontEngine *fe, glyph_t glyph, bool doubleResolution) + +QDistanceField::QDistanceField() + : d(new QDistanceFieldData) { - QFixedPoint position; - QPainterPath path; - fe->addGlyphsToPath(&glyph, &position, 1, &path, 0); - path.translate(-path.boundingRect().topLeft()); - path.setFillRule(Qt::WindingFill); +} - return renderDistanceFieldPath(path, doubleResolution); +QDistanceField::QDistanceField(int width, int height) + : d(QDistanceFieldData::create(QSize(width, height))) +{ } -QImage qt_renderDistanceFieldGlyph(const QRawFont &font, glyph_t glyph, bool doubleResolution) +QDistanceField::QDistanceField(const QDistanceField &other) +{ + d = other.d; +} + +QDistanceField::QDistanceField(const QRawFont &font, glyph_t glyph, bool doubleResolution) +{ + setGlyph(font, glyph, doubleResolution); +} + +QDistanceField::QDistanceField(QFontEngine *fontEngine, glyph_t glyph, bool doubleResolution) +{ + setGlyph(fontEngine, glyph, doubleResolution); +} + +QDistanceField::QDistanceField(QDistanceFieldData *data) + : d(data) +{ +} + +bool QDistanceField::isNull() const +{ + return !d->data; +} + +glyph_t QDistanceField::glyph() const +{ + return d->glyph; +} + +void QDistanceField::setGlyph(const QRawFont &font, glyph_t glyph, bool doubleResolution) { QRawFont renderFont = font; renderFont.setPixelSize(QT_DISTANCEFIELD_BASEFONTSIZE(doubleResolution) * QT_DISTANCEFIELD_SCALE(doubleResolution)); @@ -802,7 +867,158 @@ QImage qt_renderDistanceFieldGlyph(const QRawFont &font, glyph_t glyph, bool dou path.translate(-path.boundingRect().topLeft()); path.setFillRule(Qt::WindingFill); - return renderDistanceFieldPath(path, doubleResolution); + d = QDistanceFieldData::create(path, doubleResolution); + d->glyph = glyph; +} + +void QDistanceField::setGlyph(QFontEngine *fontEngine, glyph_t glyph, bool doubleResolution) +{ + QFixedPoint position; + QPainterPath path; + fontEngine->addGlyphsToPath(&glyph, &position, 1, &path, 0); + path.translate(-path.boundingRect().topLeft()); + path.setFillRule(Qt::WindingFill); + + d = QDistanceFieldData::create(path, doubleResolution); + d->glyph = glyph; +} + +int QDistanceField::width() const +{ + return d->width; +} + +int QDistanceField::height() const +{ + return d->height; +} + +QDistanceField QDistanceField::copy(const QRect &r) const +{ + if (isNull()) + return QDistanceField(); + + if (r.isNull()) + return QDistanceField(new QDistanceFieldData(*d)); + + int x = r.x(); + int y = r.y(); + int w = r.width(); + int h = r.height(); + + int dx = 0; + int dy = 0; + if (w <= 0 || h <= 0) + return QDistanceField(); + + QDistanceField df(w, h); + if (df.isNull()) + return df; + + if (x < 0 || y < 0 || x + w > d->width || y + h > d->height) { + memset(df.d->data, 0, df.d->nbytes); + if (x < 0) { + dx = -x; + x = 0; + } + if (y < 0) { + dy = -y; + y = 0; + } + } + + int pixels_to_copy = qMax(w - dx, 0); + if (x > d->width) + pixels_to_copy = 0; + else if (pixels_to_copy > d->width - x) + pixels_to_copy = d->width - x; + int lines_to_copy = qMax(h - dy, 0); + if (y > d->height) + lines_to_copy = 0; + else if (lines_to_copy > d->height - y) + lines_to_copy = d->height - y; + + const uchar *src = d->data + x + y * d->width; + uchar *dest = df.d->data + dx + dy * df.d->width; + for (int i = 0; i < lines_to_copy; ++i) { + memcpy(dest, src, pixels_to_copy); + src += d->width; + dest += df.d->width; + } + + df.d->glyph = d->glyph; + + return df; +} + +uchar *QDistanceField::bits() +{ + return d->data; +} + +const uchar *QDistanceField::bits() const +{ + return d->data; +} + +const uchar *QDistanceField::constBits() const +{ + return d->data; +} + +uchar *QDistanceField::scanLine(int i) +{ + if (isNull()) + return 0; + + Q_ASSERT(i >= 0 && i < d->height); + return d->data + i * d->width; +} + +const uchar *QDistanceField::scanLine(int i) const +{ + if (isNull()) + return 0; + + Q_ASSERT(i >= 0 && i < d->height); + return d->data + i * d->width; +} + +const uchar *QDistanceField::constScanLine(int i) const +{ + if (isNull()) + return 0; + + Q_ASSERT(i >= 0 && i < d->height); + return d->data + i * d->width; +} + +QImage QDistanceField::toImage(QImage::Format format) const +{ + if (isNull()) + return QImage(); + + QImage image(d->width, d->height, format == QImage::Format_Indexed8 ? + format : QImage::Format_ARGB32_Premultiplied); + if (image.isNull()) + return image; + + if (format == QImage::Format_Indexed8) { + for (int y = 0; y < d->height; ++y) + memcpy(image.scanLine(y), scanLine(y), d->width); + } else { + for (int y = 0; y < d->height; ++y) { + for (int x = 0; x < d->width; ++x) { + uint alpha = *(d->data + x + y * d->width); + image.setPixel(x, y, alpha << 24); + } + } + + if (image.format() != format) + image = image.convertToFormat(format); + } + + return image; } QT_END_NAMESPACE diff --git a/src/gui/text/qdistancefield_p.h b/src/gui/text/qdistancefield_p.h index f181aadd9d..d4c4f8f46d 100644 --- a/src/gui/text/qdistancefield_p.h +++ b/src/gui/text/qdistancefield_p.h @@ -55,6 +55,7 @@ #include #include +#include QT_BEGIN_NAMESPACE @@ -78,9 +79,69 @@ QT_BEGIN_NAMESPACE QT_DISTANCEFIELD_DEFAULT_RADIUS) bool Q_GUI_EXPORT qt_fontHasNarrowOutlines(const QRawFont &f); -QImage Q_GUI_EXPORT qt_renderDistanceFieldGlyph(const QRawFont &font, glyph_t glyph, bool doubleResolution); bool Q_GUI_EXPORT qt_fontHasNarrowOutlines(QFontEngine *fontEngine); -QImage Q_GUI_EXPORT qt_renderDistanceFieldGlyph(QFontEngine *fontEngine, glyph_t glyph, bool doubleResolution); + +class Q_GUI_EXPORT QDistanceFieldData : public QSharedData +{ +public: + QDistanceFieldData() : glyph(0), width(0), height(0), nbytes(0), data(0) {} + QDistanceFieldData(const QDistanceFieldData &other); + ~QDistanceFieldData(); + + static QDistanceFieldData *create(const QSize &size); + static QDistanceFieldData *create(const QPainterPath &path, bool doubleResolution); + + glyph_t glyph; + int width; + int height; + int nbytes; + uchar *data; +}; + +class Q_GUI_EXPORT QDistanceField +{ +public: + QDistanceField(); + QDistanceField(int width, int height); + QDistanceField(const QRawFont &font, glyph_t glyph, bool doubleResolution = false); + QDistanceField(QFontEngine *fontEngine, glyph_t glyph, bool doubleResolution = false); + QDistanceField(const QDistanceField &other); + + bool isNull() const; + + glyph_t glyph() const; + void setGlyph(const QRawFont &font, glyph_t glyph, bool doubleResolution = false); + void setGlyph(QFontEngine *fontEngine, glyph_t glyph, bool doubleResolution = false); + + int width() const; + int height() const; + + QDistanceField copy(const QRect &rect = QRect()) const; + inline QDistanceField copy(int x, int y, int w, int h) const + { return copy(QRect(x, y, w, h)); } + + uchar *bits(); + const uchar *bits() const; + const uchar *constBits() const; + + uchar *scanLine(int); + const uchar *scanLine(int) const; + const uchar *constScanLine(int) const; + + QImage toImage(QImage::Format format = QImage::Format_ARGB32_Premultiplied) const; + +private: + QDistanceField(QDistanceFieldData *data); + QSharedDataPointer d; + + friend class QDistanceFieldData; +}; + + +inline QImage Q_GUI_EXPORT qt_renderDistanceFieldGlyph(const QRawFont &f, glyph_t g, bool d) +{ return QDistanceField(f, g, d).toImage(QImage::Format_Indexed8); } +inline QImage Q_GUI_EXPORT qt_renderDistanceFieldGlyph(QFontEngine *fe, glyph_t g, bool d) +{ return QDistanceField(fe, g, d).toImage(QImage::Format_Indexed8); } QT_END_NAMESPACE -- cgit v1.2.3