QIcon::fromTheme(): Always consult "hicolor" theme last

The Freedesktop Icon Theme Specification [1] describes that,
if a theme does not specify anything for its 'Inherits' key,
"implementations are required to add the 'hicolor' theme to
the inheritance tree. An implementation may optionally add
other default themes in between the last specified theme and
the hicolor theme."

And later, when describing the lookup algorithm, that "The
lookup is done first in the current theme, and then recursively
in each of the current theme's parents, and finally in the
default theme called 'hicolor' (implementations may add more
default themes before 'hicolor', but 'hicolor' must be last)".

But it doesn't explicitly describe the behavior when a theme
does specify a list of inherited themes via the 'Inherits' key,
and this list explicitly includes 'hicolor'.

In that case, our custom fallback theme, which we inject after
the theme's explicit parents, will be prioritized after 'hicolor'.

As it's likely that the theme author added 'hicolor' to their
parent list to ensure that 'hicolor' is at some point consulted,
but didn't intent it to be priorized, and that the spec puts focus
on 'hicolor' being last, it seems reasonable that we can move the
'hicolor' theme to the end of the fallback list, and as a result
always prioritize fallbackThemeName() over 'hicolor'.

[ChangeLog][QtGui][QIcon] The 'hicolor' theme will now always be
prioritized last when looking up fallback themes, even if
explicitly declared as a theme parent in a theme.

[1] https://specifications.freedesktop.org/icon-theme-spec/icon-theme-spec-latest.html

Pick-to: 6.6
Change-Id: I76538e4e7e9e395f9e5a38e704c60fb6b9688885
Reviewed-by: Axel Spoerl <axel.spoerl@qt.io>
Reviewed-by: Friedemann Kleint <Friedemann.Kleint@qt.io>
This commit is contained in:
Tor Arne Vestbø 2023-05-11 16:06:33 +02:00
parent addde7843f
commit e603661c48

View File

@ -408,9 +408,9 @@ QStringList QIconTheme::parents() const
if (!fallback.isEmpty())
result.append(fallback);
// Ensure that all themes fall back to hicolor
if (!result.contains("hicolor"_L1))
result.append("hicolor"_L1);
// Ensure that all themes fall back to hicolor as the last theme
result.removeAll("hicolor"_L1);
result.append("hicolor"_L1);
return result;
}