Preload or cache user interface icons

Users and developers helping users with technical Pale Moon issues (Windows and other non-Linux O.S.). Please direct questions about the Linux version to the appropriate Linux board.

Moderators: trava90, satrow

Forum rules
This board is for technical/usage questions and troubleshooting for the Pale Moon browser only. The main focus here is on Pale Moon on Windows. Please direct your questions for Linux, Android and Mac to the dedicated boards.
Technical issues and questions not related to the Pale Moon browser should be posted in "technical chat"
Please keep off-topic and general discussion out of this board, thank you!
User avatar
ladnalo
Moongazer
Moongazer
Posts: 7
Joined: 2019-01-05, 11:37
Location: Hungary

Preload or cache user interface icons

Unread post by ladnalo » 2019-01-05, 12:31

I always notice that icons in context menus of Pale Moon appear with some delay when they're first shown. Then get cached (I suppose) and appear instantly.

Below you can see the 3 frames of a 30 FPS screen recording showing how a right click context menu is being displayed on palemoon.org after a cold start. The webpage has already been loaded so there's no way it could have slowed down icon loading.
recorded.jpg
Same is true for the upper File | Edit | View | History | Bookmarks (most noticeable) | Tools menus.

I think it would just be a matter of some extra memory to preload those icons at startup and get rid of the annoyance. I would like to ask if there is a trick about this or hidden option in about:config. Tried to search for icon, icons, etc. among the configuration options but found nothing relevant. Although I made the above recording and extracted samples on Linux, same is experienced on Windows as well so I wouldn't think this is platform-specific.

vannilla
Lunatic
Lunatic
Posts: 496
Joined: 2018-05-05, 13:29

Re: Preload or cache user interface icons

Unread post by vannilla » 2019-01-05, 13:23

Those menus are built with XUL, so it's likely to be just the usual asynchronous image loading like it's in HTML.
If that's the case it's intended behaviour, but there's still the question as to why the icons aren't loaded until the menu is opened.

User avatar
ladnalo
Moongazer
Moongazer
Posts: 7
Joined: 2019-01-05, 11:37
Location: Hungary

Re: Preload or cache user interface icons

Unread post by ladnalo » 2019-01-05, 13:50

I'm pretty sure this is an issue related to icon caching. I checked Pale Moon using strace and found out that on first click it accesses the icon files.

Code: Select all

