diff options
author | Aylur <[email protected]> | 2024-10-15 01:22:24 +0000 |
---|---|---|
committer | Aylur <[email protected]> | 2024-10-15 01:22:24 +0000 |
commit | ede8890a08b3fbbb1f6df3b8c277ab6424d1befd (patch) | |
tree | edcf54da90550a1c53c0221a7340e43b479ecee5 /docs/guide/typescript/variable.md | |
parent | d63332b533b390e7e68f8f1fc2432958c4d36a4f (diff) |
docs: better explain ags
Diffstat (limited to 'docs/guide/typescript/variable.md')
-rw-r--r-- | docs/guide/typescript/variable.md | 153 |
1 files changed, 153 insertions, 0 deletions
diff --git a/docs/guide/typescript/variable.md b/docs/guide/typescript/variable.md new file mode 100644 index 0000000..4207f61 --- /dev/null +++ b/docs/guide/typescript/variable.md @@ -0,0 +1,153 @@ +# Variable + +```js +import { Variable } from "astal" +``` + +Variable is just a simple object which holds a single value. +It also has some shortcuts for hooking up subprocesses, intervals and other gobjects. + +:::info +The `Variable` object imported from the `"astal"` package is **not** [Astal.Variable](https://aylur.github.io/libastal/class.Variable.html). +::: + +## Example Usage + +```typescript +const myvar = Variable("initial-value") + +// whenever its value changes, callback will be executed +myvar.subscribe((value: string) => { + console.log(value) +}) + +// settings its value +myvar.set("new value") + +// getting its value +const value = myvar.get() + +// binding them to widgets +Widget.Label({ + label: bind(myvar).as((value) => `transformed ${value}`), + label: myvar((value) => `transformed ${value}`), // shorthand for the above +}) +``` + +:::warning +Make sure to make the transform functions passed to `.as()` are pure. +The `.get()` function can be called anytime by `astal` especially when `deriving`, +so make sure there are no sideeffects. +::: + +## Variable Composition + +Using `Variable.derive` any `Subscribable` object can be composed. + +```typescript +const v1: Variable<number> = Variable(1) +const v2: Binding<number> = bind(obj, "prop") +const v3: Subscribable<number> = { + get: () => 3, + subscribe: () => () => {}, +} + +// first argument is a list of dependencies +// second argument is a transform function, +// where the parameters are the values of the dependencies in the order they were passed +const v4: Variable<number> = Variable.derive( + [v1, v2, v3], + (v1: number, v2: number, v3: number) => { + return v1 * v2 * v3 + } +) +``` + +:::info +The types are only for demonstration purposes, you do not have to declare +the type of a Variable, they will be inferred from their initial value. +::: + +## Subprocess shorthands + +Using `.poll` and `.watch` we can start subprocesses and capture their +output. They can poll and watch at the same time, but they +can only poll/watch once. + +:::warning +The command parameter is passed to [execAsync](/guide/ags/utilities#executing-external-commands-and-scripts) +which means they are **not** executed in a shell environment, +they do **not** expand ENV variables like `$HOME`, +and they do **not** handle logical operators like `&&` and `||`. + +If you want bash, run them with bash. + +```js +Variable("").poll(1000, ["bash", "-c", "command $VAR && command"]) +``` + +::: + +```typescript +const myVar = Variable(0) + .poll(1000, "command", (out: string, prev: number) => parseInt(out)) + .poll(1000, ["bash", "-c", "command"], (out, prev) => parseInt(out)) + .poll(1000, (prev) => prev + 1) +``` + +```typescript +const myVar = Variable(0) + .watch("command", (out: string, prev: number) => parseInt(out)) + .watch(["bash", "-c", "command"], (out, prev) => parseInt(out)) +``` + +You can temporarily stop them and restart them whenever. + +```js +myvar.stopWatch() // this kills the subprocess +myvar.stopPoll() + +myvar.startListen() // launches the subprocess again +myvar.startPoll() + +console.log(myvar.isListening()) +console.log(myvar.isPolling()) +``` + +## Gobject connection shorthands + +Using `.observe` you can connect gobject signals and capture their value. + +```typescript +const myvar = Variable("") + .observe(obj1, "signal", () => "") + .observe(obj2, "signal", () => "") +``` + +## Dispose if no longer needed + +This will stop the interval and force exit the subprocess and disconnect gobjects. + +```js +myVar.drop() +``` + +:::warning +Don't forget to drop derived variables or variables with +either `.poll`, `.watch` or `.observe` when they are defined inside closures. + +```tsx +function MyWidget() { + const myvar = Variable().poll() + const derived = Variable.derive() + + return <box + onDestroy={() => { + myvar.drop() + derived.drop() + }} + /> +} +``` + +::: |