What is the recommended use of makeDesktopItem? How to setup the icon correctly?

I am new to Nix and trying to learn the best practices. My first little project is to package TiddlyDesktop (as overlay only so far, but still), and I would like to create a desktop item for it (using KDE Plasma desktop).

My question: How to setup the icon correctly for the desktop-item?

Some background about what I learned so far:

  • There is makeDesktopItem nix function which creates a new derivation for a desktopitem and puts it in a directory known to XDG_DATA_DIRS environment variable
  • the icon file (tiddlydesktop.png) which I would like to use is part of the tiddlydesktop package, hence gets created by the new derivation I am writing myself now. For simplicity, let’s assume this icon sits at the following location: ${tiddlydesktop}/share/icons/tiddlydesktop.png

This seems to mean that there are two derivations which I somehow need to link to one another in order to let the one recognize the icon file of the other. These next steps came to my mind, however I don’t know how to do either of them:

  1. add ${tiddlydesktop}/share to XDG_DATA_DIRS environment in a consistent and nixos-compatible manner. This would enable that the icon in makeDesktopItem can be named “tiddlydesktop.png” simply, and would be found.
  2. use absolute pahts in makeDesktopItem, however this would require to compute the output path of tiddlydesktop. I know that I can access this path as the $out environment variable in the builder script, however here I cannot call makeDesktopItem (as it is a nix function and not a bash function). Or I can refer to it after creating the tiddlydesktop derivation, but then the desktop item needs to be installed separately and does not come together with tiddlydesktop, which seems akward. So both ways of linking do not seem to work… I bet there is another alternative

Does someone knows a trick to link the desktop file to the icon correctly?
Thanks a lot



Start by having your derivation for tiddlydesktop install its icon into one of ${tiddlydesktop}/share/pixmaps or ${tiddlydesktop}/share/icons. The Freedesktop icon theme spec says that these are equivalent, with the latter taking precedence over the former (and ~/.icons taking overriding both of these). However, what’s usually done is that share/pixmaps is used to hold random “unthemed” icons with no subdirectories, e.g. for programs that only ship a single image file. share/icons usually has subdirectories for icon themes rather than files at the top level, and there’s the hicolor theme which is the “generic” theme for icons to be installed into. Putting your icon file directly at ${tiddlydesktop}/share/icons should work though.

Then in your desktop file, I would recommend not using an absolute path, and just having:


By just giving a single name, this allows whatever icon theme the user chooses to override the program’s icon. If you give an absolute path, then that exact file is used, and no theming is possible.

Similarly, I also recommend using e.g. Exec=tiddlydesktop ... in the desktop file rather than an absolute path so that the user can provide their own wrapper around programs on their path if they want to.

There’s lots of good reading in both the icon theme spec I linked above and in the desktop file spec if you want the details about how all this works. If you want to see an example, I hooked up a desktop file for gkrellm somewhat recently.


Thank you very much for the detailed explanations. It happens that my system didn’t pick up the icon when I put it directly under ${tiddlydesktop}/share/icons/, however when put under ${tiddlydesktop}/share/icons/hicolor/128x128/apps (found by searching through nixpkgs for makeDesktopItem) it is found automagically and works nicely.

Still figuring out the details why this is the case. At least it works now and I know that it is best practice to do so.

1 Like

Hey, I’d like to try tiddlydesktop out, if you succeeded in packaging it maybe consider to send the expression to nixpkgs or in a NUR

1 Like

Excuses for my late reply,

I don’t feel comfortable yet with committing to nixpkgs, as my fixes are rather local fixes. I guess I will feel more confident over the next months.

Nevertheless I spend some effort making my fixes reusable by others. I implemented them as overlays and used best-practice coding to simplify later transitioning into nixpkgs.

Today I created a git repository for my personal nixos configuration, where also all my overlays are included.

Please take a look at GitHub - schlichtanders/nixos-personal: The nixos configuration for my personal computer, consisting of zsh, kde, conda, julia, vscode, tiddlywiki and others and for tiddlydesktop you need to install this overlay nixos-personal/overlay-tiddlydesktop.nix at 7ec6fe5e9151b3d0cc5be7861842311b5e9ec7cc · schlichtanders/nixos-personal · GitHub

I hope that helps

1 Like

I used the overlay and it works like a charm, thank you very much! I read it and acknowledge that it’s not the latest version but it’s more than enough for me to try tiddlydesktop out (and learn how to make desktop items) so thank you again

1 Like

Correct icon location is a bit messy in general. nixpkgs/icon-paths.patch at 4e6aa65c539ce5f1271c6d84a67d40bb2c94a32c · NixOS/nixpkgs · GitHub is a perfect example where the software isn’t talking into account the spec and nix isn’t creating the expected /usr/share directories so a quick patch makes it ~mostly work for nix things.

For the case “I have an icon where do I put it” the spec recommends ${XDG_DATA_DIR}/icons/hicolor/48x48/apps (or w/e sizing is correct for your icon, the above it was 128x128). The /usr/share/pixmaps location is listed as is without dynamic lookup specified. Applications will dynamically lookup the first and hard code the second (or incorrectly hardcode the both like the swayr example).

If your application is placing things in /pixmaps you’re crossing your fingers enough patches/config are in place to for /run/current-system/sw/share/pixmaps to be recognized. I believe you should prefer ${XDG_DATA_DIR}/icons/hicolor/<iconsize>/apps (where XDG_DATA_DIR is likely to include $out/share...)

1 Like