stat("/usr/share/icons/gnome", {st_mode=S_IFDIR|0755, st_size=4096, ...}) = 0
stat("/usr/local/share/icons/gnome", 0x7ffca817dc20) = -1 ENOENT (No such file or directory)
stat("/home/ladnalo/.local/share/icons/gnome", 0x7ffca817dc20) = -1 ENOENT (No such file or directory)
stat("/home/ladnalo/.icons/gnome", 0x7ffca817dc20) = -1 ENOENT (No such file or directory)
stat("/home/ladnalo/.icons/Adwaita", 0x7ffca817dc20) = -1 ENOENT (No such file or directory)
stat("/home/ladnalo/.local/share/icons/Adwaita", 0x7ffca817dc20) = -1 ENOENT (No such file or directory)
stat("/usr/local/share/icons/Adwaita", 0x7ffca817dc20) = -1 ENOENT (No such file or directory)
stat("/usr/share/icons/Adwaita", {st_mode=S_IFDIR|0755, st_size=4096, ...}) = 0
stat("/home/ladnalo/.icons/hicolor", 0x7ffca817dc20) = -1 ENOENT (No such file or directory)
stat("/home/ladnalo/.local/share/icons/hicolor", {st_mode=S_IFDIR|0700, st_size=4096, ...}) = 0
stat("/usr/local/share/icons/hicolor", 0x7ffca817dc20) = -1 ENOENT (No such file or directory)
stat("/usr/share/icons/hicolor", {st_mode=S_IFDIR|0755, st_size=4096, ...}) = 0
stat("/home/ladnalo/.icons", {st_mode=S_IFDIR|0755, st_size=4096, ...}) = 0
stat("/home/ladnalo/.local/share/icons", {st_mode=S_IFDIR|0700, st_size=4096, ...}) = 0
stat("/usr/local/share/icons", 0x7ffca817dc20) = -1 ENOENT (No such file or directory)
stat("/usr/share/icons", {st_mode=S_IFDIR|0755, st_size=4096, ...}) = 0
lstat("/usr/share/icons/Adwaita/16x16/actions/document-save-as.png", {st_mode=S_IFREG|0644, st_size=689, ...}) = 0
open("/usr/share/icons/Adwaita/16x16/actions/document-save-as.png", O_RDONLY|O_NOATIME) = -1 EPERM (Operation not permitted)
open("/usr/share/icons/Adwaita/16x16/actions/document-save-as.png", O_RDONLY) = 52
open("/usr/share/icons/Adwaita/16x16/actions/document-save-as.png", O_RDONLY) = 52
lstat("/usr/share/icons/Adwaita/16x16/actions/edit-copy.png", {st_mode=S_IFREG|0644, st_size=549, ...}) = 0
open("/usr/share/icons/Adwaita/16x16/actions/edit-copy.png", O_RDONLY|O_NOATIME) = -1 EPERM (Operation not permitted)
open("/usr/share/icons/Adwaita/16x16/actions/edit-copy.png", O_RDONLY) = 52
open("/usr/share/icons/Adwaita/16x16/actions/edit-copy.png", O_RDONLY) = 52
lstat("/usr/share/icons/Adwaita/16x16/actions/media-playback-start.png", {st_mode=S_IFREG|0644, st_size=549, ...}) = 0
open("/usr/share/icons/Adwaita/16x16/actions/media-playback-start.png", O_RDONLY|O_NOATIME) = -1 EPERM (Operation not permitted)
open("/usr/share/icons/Adwaita/16x16/actions/media-playback-start.png", O_RDONLY) = 52
open("/usr/share/icons/Adwaita/16x16/actions/media-playback-start.png", O_RDONLY) = 52
lstat("/usr/share/icons/Adwaita/16x16/actions/media-playback-pause.png", {st_mode=S_IFREG|0644, st_size=398, ...}) = 0
open("/usr/share/icons/Adwaita/16x16/actions/media-playback-pause.png", O_RDONLY|O_NOATIME) = -1 EPERM (Operation not permitted)
open("/usr/share/icons/Adwaita/16x16/actions/media-playback-pause.png", O_RDONLY) = 52
open("/usr/share/icons/Adwaita/16x16/actions/media-playback-pause.png", O_RDONLY) = 52
lstat("/usr/share/icons/gnome/16x16/actions/gtk-go-back-ltr.png", {st_mode=S_IFLNK|0777, st_size=15, ...}) = 0
stat("/usr/share/icons/gnome/16x16/actions/gtk-go-back-ltr.png", {st_mode=S_IFREG|0644, st_size=677, ...}) = 0
readlink("/usr/share/icons/gnome/16x16/actions/gtk-go-back-ltr.png", "go-previous.png", 256) = 15
open("/usr/share/icons/gnome/16x16/actions/gtk-go-back-ltr.png", O_RDONLY|O_NOATIME) = -1 EPERM (Operation not permitted)
open("/usr/share/icons/gnome/16x16/actions/gtk-go-back-ltr.png", O_RDONLY) = 52
open("/usr/share/icons/gnome/16x16/actions/gtk-go-back-ltr.png", O_RDONLY) = 52
lstat("/usr/share/icons/gnome/16x16/actions/gtk-go-forward-ltr.png", {st_mode=S_IFLNK|0777, st_size=11, ...}) = 0
stat("/usr/share/icons/gnome/16x16/actions/gtk-go-forward-ltr.png", {st_mode=S_IFREG|0644, st_size=640, ...}) = 0
readlink("/usr/share/icons/gnome/16x16/actions/gtk-go-forward-ltr.png", "go-next.png", 256) = 11
open("/usr/share/icons/gnome/16x16/actions/gtk-go-forward-ltr.png", O_RDONLY|O_NOATIME) = -1 EPERM (Operation not permitted)
open("/usr/share/icons/gnome/16x16/actions/gtk-go-forward-ltr.png", O_RDONLY) = 52
open("/usr/share/icons/gnome/16x16/actions/gtk-go-forward-ltr.png", O_RDONLY) = 52
lstat("/usr/share/icons/Adwaita/16x16/actions/edit-undo.png", {st_mode=S_IFREG|0644, st_size=636, ...}) = 0
open("/usr/share/icons/Adwaita/16x16/actions/edit-undo.png", O_RDONLY|O_NOATIME) = -1 EPERM (Operation not permitted)
open("/usr/share/icons/Adwaita/16x16/actions/edit-undo.png", O_RDONLY) = 52
open("/usr/share/icons/Adwaita/16x16/actions/edit-undo.png", O_RDONLY) = 52
lstat("/usr/share/icons/Adwaita/16x16/actions/edit-cut.png", {st_mode=S_IFREG|0644, st_size=959, ...}) = 0
open("/usr/share/icons/Adwaita/16x16/actions/edit-cut.png", O_RDONLY|O_NOATIME) = -1 EPERM (Operation not permitted)
open("/usr/share/icons/Adwaita/16x16/actions/edit-cut.png", O_RDONLY) = 52
open("/usr/share/icons/Adwaita/16x16/actions/edit-cut.png", O_RDONLY) = 52
lstat("/usr/share/icons/Adwaita/16x16/actions/edit-paste.png", {st_mode=S_IFREG|0644, st_size=722, ...}) = 0
open("/usr/share/icons/Adwaita/16x16/actions/edit-paste.png", O_RDONLY|O_NOATIME) = -1 EPERM (Operation not permitted)
open("/usr/share/icons/Adwaita/16x16/actions/edit-paste.png", O_RDONLY) = 52
open("/usr/share/icons/Adwaita/16x16/actions/edit-paste.png", O_RDONLY) = 52
lstat("/usr/share/icons/Adwaita/16x16/actions/edit-delete.png", {st_mode=S_IFREG|0644, st_size=1031, ...}) = 0
open("/usr/share/icons/Adwaita/16x16/actions/edit-delete.png", O_RDONLY|O_NOATIME) = -1 EPERM (Operation not permitted)
open("/usr/share/icons/Adwaita/16x16/actions/edit-delete.png", O_RDONLY) = 52
open("/usr/share/icons/Adwaita/16x16/actions/edit-delete.png", O_RDONLY) = 52
lstat("/usr/share/icons/Adwaita/16x16/actions/edit-select-all.png", {st_mode=S_IFREG|0644, st_size=822, ...}) = 0
open("/usr/share/icons/Adwaita/16x16/actions/edit-select-all.png", O_RDONLY|O_NOATIME) = -1 EPERM (Operation not permitted)
open("/usr/share/icons/Adwaita/16x16/actions/edit-select-all.png", O_RDONLY) = 52
open("/usr/share/icons/Adwaita/16x16/actions/edit-select-all.png", O_RDONLY) = 52
lstat("/usr/share/icons/Adwaita/16x16/status/dialog-information.png", {st_mode=S_IFREG|0644, st_size=813, ...}) = 0
open("/usr/share/icons/Adwaita/16x16/status/dialog-information.png", O_RDONLY|O_NOATIME) = -1 EPERM (Operation not permitted)
open("/usr/share/icons/Adwaita/16x16/status/dialog-information.png", O_RDONLY) = 52
open("/usr/share/icons/Adwaita/16x16/status/dialog-information.png", O_RDONLY) = 52
lstat("/usr/share/icons/gnome/16x16/actions/gtk-go-forward-ltr.png", {st_mode=S_IFLNK|0777, st_size=11, ...}) = 0
stat("/usr/share/icons/gnome/16x16/actions/gtk-go-forward-ltr.png", {st_mode=S_IFREG|0644, st_size=640, ...}) = 0
readlink("/usr/share/icons/gnome/16x16/actions/gtk-go-forward-ltr.png", "go-next.png", 256) = 11
open("/usr/share/icons/gnome/16x16/actions/gtk-go-forward-ltr.png", O_RDONLY|O_NOATIME) = -1 EPERM (Operation not permitted)
open("/usr/share/icons/gnome/16x16/actions/gtk-go-forward-ltr.png", O_RDONLY) = 52
open("/usr/share/icons/gnome/16x16/actions/gtk-go-forward-ltr.png", O_RDONLY) = 52
lstat("/usr/share/icons/Adwaita/16x16/actions/edit-delete.png", {st_mode=S_IFREG|0644, st_size=1031, ...}) = 0
open("/usr/share/icons/Adwaita/16x16/actions/edit-delete.png", O_RDONLY|O_NOATIME) = -1 EPERM (Operation not permitted)
open("/usr/share/icons/Adwaita/16x16/actions/edit-delete.png", O_RDONLY) = 52
open("/usr/share/icons/Adwaita/16x16/actions/edit-delete.png", O_RDONLY) = 52
lstat("/usr/share/icons/Adwaita/16x16/actions/edit-undo.png", {st_mode=S_IFREG|0644, st_size=636, ...}) = 0
open("/usr/share/icons/Adwaita/16x16/actions/edit-undo.png", O_RDONLY|O_NOATIME) = -1 EPERM (Operation not permitted)
open("/usr/share/icons/Adwaita/16x16/actions/edit-undo.png", O_RDONLY) = 52
open("/usr/share/icons/Adwaita/16x16/actions/edit-undo.png", O_RDONLY) = 52
lstat("/usr/share/icons/Adwaita/16x16/actions/process-stop.png", {st_mode=S_IFREG|0644, st_size=673, ...}) = 0
open("/usr/share/icons/Adwaita/16x16/actions/process-stop.png", O_RDONLY|O_NOATIME) = -1 EPERM (Operation not permitted)
open("/usr/share/icons/Adwaita/16x16/actions/process-stop.png", O_RDONLY) = 52
open("/usr/share/icons/Adwaita/16x16/actions/process-stop.png", O_RDONLY) = 52
But on a second click, no files are opened and the icons are displayed instantly, along with the widget of the context menu. Pale Moon also loads tons of icons at startup. I think the icons of the context menu (as well as of the upper menu) should be loaded on startup, which would make them appear without delay.

