guide: add multiple files and singletons sections to intro
This commit is contained in:
parent
dfa95a1ece
commit
581ec772ac
|
@ -514,3 +514,293 @@ ShellRoot {
|
|||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Multiple files
|
||||
|
||||
In an example as small as this it isn't a problem, but as your project
|
||||
gets bigger you may become annoyed having everything all
|
||||
in one file. Luckily its easy to break a component out to a new file.
|
||||
|
||||
Lets move the entire bar into a new file to make space for other widgets:
|
||||
```qml {filename="shell.qml"}
|
||||
import Quickshell
|
||||
|
||||
ShellRoot {
|
||||
Bar {}
|
||||
}
|
||||
```
|
||||
|
||||
```qml {filename="Bar.qml"}
|
||||
import Quickshell
|
||||
import Quickshell.Io
|
||||
import QtQuick
|
||||
|
||||
Scope {
|
||||
property string time;
|
||||
|
||||
Variants {
|
||||
variants: Quickshell.screens.map(screen => ({ screen }))
|
||||
|
||||
PanelWindow {
|
||||
anchors {
|
||||
top: true
|
||||
left: true
|
||||
right: true
|
||||
}
|
||||
|
||||
height: 30
|
||||
|
||||
Text {
|
||||
anchors.centerIn: parent
|
||||
|
||||
// now just time instead of root.time
|
||||
text: time
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Process {
|
||||
id: dateProc
|
||||
command: ["date"]
|
||||
running: true
|
||||
|
||||
stdout: SplitParser {
|
||||
// now just time instead of root.time
|
||||
onRead: data => time = data
|
||||
}
|
||||
}
|
||||
|
||||
Timer {
|
||||
interval: 1000
|
||||
running: true
|
||||
repeat: true
|
||||
onTriggered: dateProc.running = true
|
||||
}
|
||||
}
|
||||
```
|
||||
<span class="small">See also: [Scope](/docs/types/quickshell/scope/)</span>
|
||||
|
||||
Any qml file that starts with an uppercase letter can be referenced this way.
|
||||
We can bring in other folders as well using
|
||||
[import statements](/docs/configuration/qml-overview/#explicit-imports).
|
||||
|
||||
Now what about breaking out the clock? This is a bit more complex because
|
||||
the clock component in the bar and the process and timer that make up the actual
|
||||
clock both need to be dealt with.
|
||||
|
||||
To start with let's move the clock to a new file. For now it's just a
|
||||
single `Text` object but the same concepts apply regardless of complexity
|
||||
(and you probably want a more complicated clock than this.)
|
||||
|
||||
```qml {filename="ClockWidget.qml"}
|
||||
import QtQuick
|
||||
|
||||
// Item is a common base type for visual components
|
||||
Item {
|
||||
// make a property the creator of this type is required to set
|
||||
required property string time
|
||||
|
||||
// size the item to its children
|
||||
width: childrenRect.width
|
||||
height: childrenRect.height
|
||||
|
||||
// use the default property to contain the clock
|
||||
Text {
|
||||
text: time
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
```qml {filename="Bar.qml"}
|
||||
import Quickshell
|
||||
import Quickshell.Io
|
||||
import QtQuick
|
||||
|
||||
Scope {
|
||||
id: root
|
||||
property string time;
|
||||
|
||||
Variants {
|
||||
variants: Quickshell.screens.map(screen => ({ screen }))
|
||||
|
||||
PanelWindow {
|
||||
anchors {
|
||||
top: true
|
||||
left: true
|
||||
right: true
|
||||
}
|
||||
|
||||
height: 30
|
||||
|
||||
// the ClockWidget type we just created
|
||||
ClockWidget {
|
||||
anchors.centerIn: parent
|
||||
// Warning: setting `time: time` will bind time to itself which is not what we want
|
||||
time: root.time
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Process {
|
||||
id: dateProc
|
||||
command: ["date"]
|
||||
running: true
|
||||
|
||||
stdout: SplitParser {
|
||||
onRead: data => time = data
|
||||
}
|
||||
}
|
||||
|
||||
Timer {
|
||||
interval: 1000
|
||||
running: true
|
||||
repeat: true
|
||||
onTriggered: dateProc.running = true
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
While this example is larger than what we had before, we can now expand
|
||||
on the clock widget without cluttering the bar file.
|
||||
|
||||
Let's deal with the clock's update logic now:
|
||||
|
||||
```qml {filename="Time.qml"}
|
||||
import Quickshell
|
||||
import Quickshell.Io
|
||||
import QtQuick
|
||||
|
||||
Scope {
|
||||
property string time;
|
||||
|
||||
Process {
|
||||
id: dateProc
|
||||
command: ["date"]
|
||||
running: true
|
||||
|
||||
stdout: SplitParser {
|
||||
onRead: data => time = data
|
||||
}
|
||||
}
|
||||
|
||||
Timer {
|
||||
interval: 1000
|
||||
running: true
|
||||
repeat: true
|
||||
onTriggered: dateProc.running = true
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
```qml {filename="Bar.qml"}
|
||||
import Quickshell
|
||||
|
||||
Scope {
|
||||
// the Time type we just created
|
||||
Time { id: timeSource }
|
||||
|
||||
Variants {
|
||||
variants: Quickshell.screens.map(screen => ({ screen }))
|
||||
|
||||
PanelWindow {
|
||||
anchors {
|
||||
top: true
|
||||
left: true
|
||||
right: true
|
||||
}
|
||||
|
||||
height: 30
|
||||
|
||||
ClockWidget {
|
||||
anchors.centerIn: parent
|
||||
// now using the time from timeSource
|
||||
time: timeSource.time
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Singletons
|
||||
|
||||
Now you might be thinking, why do we need the `Time` type in
|
||||
our bar file, and the answer is we don't. We can make `Time`
|
||||
a [singleton](/docs/configuration/qml-overview/#singletons).
|
||||
|
||||
A singleton object has only one instance, and is accessible from
|
||||
any scope.
|
||||
|
||||
```qml {filename="Time.qml"}
|
||||
// with this line our type becomes a singleton
|
||||
pragma Singleton
|
||||
|
||||
import Quickshell
|
||||
import Quickshell.Io
|
||||
import QtQuick
|
||||
|
||||
// your singletons should always have Singleton as the type
|
||||
Singleton {
|
||||
property string time;
|
||||
|
||||
Process {
|
||||
id: dateProc
|
||||
command: ["date"]
|
||||
running: true
|
||||
|
||||
stdout: SplitParser {
|
||||
onRead: data => time = data
|
||||
}
|
||||
}
|
||||
|
||||
Timer {
|
||||
interval: 1000
|
||||
running: true
|
||||
repeat: true
|
||||
onTriggered: dateProc.running = true
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
```qml {filename="ClockWidget.qml"}
|
||||
import QtQuick
|
||||
|
||||
Item {
|
||||
// we no longer need time as an input
|
||||
|
||||
width: childrenRect.width
|
||||
height: childrenRect.height
|
||||
|
||||
Text {
|
||||
// directly access the time property from the Time singleton
|
||||
text: Time.time
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
```qml {filename="Bar.qml"}
|
||||
import Quickshell
|
||||
|
||||
Scope {
|
||||
// no more time object
|
||||
|
||||
Variants {
|
||||
variants: Quickshell.screens.map(screen => ({ screen }))
|
||||
|
||||
PanelWindow {
|
||||
anchors {
|
||||
top: true
|
||||
left: true
|
||||
right: true
|
||||
}
|
||||
|
||||
height: 30
|
||||
|
||||
ClockWidget {
|
||||
anchors.centerIn: parent
|
||||
|
||||
// no more time binding
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
|
|
@ -679,12 +679,14 @@ QML Types can be easily made into a singleton, meaning there is only one instanc
|
|||
of the type.
|
||||
|
||||
To make a type a singleton, put `pragma Singleton` at the top of the file.
|
||||
To ensure it behaves correctly with quickshell you should also make
|
||||
[Singleton](/docs/types/quickshell/singleton) the root item of your type.
|
||||
|
||||
```qml
|
||||
pragma Singleton
|
||||
import ...
|
||||
|
||||
Item { ... }
|
||||
Singleton { ... }
|
||||
```
|
||||
|
||||
once a type is a singleton, its members can be accessed by name from neighboring
|
||||
|
|
|
@ -22,11 +22,11 @@
|
|||
]
|
||||
},
|
||||
"locked": {
|
||||
"lastModified": 1710162131,
|
||||
"narHash": "sha256-iaLK3zoKZ84VWvykaupB4Vk0i5xJxFkCR8xqsxiob3g=",
|
||||
"lastModified": 1710400582,
|
||||
"narHash": "sha256-Qr6Nt12Wi7t5X1wbij+FuXKJnHnH2E4KpGjc9XcqTaA=",
|
||||
"ref": "refs/heads/master",
|
||||
"rev": "d11868c32f9c82c7e6f404f77ffe1137e8c093e0",
|
||||
"revCount": 109,
|
||||
"rev": "ffbdac9977588dd89ba6f077eb1f45890002663d",
|
||||
"revCount": 115,
|
||||
"type": "git",
|
||||
"url": "https://git.outfoxxed.me/outfoxxed/quickshell"
|
||||
},
|
||||
|
|
Loading…
Reference in a new issue