jwijenbergh / puregotk

Autogenerated GTK4+Adwaita bindings for Go leveraging ebitengine/purego
MIT License
13 stars 3 forks source link

Puregotk

NOTE: This library is currently expiremental and needs thorough testing. Some APIs might be incorrectly exposed

Autogenerated GTK4+Adwaita bindings for Go leveraging purego

Motivation

I created this library because I found that alternative libraries using Cgo had much too slow compilation speed. For my laptop around 15 minutes to build a simple example (without build cache) for gotk3 and also gotk4. Whilst this is maybe not a big problem for development, I found it annoying for CI and package building where you would not want to rely on a cache. Additionally, having Cgo involved means harder cross compilation.

This is not a fault for these libraries as CGo compilation is just inherently slow in Go. In this project I want to test a new approach by levering purego which allows you to load libraries using dlopen without needing cgo.

Compilation speed currently is around 40 seconds for me on basic examples.

Advantages

No Cgo needed, thus:

Disadvantages

Limitations of this library as compared to the alternatives using cgo:

Planned features

In order of priority:

Basic example

package main

import (
    "os"

    "github.com/jwijenbergh/puregotk/v4/gio"
    "github.com/jwijenbergh/puregotk/v4/gtk"
)

func main() {
    app := gtk.NewApplication("com.github.jwijenbergh.puregotk.gtk4.hello", gio.GApplicationFlagsNoneValue)
    // cleanup, no finalizers are used in this library
    defer app.Unref()
    // functions with callback arguments take function pointers
    // this is for internal re-use of callbacks
    actcb := func(_ gio.Application) {
        activate(app)
    }
    app.ConnectActivate(&actcb)

    if code := app.Run(len(os.Args), os.Args); code > 0 {
        os.Exit(code)
    }
}

func activate(app *gtk.Application) {
    window := gtk.NewApplicationWindow(app)
    window.SetTitle("purego")
    label := gtk.NewLabel("Hello, World!")
    window.SetChild(&label.Widget)
    // cleanup, no finalizers are used in this library
    label.Unref()
    window.SetDefaultSize(500, 500)
    window.Present()
}

Save this to a main.go and then build & run with

go run main.go

NOTE: You can also use CGO_ENABLED=0 to build without cgo!

Library loading

Because the GTK libs are loading at runtime (in init), we have to know where your libs are located. The default configuration is a "just works" configuration, we hardcode some paths that are common.

However, for systems such as NixOS or distros that use other paths the following environment variables might help:

See https://github.com/jwijenbergh/puregotk/blob/main/internal/core/core.go for exact implementation details.

Additionally we also have a fallback to pkg-config, but I would say only rely on this as a last effort due to the increased startup time. When packaging code, always make sure that correct paths are used by e.g. using the aforementioned environment variables.

Generating the library

This library is automatically generated by reading GIR files.

To generate the library, run:

./gen.sh

In the root of the project. This needs:

License

MIT

Acknowledgements