User avatar
Moonchild
Pale Moon guru
Pale Moon guru
Posts: 23697
Joined: 2011-08-28, 17:27
Location: 58°2'16"N 14°58'31"E
Contact:

Re: Preload or cache user interface icons

Unread post by Moonchild » 2019-01-05, 13:59

Menus are built dynamically from XUL for display. Icons in those menus are often fetched from many different places, if present (including extensions and specific shared locations in the operating system in the case of Linux). Once they have been fetched and the menu is built, it will be cached. This is normal operation and an essential mechanism behind XUL user interfaces that do not load any resources until they are actually being used.

The context menu is a very complex menu that does take some time (in computer terms) to properly populate, especially if you have extensions that add items to it or that add additional icons to menus that normally don't have any.
Considering you're looking at a latency of 2 frames @ 30 fps, ~70 ms, to grab icons, decode them, resize them (if necessary, often the case on Linux where these icons are larger-sized PNGs), slot them in layout and render them, I don't see what there is to complain about that asks for preloading/prerendering of these menus, negating some of the resource advantages XUL inherently has (not to mention making things more complex and slowing browser startup).
City of Heroes public server: https://www.moonshard.org/ -- Vote for it: Image

"If you want to build a better world for yourself, you have to be willing to build one for everybody." -- Coyote Osborne
"I'm afraid you have me mistaken for someone who can be shamed by a child." -- Quillspawn

