Hi! In this post I briefly mentioned an immediate-mode GUI library I was working on, that is being used to build a watch-party MPV client. I wanted to make a more detailed post sharing more about the GUI library knots which i find myself spending more and more time on. knots is an immediate mode GUI rendering library/framework (I don’t like the idea of a framework but I think it makes it more clear that it handles more than just putting stuff on the screen).
You might already be familiar with projects like dvui (awesome project, you should check it out), and while there is definitely a large overlap in terms of features I would say the main differentiator between knots and dvui are the goals. dvui is a lot more “general-purpose”, from their README: “GUI toolkit for whole applications or debugging windows in existing apps/games.”. The current scope of knots is a lot slimmer/focused, I am mainly interested in providing a way for people to build really performant cross-platform standalone desktop applications, where “UI code” is essentially out of the way entirely, so you can spend more time on solving “real” problems. I.e, if you are looking for a library that lets you easily create a debug UI for your game engine, or really render anything on top of an existing application/surface, knots is not for you, and will likely never be. It goes without saying that this library is in very early stages, (I just recently decided to stop force pushing on to the initial commit, as I was making massive overhauls to parts of the library every other day). Particularly, you will find many basic widgets/components to not be implemented yet, as I am still putting most of my focus on trimming down the main core of the library.
Below are just some questions and answers I think most of you might have:
- What platforms are supported?
- Windows, macOS, Linux, and web via emscripten + webgpu
- Any examples?
- Like I mentioned before, this mpv client shaven is being built with knots. You can also clone the knots repo and run some of the examples, or test the playground app on the web Playground!
- What are you currently working on?
- I am trying to get rid of all my c/c++ dependencies, to trim down compile times and binary sizes. I used to depend on GLFW for windowing but have now dropped it in favor of platform specific implementations which have been implemented for windows, macOS (partially), and emscripten/web. Linux builds unfortunately still depend on GLFW. As of this PR, I deleted harfbuzz as a dependency as I was not using any of its features anyways, and it was pulling all kinds of garbage like libc++, this open PR will drop freetype as a dependency in favor of https://codeberg.org/andrewrk/TrueType (built by Andrew Kelley!) to remove the final C dependency. After that, I will likely spend some time improving how text is handled in the layout module, to support text wrapping and other niceties.
- Cross platform GUI rendering? How?
- This is particularly important to get right and I took some risks here which might have repercussions in the future. I bet essentially on two APIs, WebGPU and Vulkan. Why these two? Well I always wanted to have the door open for supporting web, and to do that I would need to either support WebGL or WebGPU, afaik WebGL is planned to be superseded by WebGPU, and while WebGPU will potentially not work on some browsers, I am fine with that knowing they will eventually support it. I also get the added benefit of WebGPU acting as a “catch-all” GPU API which can be used when targeting native builds as well. This means you can build knots with only the WebGPU backend and be able to target Windows, macOS, Linux and Web! So why also support Vulkan? I wanted to leave the door open for opting in to even better performance for native builds, and Vulkan seemed to be the best choice here for performant cross-platform graphics. I honestly can’t see myself maintaining more than 2 GPU backends, so it is likely this will not change any time soon. Also, the WebGPU backend for native builds depends on wgpu-native being statically linked to the binary, which bloats binary sizes quite a bit (however, ensure it will run on a lot more machines).
Okay, I rambled quite a bit now and need to get back to work, please let me know if you have any more questions/concerns. This is not really an ad, as I still think the library is far from being useable for production apps. I am just more interested in what people think, am I wasting my time, or is it something you would be interested in?
