forked from quickshell/quickshell
feat: add PersistentProperties
This commit is contained in:
parent
ed62193978
commit
083fff57be
|
@ -39,6 +39,7 @@ qt_add_executable(quickshell
|
||||||
src/cpp/qmlscreen.cpp
|
src/cpp/qmlscreen.cpp
|
||||||
src/cpp/watcher.cpp
|
src/cpp/watcher.cpp
|
||||||
src/cpp/region.cpp
|
src/cpp/region.cpp
|
||||||
|
src/cpp/persistentprops.cpp
|
||||||
)
|
)
|
||||||
|
|
||||||
qt_add_qml_module(quickshell URI QuickShell)
|
qt_add_qml_module(quickshell URI QuickShell)
|
||||||
|
|
|
@ -9,6 +9,7 @@ headers = [
|
||||||
"proxywindow.hpp",
|
"proxywindow.hpp",
|
||||||
"layershell.hpp",
|
"layershell.hpp",
|
||||||
"region.hpp",
|
"region.hpp",
|
||||||
|
"persistentprops.hpp",
|
||||||
]
|
]
|
||||||
-----
|
-----
|
||||||
The core types provided by QuickShell
|
The core types provided by QuickShell
|
||||||
|
|
24
src/cpp/persistentprops.cpp
Normal file
24
src/cpp/persistentprops.cpp
Normal file
|
@ -0,0 +1,24 @@
|
||||||
|
#include "persistentprops.hpp"
|
||||||
|
|
||||||
|
#include <qobject.h>
|
||||||
|
#include <qtmetamacros.h>
|
||||||
|
|
||||||
|
void PersistentProperties::onReload(QObject* oldInstance) {
|
||||||
|
if (qobject_cast<PersistentProperties*>(oldInstance) == nullptr) {
|
||||||
|
emit this->loaded();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const auto* metaObject = this->metaObject();
|
||||||
|
for (auto i = metaObject->propertyOffset(); i < metaObject->propertyCount(); i++) {
|
||||||
|
const auto prop = metaObject->property(i);
|
||||||
|
auto oldProp = oldInstance->property(prop.name());
|
||||||
|
|
||||||
|
if (oldProp.isValid()) {
|
||||||
|
this->setProperty(prop.name(), oldProp);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
emit this->loaded();
|
||||||
|
emit this->reloaded();
|
||||||
|
}
|
57
src/cpp/persistentprops.hpp
Normal file
57
src/cpp/persistentprops.hpp
Normal file
|
@ -0,0 +1,57 @@
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include <qobject.h>
|
||||||
|
#include <qqmlintegration.h>
|
||||||
|
|
||||||
|
#include "reload.hpp"
|
||||||
|
|
||||||
|
///! Object that holds properties that can persist across a config reload.
|
||||||
|
/// PersistentProperties holds properties declated in it across a reload, which is
|
||||||
|
/// often useful for things like keeping expandable popups open and styling them.
|
||||||
|
///
|
||||||
|
/// Below is an example of using `PersistentProperties` to keep track of the state
|
||||||
|
/// of an expandable panel. When the configuration is reloaded, the `expanderOpen` property
|
||||||
|
/// will be saved and the expandable panel will stay in the open/closed state.
|
||||||
|
///
|
||||||
|
/// ```qml
|
||||||
|
/// PersistentProperties {
|
||||||
|
/// id: persist
|
||||||
|
/// reloadableId: "persistedStates"
|
||||||
|
///
|
||||||
|
/// property bool expanderOpen: false
|
||||||
|
/// }
|
||||||
|
///
|
||||||
|
/// Button {
|
||||||
|
/// id: expanderButton
|
||||||
|
/// anchors.centerIn: parent
|
||||||
|
/// text: "toggle expander"
|
||||||
|
/// onClicked: persist.expanderOpen = !persist.expanderOpen
|
||||||
|
/// }
|
||||||
|
///
|
||||||
|
/// Rectangle {
|
||||||
|
/// anchors.top: expanderButton.bottom
|
||||||
|
/// anchors.left: expanderButton.left
|
||||||
|
/// anchors.right: expanderButton.right
|
||||||
|
/// height: 100
|
||||||
|
///
|
||||||
|
/// color: "lightblue"
|
||||||
|
/// visible: persist.expanderOpen
|
||||||
|
/// }
|
||||||
|
/// ```
|
||||||
|
class PersistentProperties: public Reloadable {
|
||||||
|
Q_OBJECT;
|
||||||
|
QML_ELEMENT;
|
||||||
|
|
||||||
|
public:
|
||||||
|
PersistentProperties(QObject* parent = nullptr): Reloadable(parent) {}
|
||||||
|
|
||||||
|
void onReload(QObject* oldInstance) override;
|
||||||
|
|
||||||
|
signals:
|
||||||
|
/// Called every time the reload stage completes.
|
||||||
|
/// Will be called every time, including when nothing was loaded from an old instance.
|
||||||
|
void loaded();
|
||||||
|
/// Called every time the properties are reloaded.
|
||||||
|
/// Will not be called if no old instance was loaded.
|
||||||
|
void reloaded();
|
||||||
|
};
|
|
@ -52,7 +52,9 @@ class Reloadable: public QObject, public QQmlParserStatus {
|
||||||
public:
|
public:
|
||||||
explicit Reloadable(QObject* parent = nullptr): QObject(parent) {}
|
explicit Reloadable(QObject* parent = nullptr): QObject(parent) {}
|
||||||
|
|
||||||
/// called unconditionally in the reload phase, with nullptr if no source could be determined
|
// Called unconditionally in the reload phase, with nullptr if no source could be determined.
|
||||||
|
// If non null the old instance may or may not be of the same type, and should be checked
|
||||||
|
// by `onReload`.
|
||||||
virtual void onReload(QObject* oldInstance) = 0;
|
virtual void onReload(QObject* oldInstance) = 0;
|
||||||
|
|
||||||
// TODO: onReload runs after initialization for reloadable objects created late
|
// TODO: onReload runs after initialization for reloadable objects created late
|
||||||
|
|
Loading…
Reference in a new issue