User avatar
ladnalo
Moongazer
Moongazer
Posts: 7
Joined: 2019-01-05, 11:37
Location: Hungary

Re: Preload or cache user interface icons

Unread post by ladnalo » 2019-01-05, 14:56

That ~70 ms might be a short period of time but it can vary according to I/O load. I'm on a 4th generation Haswell with SSD that causes it to be short. On a computer with an HDD the delay may be longer. The problem is not with the length of the delay. The problem is there is such a delay and the fact it's noticeable by the user. I'm also personally annoyed by it as it gives an unprofessional, sluggish experience.

In my humble opinion storing icons as separate heavily compressed PNG files is the single worst idea ever in the age of cheap storage. ICO, BMP files or uncompressed PNG files would be enough. Even compressed icon maps (pixmaps stored in a single image) would be better. However, this is not the resort of Pale Moon development, icons are loaded according to the GNOME/GTK theme.

As for the processing part, they definitely don't need to be resized. As you can see in the strace log, they're taken from folders according to their proper dimensions (e.g. 16x16). Then they're displayed without being resized. The only icon that may be resized is the icon of uBlock Origin, however disabling that extension won't help. Other icons (View Page Info, Save Page As, etc.) still load with a delay in that case.

As for the rendering part, they're rendered pretty quick as soon as they have been cached. There's no noticeable delay at all if icons are already in the cache. The only thing that causes the delay is the cache miss of the icons. Which could be solved by loading them at startup time. As we also load the 16x16 view-refresh.png icon without displaying it. That's why the Refresh icon is already there on the first frame.

