Hacker News new | comments | ask | show | jobs | submit login
Libui: a portable GUI library for C (github.com)
356 points by axiomdata316 9 months ago | hide | past | web | favorite | 162 comments

A lot of the comments have mentioned the lack of documentation this project has, and then they've received replies of the form "you should submit a pull request, the author doesn't owe you anything". Here's my take on it: I don't owe the author anything either. But if I'm considering which project to use, I'd probably choose the one with documentation, since it signals better goals and higher code quality. It's absurd to think that I should just pick up a random project and be obligated to make it better, and that I should be called out for giving advice on how I think a project can be improved. This isn't to say that I've never submitted an unsolicited pull request to a project to get it improved–on the contrary, this is something I do very often–but I do this because I feel that the project has something of value and can be improved. I shouldn't be forced to make a contribution to a project if I just don't think it's doing everything right. (This comment isn't mean to be aimed at this project in particular, by the way, it's just a general response to all the people in this thread.)

Documentation gives at least the functional, if not detailed, requirements for what the code is supposed to do (as well as not do). "Submit a pull request for documentation" is basically "please write down the set of requirements for what you think I might have coded up here and send them to me" which is an absurd way to do engineering, regardless of considerations of licensing and compensation structure.

It's okay to have that attitude about tutorials, and guides to internals, and other satellite docs, but not core documentation (reference manual or spec).

Yup, here is a good example of that in the wild: https://github.com/mholt/PapaParse/issues/495

The README says right there that they haven't found a good autodoc tool for C and that their API instability makes it burdensome to maintain documentation right now; calling them bad engineers for that is a bit much. Their only "mistake" is being a project for which outside enthusiasm has far outpaced its progress.

People suck at communicating, but people want to communicate. People love to complain more than they love to fix things. A lot of the time a complaint is half frustration, half trying-to-be-helpful-suggestion. Sometimes it's just people complaining about other people complaining (like the "fix it yourself" crowd or the "didn't you reflect before posting that the issue of X is already a known concern?" crowd) but this just goes back to people wanting to communicate.

