mirror of
https://github.com/zoriya/astal.git
synced 2025-12-06 06:06:10 +00:00
docs: touchups
* code block langs * ags faq * fix broken links
This commit is contained in:
@@ -2,7 +2,7 @@
|
||||
|
||||
`App` is a singleton **instance** of [Astal.Application](https://aylur.github.io/libastal/class.Application.html).
|
||||
|
||||
```tsx
|
||||
```ts
|
||||
import { App } from "astal"
|
||||
```
|
||||
|
||||
@@ -29,7 +29,7 @@ You can not instantiate widgets outside of the main function.
|
||||
|
||||
You can run multiple instance by defining a unique instance name.
|
||||
|
||||
```tsx
|
||||
```ts
|
||||
App.start({
|
||||
instanceName: "my-instance", // defaults to "astal"
|
||||
main() {},
|
||||
@@ -52,16 +52,20 @@ App.start({
|
||||
})
|
||||
```
|
||||
|
||||
```bash
|
||||
# ags cli
|
||||
$ ags -m "say hi"
|
||||
hi cli
|
||||
:::code-group
|
||||
|
||||
# astal cli
|
||||
$ astal say hi
|
||||
hi cli
|
||||
```sh [ags]
|
||||
ags -m "say hi"
|
||||
# hi cli
|
||||
```
|
||||
|
||||
```sh [astal]
|
||||
astal say hi
|
||||
# hi cli
|
||||
```
|
||||
|
||||
:::
|
||||
|
||||
If you want to run arbitrary JavaScript from cli, you can use `App.eval`.
|
||||
It will evaluate the passed string as the body of an `async` function.
|
||||
|
||||
@@ -76,19 +80,19 @@ App.start({
|
||||
|
||||
If the string does not contain a semicolon, a single expression is assumed and returned implicity.
|
||||
|
||||
```bash
|
||||
$ ags -m "'hello'"
|
||||
hello
|
||||
```sh
|
||||
ags -m "'hello'"
|
||||
# hello
|
||||
```
|
||||
|
||||
If the string contains a semicolon, you have to return explicitly
|
||||
|
||||
```bash
|
||||
$ ags -m "'hello';"
|
||||
undefined
|
||||
```sh
|
||||
ags -m "'hello';"
|
||||
# undefined
|
||||
|
||||
$ ags -m "return 'hello';"
|
||||
hello
|
||||
ags -m "return 'hello';"
|
||||
# hello
|
||||
```
|
||||
|
||||
## App without AGS
|
||||
|
||||
@@ -8,7 +8,7 @@ a `Gdk.Monitor` object which you can get from compositor libraries.
|
||||
|
||||
Example with Hyprland
|
||||
|
||||
```js
|
||||
```tsx
|
||||
import Hyprland from "gi://AstalHyprland"
|
||||
|
||||
function Bar(gdkmonitor) {
|
||||
@@ -28,7 +28,7 @@ App.start({ main })
|
||||
|
||||
JavaScript is **not** an bash.
|
||||
|
||||
```tsx
|
||||
```ts
|
||||
const HOME = exec("echo $HOME") // does not work
|
||||
```
|
||||
|
||||
@@ -39,7 +39,7 @@ to the `echo` program.
|
||||
:::danger Please don't do this
|
||||
You could pass it to bash, but that is a horrible approach.
|
||||
|
||||
```tsx
|
||||
```ts
|
||||
const HOME = exec("bash -c 'echo $HOME'")
|
||||
```
|
||||
|
||||
@@ -47,7 +47,7 @@ const HOME = exec("bash -c 'echo $HOME'")
|
||||
|
||||
You can read environment variables with [GLib.getenv](https://gjs-docs.gnome.org/glib20~2.0/glib.getenv).
|
||||
|
||||
```tsx
|
||||
```ts
|
||||
import GLib from "gi://GLib"
|
||||
|
||||
const HOME = GLib.getenv("HOME")
|
||||
@@ -58,8 +58,9 @@ const HOME = GLib.getenv("HOME")
|
||||
Put the svgs in a directory, named `<icon-name>-symbolic.svg`
|
||||
and use `App.add_icons` or `icons` parameter in `App.start`
|
||||
|
||||
```js
|
||||
// app.ts
|
||||
:::code-group
|
||||
|
||||
```ts [app.ts]
|
||||
App.start({
|
||||
icons: `${SRC}/icons`,
|
||||
main() {
|
||||
@@ -71,6 +72,8 @@ App.start({
|
||||
})
|
||||
```
|
||||
|
||||
:::
|
||||
|
||||
:::info
|
||||
If there is a name clash with an icon from your current icon pack
|
||||
the icon pack will take precedence
|
||||
@@ -82,7 +85,7 @@ The `console` API in gjs uses glib logging functions.
|
||||
If you just want to print some text as is to stdout
|
||||
use the globally available `print` function or `printerr` for stderr.
|
||||
|
||||
```js
|
||||
```ts
|
||||
print("print this line to stdout")
|
||||
printerr("print this line to stderr")
|
||||
```
|
||||
@@ -91,7 +94,7 @@ printerr("print this line to stderr")
|
||||
|
||||
The `bind` function can take two types of objects.
|
||||
|
||||
```typescript
|
||||
```ts
|
||||
interface Subscribable<T = unknown> {
|
||||
subscribe(callback: (value: T) => void): () => void
|
||||
get(): T
|
||||
@@ -108,7 +111,7 @@ and custom objects.
|
||||
|
||||
For example you can compose `Variables` in using a class.
|
||||
|
||||
```typescript
|
||||
```ts
|
||||
type MyVariableValue = {
|
||||
number: number
|
||||
string: string
|
||||
@@ -154,3 +157,58 @@ function MyWidget() {
|
||||
return <label label={label} />
|
||||
}
|
||||
```
|
||||
|
||||
## Populate the global scope with frequently accessed variables
|
||||
|
||||
It might be annoying to always import Gtk only for `Gtk.Align` enums.
|
||||
|
||||
:::code-group
|
||||
|
||||
```ts [globals.ts]
|
||||
import Gtk from "gi://Gtk"
|
||||
|
||||
declare global {
|
||||
const START: number
|
||||
const CENTER: number
|
||||
const END: number
|
||||
const FILL: number
|
||||
}
|
||||
|
||||
Object.assign(globalThis, {
|
||||
START: Gtk.Align.START,
|
||||
CENTER: Gtk.Align.CENTER,
|
||||
END: Gtk.Align.END,
|
||||
FILL: Gtk.Align.FILL,
|
||||
})
|
||||
```
|
||||
|
||||
:::
|
||||
|
||||
:::code-group
|
||||
|
||||
```tsx [Bar.tsx]
|
||||
export default function Bar() {
|
||||
return <window>
|
||||
<box halign={START} />
|
||||
</window>
|
||||
}
|
||||
```
|
||||
|
||||
:::
|
||||
|
||||
:::code-group
|
||||
|
||||
```ts [app.ts]
|
||||
import "./globals"
|
||||
import Bar from "./Bar"
|
||||
|
||||
App.start({
|
||||
main: Bar
|
||||
})
|
||||
```
|
||||
|
||||
:::
|
||||
|
||||
:::info
|
||||
It is considered bad practice to populate the global scope, but its your code, not a public library.
|
||||
:::
|
||||
|
||||
@@ -14,14 +14,14 @@ Read more about it on the [nix page](../getting-started/nix.md)
|
||||
|
||||
:::code-group
|
||||
|
||||
```sh [Fedora]
|
||||
sudo dnf install golang npm gjs
|
||||
```
|
||||
|
||||
```sh [Arch]
|
||||
sudo pacman -Syu go npm gjs
|
||||
```
|
||||
|
||||
```sh [Fedora]
|
||||
sudo dnf install golang npm gjs
|
||||
```
|
||||
|
||||
```sh [Alpine]
|
||||
sudo apk add go npm gjs
|
||||
```
|
||||
@@ -30,7 +30,7 @@ sudo apk add go npm gjs
|
||||
sudo apt install golang-go npm gjs
|
||||
```
|
||||
|
||||
```bash [openSUSE]
|
||||
```sh [openSUSE]
|
||||
sudo zypper install go npm gjs
|
||||
```
|
||||
|
||||
@@ -38,10 +38,10 @@ sudo zypper install go npm gjs
|
||||
|
||||
3. Clone the repo and Install
|
||||
|
||||
```bash
|
||||
```sh
|
||||
git clone https://github.com/aylur/ags.git
|
||||
cd ags
|
||||
git checkout v2
|
||||
git checkout v2 # https://github.com/Aylur/ags/pull/504
|
||||
go install
|
||||
```
|
||||
|
||||
|
||||
@@ -115,7 +115,7 @@ sudo apk add dart-sass
|
||||
npm install -g sass # not packaged on Ubuntu
|
||||
```
|
||||
|
||||
```bash [openSUSE]
|
||||
```sh [openSUSE]
|
||||
sudo zypper install dart-sass
|
||||
```
|
||||
|
||||
@@ -128,7 +128,7 @@ Importing `scss` files will simply return transpiled css.
|
||||
```ts [app.ts]
|
||||
import style from "./style.scss"
|
||||
|
||||
App.config({
|
||||
App.start({
|
||||
css: style,
|
||||
main() {},
|
||||
})
|
||||
@@ -156,7 +156,7 @@ writeFile(tmpscss, `
|
||||
|
||||
exec(`sass ${tmpscss} ${target}`)
|
||||
|
||||
App.config({
|
||||
App.start({
|
||||
css: target,
|
||||
})
|
||||
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
|
||||
Import them from `astal` or `astal/file`
|
||||
|
||||
```js
|
||||
```ts
|
||||
import {
|
||||
readFile,
|
||||
readFileAsync,
|
||||
@@ -16,21 +16,21 @@ import {
|
||||
|
||||
### Reading files
|
||||
|
||||
```typescript
|
||||
```ts
|
||||
function readFile(path: string): string
|
||||
function readFileAsync(path: string): Promise<string>
|
||||
```
|
||||
|
||||
### Writing files
|
||||
|
||||
```typescript
|
||||
```ts
|
||||
function writeFile(path: string, content: string): void
|
||||
function writeFileAsync(path: string, content: string): Promise<void>
|
||||
```
|
||||
|
||||
### Monitoring files
|
||||
|
||||
```typescript
|
||||
```ts
|
||||
function monitorFile(
|
||||
path: string,
|
||||
callback: (file: string, event: Gio.FileMonitorEvent) => void,
|
||||
@@ -41,7 +41,7 @@ function monitorFile(
|
||||
|
||||
Import them from `astal` or `astal/time`
|
||||
|
||||
```js
|
||||
```ts
|
||||
import { interval, timeout, idle } from "astal"
|
||||
```
|
||||
|
||||
@@ -56,7 +56,7 @@ which return an [Astal.Time](https://aylur.github.io/libastal/class.Time.html) i
|
||||
|
||||
Will immediately execute the function and every `interval` millisecond.
|
||||
|
||||
```typescript
|
||||
```ts
|
||||
function interval(interval: number, callback?: () => void): Astal.Time
|
||||
```
|
||||
|
||||
@@ -64,7 +64,7 @@ function interval(interval: number, callback?: () => void): Astal.Time
|
||||
|
||||
Will execute the `callback` after `timeout` millisecond.
|
||||
|
||||
```typescript
|
||||
```ts
|
||||
function timeout(timeout: number, callback?: () => void): Astal.Time
|
||||
```
|
||||
|
||||
@@ -72,13 +72,13 @@ function timeout(timeout: number, callback?: () => void): Astal.Time
|
||||
|
||||
Executes `callback` whenever there are no higher priority events pending.
|
||||
|
||||
```typescript
|
||||
```ts
|
||||
function idle(callback?: () => void): Astal.Time
|
||||
```
|
||||
|
||||
Example:
|
||||
|
||||
```typescript
|
||||
```ts
|
||||
const timer = interval(1000, () => {
|
||||
console.log("optional callback")
|
||||
})
|
||||
@@ -98,7 +98,7 @@ timer.cancel()
|
||||
|
||||
Import them from `astal` or `astal/proc`
|
||||
|
||||
```js
|
||||
```ts
|
||||
import { subprocess, exec, execAsync } from "astal"
|
||||
```
|
||||
|
||||
@@ -107,7 +107,7 @@ import { subprocess, exec, execAsync } from "astal"
|
||||
You can start a subprocess and run callback functions whenever it outputs to
|
||||
stdout or stderr. [Astal.Process](https://aylur.github.io/libastal/class.Process.html) has a `stdout` and `stderr` signal.
|
||||
|
||||
```typescript
|
||||
```ts
|
||||
function subprocess(args: {
|
||||
cmd: string | string[]
|
||||
out?: (stdout: string) => void
|
||||
@@ -123,7 +123,7 @@ function subprocess(
|
||||
|
||||
Example:
|
||||
|
||||
```typescript
|
||||
```ts
|
||||
const proc = subprocess(
|
||||
"some-command",
|
||||
(out) => console.log(out), // optional
|
||||
@@ -138,14 +138,14 @@ proc.connect("stderr", (err) => console.error(err))
|
||||
|
||||
### Executing external commands and scripts
|
||||
|
||||
```typescript
|
||||
```ts
|
||||
function exec(cmd: string | string[]): string
|
||||
function execAsync(cmd: string | string[]): Promise<string>
|
||||
```
|
||||
|
||||
Example:
|
||||
|
||||
```typescript
|
||||
```ts
|
||||
try {
|
||||
const out = exec("/path/to/script")
|
||||
console.log(out)
|
||||
@@ -166,7 +166,7 @@ and they do **not** handle logical operators like `&&` and `||`.
|
||||
|
||||
If you want bash, run them with bash.
|
||||
|
||||
```js
|
||||
```ts
|
||||
exec(["bash", "-c", "command $VAR && command"])
|
||||
exec("bash -c 'command $VAR' && command")
|
||||
```
|
||||
|
||||
@@ -123,14 +123,12 @@ function MyWidget() {
|
||||
return <ColorButton
|
||||
setup={setup}
|
||||
useAlpha
|
||||
rgba={
|
||||
new Gdk.RGBA({
|
||||
red: 1,
|
||||
green: 0,
|
||||
blue: 0,
|
||||
alpha: 0.5,
|
||||
})
|
||||
}
|
||||
rgba={new Gdk.RGBA({
|
||||
red: 1,
|
||||
green: 0,
|
||||
blue: 0,
|
||||
alpha: 0.5,
|
||||
})}
|
||||
onColorSet={(self) => {
|
||||
console.log(self.rgba)
|
||||
}}
|
||||
@@ -143,3 +141,42 @@ Signal properties have to be annotated manually for TypeScript.
|
||||
You can reference [Gtk3](https://gjs-docs.gnome.org/gtk30~3.0/)
|
||||
and [Astal](https://aylur.github.io/libastal/index.html#classes) for available signals.
|
||||
:::
|
||||
|
||||
## TypeScript
|
||||
|
||||
Type of widgets are available through `Widget`.
|
||||
Here is an example Widget that takes in and handles a possibly `Binding` prop.
|
||||
|
||||
```tsx
|
||||
import { Binding, Variable, Widget } from "astal"
|
||||
|
||||
export interface ToggleButtonProps extends Widget.ButtonProps {
|
||||
onToggled?: (self: Widget.Button, on: boolean) => void
|
||||
state?: Binding<boolean> | boolean
|
||||
child?: JSX.Element
|
||||
}
|
||||
|
||||
export default function ToggleButton(btnprops: ToggleButtonProps) {
|
||||
const { state = false, onToggled, setup, child, ...props } = btnprops
|
||||
const innerState = Variable(state instanceof Binding ? state.get() : state)
|
||||
|
||||
return <button
|
||||
{...props}
|
||||
setup={self => {
|
||||
setup?.(self)
|
||||
|
||||
self.toggleClassName("active", innerState.get())
|
||||
self.hook(innerState, () => self.toggleClassName("active", innerState.get()))
|
||||
|
||||
if (state instanceof Binding) {
|
||||
self.hook(state, () => innerState.set(state.get()))
|
||||
}
|
||||
}}
|
||||
onClicked={self => {
|
||||
onToggled?.(self, !innerState.get())
|
||||
}}
|
||||
>
|
||||
{child}
|
||||
</button>
|
||||
}
|
||||
```
|
||||
|
||||
@@ -26,7 +26,7 @@ yay -S libastal-meta
|
||||
|
||||
1. Clone the repo
|
||||
|
||||
```bash
|
||||
```sh
|
||||
git clone https://github.com/aylur/astal.git
|
||||
cd astal/core
|
||||
```
|
||||
@@ -35,14 +35,14 @@ cd astal/core
|
||||
|
||||
:::code-group
|
||||
|
||||
```sh [Fedora]
|
||||
sudo dnf install meson gcc valac gtk3-devel gtk-layer-shell-devel
|
||||
```
|
||||
|
||||
```sh [Arch]
|
||||
sudo pacman -Syu meson vala gtk3 gtk-layer-shell gobject-introspection
|
||||
```
|
||||
|
||||
```sh [Fedora]
|
||||
sudo dnf install meson gcc valac gtk3-devel gtk-layer-shell-devel
|
||||
```
|
||||
|
||||
```sh [Alpine]
|
||||
sudo apk add meson g++ vala gtk+3.0-dev gtk-layer-shell-dev gobject-introspection-dev
|
||||
```
|
||||
@@ -51,7 +51,7 @@ sudo apk add meson g++ vala gtk+3.0-dev gtk-layer-shell-dev gobject-introspectio
|
||||
sudo apt install meson valac libgtk3-dev libgtk-layer-shell-dev gobject-introspection
|
||||
```
|
||||
|
||||
```bash [openSUSE]
|
||||
```sh [openSUSE]
|
||||
sudo zypper install gcc meson vala gtk3-devel gtk-layer-shell-devel gobject-introspection-devel
|
||||
```
|
||||
|
||||
@@ -59,7 +59,7 @@ sudo zypper install gcc meson vala gtk3-devel gtk-layer-shell-devel gobject-intr
|
||||
|
||||
3. Build and install with `meson`
|
||||
|
||||
```bash
|
||||
```sh
|
||||
meson setup build
|
||||
meson install -C build
|
||||
```
|
||||
@@ -69,7 +69,7 @@ Most distros recommend manual installs in `/usr/local`,
|
||||
which is what `meson` defaults to. If you want to install to `/usr`
|
||||
instead which most package managers do, set the `prefix` option:
|
||||
|
||||
```bash
|
||||
```sh
|
||||
meson setup --prefix /usr build
|
||||
meson install -C build
|
||||
```
|
||||
|
||||
@@ -19,5 +19,5 @@ Have you ever wanted to write a custom bar, custom notification popups
|
||||
or an applauncher, but gave up because writing a workspace widget,
|
||||
implementing the notification daemon or handling a search filter was too much of a hassle?
|
||||
|
||||
Astal libraries have you [covered](/astal/libraries/references), you don't have to worry about these,
|
||||
Astal libraries have you [covered](/libraries/references), you don't have to worry about these,
|
||||
you just define the layout, style it with CSS and that's it.
|
||||
|
||||
Reference in New Issue
Block a user