How to build an only-slightly-less-than-trivial GTK4 app using Flatpak

GTK4 is pretty new, and so it's likely that if you want to target it, you'll need to get your head around Flatpak in order to distribute your work.

Herein is the GTK4 'custom drawing' example from the docs wrapped in a meson and Flatpak example.

(Note, this write up doesn't cover publishing your application... yet)

App name:
drawing-example
App domain:
com.verynoisy This is my domain, make up your own!
Build system:
meson + ninja (c.f. configure + make)

Dir structure:

drawing-example/
  source/
    meson.build
    src/
      meson.build
      drawing-example.c

Grab the source from the gtk4 docs: https://developer.gnome.org/gtk4/stable/ch01s04.html

Place in drawing-example/source/src/drawing-example.c

Edit the source so the app name is com.verynoisy.drawing-example on line 182 - this is important to ensure DBus permissions are correct, since Flatpak by default will only grant portal permissions to the bus of the same name as the app.

Install latest flatpak:

sudo add-apt-repository ppa:alexlarsson/flatpak
sudo apt update
sudo apt install flatpak flatpak-builder

Install latest platform and sdk images:

flatpak install org.gnome.Sdk//master
flatpak install org.gnome.Platform//40

Create top level meson build specification:

In drawing-example/source/meson.build:

project('drawing-example', 'c',
  meson_version: '>= 0.56.0',
  default_options: [
    'warning_level=2',
    'c_std=gnu11',
  ],
)

subdir('src')

...and one in the actual source directory:

drawing_example_sources = [
  'drawing-example.c',
]

drawing_example_deps = [
  dependency('gtk4', version: '>= 4.0'),
]

executable('drawing-example', drawing_example_sources,
  dependencies: drawing_example_deps, install: true
)

(This is needlessly fragmented for a simple project, but you'll need this separation the moment your project gets even vaguely complex.)

Create flatpak manifest so it knows how to invoke your build, etc, in drawing-example/com.verynoisy.drawing-example.yml:

---
app-id: com.verynoisy.drawing-example
runtime: org.gnome.Platform
runtime-version: '40'
sdk: org.gnome.Sdk
command: drawing-example
finish-args:
  - "--share=ipc"
  - "--socket=x11"
  - "--share=network"
  - "--device=dri"  # for opengl
modules:
  - name: drawing-example
    buildsystem: meson
    sources:
      - type: dir
        path: source

Build:

flatpak-builder --install \
  --user \
  build-dir \
  com.verynoisy.drawing-example.yml \
  com.verynoisy.drawing-example

(You can add --force-clean if you've just made changes to configs)

This will do this following:

Test:

flatpak-builder \
  --run --socket=x11 \
  --share=ipc \
  --device=dri \
  build-dir \
  com.verynoisy.drawing-example.yml \
  /app/bin/drawing-example

debugging DBus probs (e.g. can't register, etc)

Listen for all DBus activity

dbus-monitor --session

See what this app tries to do:

flatpak-builder --run \
  --socket=session-bus \
  --share=network \
  --socket=x11 \
  --share=ipc \
  --device=dri \
  build-dir \
  com.verynoisy.drawing-example.yml \
  /app/bin/drawing-example

TODO: