tabbed-casilda/tabbed_casilda.py
Andrew Hamilton ac0f16d0de Maximize embedded terminals via casilda maximized property
Set compositor.props.maximized=True in each tab so the spawned client
fills the tab and tracks window resizes. Add run.sh wrapper pointing
GI_TYPELIB_PATH/LD_LIBRARY_PATH at the vendored build, and a local
build.sh (no sudo, installs into vendor/casilda/prefix).
2026-08-12 18:13:20 +10:00

66 lines
1.8 KiB
Python

#!/usr/bin/env python3
# /// script
# requires-python = ">=3.11"
# dependencies = [
# "PyGObject",
# ]
# ///
import argparse
import gi
import shlex
import shutil
import sys
gi.require_version("Gtk", "4.0")
gi.require_version("Casilda", "1.0")
from gi.repository import GLib, Gtk, Casilda
def make_tab(notebook, command):
compositor = Casilda.Compositor()
compositor.props.maximized = True
label = Gtk.Label(label=command)
notebook.append_page(compositor, label)
argv = shlex.split(command)
if not argv:
print(f"skip empty command: {command!r}", flush=True)
return
argv[0] = shutil.which(argv[0]) or argv[0]
ok = compositor.spawn_async(None, argv, None, GLib.SpawnFlags.DEFAULT)
print(f"spawn {argv[0]}: ok={ok}", flush=True)
class Spike(Gtk.Application):
def __init__(self, commands):
super().__init__(application_id="local.spike")
self.win = None
self.commands = commands
def do_activate(self):
if self.win:
self.win.present()
return
win = Gtk.ApplicationWindow(application=self, title="spike")
win.set_default_size(900, 700)
nb = Gtk.Notebook()
win.set_child(nb)
for command in self.commands:
make_tab(nb, command)
win.present()
GLib.timeout_add(90000, lambda: (self.quit(), False)[1])
self.win = win
if __name__ == "__main__":
parser = argparse.ArgumentParser(
description="GTK4 notebook, one tab per embedded Wayland terminal",
)
parser.add_argument(
"commands",
nargs="+",
metavar="COMMAND",
help='quoted command, e.g. "foot -T htop"',
)
args = parser.parse_args(sys.argv[1:])
app = Spike(args.commands)
sys.exit(app.run([sys.argv[0]]))