File indexing completed on 2024-05-12 15:34:14
0001 /* 0002 SPDX-FileCopyrightText: 2022 Volker Krause <vkrause@kde.org> 0003 SPDX-License-Identifier: LGPL-2.0-or-later 0004 */ 0005 0006 #ifndef KWINDOWSTATESAVER_H 0007 #define KWINDOWSTATESAVER_H 0008 0009 #include <kconfiggroup.h> 0010 #include <kconfiggui_export.h> 0011 0012 #include <QObject> 0013 0014 class QWindow; 0015 class KWindowStateSaverPrivate; 0016 0017 /** 0018 * Saves and restores a window size and (when possible) position. 0019 * 0020 * This is useful for retrofitting persisting window geometry on existing windows or dialogs, 0021 * without having to modify those classes themselves, or having to inherit from them. 0022 * For this, create a new instance of KWindowStateSaver for every window that should have it's 0023 * state persisted, and pass it the window or widget as well as the config group the state 0024 * should be stored in. The KWindowStateSaver will restore an existing state and then monitor 0025 * the window for subsequent changes to persist. It will delete itself once the window is 0026 * deleted. 0027 * 0028 * @code 0029 * QPrintPreviewDialog dlg = ... 0030 * new KWindowStateSaver(&dlg, "printPreviewDialogState"); 0031 * ... 0032 * dlg.exec(); 0033 * @endcode 0034 * 0035 * Note that freshly created top-level QWidgets (such as the dialog in the above example) 0036 * do not have an associated QWindow yet (ie. windowHandle() return @c nullptr). KWindowStateSaver 0037 * supports this with its QWidget constructors which will monitor the widget for having 0038 * its associated QWindow created before continuing with that. 0039 * 0040 * When implementing your own windows/dialogs, using KWindowConfig directly can be an 0041 * alternative. 0042 * 0043 * @see KWindowConfig 0044 * @since 5.92 0045 */ 0046 class KCONFIGGUI_EXPORT KWindowStateSaver : public QObject 0047 { 0048 Q_OBJECT 0049 public: 0050 /** 0051 * Create a new window state saver for @p window. 0052 * @param configGroup A KConfigGroup that holds the window state. 0053 */ 0054 explicit KWindowStateSaver(QWindow *window, const KConfigGroup &configGroup); 0055 /** 0056 * Create a new window state saver for @p window. 0057 * @param configGroupName The name of a KConfigGroup in the default state 0058 * configuration (see KSharedConfig::openStateConfig) that holds the window state. 0059 */ 0060 explicit KWindowStateSaver(QWindow *window, const QString &configGroupName); 0061 /** 0062 * Create a new window state saver for @p window. 0063 * @param configGroupName The name of a KConfigGroup in the default state 0064 * configuration (see KSharedConfig::openStateConfig) that holds the window state. 0065 */ 0066 explicit KWindowStateSaver(QWindow *window, const char *configGroupName); 0067 0068 /** 0069 * Create a new window state saver for @p widget. 0070 * Use this for widgets that aren't shown yet and would still return @c nullptr from windowHandle(). 0071 * @param configGroup A KConfigGroup that holds the window state. 0072 */ 0073 template<typename Widget> 0074 explicit inline KWindowStateSaver(Widget *widget, const KConfigGroup &configGroup); 0075 /** 0076 * Create a new window state saver for @p widget. 0077 * Use this for widgets that aren't shown yet and would still return @c nullptr from windowHandle(). 0078 * @param configGroupName The name of a KConfigGroup in the default state 0079 * configuration (see KSharedConfig::openStateConfig) that holds the window state. 0080 */ 0081 template<typename Widget> 0082 explicit inline KWindowStateSaver(Widget *widget, const QString &configGroupName); 0083 /** 0084 * Create a new window state saver for @p widget. 0085 * Use this for widgets that aren't shown yet and would still return @c nullptr from windowHandle(). 0086 * @param configGroupName The name of a KConfigGroup in the default state 0087 * configuration (see KSharedConfig::openStateConfig) that holds the window state. 0088 */ 0089 template<typename Widget> 0090 explicit inline KWindowStateSaver(Widget *widget, const char *configGroupName); 0091 0092 ~KWindowStateSaver(); 0093 0094 private: 0095 void timerEvent(QTimerEvent *event) override; 0096 bool eventFilter(QObject *watched, QEvent *event) override; 0097 0098 // API used by template code, so technically part of the ABI 0099 void initWidget(QObject *widget, const std::function<QWindow *()> &windowHandleCallback, const KConfigGroup &configGroup); 0100 void initWidget(QObject *widget, const std::function<QWindow *()> &windowHandleCallback, const QString &configGroupName); 0101 void initWidget(QObject *widget, const std::function<QWindow *()> &windowHandleCallback, const char *configGroupName); 0102 0103 // cannot use std::unique_ptr due to the template ctors 0104 // not seeing the full private class 0105 KWindowStateSaverPrivate *d = nullptr; 0106 }; 0107 0108 template<typename Widget> 0109 KWindowStateSaver::KWindowStateSaver(Widget *widget, const KConfigGroup &configGroup) 0110 : QObject(widget) 0111 { 0112 initWidget( 0113 widget, 0114 [widget]() { 0115 return widget->windowHandle(); 0116 }, 0117 configGroup); 0118 } 0119 0120 template<typename Widget> 0121 KWindowStateSaver::KWindowStateSaver(Widget *widget, const QString &configGroupName) 0122 : QObject(widget) 0123 { 0124 initWidget( 0125 widget, 0126 [widget]() { 0127 return widget->windowHandle(); 0128 }, 0129 configGroupName); 0130 } 0131 0132 template<typename Widget> 0133 KWindowStateSaver::KWindowStateSaver(Widget *widget, const char *configGroupName) 0134 : QObject(widget) 0135 { 0136 initWidget( 0137 widget, 0138 [widget]() { 0139 return widget->windowHandle(); 0140 }, 0141 configGroupName); 0142 } 0143 0144 #endif // KWINDOWSTATESAVER_H