I suppose all I really wanted to say was that maybe people in general should open their mouths / comment boxes less. (Yeah my comment sucks, doesn't listen to its own advice...)

It's a hell of a lot easier to be negative or express a frustration than it is to put the energy into a positive, constructive conversation. It's not an easy problem to solve because the different parties to the conversation have different experiences and are often unaware of the situation for the other people involved.

For example, what might have been an innocent question for one person is actually an annoying nag to somebody else, because they've been answering that sort of question for a long time and have built up an expectation for everyone else to do more research first. The person asking the innocent question doesn't know that they're the hundredth person to ask, so to them the response seems harsh and unkind. Someone observing the exchange from the outside is going to have their own judgments on the quality of the community.

The solution to difficult communication isn't to communicate less, it's generally to communicate more and that doesn't necessarily mean more conversations, because communication can take place in many different ways.

What would help even more is to approach communication with some level of empathy and compassion, and accountability for how you react to those reaching out to you (or those you're reaching out to, of course). If it always seems difficult and sucky then you need to understand why you continue to see it that way, why you get frustrated, and what you can do for your part in that communication to make it more pleasant for yourself. And then make that position clear so there's no misunderstanding of intent.

A large part of communication in those terms, and at the scale we're looking at here, is setting clear boundaries on how you wish to be communicated with and how you'll do your best to respond. It's not useful to act out and complain and moan because nobody can guess what it is you want from them.

I completely agree. Besides, how can you submit a pull request for documentation when there’s no documentation for you to understand the code with? I say that as someone who spent a week trying to figure out a project recently, including reading the source code to figure out how it worked, submitted a pull request to improve some of the code and wrote a beginner getting started tutorial. That is, I have went through the effort and it really was a lot of effort to the point where I’ve been meaning to finish a followup article but just lost all energy for the project and moved onto other things.

Documentation is so important if you want to get people interested in your project. Personally, I value good documentation above features because without documentation I may never learn how to use your features and may never get started using the project. If I never use your project then there’s zero chance that I will contribute. Or, like above, I do, but run out of steam really quickly and lose interest.

> Besides, how can you submit a pull request for documentation when there’s no documentation for you to understand the code with?

By reading the code? You're posing it as some kind of impossible paradox, but with the full source code available you have a pretty readable specification of how it works.

It’s very hard to understand an unfamiliar codevase. The documentation doesn’t have to be super-fine grained, it just has to give a helping hand in understanding the high level design and use of the code. I can usually figure out api parameters, but that’s often not enough to use the code and certainly not enough to document it.

Don’t get me wrong, I’m talking extremes here and I don’t expect a lot from someone’s passion project in terms of documentation effort, just a little helping hand if you want me to have a good experience (which is a prerequisite for me to care enough to contribute).

> It’s very hard to understand an unfamiliar codevase.

I agree - the high level design and stuff is hard. But being a user and having the code allows you to document

1. Function level documentation including inputs, outputs. Even if you don’t understand how it fits in to the bigger picture.

2. Provide examples of working code (recipes) with some explanation of what it does.

You're going off on a tangent.

The question wasn't "is it harder to figure out what the code does by reading it than reading well written documentation?", it was "how can you submit a pull request for documentation when there’s no documentation for you to understand the code with", and the obvious answer is: by reading the code—in fact, that's ongoing work by some of the project's contributors.

Decisions are made by those who show up.

I agree with your point about reading the signals of which projects are probably the best.

But with great power comes great responsibility. It's entirely possible YOU are the person who makes this project great, just by the Butterfly Effect of getting the documentation good enough that the next person who comes along will be willing to choose this and push a little harder, and so on.

You're not forced. You're not obligated.

But if you show up, you get to make decisions.

> But if you show up, you get to make decisions.

That's not true with documentation. the decision has already been made. if you show up later and write the docs then you're just hoping you interpreted the decision correctly and aren't misleading people.

Plus, you are interpreting whether or not a decision was even made. Maybe it was an implementation detail that leaked out, or maybe the decision is still left as a TODO in the backlog somewhere.

If there wasn't an intentional design decision, then who knows if the behavior you try to document lasts beyond the current version, who knows how quickly that documentation is out of date. (Likely if a project doesn't care about documentation before you arrive, they might not likely care about stale documentation either.)

Isn’t that what the PR is for? one would assume “send a PR for docs” means “i’ll review before merging”. it seems like nobody wants to write the docs and the author already wrote the code so why double tax him when he is doing this all for free?

It's hard to "just send pull request" with such core and large aspect as documentation. You can work on your own and submit bug fixes, improvements, more examples and clarification for existing docs, but making documentation from scratch requires communicating and planning together with project authors. And you should know the project very well to write docs, at level of core developers.

One of the ways it can be done is to start independent documentation effort, without even considering to merge it to project repository. Then, having these "draft" docs, it will be easier to make "official" documentation. Even blog posts "how to get started with libui" can be useful. This project looks very promising, like WXWidgets, but in C and not C++, for this reason it has lots of language bindings already.

>I do this because I feel that the project has something of value and can be improved

If you don't already feel the project has value, I doubt the availability of documentation would sway you.

>I shouldn't be forced to make a contribution to a project if I just don't think it's doing everything right.

You're not being forced to do anything. We're just saying different people have different priorities: what's important to you might not be important to other people. Who knows? Maybe the programmer thought the header file was sufficient. It might very well be more than enough for his own needs. Instead of saying "somebody should write detailed documentation", people expect that you will be that somebody, since you're the one who raised the issue.

Many people have no problem using libui. There are even many bindings available that people use some of which have documentation. I was able to start using libui instantly, but mostly because I already have experience using other GUI libraries.

People that know C should be able to read and understand the interface file at:


The function / variable names are informative enough. There are examples which should get you started at:


Even if they would add comments to the interface files (that may be used to generate docs), it will not add much value if it will become as follows:

  // Set window title. First argument should be the window and the second the title as a string
  uiWindowSetTitle(uiWindow *w, const char *title);
What I think is more important is adding tests etc. Tests can then also serve as a kind of documentation.

> Tests can then also serve as a kind of documentation.

They would have to be written with documentation in mind, which distracts them from their primary purpose: catching bugs. Trying to understand Monocypher from just its test suite¹ for instance would be a pretty bad idea. That test suite is top notch at catching bugs, but it sucks big time at documenting Monocypher.


> It's absurd to think that I should just pick up a random project and be obligated to make it better, and that I should be called out for giving advice on how I think a project can be improved.

You have no obligation to contribute to the project, but if you think it is lacking in some respects, making your own contribution is the most obvious way forward. So you give some constructive criticism, and the response is a suggestion for a way to address it. No one is telling you that you are obligated to contribute, and no one is calling you out. You want work done and you aren't compensating anyone for doing it, so the only way the work will ever be made is if some actual contributors' interests happen to align with yours, if you become a contributor yourself or if someone is willing to work for you without compensation.

As it stands with this library, there is an open master issue to improve the documentation. The author has acknowledged the problem and is accepting pull requests to improve it. The general advice to improve the documentation is at this point is not adding any information to the contributors of the project, because now it's only a matter of actually documenting the issues in the github ticket system and for people to put in the work. The suggestion to make a contribution yourself makes even more sense given this context.

> I shouldn't be forced to make a contribution to a project if I just don't think it's doing everything right.

You use the words "obligation" and "force" very loosely throughout your post. It's not adding to your point that you blatantly misrepresent the suggestion to contribute the work that you want to see put into an open source project as some sort of coercion or shaming.

I think it breaks down to people skills. There is one group of people looking to use the lib for a project and another group that would be interested in contributing. Saying make a contribution to people not in the latter group is a bit rude. A better response would be to thank them for their feedback and mention contributors are welcome from those that are willing.

> Saying make a contribution to people not in the latter group is a bit rude. A better response would be to thank them for their feedback and mention contributors are welcome from those that are willing.

I think that it's better to be clear about it. I'd find it rude if someone said "thanks for your feedback" without intending to seriously evaluate or address it. If submitting pull requests is the best way to get work done in a project, its maintainers should be clear about it.

I see it completely differently. This is a fantastic body of work, and as far as documentation goes: read the source.

If you don't have time for that, its not the problem of the authors.

That said, were this a commercially driven enterprise, the lack of documentation is an issue. But, true fact, most open source projects can immediately benefit from the involvement of someone, anyone, willing to update the docs .. so, be a hero: submit a PR, someone.

I am quite oposite, I want example code using as much aspects of library as possible - sort of "a picture is worth a thousand words". Documentation is nice to have, but I personally consider a well written code a documentation, and it doesnt get outdated ;)

Have you checked this: https://github.com/andlabs/libui/blob/master/examples/contro... ?

Firstly, good documentation will include example code anyway. That's part of the course of documenting.

Secondly, exams code can get outdated just as much as human documentation. I've lost count of the number of times I've gone to compile example code only to find it doesn't work because of API changes or such like. I've also had example code crash my whole machine because it effectively created a fork bomb (thanks Microsoft for that one!)

So the arguement of example code Vs documentation isn't a mutually exclusive one.

Outdated examples can be mostly avoided by building them as part of CI and if possible running. Using deprecated attribute can even detect some of the cases when example builds but doesn't match recommended way of doing things.

Sure, but that would depend on project contributors doing that as part of their process. Which leads us back to square one on 'core documentation should not be something that has to be submitted via pull request.'

