Lagrange v1.9

This release introduces automatic updates on Windows and macOS, and adds a number of small improvements and requested features. Various glitchy parts of the user interface have been fixed.

Automatic updates

Self-updating is quite the hallmark of modern browsers, but I'm not keen on implementing that in Lagrange. You should be in control of when and if you want to upgrade. However, with releases coming out frequently, it is polite to make the process more streamlined.

Luckily many platforms have standard package managers that help you keep software up to date. Therefore, I'm focusing automatic updating on Windows and macOS, where it is not so customary to build software yourself or get it from repositories. Lagrange does have a Homebrew cask on macOS, and that's nice if you have installed Homebrew, but that shouldn't be a requirement for keeping the app updated.

This enabled taking the Sparkle and WinSparkle libraries into use. They provide an unobtrusive way for an app to find the latest updates and download them automatically.

User interface

I'm continually evolving and refining the app UI. This release has no radical changes, but it attempts to tie up various loose ends from previous versions.


The Identity toolbar button has been moved to the right side of the URL field to make room for a sidebar toggle button. In fact, this is now the same layout that I've been using in the mobile (tablet) version. On the desktop it accommodates mouse-only use.

Another shortcoming has been an easy way to get out of split view mode. While you can always use ☰ > Split view... > Merge Tabs (renamed to "Unsplit" in v1.9), that is quite a lot more work than a single click on "Open Link to the Side". Therefore, I've added an ⨯ button that appears in the toolbar in split view mode, letting you quickly unsplit the view while keeping all tabs open.

Sidebars, menus, and text input

Page layout and theming

Footer action buttons were introduced in v1.5. The layout of these buttons is a bit special because it requires anchoring normal UI controls to the scrollable and scalable page content, and in previous releases it has never worked quite right. Now in v1.9, I've revised the code that does the button placement and re-checked that page content centering takes them correctly into account.

Perhaps the most notable theme change is the switching of font weights of heading levels 2 and 3, with the intent of making each level more distinct from each other. Previously, it may not have been immediately obvious if one were looking at level 1 or 2. Now the difference in font weights should make it clearer.

ANSI styling

When the ANSI foreground color has been set, it will now be altered to suit colored theme backgrounds (e.g., Sepia) to avoid color clashes. The foreground colors specified in ANSI control sequences are only used as-is on black or dark backgrounds. On light and colored backgrounds they are darkened or muted accordingly.

This bring us to ANSI background colors. The SGR control sequences for setting the background color are now supported, although they are disabled by default in Preferences. This enables one to see/use much more powerful colored ASCII/Unicode art in preformatted blocks, if one is so inclined.

As things stand, a client can handle these however it wants or let a terminal emulator take care of it. Adding support for this in Lagrange levels the playing field a bit in terms of what content TUI and GUI clients are able to display.

I acknowledge that some people are not thrilled about this kind of features, which is why it's opt-in. Should the specification be updated to prohibit or limit the use of control characters such as ESC, I'm happy to change things accordingly.

Other changes

Continuing the saga of subscription glitches, I noticed that if a feed has multiple entries with the same URL, the entry always come out as unread because the subscription manager thought that the additional entries were updates to the original one. Now any duplicates are ignored; the entry URL is considered a unique identifier. If the date or title of an entry changes, it will still be marked as unread.

When navigating backward and forward in history, input query responses are now skipped, i.e., no input query prompts will reappear. This makes input query responses similar to redirections in that the navigation history will ignore them. It might be nice to add a "Repeat Query" feature that would request again the URL that resulted in a 1x status code, so one could manually redo a prompt, but I don't know if that's very useful.

An internal change: the resource file (resources.lgr) is now a ZIP archive instead of a custom binary blob. This makes it inspectable using normal ZIP utilities, and allows it to do double-duty as a fontpack. The file now contains the application version number to avoid problems trying to load obsolete resource files.

Next steps 🎄🎁

This is the last big release of the year. I plan to wind things down for the holidays, for a nice bit of rest. I'll likely continue the bugfix/minor feature focus for a while before tackling multiple windows and system fonts.

📅 2021-11-27

🏷 Lagrange

CC-BY-SA 4.0

The original Gemtext version of this page can be accessed with a Gemini client: gemini://