summaryrefslogtreecommitdiffstats
path: root/src/widgets/widgets/qmainwindowlayout.cpp
Commit message (Collapse)AuthorAgeFilesLines
* QMainWindowLayout: rewrite validateToolBarArea() to return by valueMarc Mutz2024-03-261-5/+6
| | | | | | | | | | | | | | | | | | | | | | | | | | | Coverity complains that QToolBarAreaLayout's addToolBarBreak(QInternal::DockPosition) could access QToolBarAreaLayout::docks out of bounds if passed QInternal::DockCount. That is correct, but a valid pos seems to be a precondition for this function, judging from its sister functions, e.g. addToolBar(DockPosition, .) or insertItem(DockPosition, .), which also don't validate `pos`. All in-module callers of addToolBarBreak() only pass valid positions, and use validateToolBarArea() to ensure that. So it seems that Coverity doesn't grok the pass-by-in/out -parameter used by that function. That, or it doesn't track back far enough. Before attempting more drastic measures, first try rewriting the function to return-by-value instead, and see what Coverity has to say afterwards. As a drive-by, make validateToolBarArea() constexpr. Pick-to: 6.7 6.6 6.5 6.2 5.15 Coverity-Id: 444141 Coverity-Id: 444135 Change-Id: I5fcc664c3cea608429036cad75c37f5c38059733 Reviewed-by: Richard Moe Gustavsen <richard.gustavsen@qt.io>
* Fix -Wimplicit-fallthrough for clangTim Blechmann2024-03-011-0/+1
| | | | | | | | | | | | | | | | | | | Clang's `-Wimplicit-fallthrough` warnings are a little stricter than gcc's interpretation: switch (i) { case 0: foo(); case 4: break; } While gcc accepts the implicit fallthrough, if the following statement is a trivial `break`, clang will warn about it. Pick-to: 6.7 Change-Id: I38e0817f1bc034fbb552aeac21de1516edcbcbb0 Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io>
* Refactor and fix QMainWindow::tabifiedDockWidgets()Axel Spoerl2024-02-291-13/+39
| | | | | | | | | | | | | | | | | | | | | | | | | | | | The method traversed QDockAreaLayoutInfo::item_list, to identify dock widgets tabbed with the QDockWidget argument in a tab bar It relied on bool QDockAreLayoutInfo::tabbed, which is set to true, when a QMainWindowTabBar is to be added to a QDockAreaLayoutInfo. This flag isn't cleared, when the second last dock widget is removed from the tab bar. It can't be replaced by QMainWindowLayout::isDockWidgetTabbed, because the flag also represents intermediate states, where e.g. a dock widget is hovered over, prepares to become a floating tab and then rolls back, because hovering doesn't result in a drop. In that case, tabbed must become true, which the dock widget isn't actually tabbed. Furthermore, the way to traverse item_list didn't find dock widgets in a floating tab. In that case, tabifiedDockWidgets() wrongly returned an empty list. To fix both issues, refactor QMainWindow::tabifiedDockWidgets() to read the list of dock widgets directly from the QMainWindowTabBar. Add tests in tst_QDockWidget::floatingTabs() and updateTabBarOnVisibilityChanged() Fixes: QTBUG-122001 Pick-to: 6.7 6.6 6.5 Change-Id: Ia9eb3711be642101261f34ee447521cc6accc20c Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io>
* Prevent re-replacing state in setGeometryTomi Korpipää2024-02-271-1/+3
| | | | | | | | | | | Do not allow replacing a state again if it is already being replaced. Cleaned up from the patch provided in QTBUG-121126. Fixes: QTBUG-121126 Pick-to: 6.6 6.7 Change-Id: Icca932b0e5cccd2f39ac18f29d8f7707887d147f Reviewed-by: Richard Moe Gustavsen <richard.gustavsen@qt.io>
* Widgets: pass widget to QStyle::pixelMetric()Christian Ehrlicher2024-01-161-1/+1
| | | | | | | | | | | | Make sure to pass the widget to QStyle::pixelMetric() as some styles might use this (e.g. the new windows styles) to determine the correct pixel metric. Pick-to: 6.7 6.6 6.5 6.2 Task-number: QTBUG-1857 Change-Id: I5c32f5af8b284749732b610e56b4e3d8c8ed1946 Reviewed-by: Axel Spoerl <axel.spoerl@qt.io> Reviewed-by: David Faure <david.faure@kdab.com>
* Revert "QDockWidget: Always show dock widgets with the main window"Axel Spoerl2023-12-291-11/+0
| | | | | | | | | This reverts commit 4c60a11d8f935abb762a83b0ab99cefa6db3060c. Reason for revert: Breaks QMainWindow::restoreState(). Dock widget is shown, even if restored into hidden state. Change-Id: I9808de4e0fd48871c3b234ae9bbaf6c64c8e832d Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io>
* QMainWindow: don't crash when restored state is modified before appliedVolker Hilsheimer2023-12-131-0/+28
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | Amends 32edae5e268b968aff82f0713612eff2feffb4e1, after which we keep a copy of the restored state if the state couldn't be applied yet. Since making a copy of the entire state results in multiple copies of layout item pointers, we might end up with dangling pointers if the layout structure is modified while we keep the copy. This can happen if methods such as tabifyDockWidgets or splitDockWidget get called; e.g. tabifying dock widgets will destroy the layout items that were added for them. Unfortunately, the layout items do not have a pointer back to the layout they live in, and the items in the stored state might not yet live in a layout anyway. So we cannot remove the items from their layout in a QDockWidgetItem destructor implementation. Instead, we have to forget the stored state. Add a helper function that writes the stored state back to the actual state, and deletes the stored state afterwards. Call this function when the layout might get modified programmatically. Add a test case that reproduces the crash without the fix, and passes with the patch. Fixes: QTBUG-120025 Pick-to: 6.7 6.6 6.5 Change-Id: I8f7e886f3c4ac38e25f9b8bc194eea0833e5974f Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: Axel Spoerl <axel.spoerl@qt.io>
* Harden internal documentation of QDockWidgetGroupWindowAxel Spoerl2023-12-041-10/+34
| | | | | | | | | | | | | QDockWidgetGroupWindow was documented by a few lines of code comments, omitting the most critical part of its design: It must not become able to acquire focus (i.e. be dragged or dropped) while having only one QDockWidget child. => replace legacy code comments by structured internal documentation. Pick-to: 6.6 6.5 Change-Id: I410ebf2e4c20c7479038417a4d8448dce8ab995f Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io>
* QMainWindowTabBar: make destructor publicAxel Spoerl2023-11-201-1/+1
| | | | | | | | Was private by mistake => make it public. Pick-to: 6.6 6.5 Change-Id: I6b07a19687ddf84e8456aa70bc34b1cc714a299e Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io>
* QDockWidget: Fix group unpluggingAxel Spoerl2023-11-181-83/+192
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | A floating dock widget could either be a single QDockWidget object, or a QDockWidgetGroupWindow with a single QDockWidget child. The former could be dropped on the latter. Dropping the latter on the former caused a crash. The existence of QDockWidgetGroupWindows with a single dock widget child was accepted to be by design. Previous fixes, such as 9ff40b59da58160dc26c54204a615a2456e07405, attempted to wrap all single floating dock widgets in QDockWidgetGroupWindows. These attempts fell short, because of the manifold programmatic and manual options to create a floating dock widget: - drag a single dock widget out of a main window dock area - drag a dock widget out of a tab bar on the main window - drag a dock widget out of a floating tab - call `QDockWidget::setFloating(true)` in any situation - create a new QDockWidget, that floats from the beginning Whenever a QDockWidgetGroupWindow with a single QDockWidget child was hovered and/or dropped on a QDockWidget without a group window, crashes or screen artifacts were observed. Previous fixes made them occur less often. QDockWidgetGroupWindow is not designed to hold a single QDockWidget child. Such a state is inconsistent and may only exist, while a QDockWidgetGroupWindow is constructed. The reason why such invalid QDockWidgetGroupWindows started to exist, is a bool trap: QDockWidgetPrivate::mouseMoveEvent() starts a drag operation, when a dock widget is moved by mouse. It called startDrag() with no argument, which defaulted to startDrag(true) and caused a group drag. This assumption is *correct*, when a tabbed group of dock widgets is dragged out of the main dock as a whole, to become floating tabs. *wrong*, when a single dock widget is dragged out of a docked group, to become a single floating dock widget. In the second case, the dock widget was wrapped in a new, floating, invisible QDockWidgetGroupWindow. Looking like a single, floating dock widget, the group window caused a crash, when attempted to be dropped on another dock widget. This patch eliminates all cases, where a QDockWidgetGroupWindow with a single QDockWidget is created: (1) Implement QDockWidgetPrivate::isTabbed(). This enables mouseMoveEvent to determine, whether the move relates to a group of tabbed dock widgets, or to a single dock widget. startDrag() can therefore be called with the right argument. It will no longer create a QDockWidgetGroupWindow with a single QDockWidget child. (2) Change QMainWindowTabBar::mouseReleaseEvent When a dock widget was dragged out of a tab bar and became a single, floating dock widget, it was still parented to the group window. That is wrong, because it has no more relationship with that group window. => Reparent it to the main window, just like any other single floating dock widget. That enables QDockWidgetGroupWindow to detect, that the 2nd last child has gone and no more group window is needed (see next point). (3) React to reparenting, closing and deleting If the second last dock widget in a floating tab gets closed (manually or programmatically), reparented or deleted, also unplug the last one and remove the group window. (4) Amend 9ff40b59da58160dc26c54204a615a2456e07405 Remove the code path where a QDockWidgetGroupWindow with a single QDockWidget child was created 'just in case', to make it compatible others, created by (1), (2) or (3). (5) Change QMainWindowLayout::hover() When the hover ends without a successful drop and a temporary group window with a single dock widget child has been created, remove the group window. The patch fixes smaller inconsistencies, which have not become visible due to assertions and crashes earlier in the chain. The patch finally extends tst_QDockWidget, to cover all 4 cases. - Creation of floating tabs The creation of floating tabs is extracted from floatingTabs() to the helper function createFloatingTabs(). In addition to creating floating tabs, the helper verifies that dragging a dock widget out of the main window doesn't accidently wrap it in a group window. This covers case (1). - tst_QDockWidget::floatingTabs() The test function verifies now, that both test dock widgets have the same path before plugging them together and after unplugging them from the floating tab. This covers case(4). - tst_QDockwidget::deleteFloatingTabWithSingleDockWidget() This test function is added, to cover cases (2) and (3). - tst_QDockWidget::hoverWithoutDrop() This test function hovers two floating dock widgets hover each other, and returns the moved dock widget to its origin before releasing the mouse. This covers case(5). This fixes a lot of long standing bugs, making the author of this patch modestly happy :-) Fixes: QTBUG-118223 Fixes: QTBUG-99136 Fixes: QTBUG-118578 Fixes: QTBUG-118579 Fixes: QTBUG-56799 Fixes: QTBUG-35736 Fixes: QTBUG-63448 Fixes: QTBUG-88329 Fixes: QTBUG-88157 Fixes: QTBUG-94097 Fixes: QTBUG-44540 Fixes: QTBUG-53808 Fixes: QTBUG-72915 Fixes: QTBUG-53438 Found-by: Keith Kyzivat <keith.kyzivat@qt.io> Found-by: Frederic Lefebvre <frederic.lefebvre@qt.io> Pick-to: 6.6 6.5 Change-Id: I51b5f9e40cb2dbe55fb14d769541067730538463 Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io>
* QMainWindowTabBar: Add destructorAxel Spoerl2023-11-181-5/+16
| | | | | | | | | | | | | | | | | | | | QMainWindowLayout re-uses tab bars. A QSet and a QList member are kept, to track used and unused tab bars. Corner cases upon application close down leave dangling pointers in those containers. => Add a destructor to QMainWindowTabBar => remove the tab bar from used and unused tab bar containers, if not directly parented to the main window. => No longer reparent unused tab bars of a QDockWidgetGroupWindow to the main window. Let them be destroyed as a group window child, and its destructor remove it from the used/unused tab bar container. Pick-to: 6.6 6.5 Change-Id: If2388cf878553dc89583dbc8585748fad65bbab2 Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io>
* Remove bool trap in QDockWidgetPrivate::endDrag()Axel Spoerl2023-11-171-3/+3
| | | | | | | | | | | | | | endDrag(false) meant to end a drag with a dock location change. endDrag(true) meant to abort a drag without a dock location change. Replace this with a meaningful enumeration. Define a dummy enum for builds w/o QDockWidget. Task-number: QTBUG-118578 Task-number: QTBUG-118579 Pick-to: 6.6 6.5 Change-Id: I786f4210f5a3ee67ffcf0dc9285f77a480148569 Reviewed-by: David Faure <david.faure@kdab.com>
* Fix build with -no-feature-dockwidgetTasuku Suzuki2023-11-161-1/+1
| | | | | | Pick-to: 6.6 6.5 Change-Id: Ie6d4e9a2dcfa6da5392bfb2507aafc57b6511ba3 Reviewed-by: Axel Spoerl <axel.spoerl@qt.io>
* QDockAreaLayout: implement widget based add() and remove()Axel Spoerl2023-11-151-1/+1
| | | | | | | | | | | | | | | The item_list of a QDockAreaLayoutInfo has abstraction methods for reading the item list. Adding to and removing from the item list is done directly, by using the QList api. Implement an abstraction, that takes a QWidget *. The argument may either be a QDockWidgetGroupWindow or a QDockWidget. Task-number: QTBUG-118578 Task-number: QTBUG-118579 Pick-to: 6.6 6.5 Change-Id: Ib2ccd7557a21a43b68f184fe4575018f2a97004b Reviewed-by: David Faure <david.faure@kdab.com>
* QDockWidget: call raise() when a dock widget starts to hoverAxel Spoerl2023-11-151-0/+1
| | | | | | | | | | | | | | | | | | | | | | When dock widget (1) starts to hover over another floating dock widget (2), the latter animates a rubber band, to indicate to the user that it is ready to accept a drop. The creation of a QRubberBand moves (2) one position up in the Z order. The consequence is a visual glitch: While - the mouse cursor dragging (1) is still outside (2) and - the visual rectangle of (1) starts overlapping (2) (1) hides behind (2). As soon as the mouse cursor enters (2), (1) suddenly comes on top and (2) hides behind (1). => raise() 1 as soon as it starts hovering. That brings it on top of the Z order, which is expected behavior. Pick-to: 6.6 6.5 Change-Id: I1140fc6ff109c7a713e7e2617072698467375585 Reviewed-by: Richard Moe Gustavsen <richard.gustavsen@qt.io> Reviewed-by: David Faure <david.faure@kdab.com>
* QDockWidget: Always show dock widgets with the main windowAxel Spoerl2023-11-141-0/+11
| | | | | | | | | | | | | | | | | | | QMainWindow::show() also showed its dock widget children. When a main window with dock widget children consumed a show event for another reason, hidden dock widget children remained hidden. If a dock widget application went to the background, e.g. because it was hidden behind another application gaining focus, a klick on the dock widget application's app icon would not show its dock widget children. Unless the dock widget application provides shows them explicitly, they can never been shown again by the user. => show all dock widget and group window children, when QMainWindow consumes a show event. Pick-to: 6.6 6.5 Change-Id: I7e8b59f021ec4ec5679d0d08d0eeda1e3225a385 Reviewed-by: David Faure <david.faure@kdab.com>
* QMainWindowLayout: remove redundant #ifdef'ryAxel Spoerl2023-11-141-4/+0
| | | | | | | | Remove #if QT_CONFIG(dockwidget) nested within each other. Pick-to: 6.6 6.5 Change-Id: I6c662909676ffada3ac52e41a9c2d8b9fd491689 Reviewed-by: David Faure <david.faure@kdab.com>
* QDockWidget: Remove "group" bool trapAxel Spoerl2023-11-091-6/+6
| | | | | | | | | | | | | | | | | | | | | | The unplug() and startDrag() functions of QMainWindowLayout and QDockWidget used a boolean argument specifying whether a single dock widget or a group of dock widgets should be unplugged. The argument defaulted to true. That has lead to inconsistent unplug operations, broken item_lists and crashes, especially when the methods were called without an argument. To improve code readability, replace bool trap with a meaningful enum. Remove default arguments, in order to force explicit calls. This patch does not change behavior, it is just carved out to facilitate reviews. Task-number: QTBUG-118578 Task-number: QTBUG-118579 Pick-to: 6.6 6.5 Change-Id: I50341b055f0bb76c2797b2fb1126a10de1fee7dd Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io>
* QDockWidgetGroupWindow::adjustFlags() - don't show() empty group windowAxel Spoerl2023-08-151-1/+20
| | | | | | | | | | | | | | | | | | | | The method calls show() on a dock widget group window, when the window flags have changed. When all of its contained, tabbed dock widgets are programmatically hidden or docked on the main window, an empty group window is shown. This patch implements bool hasVisibleDockWidgets(). It returns true, if at least one of the group window's dockwidget children is not hidden. It replaces show() by setVisible(), passing the return value of hasVisibleChildren(). It adapts tst_QDockWidget::floatingTabs() to test the fix. (Drive-by: remove dead code) Fixes: QTBUG-115058 Pick-to: 6.6 6.5 6.2 Change-Id: Ifb8e2450e91a7c78decc06f592e160631ca2faf5 Reviewed-by: Richard Moe Gustavsen <richard.gustavsen@qt.io>
* QDockWidget: Don't insert gap item if QDockWidgetGroupWindow has oneAxel Spoerl2023-06-201-2/+6
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | When a dock widget is hovered over a QDockWidgetGroupWindow, a gap item is inserted at its potential docking position. Since only one item at a time can be moved with the mouse, only one such gap item can exist. QDockAreaLayoutInfo::insertGap() therefore contains an assertion, that kicks in if a second gap item is inserted. QDockWidgetGroupWindow::hover() checks if the dock widget is hovered over a gap item. If that is the case, no additional gap item is inserted. The check fails if a gap item exists in the group window, but the dock widget is hovered over another part of that group window. This can be the case if the group window already contains more than one dock widget: By inserting the gap, the group window's size changes, one of the existing dock widgets receives another hover event and a second gap insertion is attempted. This patch adds QDockAreaLayoutInfo::hasGapItem() to check if a gap already exists. The method is queried in addition to prevent a second gap insertion. An autotest has not been added, because gap items appear and disappear during hovering. The improved functionality can be tested manually with the mainwindow example. Fixes: QTBUG-112491 Fixes: QTBUG-114542 Pick-to: 6.6 6.5 Change-Id: I9ea64e729873a86eb98ea950fbb066817fc25a07 Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io>
* Use platform drags for drags of docks and toolbars on waylandDavid Redondo2023-06-021-0/+39
| | | | | | | | | | | | | | | | | | On Wayland we can't know where windows are in relation to each other so the whole mechanism was broken, toolbars were unmovable once undocked and could be blindly redocked. Dockwidgets had native toolbars to move them around but could not be redocked. This introduces an alternative code path that uses a platform drag with a special mimetype that enables the platform to issue a combined drag and window move using the relevant protocol. Should the protocol not be available this doesn't make things actively worse as it will be similar broken as before. Fixes: QTBUG-87332 Change-Id: I3b8bdc0b1bc22569a64cb8bf7ca7d37d223936a6 Reviewed-by: David Edmundson <davidedmundson@kde.org> Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
* QMainWindow: fix potential crash when restoring tab bar stateColin Snover2023-04-111-1/+4
| | | | | | | | | | Don't activate the mainwindow layout while it is being restored. Otherwise we might end up in recursive calls to setGeometry. Pick-to: 6.5 Fixes: QTBUG-111538 Change-Id: I4b6cba9e0abfbae479f71a65b1c4526d92dac081 Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io>
* QtWidgets: Disambiguate static functions/variables and definesFriedemann Kleint2023-01-141-14/+2
| | | | | | | | | | | | | They cause clashes in CMake Unity (Jumbo) builds. Properly prefixing the childWidgets() function also prevents it from cluttering static builds. Task-number: QTBUG-109394 Pick-to: 6.5 Change-Id: Idd2b1ec748f33cfae8f3213847c43b3fb0550377 Reviewed-by: Axel Spoerl <axel.spoerl@qt.io> Reviewed-by: Jan Arve Sæther <jan-arve.saether@qt.io> Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
* Fix size calculation of unplugged dock widgetsAxel Spoerl2022-12-291-4/+19
| | | | | | | | | | | | | | | When unplugging a dock widget, it still grows by the separator size when dragged upwards or to the left. The unplugged dock widget's size can become too small to drag it or to access window handles. This patch corrects the size offset for all drag directions. It expands the target size to a minimum size, making sure that title bar and window handles can be accessed after unplugging. Fixes: QTBUG-106531 Pick-to: 6.5 6.4 6.2 Change-Id: Ie771a9338ebfb4c0eafd3b3b4205de730cbd20ac Reviewed-by: Shawn Rutledge <shawn.rutledge@qt.io>
* Port from qAsConst() to std::as_const()Marc Mutz2022-10-111-3/+3
| | | | | | | | | | | | | | | | We've been requiring C++17 since Qt 6.0, and our qAsConst use finally starts to bother us (QTBUG-99313), so time to port away from it now. Since qAsConst has exactly the same semantics as std::as_const (down to rvalue treatment, constexpr'ness and noexcept'ness), there's really nothing more to it than a global search-and-replace, with manual unstaging of the actual definition and documentation in dist/, src/corelib/doc/ and src/corelib/global/. Task-number: QTBUG-99313 Change-Id: I4c7114444a325ad4e62d0fcbfd347d2bbfb21541 Reviewed-by: Ivan Solovev <ivan.solovev@qt.io>
* Port from container.count()/length() to size()Marc Mutz2022-10-041-5/+5
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | This is semantic patch using ClangTidyTransformator: auto QtContainerClass = expr(hasType(namedDecl(hasAnyName(<classes>)))).bind(o) makeRule(cxxMemberCallExpr(on(QtContainerClass), callee(cxxMethodDecl(hasAnyName({"count", "length"), parameterCountIs(0))))), changeTo(cat(access(o, cat("size"), "()"))), cat("use 'size()' instead of 'count()/length()'")) a.k.a qt-port-to-std-compatible-api with config Scope: 'Container'. <classes> are: // sequential: "QByteArray", "QList", "QQueue", "QStack", "QString", "QVarLengthArray", "QVector", // associative: "QHash", "QMultiHash", "QMap", "QMultiMap", "QSet", // Qt has no QMultiSet Change-Id: Ibe8837be96e8d30d1846881ecd65180c1bc459af Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io>
* Fix native titlebar offset and resizing upon unplugging dock widgetsAxel Spoerl2022-09-241-2/+15
| | | | | | | | | | | | | | | | | | | | | | | When a dock widget received a native title bar upon unplugging, the position of the newly unplugged dock widget was calculated without taking the title bar's height into consideration. Furthermore, dock widgets grew by the separator size upon undocking. That is fixed by 10a143ccd762c810f4096a5b2e986d16ea0107ad by relying on the assumption that passing a QRect() to the unplugging method leads to un unchanged dock widget geometry. However, when more than one dock widgets are docked in the same main window dock on macOS or Windows, the size is stil increased. This patch corrects the position offset for native title bars. It also corrects an unplugged dock widget's geometry by the sparator's size. Fixes: QTBUG-106530 Fixes: QTBUG-106531 Pick-to: 6.4 6.2 5.15 Change-Id: Ia4bcb556841e14146f19c1377f4010d5ae009bcf Reviewed-by: Shawn Rutledge <shawn.rutledge@qt.io>
* Prevent dock widget from resizing upon unplugging from main windowAxel Spoerl2022-09-211-1/+3
| | | | | | | | | | | | | | | | | | | | | | | | | QDockWidgetLayoutState::itemRect() has been used to calculate a dock widget's size when unplugging from the main window. This method is meant to calculate the size of the rubber band, showing the dock widget's dock area. The rubber band is by QDockAreaLayout::sep wider (top or bottom dock) or higher (left or right dock) than the respective dock widget. This is to make sure the rubber band is never fully covered by the dock widget. By wrongly using itemRect() also for the dock widget's size after unplugging, the dock widget grows in size each time it is unplugged. This patch passes an invalid QRect to QDockWidgetPrivate::unplug(), in order to prevent resizing. tst_QDockWidget::unplugAndResize() is extended to check size consistency after unplugging (corrected for frame margins). Fixes: QTBUG-106531 Pick-to: 6.4 6.2 Change-Id: I1cf9f695691b0e165a5cb2881781602426e5d587 Reviewed-by: Shawn Rutledge <shawn.rutledge@qt.io>
* Fix wrong debug output upon creation of floating dockwidget tabsAxel Spoerl2022-07-131-1/+1
| | | | | | | | | | | When a floating dock is created, a qCDebug message is logged to indicate the hovered dock widget. By mistake, the target pointer to the floating tab is dumped, which is nullptr at that moment. This patch corrects the debugging output. Pick-to: 6.4 6.3 6.2 Change-Id: I317f057ef4b2d8fe508be687152bcede61c22f46 Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io>
* QtWidgets: restore Qt 5 compatibility for save/restore stateGiuseppe D'Angelo2022-05-181-0/+2
| | | | | | | | | | | | | | | | | | | | | | | Several classes in QWidget use QDataStream internally in order to save and restore state. These QDataStream usages were not versioned, meaning that if Qt changes the serialization for some datatype, then the data saved between different Qt versions becomes incompatible. Note that the save/restore API in question just produce opaque blobs as QByteArrays -- the user has no control over the QDataStream objects and thus versions. Fix by version the usages. In QHeaderView this has caused a regression because QBitArray *did* change version between Qt 5 and 6. In general, using QDataStream without explicit versioning is a mistake, so deploy the same fix elsewhere as well. Fixes: QTBUG-99487 Pick-to: 5.15 6.2 6.3 Change-Id: I82bb5c266f4e5dedc0887cbef855dccab1015e29 Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io> Reviewed-by: <doctor.whom@gmail.com>
* Use SPDX license identifiersLucie Gérard2022-05-161-39/+3
| | | | | | | | | | | | | Replace the current license disclaimer in files by a SPDX-License-Identifier. Files that have to be modified by hand are modified. License files are organized under LICENSES directory. Task-number: QTBUG-67283 Change-Id: Id880c92784c40f3bbde861c0d93f58151c18b9f1 Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: Lars Knoll <lars.knoll@qt.io> Reviewed-by: Jörg Bornemann <joerg.bornemann@qt.io>
* QtWidgets: use _L1 for for creating Latin-1 string literalsSona Kurazyan2022-05-021-11/+13
| | | | | | Task-number: QTBUG-98434 Change-Id: I310ea8f19d73a79d985ebfb8bfbff7a02c424360 Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io>
* Fix QDockWidget parenting and dock permissionsAxel Spoerl2022-04-191-101/+230
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | Check DockWidgetArea permissions of QDockWidgetGroupWindows with single dock widget. Obtain a dock widget's tab position from a dock widget group window if it can't be established otherwise. Remove hardcoded assumption that a dock widget is in the left dock. Both cases have lead to inconsistent entries and dangling pointers in QDockAreaLayoutInfo::item_list. Remove warning: QMainWindowLayout::tabPosition called with out-of-bounds value '0', which becomes obsolete by the fix. Create a QDockWidgetGroup window prepered to become a floating tab, whenever a dock widget is being hovered over. Store it in item_list so it can be found and deleted when required. No longer call e->ignore() after propagating close events to the first dock widget and thus preventing others from receiving the event. Add logging category qt.widgets.dockwidgets Update dock widget autotest with tests to check the fixes mentioned: plugging, unplugging, hiding, showing, closing and deleting. Blackist closeAndDelete, floatingTabs test on macos, QEMU, arm, android due to flaky isFloating() response after a dock widget has been closed or plugged. QSKIP dockPermissions and floatingTabs test on Windows due to mouse simulation malfunction. QSKIP hideAndShow test on Linux in case of xcb error (QTBUG-82059) Fixes: QTBUG-99136 Pick-to: 6.3 6.2 Change-Id: Ibd353e0acc9831a0d67c9f682429ab46b94bdbb0 Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io>
* QMainWindow: Fix unused separator widgets blocking mouse eventsEike Ziller2022-03-161-0/+8
| | | | | | | | | | | We need to hide separator widgets that are unused, otherwise they block mouse events from the underlying widgets. Pick-to: 6.2 6.3 Fixes: QTCREATORBUG-24600 Change-Id: I98c6d4860f683a861b89c4cad042bb734f590000 Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io>
* Fix QDockWidget's dock area permissions after hoveringAxel Spoerl2022-03-111-2/+12
| | | | | | | | | | | | | | | | | When a QDockWidget's dock areas are restricted by setAllowedAreas(...) and a second QDockWidget is hovered over it, the first QDockWidget can be docked to any dock area of the main window. Area restrictions will be ignored. That is due to the first QDockWidget being implicitely mutated into a QDockWidgetGroupWindow upon hovering. By definition, the latter has no docking restricitons. This fix adds a check if a QDockWidgetGroupWindow has a single QDockWidget child. In that case, the single child's area permissions will restrict docking. Fixes: QTBUG-100670 Pick-to: 6.3 6.2 5.15 Change-Id: I903b074739953791634f482c9cf4b9a95a1d93d3 Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io>
* Fix restoring main window state for maximized/fullscreen windowsVolker Hilsheimer2021-10-161-0/+73
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | On systems that asynchronously resize the window to maximized or full screen state, the window will become visible in its normal geometry before it gets the final size by the windowing system. This might cause multiple resize events, to each of which the widget's layout responds with a call to its setGeometry implementation. The QMainWindowLayout is special in that it will shrink dock widgets if there is not enough space for them, but it doesn't grow them back once there is. With the initial resize event being for a smaller size than what was restored, the state is not restored correctly, but remains in the state that fit into the smallest size with which setGeometry got called. To fix this, we have to keep the restored state around until the window either gets a size that is large enough for it to fit, or until we can be reasonably certain that the windowing system is done resizing the window while transitioning it to the maximized or full screen state. Since across the various platforms and windowing systems there is no reliable way to know when the window reaches its final size, we have to use a timer that we (re)start for each call to setGeometry with a size that's not large enough. Once the timer times out, we have to give up; then the last layout state calculated is the final state. To calculate the size of the layout, introduce a function to the QDockAreaLayout that returns the size required for the current sizes of the docks. Refactor sizeHint and minimumSize (which were identical) into a helper template that takes member-function pointers to call the respective method from the dock area layout's content items. Add a test case for various permutations of the scenario. The timeout of 150ms is based on running this test case repeatedly on various desktop platforms and X11 window managers. Fixes: QTBUG-46620 Change-Id: I489675c2c40d3308ac8194aeb4267172b2fb38be Reviewed-by: Albert Astals Cid <albert.astals.cid@kdab.com> Reviewed-by: Lars Knoll <lars.knoll@qt.io> Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
* QObject: optimize the common case of findChildren(QString())Marc Mutz2021-07-131-7/+7
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | Outside tests, all in-tree callers of QObject::findChildren() pass no name to match, and in my experience that is also true for the vast majority of out-of-tree users. Avoid the temporary QString creation in the caller and the repeated QString::isNull() checks in the implementation by overloading findChildren() without a name argument and checking for name.isNull() only once, forking off into separate helper functions. Adjust in-tree callers that used an explicit `QString()` argument in order to pass options, which goes to show that `name` should never have been the first argument of findChilden() in the first place, even though I appreciate the symmetry with findChild() (the use-cases of which, however, are radically different). Change a `findChildren().size() == 0` call found while scanning for findChildren() calls to `!findChild()` as a drive-by. Modernize loops in the various qt_qFindChild{,ren}_helper() overloads to match how the new code looks. [ChangeLog][QtCore][QObject] Added findChildren() overload taking no name (thus optimizing this common case). Change-Id: Ifc56e5438023d079b40c67f11ae274a3e128ad5e Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io> Reviewed-by: Mårten Nordheim <marten.nordheim@qt.io>
* QWidget: mark obsolete function isTopLevel() as deprecatedChristian Ehrlicher2020-12-091-1/+1
| | | | | | | | QWidget::isTopLevel() is deprecated and can be replaced 1:1 with isWindow(). Sadly it's was not marked with Q_DECL_DEPRECATED in 5.15 Change-Id: I4508fbde41927f3b82e47a75011179548325029d Reviewed-by: Friedemann Kleint <Friedemann.Kleint@qt.io>
* Another round of replacing 0 with nullptrAllan Sandfeld Jensen2020-10-071-13/+13
| | | | | | | | | This time based on grepping to also include documentation, tests and examples previously missed by the automatic tool. Change-Id: Ied1703f4bcc470fbc275f759ed5b7c588a5c4e9f Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: Friedemann Kleint <Friedemann.Kleint@qt.io>
* QLayout::indexOf: redo implementationGiuseppe D'Angelo2020-08-261-2/+4
| | | | | | | | | | | | Stop relying on the "magic" of itemAt returning nullptr for out of bounds. Just use count(). Unfortunately, QMainWindowLayout breaks the API contract by NOT implementing count() properly. So, make its count() crash if called; and move the itemAt implementation there. Change-Id: I120686a834bab15dd537598a56bd93d6a5924aa5 Reviewed-by: Richard Moe Gustavsen <richard.gustavsen@qt.io>
* Remove deprecated QStyleOption::init()Christian Ehrlicher2020-06-211-1/+1
| | | | | | | | Even it was not marked as deprecated the replacement function initFrom() is available since Qt4 times (and init() is deprecated since then) Change-Id: I09a4ebbf66b01fbe7aec67691dc68d2e42d1cd78 Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io>
* Replace calls to deprecated QEvent accessor functionsShawn Rutledge2020-06-081-2/+2
| | | | | | | Many of these were generated by clazy using the new qevent-accessors check. Change-Id: Ie17af17f50fdc9f47d7859d267c14568cc350fd0 Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io>
* Explicitly prevent out-of-bounds access to tabPositions arrayVolker Hilsheimer2020-05-051-1/+5
| | | | | | | | | | | Use DockCount enum value for the size of the array, and explicitly handle when toDockPos returns DockCount (which it might). Change-Id: Id52399607fb1ae74a24a050de7a8481264c03e47 Fixes: QTBUG-83983 Coverity-Id: 218539 Pick-to: 5.15 Reviewed-by: Marc Mutz <marc.mutz@kdab.com>
* QMainWindow: don't grow memory when modifying tabbed docks while hiddenVolker Hilsheimer2020-04-241-0/+9
| | | | | | | | | | | | | | | | | | | QMainWindow tries to avoid memory allocations by caching tab bars that are no longer used. That cache is populated when the layout is activated. The layout might never be activated when the main window is never shown, in which case adding and removing dock widgets at runtime will continuously allocate more memory for tab bars that are created. A workaround is to call QMainWindow::layout()->activate() explicitly in application code, once all dock widgets have been removed. This change avoids that applications have to do that. Change-Id: I70eb585d2120f0b7b73f59c3ee65d7242c12ec59 Fixes: QTBUG-83135 Pick-to: 5.15 Reviewed-by: Richard Moe Gustavsen <richard.gustavsen@qt.io>
* Unexport QWidgetResizeHandler and remove move functionalityVolker Hilsheimer2020-04-031-2/+1
| | | | | | | | | | | | Address FIXME comment. The class is not public, and only used in QtWidgets for the resizing of docking widgets. The move functionality is unused, and has been removed. Change-Id: Id477f36cb7d449b06e124950fed6f5f182aa5721 Reviewed-by: Richard Moe Gustavsen <richard.gustavsen@qt.io> Reviewed-by: Friedemann Kleint <Friedemann.Kleint@qt.io>
* Tidy nullptr usageAllan Sandfeld Jensen2019-12-061-44/+44
| | | | | | | | | | | Move away from using 0 as pointer literal. Done using clang-tidy. This is not complete as run-clang-tidy can't handle all of qtbase in one go. Change-Id: I1076a21f32aac0dab078af6f175f7508145eece0 Reviewed-by: Friedemann Kleint <Friedemann.Kleint@qt.io> Reviewed-by: Lars Knoll <lars.knoll@qt.io>
* Fix build without feature.tabbarTasuku Suzuki2019-07-021-22/+31
| | | | | Change-Id: I0891f8f6054382407f5ce2fdb3ead0203d255945 Reviewed-by: Richard Moe Gustavsen <richard.gustavsen@qt.io>
* Fix build without feature.dockwidget and tabwidgetTasuku Suzuki2019-07-021-3/+5
| | | | | Change-Id: I621664f646475c1b5cfde47b7087c0c9f5ad8e4d Reviewed-by: Richard Moe Gustavsen <richard.gustavsen@qt.io>
* Add accessors for QWindow and QScreen to QWidgetPrivateFriedemann Kleint2019-06-181-3/+3
| | | | | | | | | | | | | | | | | Rewrite the existing accessor QWidgetPrivate::windowHandle() to accept a mode enumeration that has an "Any" convenience. Based on that, add QWidgetPrivate::associatedScreen(), which is seful in many places where scaling is performed. Prototypically simplify the code. Task-number: QTBUG-62094 Task-number: QTBUG-73231 Change-Id: I516288363d329bce9bc94e4951106f9357bc6cde Reviewed-by: Tor Arne Vestbø <tor.arne.vestbo@qt.io>
* QDockWidget: Store tab position when undockingFriedemann Kleint2019-03-251-1/+26
| | | | | | | | | Add a field remembering the tab position of the dock widget area to QDockWidgetPrivate and use that when grouping floating docks. Fixes: QTBUG-74242 Change-Id: I2a453080cb39dd4a5491976f1aeca70ae681682a Reviewed-by: Richard Moe Gustavsen <richard.gustavsen@qt.io>