An experimental Go cross platform UI library.


GXUI - A Go cross platform UI library.

Join the chat at Build Status GoDoc


Unfortunately due to a shortage of hours in a day, GXUI is no longer maintained.

If you're looking for a GUI library for your next Go project, check out these alternatives.


The code is mostly undocumented, and is certainly not idiomatic Go.

This is not an official Google product (experimental or otherwise), it is just code that happens to be owned by Google.



In order to build GXUI on linux, you will need the following packages installed:

sudo apt-get install libxi-dev libxcursor-dev libxrandr-dev libxinerama-dev mesa-common-dev libgl1-mesa-dev libxxf86vm-dev


After setting up GOPATH (see Go documentation), you can then fetch the GXUI library and its dependencies:

go get -u


Samples can be found in gxui/samples.

To build all samples run:

go install

And they will be built into GOPATH/bin.

If you add GOPATH/bin to your PATH, you can simply type the name of a sample to run it. For example: image_viewer.


gxui code is cross platform and can be compiled using GopherJS to JavaScript, allowing it to run in browsers with WebGL support. To do so, you'll need the GopherJS compiler and some additional dependencies:

go get -u
go get -u -d -tags=js

Afterwards, you can try the samples by running gopherjs serve command and opening http://localhost:8080/ in a browser.


Many of the samples require a font to render text. The dark theme (and currently the only theme) uses Roboto. This is built into the gxfont package.

Make sure to mention this font in any notices file distributed with your application.


GXUI was written by a couple of Googlers as an experiment and is now unmaintained.

Contributions, however small, will require the author to have signed the Google Individual Contributor License Agreement.

