[Development] Dark mode, palettes, styles etc.

Shawn Rutledge Shawn.Rutledge at qt.io
Fri Jul 6 10:50:44 CEST 2018

> On 4 Jul 2018, at 16:19, Morten Sørvig <Morten.Sorvig at qt.io> wrote:
> Hi all,
> macOS 10.14 is now in (public) beta and we've had some time to test Qt on it.
> ...
> Dark appearance: In theory, applications should pick up the dark appearance via
> the style and palette. In practice, they may not due to incomplete/buggy QPalette
> and QMacStyle implementations, or hardcoded colors in Qt or the application.
> The current state of the patches for dev/5.12 is that custom-styled applications
> can work well in dark mode, for example Qt Creator with a dark theme.
> The plan is to disable dark mode support by default in Qt, at least until
> QMacStyle is fixed. This means that applications will start up using standard
> Aqua theme/colors, also when the desktop is configured for dark mode.
> The application has the final call here, and can opt in or out by setting the
> NSRequiresAquaSystemAppearance key in the Info.plist file. For example:
>  <key>NSRequiresAquaSystemAppearance</key>
>  <false/>
> will indicate that the app _does_ support dark mode, and Qt will get out
> of the way and not apply its disable. Setting it to true will insulate the
> app against any changes in the Qt default.

I would like to see this feature as a cross-platform feature rather than mac-specific.

I missed that news about Apple until now, but I had the idea a few years ago anyway that there should be an easy global switch (always within reach, not having to paw through system settings) to toggle quickly between light and dark themes.  There was the first time I started up my laptop on a plane while other passengers were trying to sleep, and got some dirty looks because I didn’t have much control over the brightness (the laptop’s backlight level couldn’t be reduced enough, and it took some time to open up the system settings and switch themes, and then I think I had to log out and back in again too.  Creator didn’t have themes at all back then.)  And there was a consultancy customer a few years ago who planned to have themes with different brightness levels in an embedded application, but AFAIK they still haven’t gotten around to it, maybe because we didn’t make it particularly easy in Qt Quick.  And actually I tend to switch themes at least seasonally: if there’s a lot of sun and I’m trying to hack while riding the metro, I can’t see well enough if the theme is too dark, but otherwise I like using a dark theme in darker conditions.  So it’s been annoying me for years that most applications can’t easily switch (they tend to make up for lack of system-wide settings by having their own instead), and some desktop environments have inconvenient controls, and/or the theme changes don’t necessarily propagate to all apps at once.

But now that Apple is finally doing something, I think the copycats are inevitable, so I fully expect to see news that an identical or better feature is coming soon to KDE and/or Gnome any day now.  For now there’s just “redshift", it seems.  But IMO having a lot of white space that has gone dingy in the dark is not as nice as having a theme that looks good without having so much white in it.  And so far Apple didn’t put the switch in the menubar, but I suppose that’s probably inevitable too: a utility will probably show up in the app store, if there’s an API to make it possible.

Anyway, to the extent that widgets and controls are drawn with QPalette colors, switching the palette globally ought to be easy; and we have QEvent::PaletteChange, so applications have already been able to respond quickly to system-wide palette changes for ages, right?  But there’s the trend of using image-based styles more, which contributes to the annoyance that you don’t actually have system-wide control over colors and styles.  So it just becomes more work for widgets, controls and applications to have both sets of images, in addition to having different resolutions for high-dpi support, whenever they are built that way.

The default Fusion widget style still has hard-coded colors, by the way.  I wanted to fix it, but ran into resistance about using QSettings for that, and yet no other solution has been forthcoming either.

One of the contributing reasons that _we_ use images more is probably because of the perception that a GPU is best used as a texture-flinging device, because it's not so good at drawing vector graphics.  (So much so that Shapes are a really recent addition, while Canvas and QtSVG continue to use QPainter to render to a texture.)  That’s always been unfortunate from my perspective… _our_ use of today’s gaming-oriented GPUs still hasn't advanced the state of the art in 2D since the 1980’s, unless you use vendor-specific stuff like NV_path_rendering, or if you draw aliased graphics and then apply (expensive) global antialiasing techniques like MSAA.  (But I continue to believe it’s possible to do better than that.  Especially now that we have Vulkan.)  You can write smarter shaders, but then you need a diversity of shaders, and that breaks batching in the scene graph.  That’s just wrong IMO.  Fixing that somehow would enable us to go back to having styles that use vector graphics and therefore can respond to changes in the palette.  But another way is to use a fragment shader to switch specific colors on the fly.  I did this with my PDF viewer, to make it possible to read “white papers” in the dark: it inverts black and white, but leaves color images intact.  It could at least be a workaround for applications that use too many images.

Another easy thing I think we could add to QPalette is the set of (16?) most-common colors.  That way, when an application really wants something to be blue, it could use QPalette:Blue, and the theme would be able to control the brightness and the exact shade of blue.  (The color of blue that is default on a white xterm is nowhere near the one you want if your terminal is black.)  So you could easily "solarize" your whole desktop, if that’s your thing, even while applications retain control over the general hues.  Then terminal applications, editors that have syntax highlighting, and such things would be able to use those colors.  The settings to define each of those would be global, and the need for e.g. Konsole and Creator to have their own independent sets of themes for text highlighting would go away.  (Although, Creator would still need settings to map highlighting classes to QPalette colors: e.g. comments are green and keywords are blue, or whatever.)  So they too would respond to global theme changes.

There is talk of rearchitecting QStyle in Qt 6.  IMO this is a very important feature we should take into account.

More information about the Development mailing list