In an attempt to mitigate this, you could include the examples in your testing suite, at least to see that it still compiles properly. This is sort of standardised in the flow of Go, with godoc and the testing framework. Both uses examples from the same test files, producing standalone docs and testing them(at a minimum compiling them) .

This also happens in the Rust documentation generator. The code snippets in any piece of Rust documentation are compiled and run, and the assertions found in it will be reported if they fail. They're sort-of automatically part of the test suite.

Indeed, but we are talking about the lower end of the spectrum in terms of documentation (ie the arguement of what takes priority). If someone is considerate enough to include examples as part of their testing suite then you can probably bet they'd be equally thoughtful with their documentation.

In fact the main open source project I'm working on automatically generates it's documentation to help ensure its accuracy - and I know for a fact that I'm not the only person to do this.

(Hint: I am trying to make libui's in-code documentation match the Go style, which no existing C-based documentation tool seems to do...)

The first thing I looked for (and found) was the examples directory.

Give me an example over documentation any day.

This is usually how I work. I only look for the documentation when it does not work.

I work for many years with FFMpeg that has no documentation and no code sample, and it's okay for me. I prefer that the developers keep their time optimizing the code rather than writing documentation that needs to be maintained and become a problem when not in sync. My state of mind is that if it's open source then just read the code.

FFmpeg's C API has pretty good documentation: https://www.ffmpeg.org/doxygen/4.0/

The C API documentation includes a ton of example code: https://ffmpeg.org/doxygen/4.0/dir_687bdf86e8e626c2168c3a2d1...

In addition to having both a man page and a --help option, The FFmpeg CLI tool has very thorough documentation: https://ffmpeg.org/ffmpeg.html

I don't understand how FFmpeg could in any way be considered to have no documentation and no code samples.

FFMpeg is not some random project - it's irreplaceable and very popular.

Well, the only way I get it to work is by searching up how to use it on Stack Overflow, so…

Then don't use the project. Good lord... the sense of entitlement is over whelming!

"I shouldn't be forced to make a contribution to a project" OMG.

Anyways, the whole argument doesn't matter and is totally irrelevant. Serious teams/engineers will analyze the code, consider using it, and then assign developers to help out with documentation if it provides sufficient value proposition. And thus the cycle of OS improvement continues.

Yes, documentation would be nice, but code quality is 100x more important. 100 times out of 100 i'll pick the project with better code quality over better documentation.

BTW, clear, understandable code and APIs is an example of good code quality. And of course, well written unit/integration tests usually provide sufficient example code.

Documentation is part of code quality.

That's rarely been my experience. In fact, documentation usually exists because code quality is poor and it needs to be explained.

In my personal experience, examples do a poor job of explaining the reasoning behind something or the big picture behind something. It depends on the project, obviously, but often examples are fine for simple things but really don’t help with big complex things. Often they also don’t explain the trade offs or when you might choose a the various different options.

In my opinion, good documentation has three parts (four if you include a tutorial too):

First is a document explaining rationale, high level/big picture design, tradeoffs, when to use what. Usually a prose document with some sample code snippets where appropriate. Second, example code showing how to solve different use cases. Finally, an api reference (often auto generated from docstrings).

Different projects need different levels of each of these. For example, a relatively simple library might get away with a few short paragraphs for the prose documentation and maybe the api reference is literally just listing the public functions (if the names and parameter names are descriptive), this can be generated without any additional markup. If the api is complex, then it may need some explanation. Or the text documentation needs to be more detailed.

Obviously I don’t expect this from everyone who release some code online. For small code snippets, I’m happy with a commented example use and appreciative that you released the code at all. However, don’t be surprised if your code doesn’t get used then and if you want me to contribute, then I need to understand your project and without documentation I can’t do that. If I don’t understand your project, I risk that any PR I do is wasted effort and my time is limited (but I’ll happily help projects I use out regardless, where I can. I may need some guidance though)

From my experience there’s little to no correlation at all.

One of the most beautiful C codebases I’ve seen - the SSH IPsec stack - had the most succinct yet comprehensive documentation. Linux kernel has virtually none of the latter but the quality is still very high. Then there’s something like Miranda IM - complete clusterfuck of the code, but really well documented. A lot Java code is that way too, but also with documentation rehashing trivial facts rather than explaining anything.

However, what does seem like a sign of a good code is longer intro comments in header files that explain the design rationale and how things fit together in general. It’s basically a level up from verbose API description, but when done right it makes the API obvious without any further detailing.

Another option (C++ LGPL w/ Lua,JS bindings): https://github.com/yue/yue

Other projects building on andlabs/ui and https://github.com/parro-it/libui-node:

https://github.com/mimecorg/vuido - vue

https://github.com/kusti8/proton-native - react

This is very, very interesting.

It allows to build the whole UI using HTML, CSS and JS and leverage it with all the tooling and libraries already built for the web.

I had my eye on yue, but it does not seem that a Golang port exists. Persoanally I would like a guide (hints) to port it to Golang or other language.

There's a golang wrapper for libui written by the same author [1], if that's of interest. Same standard of documentation, though.

[1]: https://github.com/andlabs/ui

This is great, and they're fully documented. Thanks.

I might be interested, esp. since it claims Python bindings, but documentation appears to be nil. Seriously, nonexistent. A GUI lib surely has an API complex enough to require _some_ kind of reference docs, at least. But the contents of the doc folder[1] are just a joke, most of the files contain single lines, and the .md files are fragments with many "TODO" notes.

So OK maybe I can get some insight reading the code. The "common" folder seems a good place to start[2]. Um, no. Short, generic uninformative filenames ("matrix.c", "control.c") and very few introductory comments. The opposite of "literate programming".

[1] https://github.com/andlabs/libui/blob/master/doc/main

[2] https://github.com/andlabs/libui/tree/master/common

The entire API is 1100 lines. https://github.com/andlabs/libui/blob/master/ui.h You don't need a separate documentation for that. In fact, most functions have sufficient docstrings if their names don't fully describe their function.

Your hostility toward an MIT licensed project is what is ruining the open-contribution model of developing software. In 2005, it was "Hey, this looks great, want me to write up a documentation?" Now it's "Not up to my standards, it's a joke." Absolutely disgusting behavior that is becoming gradually more common.

I got to the first function in the API:

    _UI_EXTERN const char *uiInit(uiInitOptions *options);
uiInitOptions is a struct that contains a single size_t Size. What's it the size of? Can I pass a NULL pointer? Does this function take ownership of the pointer, and if so, does it need to be allocated with malloc? If not, when can I free it - can I use a pointer onto my stack? Why does it take a non-const pointer - does the size (of whatever) change? What's the string that's returned? What's the lifetime of the string that's returned? Can another thread call uiInit, or does that break everything horribly? Or does it only break horribly if you don't copy the returned string first?

You don't need documentation, sure. But it's a good way to get users of the library that make wild assumptions so that you can no longer make reasonable upgrades to the library without breaking them, and that makes nobody (neither the library author, who wants people to use it, nor the users themselves, nor end users) happy.

>Does it take ownership of options, a struct with a single size_t.

This is a bit extreme. My first thoughts (honestly) is yes, what is the size of. Following their advice to follow their examples, I looked at examples and it literally just zeros a uiInitOptions on the stack and sends it in. Thus I think it's something I wouldn't really need to care about usually.

As for whether I need to worry about saving 8 bytes on the stack or elsewhere, that seems like such a rare question (amongst the questions people would have) that it would motivate digging a little bit. It took me probably 3 minutes to find the answer[0].

As someone said above, this is one cat's work in their free time. The gratuitous criticism is very unfair to them especially when you're worried about out circumstances most devs wouldn't have to deal with or care about.

[0] https://github.com/andlabs/libui/blob/master/unix/main.c#L11

"Usually?" What are the unusual circumstances? Will I need to care about it at an inconvenient time two years later?

I mean, yes, I can probably guess some things and end up with something that works with the current version of the library, but why would I choose this library to build on top of if I'm just guessing?

The code cannot possibly answer the question of what changes the developers may make to the project in releases they consider backwards-compatible. My question is entirely about the API, not about the code itself.

...not to mention that this is obviously a work in progress. We're looking at a project's github page, not a product release page. I would think that like with a lot of coding projects, you start with an initial idea and see where it takes you, rather than with a full specification that you then follow. Given the limited resources of a single programmer, writing an extended documentation early on and then keeping it maintained with every chance to the architecture would be a huge burden, time and effort-wise. That's not to say it cannot be done, but I understand if you want to spend your time on coding first, if it's a pet project. There's nothing that prevents documentation to be added in the future.

Yes, sorry—I should have been abundantly clear that I was responding only to the "You can figure it out yourself from the header file, you don't need docs" point. If it's an unfinished or hobby project, great! Those are cool, and I don't mean to discourage them / place high bars on them existing in public, and I am super sorry for not being clear about that.

Hobby or personal-interest projects with an expectation of no real use don't need externally-facing documentation because they have no externally-facing APIs at all, not because their APIs are obvious.

Great! If you can answer those questions, send a pull request to add it to the docstring. You've spent some time thinking of those questions, so you'd write a very complete docstring. Complaining will not solve the issue. Sending a PR will solve it. This is what I was saying above. I am attempting to orient people into the "open-contribution" community, where we share the opinion that free software is NOT free to produce. Someone must do the things you are suggesting at some point if they are to exist, and who better than yourself?

With regards to your last paragraph, a common misconception is that a "payment" of open-source software is number of users. That would be true for proprietary software where payment = number of users * price, but for open-source software the developers couldn't care less (except maybe superficially, but this mental reward is insignificant for the long-term motivation for a project). They want to make a library that solves their own problems and is stable. They allow people to help improve the library in exchange for releasing it for their unrestricted use. Otherwise, there is little motivation to release it. When I find a new library that solves a problem in an interesting way, I learn using whatever is available (existing documentation, headers, source, and examples) and write down the difficult parts. The price I pay for using the software is to send my notes back to the developers in a polished, organized form that is consistent with their existing documentation. Then, no one needs to repeat what I've done in the future.

While I agree with the general thrust of what you're saying (people should contribute far more to the free software they use rather than be angry with maintainers for not solving every issue under the sun -- and having more users is no substitute for having a few passionate external contributors), this is a fairly hostile way of trying to on-board people to a project.

Not to mention that the developers that wrote the project in the first place are in a much better position to write documentation than anyone else (in the past I've had to review documentation from external contributors and I'm pretty sure it would've been phenomenally faster if I'd just written it in the first place -- it isn't their fault, it's just that I know the code and its history much better than them because I've maintained it).

I agree that it's a somewhat hostile way to invite people to a project, but 1) I highly doubt that dropping a cheerful invite will have any convincing power other than someone replying "yeah, I should do that" and then promptly forgetting it, and 2) some scolding was needed. :)

Your second point is a good one, but the developers are in a better position to write actual features and fix bugs than anyone else, and since documentation is more public-facing than source code, it's actually a better choice if someone wants to contribute anything at all, so the primary developers can spend their time more wisely. I certainly know the "phenomenally faster if I'd just written it in the first place" effect well, which is why I recommend to contributers to not do drive-by contributions but spend a good week writing notes while they use the library, and then convert to high-quality documentation, effectively adopting a section like you would with a community garden. Quality over quantity. And if the documentation attempt is low quality, it's still a much nicer way to prod the developer to write some documentation, so he/she can use it to define their quality standards or as a possible outline.

> some scolding was needed

Was it, really? I think the parent comments did a good job at pointing out a potential, actionable, flaw in this project. That doesn't mean that they should be "scolded" for pointing it out or that they themselves need to fix it.

There are times when people report an issue to an open source project and the response is "You should fix it yourself".

Open source contribution happens when the contributor has invested themself in the project and wants to maintain the relationship. Perhaps the requester is evaluating multiple packages and wants to inform the project why they're going with another one instead. Maybe they got to the point in their evaluation that they're ready to commit only to discover a critical issue hidden in the (lack of) documentation.

It also comes off as hostile since implies that the requester's time is less valuable than the project maintainer's. Perhaps the requester is busy contributing to other open source projects. Perhaps the requester only has time right now to use the software, but has the goal of contributing in the future.

The project's maintainer's responsibility is maintaining the software, presumably because of some personal interest. Reporting and even expecting them to fix issues is absolutely normal.

>implies that the requester's time is less valuable than the project maintainer's

It is. In large projects, there are relatively few maintainers responsible for evaluating the requests, reports and code from lots of people. They're scarce resources.

https://www.youtube.com/watch?v=fMeH7wqOwXA https://www.slideshare.net/linaroorg/maintainer

I find if you maintain an open source project as if your users were customers, things tend to go pretty smooth.

Smooth for whom? Not the one beholden to a bunch of non-paying "customers" I'd wager.

What is the bad thing you posit would happen when a bunch of non-paying "customers" are treated in a professional manner?

Can you explain how you found that?

By trying it, and realizing afterwards that nothing bad happened as a consequence.

The main benefit is that it forces one to try to be professional and consistent, and to avoid being flippant, cryptic, didactic, and condescending.

Keep in mind that cutting customers loose is a natural part of the game, too. If someone demands to get a Big Mac at Chipotle there's no law that says they get to block the line for eternity.

geofft could just ignore the library completely without giving his valuable opinions on the kinds of things that should be specified in a reference document. That isn't complaining at all. Maybe the author really has no clue on what information to put into an API document; geofft's comment provides stimulating ideas.

geofft doesn't have an "issue" because he's not using the library; he can avoid the non-documentation problem for himself quite adequately by ignoring the library and moving to a different one.

> If you can answer those questions,

No you can't. You can only reverse engineer what the code does, not what the programmer intended.

Why would I sit there reverse engineering someone's code to write a document for them which codifies the bugs they didn't intend to make? They will just reject the doc "oh, thanks for writing this but that's not what's supposed to happen; that's a bug. Can you wait until next release and then change your document based on the new code? Thanks.".

Fuck that, you know?

Will the designer even take the document seriously going forward? Or will he just regard that as someone else's unimportant opinion about what a particular revision of his program did once upon a time?

We already know something about the designer's attitude is toward documentation, from the lack of it.

Satellite documentation: different story. I mean, tutorials, guides to internals and things like that. But, no, I'm not writing the basic, fundamental spec for your undocumented code you've already written.

> I am attempting to orient people into the "open-contribution" community, where we share the opinion that free software is NOT free to produce.

I agree with this position. I am also working on my own open-source projects, as well as other projects that I know have conscientious maintainers and a high-quality community. Why should I contribute my time to this project?

To be a little blunt: if this project has not thought about things like ownership of pointers and concurrency safety, it is not a project I think other people should use. My time is limited, and I use it on improving projects that I think are worth improving.

> for open-source software the developers couldn't care less (except maybe superficially, but this mental reward is insignificant for the long-term motivation for a project). They want to make a library that solves their own problems and is stable.

As an open-source maintainer, this doesn't describe me at all. I care more about things that improve the world than things that amuse me. (I also work on a few things that amuse me, but they're relatively clear about that status, and f they're not, I welcome someone calling me out on it.) All the long-term projects I work on are motivated by wanting that project to be a healthy project available as a compelling option for as many people as possible.

I had the rather delightful experience of starting a new job recently and finding that the next team over had just decided to start using a project I've been maintaining for a few years. If I had not spent time writing both code and documentation that welcomed unknown future users, this would never have happened. (And I still have not written nearly enough documentation for it!)

If my motivation were just filling my own needs, I probably wouldn't publish software at all. If it were that plus bolstering my personal brand, it would go on my blog or as CC-BY-NC-ND or something. My entire motivation for releasing software under a free license is for other people to use it.

Some people just want to use a library. Not everyone wants to build a library. When evaluating a candidate library, it’s perfectly reasonable to look at things like documentation completeness. “Don’t discuss weaknesses; fix them” isn’t helpful or constructive. There is no moral commandment to pretend all open source libraries are without flaws.

I see where you're coming from, but it's not a completed project if it's not documented. If it's only 1100 lines it shouldn't be hard to document it. If it's only 1100 lines and it's undocumented, it would probably be easier for me to continue using my own.

True. People seem to have expectations of open source projects now. They act like customers even if the programmer isn't a professional who is getting paid to work on it.

I work on several personal projects whenever I have free time and feel like programming. I keep them on private repositories because I don't think they are ready for publication. I'm not sure if they're ever gonna be ready.

With that many digits, uiPi should definitely have an L suffix.

Except that would make uiPi a long double, whereas every drawing API in libui just takes a double. Now as to whether the drawing APIs should use long double instead of double, I don't know; I will say that both cairo and Quartz/Core Graphics use double, so... (And on Windows, Direct2D takes floats, so at least on that platform, it's probably not going to make a difference at all...)

I find it a bit sad that this is the top comment. I have witnessed free software/OSS have tremendous amount of positive effect on the world, however as the years go by I can't help feeling that we have trained a generation of users to act in an entitled manner towards software that is free and often the labor of love of some fellow developer trying to get better at their craft.

I view it a bit differently. I can't help feeling that we have trained a generation of devs to act in an entitled manner towards documentation that is easy and formerly seen as requisite as the code itself. Personally, I find documenting my projects a labor of love because it's where I can distill all of my hard work in a presentable format.

> I have witnessed free software/OSS have tremendous amount of positive effect on the world, however as the years go by I can't help feeling that we have trained a generation of users to act in an entitled manner towards software that is free and often the labor of love of some fellow developer trying to get better at their craft

The only issue I see with the parent comment is that it's a bit harsh. But it's good advice to someone "trying to get better at their craft": writing software, especially one intended to be used by others, without documentation, is generally poor practice. It's not entitled at all, as far as I can see: it's not saying "I should have documentation for this project I use for free"–as far as I'm aware, they're not even using it at all. They're just evaluating whether as an interesting project they might want to take a look at later.

What about the effect of harsh comments on the creators morale?

Yes, this is a thing, which is why I called it out for being harsh. I think that it could have been a bit nicer.

I've been programming for a long time, but if it's undocumented I don't use it, period. It takes too much time, gets too buggy, and I can just write it myself and understand it completely (and document it as I go).

Definitely agree that this has started happening in the last ~10 years. The solution is to convince programmers to maintain their own open-source projects so they can discover for themselves the reasons developers do this. (e.g. it's not magic or altruism, there are real reasons.)

The readme specifically says it has no docs and asks users to look at the main header file.

For imgui (https://github.com/ocornut/imgui/) and uklear (https://github.com/vurtun/nuklear), docs are basically unnecessary. You just have to look at the examples/demos and copy pasta. Immediate mode GUIs are great.

I'm maintaining the python bindings at https://github.com/joaoventura/pylibui/. Happy to accept pull requests for it..

I have no doubt that the author would accept a patch should you see fit to contribute some documentation.

Sure, but I hope you agree that I have no obligation to submit a patch, given that I'm not using this software, just as the author has no obligation to provide documentation for me either.

try the examples folder.

That's nice, but falls quite short of proper documentation.

But let's be honest: how many people write up a really good documentation for their github project? I mean, something that actually adds substantial value on top of what the source code, code comments and examples programs can provide? And is not outdated, i.e., actually always in sync with the code portion of the project? I'm sure the answer is > 0, but I would be very astonished if the percentage would be a high double-digit number.

Let's just stay realistic: this guy is not selling a product, he's coding up something out of his own interest and is showing it to the world on github. I'm sure his interest in coding this up is much greater than his interest in writing documentation, so why should he focus on the latter? "So that anybody else can use his stuff" comes to mind as a first answer, and that's fair enough. But maybe that hasn't been his foremost interest.

One aspect that I see here is that with all the different language bindings, we're not talking about a documentation that would be trivial to write. I could imagine that an effort like that requires a lot of subtle changes to the API as more functionality is added which makes keeping the documentation up-to-date a tedious and quite hard thing to do -- so something that isn't a lot of fun. And isn't fun the main reason hobby projects get started on github in the first place?

I see your point that the current state of the project makes it very hard to use for you. Fair enough. But maybe it can become interesting again in the future when more documentation has been added -- perhaps even though the help of others. After all, it's an open source project.

For those interested, it seems to use classical grids to align elements, and it is the only way to do it, since there is no mention on coordinates (if I read it thoroughly enough).

  void uiGridInsertAt(uiGrid *g, uiControl *c, uiControl *existing, uiAt at, int xspan, int yspan, int hexpand, uiAlign halign, int vexpand, uiAlign valign);
The overall feeling is that it’s a [small] subset of GTK. I think they try to fill an empty cross-platform niche between lightweight and native-looking Tk and heavies like GTK and Qt. Doc could explain how is that better than Tk itself, but it has to be written. The other possibility is that they do it for fun and distinctive use cases are shallow – this is often seen in second order ui kits.

I think the point of this library is more to offer a native wrapping UI toolkit, including windows and Darwin, not necessarily a GTK subset, though you probably meant that in terms of a subset of components rather than implementation. This library has no renderer of its own and instead delegates that away.

Also the design of uiGrid was directly based on that of GtkGrid.

I have arrived at this library yesterday while trying to do a cross platform drag and drop app. I decided to go with x/screen package instead. The documentation and lack of examples threw me off. If I have to read the source in details to understand the app, I am better off writing the code x 3 with native tools. The library is supposed to save time not steal from it. It is wonderdul idea and I really like the name. I wish the author will make it more dev and contributor friendly so we can take it off the ground.

Not only does libui not yet do drag-and-drop, but drag-and-drop is sufficiently complex enough that simple libraries are probably not going to have this out of the box. That being said, I do plan on adding drag-and-drop later.

Thanks! The first thing I did was to click on the 'past' link. But that was no help here because the project has changed its title in between.

Judging from the comments here, it appears I have completely failed at properly getting across just how early this thing is in development. I've since updated my README with a status report.

As for documentation, that is an active WIP. I have recently pinned down a documentation style I like, and applied it to the newest APIs; all that's left to do really is to spread it to the older APIs as well, and write a tool to turn that documentation into HTML, because I have not found a documentation tool that operates how I want it to.

Oh, and one other thing I forgot to mention about documentation: the nature of this project requires me to balance what I can get behaving identically across platforms, what I can guarantee about behavior across platforms that must differ, and what I am forced to leave as "implementation-defined" with no further specification. If this was a non-native project like GTK+ and Qt, I would be the one making these decisions, but in this case I am not, so I must take a lot of factors into consideration when writing documentation. If you read through the docs I did have on package ui, you'll find a lot of TODOs about behavior.

The title should be "GUI library written in C", not "GUI library for C". There are bindings for many languages. Also "libui was originally written as part of my package ui for Go".

No Documentation? Documentation as an afterthought is not a good sign that this was well thought out. How about a white paper? A tutorial? Just code?

Why would you need an entire whitepaper for wrapping OS widgets in a window? The API is the documentation, and the example code gives you everything you need to get going. Why would you need anything else?

I’m mixed on whether api docs are needed, if you have them, they have to be kept in sync, if you don’t then examples have to cover as much of the api surface area as possible

Higher level docs would be nice though, goals and non-goals, high level feature roadmap etc.

For example a cursory reading of the code suggests that there is no a11y support, which is a deal breaker for some projects and not so important for others, it would be nice to know where that sits on the roadmap

A whitepaper for some dude’s personal project, the sense of entitlement is astonishing.

I am sorry -- I assumed since this reached the top page of HN that this was a bit more serious that just some dude's personal project. This portable graphics API thing has been tried 10000x and they are almost never useful for any significant app you want to write. I see one of these and I hope that maybe someone has figured it out -- one glance and I see no documentation nor any rational as to why this effort is unique, then I know this is not a serious offering.

I do intend on this being a serious offering; it just wasn't an offering I was ready to make yet when people jumped on it.

What have people not yet figured out about cross-platform graphics? If we knew exactly what was wrong, we could fix it...

I am surprised that ocornut/imgui [1] is not mentioned anywhere here. I used it for an admin interface in a past project. The author makes it a point to do work on the library based on donations (such as from Patreon, or PayPal). I suppose that's the main reason the project is alive and kicking today. OpenSource projects that are somehow financed - are in a much better situation than projects done on a spare time budget.


[1] https://github.com/ocornut/imgui

Interesting, never saw such way of std::vector/std::map allocations:

    g->children = new std::vector<struct gridChild *>;
    g->indexof = new std::map<uiControl *, size_t>;
At least needless level of indirection ...


There's a glaring memory leak if the second new throws.

Probably because it’s easy to create memory leaks this way…

Lately I was thinking about the Right Thing [0] of Native Crosspostform UI - write a spare frontend for every platform and write the backend in something portable. It could be a nice idea to come up with a document that would describe every platform APIs for:

- accessibility

- localization

- text rendering

- input methods

- widget toolkit

- event loop


The document should also contain example code for something basic for every platform. All this information could be then used to create the Right Thing Toolkit.

Probably it should aim for the future. So only include APIs that most probably would not be deprecated in 5 years. The platforms that I'm thinking about: Android, Freedesktop/Unix-like, iOS, macOS and Windows.

I was wondering what is current situation with Windows. Is UWP the future or will it be soon replaced by yet another API? Is side-loading currently as effortless as running of Win32 apps? Or maybe Win32 is good enough, because they will always support it?

[0] as opposed to the Worse is Better, because that's current situation and it's not all that hard, use SDL or whatever and draw everything yourself.

I would love to see a boost library that does all of this :-)

One thing I have noticed about programmers in general, and this thread tended to remind me of it, is that everyone has high expectations of other's documentation, but when put on the spot, rarely meet those expectations themselves.

At my most recent stint in a software company once of the most frequently heard retorts about absent documentation was "the code IS the documentation".

Yet often these same people were the first to complain when another developer or operations staff hadn't documented something and they'd got themselves into a pickle trying to guess what was going on rather than read the code themselves.

Often the people most vocal about documentation are the worst at preparing it themselves in my experience, a form of projection onto others. YMMV.

How does it compare to the good old (and mature) https://www.wxwidgets.org/ ? It is one of the C++ toolkits which was famous for using native widgets.

The same library for Go https://github.com/andlabs/ui

Note that this is a Go wrapper around the C libui library, not a Go implementation of it.

> libui was originally written as part of my package ui for Go.

> Now that libui is separate, package ui has become a binding to libui.

> As such, package ui is the only official binding.

From the README — https://github.com/andlabs/libui#language-bindings

I wish more projects lile this existed. Most of the tools don't need a huge UI but something simple to install and well integrated is very much needed.

I like the toga project in python : https://pybee.org/project/projects/libraries/toga/

Tkinter is terribly integrated and QT hard to install so toga hits a sweet spot. But it's very immature.

My favorite toolkit is still wx, however it just reached V3 compat so it's considered unstable. You can pip install it (well, linux support is so so yet) and all the UI looks native, including the file dialogs.

I think GTK is an excellent library for C. If you use Glade and GTKBuilder, you don't have to write the boilerplate either. You design you UI in Glade visually, add your signals, set your id's etc. Then you save your design as an XML file. In your C code you load that design with a simple function, then assign the function names for the signals you've created in the visual designer. Then you're all set to go.

The library (GTK) feels the same in every language, whether it's C, Python, Go, etc.

I admit, it can be a hassle to get the library up and running, but once you do that, it is surprisingly simple to code in.

The problem is it's not well integrated on anything else than Gnome. If you are on KDE, Windows or Mac, stuff like the file picker will make the experience painful.

Even electron apps don't try to reinvent this one and pop the OS widget.

Native file pickers on Mac and Windows (and maybe KDE via org.freedesktop.portal.FileChooser) can be used since 3.20: https://developer.gnome.org/gtk3/stable/gtk3-GtkFileChooserN...

The UI's look like garbage on anything non linux though.

Well, GIMP uses GTK and it looks really sharp on all platforms. It all comes down to theming.

I wouldn't say it looks like garbage, but if you want a more native look and feel you could certainly set it up in the settings.

(For example: you could look at https://stackoverflow.com/questions/37035936/how-to-get-nati... )

As a library purely coded in C, I still believe that GTK and GNOME lay a solid foundation for easy development in C.

Before downvoting you might want to give GTK another chance. Even this libui library uses GTK under the hood for linux.

It looks like garbage on anything not GNOME 3 with default settings.

Nice project and I like seeing the many language bindings other people have contributed. I am definitely going to try this.

I did something a little similar about 20 years ago in my two McGraw Hill books Portable GUI in C++. But Libui looks very much better.

Github badly needs a prototype/alpha/beta/rc/production tag, like Sourceforge and Pypi have.

It should be set to prototype by default.

It does this for "Releases", but not for entire projects. And if someone starts browsing files, then you'd have to worry about what that status is at the commit for the file you are reading; this will vary based on how the projects organize their git branches, tags, and releases.

One of the funniest commit messages I've ever seen: https://github.com/andlabs/libui/commit/422ec83162de7b9689b7...

How does it compare to wxwidgets? I have used neither of these. I need a platform independent(mac/Linux/windows) GUI for a upcoming project and I was comparing Qt and wxwidgets and decided to use wxwidgets. Now wonder whether I can use libui instead of wxwidgets?

wxWidgets is a lot more mature. If you are fine with a C++ API instead of plain C, I'd go with wxWidgets.

I was just reading ui.h. It's been quite a while since I wrote anything in C so this might be a dumb question, but does C not have namespaces? How can major projects use third party libraries and not have to deal with naming collisions?

No, C doesn't have namespaces as a language feature. Guess why all the function names start with ui.

But ui is a super common prefix. I've seen it used for user-interface variable and function names and also in Microsoft-world in projects that abuse Hungarian notation (unsigned int).

Clearly it must not be a problem, I just don't understand how people work around it.

C compilation units have a static section which isn't exposed to the outside world (i.e. other compilation units): https://www.codingfriends.com/index.php/2010/07/13/static-in...

I don't know, but I do know I'm in the middle of making sure any non-static symbol name in libui either has a prefix of ui[capital letter] or uipriv[capital letter] to at least ameliorate this madness.

Yeah, only ui might not be a great prefix. It is a problem when names clash, and annoying to work around. Either you rename one of them, or you can wrap one library in a library of your own that changes the names.

So what I can understand this is "just" a wrapper for existing GUI frameworks? Why is this better than just using GTK that already is portable?

Writing a GTK UI for macOS, for example, will make the interface look very different to the look and feel that the operation system is offering. If you use a library like libui, the ABI is the same for every major operating system, but the result matches what the OS is using. If you don't care about the look and feel of the interface then I guess this library is not for you. As someone who is responsible for maintaining the UI of a big application for three major systems (macOS, Windows and Linux) a library like this would have been a blessing years ago before the project started.

Apart from being curious why your comment is downvoted, did you consider using e.g. wx or tk? They both had their disadvantages last time we checked (~10 years ago), but it would be nice to hear someone’s opinion on them in this thread.

On Unix this seems to map to GTK+, so I guess it's a bit like wxWidgets then?

Interesting but since GTK+ itself is cross-platforms it feels a bit heavy to wrap it.

> GTK+ itself is cross-platforms

Only in theory. It does not look and behave even close to native anywhere except on GNOME 3 with default settings.

Uh, no, it's not aiming to be a "native-looking" interface, it's GTK+ on all supported platforms.

nuklear (https://github.com/vurtun/nuklear) is also pretty cool. and it seems to have bindings for various languages (besides C) f.e. go, rust, lua etc.

Have you ever actually used nuklear? It is awkward and confusing to even change an example and have it work, let alone creating what you really want. There is no documentation that will help you either.

Is there a portable C++ GUI library though?

Do you mean a C++ bindings for libui?

If yes, then you can check these two [1][2].

[1] https://github.com/billyquith/libui-cpp

[2] https://github.com/aoloe/cpp-libui-qtlike

Qt is the most portable GUI library. It can run on bare metal.

Except it doesn't run native controls, at least so far as I'm aware.

> Except it doesn't run native controls, at least so far as I'm aware.

Can you tell the difference? https://3.bp.blogspot.com/-O1Naap_IGVQ/VGJsRBEfQjI/AAAAAAAAA...

Well, it's not the prettiest Mac application, but it works great!

Not really a great example, as much as I love VLC.

well, yes, because it runs on platforms that don't have any kind of "native" controls. Besides, in KDE/Lumina/LXQt, Jolla phone, LG WebOS, or AsteroidOS (currently on the front page just above this!) and many automotive environments & medical devices, it is the native UI system.


What a surprise, so there are alternatives to Electron garbage! Who knew!

Qt? Although it has its own problems, the end product is often way better than Electron.

It may have changed since I last gave it a shot previously one annoyance I had with Qt was binary distribution. Getting it all packaged up correctly for each platform is much less than straightforward and if your app isn’t FOSS it’s exacerbated by LGPL linking requirements. It should really be a simple, single button process.

> Getting it all packaged up correctly for each platform is much less than straightforward and if your app isn’t FOSS it’s exacerbated by LGPL linking requirements.

Electron also has LGPL dependencies (Blink, FFMPEG) and libui depends on GTK which is also under LGPL so...

There is no LGPL linking requirements if you buy Qt commercial license.

There is also gtkmm

Not sure why I've been downvoted. What is wrong with gtkmm? It's a reasonable C++ binding to GTK+

Ironically this library is small, easy to compile, written in C++ with a C interface, and unbelievably slow. Try out the test.exe and watch everything slow to a crawl. It is worse than Atom about the speed of the slowest modern program I've ever seen - the ethereum wallet.

I assume you are using the Windows version. The slowness is a bug that I have to fix; there are several issues about it, and a few ideas of how to fix it. You can comment out some code in container.cpp if you want to have it go fast but also be ugly (the code has to do with transparency of standard controls on tabbed backgrounds).

Oops, if it wasn't container.cpp it was parent.cpp; I forget which file right now

Applications are open for YC Summer 2019

Guidelines | FAQ | Support | API | Security | Lists | Bookmarklet | Legal | Apply to YC | Contact