Moon on a stick#
Tue, 18 Dec 2018 22:31:25 +0000
Latest in my ever-expanding series of diversions from NixWRT is this foolish attempt to write a Wayland compositor using a language I don't actually understand. I'd add: not for the first time , except that now I check the link I see that was going to be a text editor not a compositor.
Anyway. This time it's a Wayland compositor, using the wlroots library (described by its author as "about 50,000 lines of code you were going to write anyway") and written in Lua. Mostly because when I get a bit further along with it I'm going to integrate Fennel into it, and then with a bit of luck will have a respectable replacement for the once-brilliant but now rather long in the tooth Sawfish . I say "when" but we all know I really mean "if".
At the time of writing it works to the extent that I have a Lua script that can set up the display appropriately then allow me to display a Konsole window into which I can type, and it renders a pointer which moves around in expected and unsurprising ways when I stroke my touchpad. It has no knowledge, though, of window decorations or of stacking order or even of focus or the channeling of pointer button/movement events onto a client.
(Decorations? Yes, I'm with the KDE guys on this one. Requiring clients to render their own window borders and resize themselves on the screen is like a bank requiring customers to track their own account balances and know which market funds their deposits were invested in: how can you ever be sure the app you thought was "Password Wallet Master Key Entry" was actually that and not, I dunno, "I'd like to add you to my professional Botnet" if you don't have some kind of trustable fence around the rectangle it's permitted to draw into. Honour system?)
Some brief notes on how I'm doing it, for the benefit of future-me and potential benefit of present-other. I'm using LuaJIT: not for speed but because the FFI can parse (most) C header files and there's a lot of FFI in this project. So far I have made a fairly literal transcription of the code in Drew DeVault's blog posts parts I-III, and then a rather sketchier interpretation of the code in Input handling in wlroots
Some stuff has changed since the blog posts were written. Here are the differences and/or relevant gotchas that I noted or can remember
-
wlr_renderer_begin
now takesint width, int height
as second and third params instead of needing awlr_output
-
wlr_compositor.surfaces
is probably the old name for what is nowwlr_compositor.surface_resources
-
wlr_render_with_matrix
has becomewlr_render_texture_with_matrix
- without an xkb keymap set (
wlr_keyboard_set_keymap
) you won't get any key events. You might think there's no need for keymaps if all you want is to look at the raw codes, but nope, it doesn't work.
-
wlr_seat_set_capabilities
is not mentioned in the blog, but you need it set right according to the inputs available at your "seat"
- to render the mouse pointer when you're running wayland-under-X (for
development, before the server is ready for dogfooding) you need to
call
wlr_output_render_software_cursors(output, nil)
while rendering output. So you don't leave a ghost trail of former pointer positions whenever the mouse is moved, you probably also want to callwlr_renderer_clear
as the first thing afterwlr_renderer_begin
- there's a bit more to wlr_xcursor than it explains, and TBH I'm just going to point you to my diff instead of trying to explain it here. Because while as a general rule I would never claim that "life's too short" for doing fun things, I must concede that the remaining available time for sleeping before my alarm goes off tomorrow morning is rapidly getting that way.