[HN Gopher] Ask HN: I'd like to practice coding GUI from scratch...
       ___________________________________________________________________
        
       Ask HN: I'd like to practice coding GUI from scratch. Any
       recommendations?
        
       Hi folks!  As the title says, I want to practice coding a GUI
       framework, probably in C++.  I read about a retained and an
       immediate modes, have a rough understanding how event loop works,
       and overall my goal is to practice architecture and optimization
       (especially cache-friendliness), and less so graphics and
       typography rendering, though I understand it's unavoidable to
       implement a rendering pipeline (I plan to start off with AGG or
       Skia graphics libraries).  The dummy app itself will be less about
       forms but more about data representation, e.g. an audio editor or a
       node-based system, where data should be updated and visualized in
       real time, and everything should feel responsive.  Could you please
       give some research directions? Maybe case studies, best practices,
       some interesting software, maybe to read more in detail about
       related architectures, etc.? Or maybe personal stories? I'm
       struggling to find related info which would not be focused on some
       framework, etc.
        
       Author : scott01
       Score  : 44 points
       Date   : 2022-03-20 20:06 UTC (2 hours ago)
        
       | cracrecry wrote:
       | I have done lots of UI interfaces in different platforms. I have
       | used Motif and X Windows, Win32, MFC, Gtk, Qt, Cocoa, simple Web
       | interfaces, DirectX, OpenGL, Metal.
       | 
       | I love Dear Imgui: https://github.com/ocornut/imgui
       | 
       | It is the simplest thing in the world. If you are starting and
       | are going to do 3D graphics anyway you don't need state(you just
       | redraw the screen 60 times per second).
       | 
       | Anything else is extremely sophisticated. I also loved Qt, but
       | the policies got a little cumbersome, and went native.
       | 
       | The big problem is that with state there is a lot of complexity
       | involved that is dependent on a platform, and once you pick one
       | it is hard to change.
       | 
       | The big advantage of 3d graphics and dear imgui or any other open
       | source software is that it works anywhere and you are not as
       | dependent on a single company.
        
         | scott01 wrote:
         | I actually started tinkering with Dear Imgui, very cool
         | library! From your experience, does this approach scale for
         | complex apps with a lot of data updates, with dozens time
         | series visualized, edited, etc., or am I overthinking?
        
           | joeld42 wrote:
           | It does, but you have to do a few extra things beyond what
           | you'd do for the typical stuff like in-game editors and debug
           | tools.
           | 
           | - Data update are the best part -- there's no synchronization
           | needed with an IMGUI approach because the "model" and "view"
           | are the same thing.
           | 
           | - adjust the event loop so it only redraws on changes (e.g.
           | mousemovement) rather than every frame (unless you're drawing
           | every frame anyways for a game)
           | 
           | - IMGUIs can have trouble with very large lists -- imagine
           | you have a tree view with 20k objects, you're going to
           | process each one of them each time through the gui, even
           | though most of them are outside the visible list. But it's
           | hard to only draw the "visible" ones since you don't know the
           | future (e.g. imagine iterating a list where some items are
           | hidden). Usually this isn't a big deal to work around, just
           | keep it in mind.
           | 
           | - Biggest problem i've run into with IMGUI style is layout.
           | Since you are processing widgets as you go, you can't adjust
           | to future things. For simple layouts like stacked property
           | sheets this is fine, but once you get beyond that it can be
           | complicated. I'm playing with some ideas now where I use a
           | constraint based layout to come up with "reference boxes" up
           | front that then the IMGUI can use to layout but it's still a
           | pretty open problem.
        
         | krapp wrote:
         | >It is the simplest thing in the world.
         | 
         | Not even close...
         | 
         | https://github.com/mitsuba-renderer/nanogui
         | 
         | https://github.com/rxi/microui
         | 
         | https://www.fltk.org/
         | 
         | https://github.com/achimdoebler/UGUI
        
       | AussieWog93 wrote:
       | I'd recommend actually building something with Dear ImGui (IMO,
       | the best GUI framework in existence by a country mile). Merely
       | reading about the differences between retained and immediate mode
       | cannot do justice to the paradigm.
        
       | hawski wrote:
       | I would only like to urge you to think about accessibility. There
       | are many custom GUI libraries out there, but almost all of them
       | are made without thinking about accessibility. It kind of forces
       | certain architecture, which may be hard to fit later. A11y APIs
       | expose widgets in form of a tree.
       | 
       | I thought about writing a cross platform GUI toolkit, that would
       | start from being a cross platform accessibility library.
        
         | scott01 wrote:
         | To be honest, I'm aiming to simply practice UI architecture and
         | optimization, and it's unlikely that something will come out of
         | it. But I didn't know about A11Y before -- thank you for
         | bringing this up, will probably check it later.
        
       | jagger27 wrote:
       | I find the SerenityOS userland code base quite approachable. It's
       | all written in C++.
        
         | scott01 wrote:
         | That looks like a good idea, probably can explore allocators,
         | etc. from there. Thanks for that!
        
       | phtrivier wrote:
       | If you have a mostly 2d UI in mind, you might to from something
       | even simpler than opengl, like SDL or raylib - anything that lets
       | you out pixels on a screen.
       | 
       | My personal experience is that starting developing in opengl
       | always ends up wasting hours getting the right libs installed to
       | get potentially full 3d GPU acceleration - which might be beyond
       | the point if you want to draw stuff.
       | 
       | Casey muratorri is spot on in saying that not having a single,
       | simple, unniversal and basic API to "open a window and draw
       | pixels" is what we lost the most during the 90s.
       | 
       | Anyway, try to bypass the not-interesting-to-you parts, and have
       | fun !
        
         | scott01 wrote:
         | Noted, thanks! Yes, I was thinking more about 2D
        
         | krapp wrote:
         | I would definitely suggest starting with SDL, because it _is_ a
         | "single, simple, universal and basic API to 'open a window and
         | draw pixels'" and it recently added an API to draw geometry
         | directly without OpenGL. It also gives you a flexible event
         | system that can be used for messaging.
        
       | loxias wrote:
       | > The dummy app itself will be less about forms but more about
       | data representation, e.g. an audio editor or a node-based system,
       | where data should be updated and visualized in real time, and
       | everything should feel responsive.
       | 
       | Would you be interested in a 'no restrictions, informal'
       | collaboration?
       | 
       | I have little to no experience writing GUIs, but your "dummy
       | apps" sound to me like the sorts of things I could populate the
       | 'guts' of, to make useful.
       | 
       | For instance, I work a lot with audio signal processing, have
       | considerable experience in that area, and am "half-assedly" (low
       | priority side project) writing tools that would benefit from a
       | GUI.
       | 
       | My email is on my profile.
        
       | svilen_dobrev wrote:
       | think about.. the various "hierarchies" / aspects / of the
       | relations of the things in it. Event-passing is one ; Containment
       | (x part-of y) is another ; Visual overlap yet another (now that
       | depends on point of view) ; ... there are more.. depending on the
       | purpose.
        
         | scott01 wrote:
         | There're definitely keywords I'm going to Google :) As for
         | hierarchy, I'd like to avoid having class hierarchies where
         | everything is a subclass of Widget, etc. I guess I want to
         | explore how much of the data required for rendering of such UI
         | can lie in contiguous memory -- hope it makes sense...
        
       | thamer wrote:
       | I've written a fair share of GUI apps in C++ on multiple
       | platforms, starting with Win32 API and MFC on Windows and later
       | Qt on Linux. The way you write applications with these frameworks
       | is different enough to have a significant impact on the structure
       | and design of the UI layer.
       | 
       | I don't have any suggestions for how to build such a framework,
       | but I would encourage you to play around with a few existing
       | frameworks to see how they are designed, what you like about
       | them, and what ideas to avoid.
       | 
       | For just one example, see the difference between managing the
       | event loop entirely by hand with Win32[1] and using "signals and
       | slots" in Qt[2]. There is a lot more to UI frameworks than this,
       | and they vary on many more aspects.
       | 
       | - [1] https://docs.microsoft.com/en-
       | us/windows/win32/winmsg/using-...
       | 
       | - [2] https://doc.qt.io/qt-5/signalsandslots.html
        
         | scott01 wrote:
         | Thanks! I had a look at signals and slots. Is this similar to
         | Smalltalk's idea of objects sending messages to each other?
         | Like messages they don't know about can be ignored, or
         | something like that (I only watched Alan Kay's videos on this
         | topic, never programmed in Smalltalk myself). If I'm not
         | mistaken, Objective-C had something similar and was also
         | successful for UI, so maybe message passing mechanism is
         | something to explore more...
        
           | thamer wrote:
           | With Qt you don't really have to deal with unexpected
           | messages. A signal is triggered by an event, like a button
           | click or a slider value changing, a checkbox being toggled,
           | this kind of thing. A slot is just a place to receive it,
           | it's a regular function or method with a compatible signature
           | for the kind of event it's meant to process. There are no
           | unexpected calls because you have to explicitly _connect_ a
           | signal to a slot, something like:
           | QObject::connect(&button, &QPushButton::clicked,
           | &mainWindowController,
           | &MainWindowController::onButtonClicked);
           | 
           | If no slot is connected, the signal just doesn't go anywhere.
           | 
           | Something that's special with Qt is that signals and slots
           | are declared in the class using custom syntax, e.g.
           | slots:             void onValueChanged(int value);
           | signals:             void valueChanged(int newValue);
           | 
           | Yes here "signals:" and "slots:" _look_ like the same kind of
           | keyword as  "public:" or "private:" in a class declaration,
           | even though internally they're #defined as "public:" and
           | "/**/" respectively.
           | 
           | Qt makes use of a tool called MOC - the Meta Object Compiler
           | - to generate code for signals and slots. It's not a pre-
           | processor but a code generator, which has to run before you
           | can actually compile the code. I think you could probably
           | implement a similar system of event subscriptions without
           | this additional code generation step.
           | 
           | See this page for details: https://woboq.com/blog/how-qt-
           | signals-slots-work.html
        
       | imachine1980_ wrote:
       | i recommend opengl for this instead of trying whit GUIs, you
       | could make easy small simulations and shot in your foot whit
       | rendering pipelines fast and easy, opengl resource are all over
       | the place, good luck.
        
       | smoyer wrote:
       | If you want to start from scratch, I'd recommend coding along
       | with Casey on https://handmadehero.org. He develops an entire
       | game starting with double-buffered pixel graphics and then moves
       | on to sprite s with movement functions. The should give you
       | plenty of background to be able to show a sound waveform (I'll
       | offer one warning though ... Being able to edit sound I'm a way
       | that still sounds good is much harder).
        
         | scott01 wrote:
         | Well, he pretty much inspired me to go into this direction,
         | such a great series! I particularly enjoy episodes on memory
         | management, though, admittedly, they're a bit over my current
         | skill level.
        
           | smoyer wrote:
           | A long time ago I wrote a CAD system that ran on DOS and
           | generated G-Codes for CNC machines. One of the features is
           | that it would show the tool's path and it cemented my love
           | for trigonometry. You seem to have found something you love
           | too - kudos for chasing it!
        
       | codr7 wrote:
       | I'm keeping an eye on Skia to try out some vector based UI ideas
       | I've been marinating for a while.
        
       | ozim wrote:
       | Start with Bresenham's line algorithm :) if you want to go with
       | "from scratch".
        
         | scott01 wrote:
         | Thanks for the reference, bookmarked! I think this might be too
         | much for current practice goals, as I'd like to practice
         | architecture that would enable me to create somewhat flexible
         | GUIs and then to attempt to optimize it for cache.
        
         | Shared404 wrote:
         | "First one must invent the universe".
         | 
         | That being said, I'm interested to see the range of answers to
         | OP's question, partially as I'm curious what HN considers "from
         | scratch" and partially because I've thought about doing the
         | same thing.
         | 
         | Edit: Same thing making-gui-from-scratch, not the audio stuff.
        
           | datavirtue wrote:
           | I started doing this in QuickBasic when I was 14 (trying to
           | copy Windows 3.1 LOL). That little project taught me more
           | about what I didn't know and it also revealed to me plainly,
           | my inexperience with abstractions. Before that I had not
           | really reflected on my own level of understanding about
           | abstractions.
        
       | jasonhong wrote:
       | I'd recommend two things. The first is Brad Myers' Software
       | Structures for User Interfaces course at Carnegie Mellon
       | University, which focuses on the guts of how graphical user
       | interfaces work.
       | 
       | https://www.cs.cmu.edu/~bam/uicourse/05631fall2021/
       | 
       | The second is Dan Olsen's book Developing User Interfaces, which
       | has all of the details of how GUIs work, from graphics to
       | interactor trees to events to dispatching. For some reason, it's
       | absurdly expensive on Amazon right now.
       | 
       | Both Dan Olsen and Brad Myers were early pioneers in GUIs and GUI
       | tools, so you'd be learning from the masters.
        
         | scott01 wrote:
         | That's just awesome info, thanks for this! Added to reading
         | list.
        
       | someweirdperson wrote:
       | First, you open a port to $DISPLAY...
       | 
       | xlib is quite a pleasure to use though, and it probably doesn't
       | qualify as a "framework" that you don't want to use.
        
       ___________________________________________________________________
       (page generated 2022-03-20 23:00 UTC)