The CLA is necessary mainly because you own the copyright to your changes, even after your contribution becomes part of our codebase, so we need your permission to use and distribute your code. We also need to be sure of various other things—for instance that you'll tell us if you know that your code infringes on other people's patents. You don't have to sign the CLA until after you've submitted your code for review and a member has approved it, but you must do it before we can put your code into our codebase. Before you start working on a larger contribution, you should get in touch with us first through the issue tracker with your idea so that we can help out and possibly guide you. Coordinating up front makes it much easier to avoid frustration later on.

  • drivers/gl: Use instead of

    drivers/gl: Use instead of

    This PR is a continuation of #78. It's different in that it simply modifies the existing driver, rather than adding an second driver.

    This PR modifies the gl driver to use package. This package offers a slightly higher level interface, with desktop (OS X, Linux) and mobile (iOS, Android) backends. There is ongoing work to add support for Windows and web browsers.

    Resolves #45. Related to #49.

    • The x/mobile/gl provides a universal GL interface which can run on desktop (OS X, Linux), mobile (iOS, Android), with current work to add support for Windows and web browsers.
    • Change index buffer data type from []uint32 to []uint16, since it offers enough size, and WebGL implementations do not support []uint32 as readily.
    • Remove stFloatMat2x3, stFloatMat2x4, stFloatMat3x2, stFloatMat3x4, stFloatMat4x2 and stFloatMat4x3 since x/mobile/gl does not currently have support for those operations they are unused.
    • Remove gl.INVALID_INDEX since x/mobile/gl does not have it.
    • Remove support for image.Gray format, since it's unused.
    • HACK: Hardcode []uint16 support in newIndexBuffer, since x/mobile/gl has poor support for non-[]uint8 types at this time, only []uint16 is used. Need to improve this.
    • HACK: Hardcode []float32 support in newVertexStream since it's the only type used, and x/mobile/gl currently has poor support for other types. Need to improve this.
    opened by dmitshur 46
  • Support wider set of platforms. Mobile? Web?

    Support wider set of platforms. Mobile? Web?

    First off, thank you for creating this incredible Go library! I've recently discovered it and I'm a huge fan! I really like the approach of using OpenGL for platform-independent, high performance UI rendering, since it allows one to stay general and not to be constrained by each platform's UI toolkits. I've experimented with OpenGL UIs here.


    Now, the description of this project says:

    GXUI - A Go cross platform UI library.

    Currently, it is cross platform in that it will run and look/behave the same on OS X, Linux and Windows. However, with relatively little work, it seems it could be expanded to support more platforms: mobile and perhaps even web.

    First, let me be a little imprecise and describe OpenGL APIs in this way:

    • OpenGL 3.2 Core - "Largest" OpenGL API available. Available on most desktop platforms (OS X, Linux, Windows).
    • OpenGL ES 2.0 - Roughly speaking, a subset of OpenGL API (with minor deviations). Available on most mobile platforms (iOS, Android).
    • WebGL 1.0 - Roughly speaking, a subset of OpenGL ES 2.0 (with minor deviations). Available in all major browsers (Chrome, Safari, Firefox, Opera, IE).

    OpenGL 3.2 Core API is currently used in gxui [1]. But with a few changes (outlined in considerations section), it's possible to reduce what it used so that it can mapped to WebGL API.

    I wanted to see what it would take to get gxui to run in browsers (and see how it'd perform), so I made a quick little prototype tonight in just a few hours. Some screenshots:





    Here's a demo you can try in your browser (no gzip compression on served assets, sorry):


    There are two different approaches to supporting additional platforms that I can see.

    First approach is to create additional drivers, similar to the existing gl one. This seems to be suggested in related issue #45.

    Another approach, which is the one I've used so far, is a little different.

    Since the three OpenGL APIs are similar enough, it's possible to create a Go package that has a single OpenGL-like API, but using build tags, it can have three different backend implementations depending on what is available on the given platform:

    • OpenGL 2.1 or 3.2 Core, etc., backend on desktops.
    • OpenGL ES backend on mobile devices.
    • WebGL backend in browser.

    The package used in my quick prototype is an example of that. It only has OpenGL 2.1 and WebGL backend implementations (incomplete), but adding OpenGL ES one would be trivial since it's a superset of WebGL. It's a WIP package with unpolished API, but I think the general approach is solid and can be turned into a production ready package.


    Here are some implementation details of the changes I needed to do to make gxui samples run in the browser.

    1. glPolygonMode is not available in WebGL (since its implementation is very inefficient; a shame because it's useful for debugging). I commented it out since it was just a debugging feature.

    2. Index buffers with uint32 types were used. It seems my WebGL implementation (latest stable Chrome on OS X) did not support that type, so I dropped it down to uint16 which worked well.

    3. My WebGL implementation seemed not to support gl.UniformMatrix3fv calls with transpose equal to true, so I had to transpose the matrix before calling the gl func. I'm guessing the WebGL implementation opts to support fewer choices for performance reasons. It'd be better to avoid needless conversions between one format to the other when rendering.

    4. WebGL fragment shaders require precision to be set, so I added this to all fragment shaders to allow them to compile under all OpenGL/WebGL versions:

      #ifdef GL_ES
          precision lowp float;
    5. Previous commits read the font directly from disk via ioutil.ReadFile. This can't work on all other platforms, so it's better to read from a virtual filesystem and each platform can provide that. It's no longer a problem since latest version embeds the font in code.

    6. My existing gogl package happens to use a higher level-style API (similar to x/mobile/gl) with types like *Texture instead of uint32, and it favors using int over int32 or uint32 the way the low-level C-style packages do. This is a design decision that is orthogonal to all other API changes, but it required me to make some changes like:

      -framebuffer uint32
      -texture     uint32
      +framebuffer *gogl.Framebuffer
      +texture     *gogl.Texture
      -gl.DeleteFramebuffers(1, &f.framebuffer)
      -gl.DeleteTextures(1, &f.texture)
      -f.framebuffer = 0
      -f.texture = 0
      +f.framebuffer = nil
      +f.texture = nil
      -gl.Viewport(0, 0, int32(fw), int32(fh))
      -gl.Scissor(0, 0, int32(fw), int32(fh))
      +gl.Viewport(0, 0, fw, fh)
      +gl.Scissor(0, 0, fw, fh)
    7. Consts like gl.TRIANGLE_STRIP are not const on all platforms. For example, to get that value in a browser, you either need to create a WebGLContext first (which can't be done at const-time), or just hardcode the const value from spec. I went with the latter for now.

    You can see the entire code change I made at Keep in mind it's a quick prototype to test what it would take, and not a fully finished and polished version.

    The performance of the web version (with Go compiled to JavaScript via GopherJS) is not as good as the desktop version with native Go. I am seeing around 20 fps. This is the result I got after doing the minimum work required to get samples to run without any profiling or optimizations. I am sure the performance can be improved if time is spent on it.


    With just a few changes (do not use transpose true, use uint16 type for index buffers, etc.) it is possible to avoid using OpenGL-only features that are not available in OpenGL ES and WebGL. Doing that seems like a good idea as it enables gxui to be more cross platform.

    This issue is to demonstrate what I've created. I'd love to hear feedback and thoughts. If you are interested, I'd love to help out with adding support for mobile and/or web and taking this prototype further.

    [1] The imported package is v3.2-core/gl, so that's the API used, but since context version glfw hints are not set, it creates an OpenGL 2.1 context. Add this snippet after gl.Init() call to confirm:

        var samples int32
        gl.GetIntegerv(gl.SAMPLES, &samples)
        fmt.Printf("OpenGL %s %s %s; %s; %v samples.\n", gl.GoStr(gl.GetString(gl.VENDOR)), gl.GoStr(gl.GetString(gl.RENDERER)), gl.GoStr(gl.GetString(gl.VERSION)),
            gl.GoStr(gl.GetString(gl.SHADING_LANGUAGE_VERSION)), samples)

    On my Mac, I got OpenGL ATI Technologies Inc. AMD Radeon HD 6770M OpenGL Engine 2.1 ATI-1.30.5; 1.20; 4 samples.. OpenGL 2.1.

    opened by dmitshur 21
  • Sample applications just keep black screen - Ubuntu 14.04

    Sample applications just keep black screen - Ubuntu 14.04

    Hi there,

    I built all samples successfully, but when running them it's just a black screen, like this: image

    I run it on Ubuntu 14.04, and: OpenGL vendor string: Intel Open Source Technology Center OpenGL renderer string: Mesa DRI Intel(R) 945GM x86/MMX/SSE2 OpenGL version string: 1.4 Mesa 10.3.2 OpenGL extensions: OpenGL ES profile version string: OpenGL ES 2.0 Mesa 10.3.2 OpenGL ES profile shading language version string: OpenGL ES GLSL ES 1.0.16 OpenGL ES profile extensions:

    opened by nguyendangminh 15
  • panic: Cannot create a label with a nil font

    panic: Cannot create a label with a nil font

    I was able to succesfully build the progress_bar binary from the samples folder using the Dockerfile described in #7. However, when I run the binary on my machine I receive the following panic:

    $ ./progress_bar 
    Warning: Failed to load default font - Unable to find font 'Arial.ttf'
    panic: Cannot create a label with a nil font
    goroutine 5 [running]:*Label).Init(0xc20807e000, 0x7f9925c2cdd8, 0xc20807e000, 0x7f9925c2cd20, 0xc20807c000, 0x0, 0x0, 0x3f4ccccd3f4ccccd, 0x3f8000003f4ccccd)
        /go/src/ +0x6f, 0x0, 0x0)
        /go/src/ +0x141*Theme).CreateLabel(0xc20807c000, 0x0, 0x0)
        /go/src/ +0x3a
    main.appMain(0x7f9925c2cc40, 0xc20803a3c0)
        /go/src/ +0x85
    created by
        /go/src/ +0x20a
    goroutine 1 [runnable, locked to thread]:
        /go/src/ +0x45
        /go/src/ +0x1b*Driver).run(0xc20803a3c0)
        /go/src/ +0x81, 0x0, 0x9077a0)
        /go/src/ +0x21a
        /go/src/ +0x48
    goroutine 17 [syscall, locked to thread]:
        /usr/src/go/src/runtime/asm_amd64.s:2232 +0x1
    opened by ShawnMilo 13
  • Errors running `go get`

    Errors running `go get`

    I'm having issues running go get on Yosemite:

    $ brew list glew
    /opt/boxen/homebrew/Cellar/glew/1.11.0/include/GL/ (3 files)
    /opt/boxen/homebrew/Cellar/glew/1.11.0/lib/pkgconfig/ (2 files)
    /opt/boxen/homebrew/Cellar/glew/1.11.0/lib/ (6 other files)
    $  go get ./...
    In file included from ../../go-gl-legacy/gl/attriblocation.go:7:
    ./gl.h:2:10: fatal error: 'GL/glew.h' file not found
    #include <GL/glew.h>
    1 error generated.
    opened by owenthereal 11
  • AdapterItemIds are too complicated.

    AdapterItemIds are too complicated.

    In writing the samples, I've come to realise that the AdapterItemIds are really complicated, and make writing adapters really difficult. The worst offender is the TreeAdapterNode - the contact for all Adapters is that a AdapterItemId needs to be unique for every item in the data set. Creating a unique integer for any data is hard, keeping it deterministic is really hard.

    For context - the point of the AdapterItemId is so that the List or Tree knows when a Control needs to be rebuilt as the data is mutated - i.e. insertion of a new control shouldn't mean all other controls need to be rebuilt. It is also a requirement if we were to do sliding animations when things are inserted or removed, so we can associate what's on screen before the mutation and after the mutation.

    I've thought about the problem a bit, and decided that actually AdapterItemIds should be replaced with AdapterItems - these are user data types (interface{}) that have equality testing. This simplifies usage heavily. For example:

    • Instead of List.Selected returning the AdapterItemId, it instead returns the actual AdapterItem data. Yay, no more looking up in the adapter.
    • If you have duplicates value types in your dataset (lets say strings) simply use a pointer as your AdapterItem. You can then guarantee it's unique.

    I've pushed the rm_itemids branch that tries out this idea. It needs a little more polish before being ready.

    opened by ben-clayton 10
  • make default font the decision of the driver

    make default font the decision of the driver

    If we cannot find one, download a reasonable default from Google. The URL will need to change in a few months when the project moves off, but so far it's the path we have.

    Updates #13.

    opened by crawshaw 10
  • Container for image

    Container for image

    There is a need to realize the similarity of the graphic editor. Need a container for images, but not the main window. What realties like Canvas. What do you advise?

    opened by DoctorovEV 8
  • Table cols and rows are reversed.

    Table cols and rows are reversed.

    Comments in table example say //rows, columns SetGrid(3, 2)

    Which would be three rows by two columns (taller than wide). However, that is not how it is treated.

    I don't think the comment should be changed, but rather the inner workings as it is normal to pass rows first, then cols.

    opened by danmondy 7
  • Add x/mobile/gl driver.

    Add x/mobile/gl driver.

    This PR adds a second driver that uses package. This package offers a slightly higher level interface, with desktop (OS X, Linux) and mobile (iOS, Android) backends. There is ongoing work to add support for Windows and web browsers.

    Resolves #45. Related to #49.

    This is a large PR, I recommend looking at the 2 commits individually:

    1. The first commit simply copies the drivers/gl package to drivers/universalgl, and renames the original drivers/gl to drivers/desktopgl. No logical changes here.
    2. The second commit makes the necessary changes to drivers/universalgl to switch from using to See commit message for detailed list of changes, and comments.

    This PR depends on a couple changes/additions to the package. I have created a CL for that, please see

    Please take a look, provide feedback, review.

    opened by dmitshur 7
  • Run sample error on windows

    Run sample error on windows

    $ go run main.go panic: Failed to initialize gl: glGetBufferParameteri64v

    goroutine 1 [running, locked to thread]:, 0x320, 0x258, 0x7 537d0, 0x5, 0xc082023e88) C:/Go/src/ +0x2ab路016() C:/Go/src/ +0x68路011() C:/Go/src/ +0x36*Driver).run(0xc08200a380) C:/Go/src/ +0x7c C:/Go/src/ +0x1ec main.main() E:/golang/app/UI/main.go:164 +0x31

    goroutine 17 [syscall, locked to thread]: runtime.goexit() c:/go/src/runtime/asm_amd64.s:2232 +0x1

    goroutine 5 [chan receive]:, 0xc08218cd2 0) C:/Go/src/ +0x137, 0x320, 0x258, 0x7537d0, 0x5, 0x0, 0x0) C:/Go/src/ +0x1e1, 0x3694f0, 0xc08201b8c 0, 0x361fd8, 0xc08200a380, 0x320, 0x258, 0x7537d0, 0x5) C:/Go/src/ +0x326, 0x320, 0x258, 0x75 37d0, 0x5, 0x0, 0x0) C:/Go/src/ +0x119, 0x320, 0x 258, 0x7537d0, 0x5, 0x0, 0x0) C:/Go/src/ +0x69 main.appMain(0x361fd8, 0xc08200a380) E:/golang/app/UI/main.go:155 +0x1de created by C:/Go/src/ +0x1dc exit status 2

    opened by justay 7
  • error on go get

    error on go get

    $ go get -u
    ../../go/src/ assignment mismatch: 2 variables but c.window.Window.GetClipboardString returns 1 values
    opened by lfaoro 1
  • building using gb fails

    building using gb fails

    env GOOS=windows GOARCH=amd64 gb build all FATAL: command "build" failed: failed to resolve import path #"xxxxx/xxxxxxxx": import "": not found make: *** [build] Error 1 Zak-MacBook-Pro:config Za$

    opened by mzakariyya 0
  • Error when run sample on web

    Error when run sample on web

    [OSX 10.10.5] when i run gxui sample project on web. but, I get this error: duplicate case glfw.KeyEnd (constant -1 of type in expression switch previous case duplicate case glfw.KeyScrollLock (constant -1 of type in expression switch previous case duplicate case glfw.KeyNumLock (constant -1 of type in expression switch previous case duplicate case glfw.KeyPrintScreen (constant -1 of type in expression switch previous case duplicate case glfw.KeyPause (constant -1 of type in expression switch previous case too many errors

    Help plz fix this.

    opened by jeenhyung 2
  • GXUI is now unmaintained

    GXUI is now unmaintained

    Unfortunately due to a severe lack of spare time, I'm no longer able to maintain GXUI.

    While I'd hoped to find a few spare hours here and there to fix all the issues I've been itching to fix, I'm weeks away from becoming a father for the first time. While this is exciting and terrifying in equal measures, it's also clear that I'm simply not going to find those spare cycles.

    I've updated the landing page to point to other GUI Go libraries, but I'd also like to highlight the awesome work going on the shiny experimental package (proposal, project) which has some remarkably smart people working on it.

    I'd like to thank those of you that have contributed to GXUI, and a special shout-out to @shurcooL who made GXUI do things I still can't quite believe.

    Cheers, Ben

    opened by ben-clayton 7
Google ❤️ Open Source
Cross-platform Go library to place an icon in the host operating system's taskbar.

trayhost Package trayhost is a cross-platform Go library to place an icon in the host operating system's taskbar. Platform Support macOS - Fully imple

null 235 Nov 6, 2022
Go cross-platform library for displaying dialogs and input boxes

dlgs dlgs is a cross-platform library for displaying dialogs and input boxes. Installation go get -u Documentation Document

Milan Nikolic 367 Dec 24, 2022
Tiny cross-platform webview library for C/C++/Golang. Uses WebKit (Gtk/Cocoa) and Edge (Windows)

webview A tiny cross-platform webview library for C/C++/Golang to build modern cross-platform GUIs. Also, there are Rust bindings, Python bindings, Ni

webview 10.8k Jan 1, 2023
Cross-platform Go/Golang GUI library.

中文 | English GoVCL Cross-platform Golang GUI library, The core binding is liblcl, a common cross-platform GUI library created by Lazarus. GoVCL is a n

不在乎y 1.7k Dec 30, 2022
Cross platform GUI in Go based on Material Design

About Fyne is an easy to use UI toolkit and app API written in Go. It is designed to build applications that run on desktop and mobile devices with a 19.1k Jan 3, 2023
Build cross-platform modern desktop apps in Go + HTML5

Lorca A very small library to build modern HTML5 desktop apps in Go. It uses Chrome browser as a UI layer. Unlike Electron it doesn't bundle Chrome in

Serge Zaitsev 7.6k Jan 6, 2023
Build cross platform GUI apps with GO and HTML/JS/CSS (powered by Electron)

Thanks to go-astilectron build cross platform GUI apps with GO and HTML/JS/CSS. It is the official GO bindings of astilectron and is powered by Electr

Quentin Renard 4.6k Jan 9, 2023
Build cross platform GUI apps with GO and HTML/JS/CSS (powered by nwjs)

gowd Build cross platform GUI apps with GO and HTML/JS/CSS (powered by nwjs) How to use this library: Download and install nwjs Install this library g

Danny 388 Dec 11, 2022
RobotGo, Go Native cross-platform GUI automation @vcaesar

Robotgo Golang Desktop Automation. Control the mouse, keyboard, bitmap, read the screen, Window Handle and global event listener. RobotGo supports Mac

vgo 8.1k Jan 7, 2023
Cross-platform GUI for go is never this easy and clean.

gimu Strongly suggest NOT to use this project anymore, the auto-generated cgo wrapper of Nuklear has a random crash issue which is hard to fix (becaus

Allen Dang 66 Jul 12, 2022
A cross-platform app-development module for Go.

The cross-platform Go module for building apps (pronounced klo-va-seed). Usecases As a lightweight alternative to Electron Write your frontend and nat

Qlova Limited 101 Dec 1, 2022
pure go, cross-platform, MIT-licensed ui toolkit for developers

duit - developer ui toolkit WARNING: this library is work in progress. backwards incompatible changes will be made. details duit is a pure go (*), cro

Mechiel Lukkien 868 Dec 24, 2022
Cross platform rapid GUI framework for golang based on Dear ImGui.

giu Cross platform rapid GUI framework for golang based on Dear ImGui and the great golang binding imgui-go. Any contribution (features, widgets, tuto

Allen Dang 1.6k Dec 28, 2022
Cross-Platform GUI Framework for Go

⚠️ I'm currently working on this project as part of my master's thesis at the Berlin University of Applied Sciences and Technology. It is under active

Jannis Rieger 3 Oct 31, 2022
Kita is a declarative, reactive GUI toolkit for build cross platform apps with web technology with single codebase

Kita is a declarative, reactive GUI toolkit for build cross platform apps with web technology with single codebase. Inspired by Flutter, React. S

zhuah 106 Apr 18, 2022
UIKit - A declarative, reactive GUI toolkit for build cross platform apps with web technology with single codebase

UIKit - A declarative, reactive GUI toolkit for build cross platform apps with web technology with single codebase

zhuah 106 Apr 18, 2022
a cross platfrom Go library to place an icon and menu in the notification area

systray is a cross-platform Go library to place an icon and menu in the notification area. Features Supported on Windows, macOS, and Linux Menu items

Lantern 2.6k Dec 27, 2022
Platform-native GUI library for Go.

ui: platform-native GUI library for Go This is a library that aims to provide simple GUI software development in Go. It is based on my libui, a simple

Pietro Gagliardi 8.2k Jan 9, 2023
A utility library to make use of the X Go Binding easier. (Implements EWMH and ICCCM specs, key binding support, etc.)

xgbutil is a utility library designed to work with the X Go Binding. This project's main goal is to make various X related tasks easier. For example,

Andrew Gallant 186 Dec 10, 2022