Isn't there an option which would pre-load all basic icons in charge of startup time? I would rather have a Pale Moon that starts a few tenths of a second later than have every menu and panel widget load their icons with a delay at first click. Is there an option for XUL to pre-load these icons at startup time? Or any other hack to prefs.js that would make Pale Moon load them so it will not have to do again when displaying context menus.

yami_
Lunatic
Lunatic
Posts: 474
Joined: 2018-04-26, 11:05

Re: Preload or cache user interface icons

Unread post by yami_ » 2019-01-05, 16:06

Is not the view-refresh.png icon is also a part of the Navigation Bar? Also AFAIK Pale Moon treats those icons like any other image that needs to be loaded so making a special case for them would not be easy.
cat came back from Berkeley waving flags -- rob pike

User avatar
ladnalo
Moongazer
Moongazer
Posts: 7
Joined: 2019-01-05, 11:37
Location: Hungary

Re: Preload or cache user interface icons

Unread post by ladnalo » 2019-01-05, 16:33

yami_ wrote:Is not the view-refresh.png icon is also a part of the Navigation Bar? Also AFAIK Pale Moon treats those icons like any other image that needs to be loaded so making a special case for them would not be easy.
Yes it is. However, on the navigation bar we show the 24x24 icon. The 16x16 icon is loaded as well that is only shown in the context menu. So we do load icons at startup that we don't show on a freshly started Pale Moon. It would be great if we could load all icons that could be shown on the core user interface (upper menu, context menus).

yami_
Lunatic
Lunatic
Posts: 474
Joined: 2018-04-26, 11:05

Re: Preload or cache user interface icons

Unread post by yami_ » 2019-01-05, 17:06

It may be possible that the browser loads all available icon sizes when an icon of particular size is requested. For example you can request 24 px reload icon using moz-icon://stock/gtk-refresh?size=toolbar and 16 px reload icon using moz-icon://stock/gtk-refresh?size=menu. Only the size parameter changes to maybe both icon sizes are cached? IIRC the 16 px version will be used in navigation bar if you enable the "Use Small Icons" customize option.
cat came back from Berkeley waving flags -- rob pike

User avatar
Moonchild
Pale Moon guru
Pale Moon guru
Posts: 23697
Joined: 2011-08-28, 17:27
Location: 58°2'16"N 14°58'31"E
Contact:

Re: Preload or cache user interface icons

Unread post by Moonchild » 2019-01-05, 17:10

FTR: I've never seen any noticeable delay myself on many different systems with Pale Moon installed, including older systems with platter drives and limited RAM to work with.

But, if you think there is room for improvement then by all means, feel free to do some research into how things are loaded now and how things could be improved without causing serious detrimental effects on initial load speed of the application. Do keep in mind that the XUL interface solution is cross-platform - they are not binary-native UI elements.
City of Heroes public server: https://www.moonshard.org/ -- Vote for it: Image

"If you want to build a better world for yourself, you have to be willing to build one for everybody." -- Coyote Osborne
"I'm afraid you have me mistaken for someone who can be shamed by a child." -- Quillspawn

Post Reply