1

I maintain a library that provides the user-accessible locations for retrieving and storing configuration, cache and other data across multiple platforms. On Windows, this functionality is implemented using the KnownFolder API.

Recently I received a request to add support for the non-admin font directory on Windows that was added in 2018.

Surprisingly, this directory was not added to the KnownFolder API – is this intentional or was this overlooked?

soc
  • 27,983
  • 20
  • 111
  • 215
  • 3
    Typically, features are added only when somebody needs them. So I guess nobody has needed this yet. (Furthermore, KnownFolders are usually for things that are redirectable. Is the per-user font folder redirectable? Is installing a font just a simple matter of copying it into the per-user font folder, or is some installation API call required? If you have to call some API, then having a KnownFolder doesn't really get you anything.) – Raymond Chen Dec 30 '21 at 02:09
  • 2
    Because there is no such directory. Available fonts are listed in the registry, the non-admin ones are in HKCU instead of HKLM. – Hans Passant Dec 30 '21 at 02:32
  • @soc Nothing in the 2018 article you linked to indicates non-admin fonts are folder-driven. – Remy Lebeau Dec 30 '21 at 02:42
  • 2
    They end up in `%userprofile%\AppData\Local\Microsoft\Windows\Fonts`, and I'd rather not add yet-another mechanism to deal with Windows' antics. Windows is the cause of 90% of the reported issues with my library, despite a majority of users not using Windows. – soc Dec 30 '21 at 03:07
  • I'm not sure what more "reputable source" than Raymond Chen you expect to find in these matters... – Simon Mourier Jan 04 '22 at 12:01
  • Probably one that isn’t as tight-lipped. – user3840170 Jan 04 '22 at 13:22
  • 1
    @RaymondChen I wouldn't call using the existing API in favor of rolling yet-another mechanism a feature. – soc Jan 06 '22 at 12:47
  • 2
    It seems that `%userprofile%\AppData\Local\Microsoft\Windows\Fonts` is just a popular location for per-user fonts, but it is not authoritative. Not every file in that directory is a per-user font, and not all per-user fonts are in that directory. So the path to that directory doesn't really mean anything. The global `CSIDL_FONTS` exists because that is a virtual folder you can send people to in order to manage their fonts. The per-user fonts directory has no special powers. – Raymond Chen Jan 06 '22 at 23:56
  • Thank you for the info! I removed support for font dirs on Windows from my library (~25m downloads). Sad that supporting Microsoft products has always have to be such a hassle. :-( – soc Jan 18 '22 at 15:47

1 Answers1

2

Raymond Chen, who showed up in question comments and whom one might have expected to know the reason, seems either reluctant to share it or ignorant himself. But if you’re willing to accept some speculation, I can guess what he might be trying to say between the lines:

Because the user font directory is none of your business.

This works on a couple of levels:

  • It is none of your business because you are not supposed to install fonts on the user’s behalf. If you want to use a specific font in your application, you should bundle it with your application and use an API like AddFontResourceEx with the FR_PRIVATE flag to load it. If the user wants to install a font to their profile permanently, that is up to them and the operating system facilities already provided. Your services are not required.
  • It is none of your business because putting a font in this directory is neither sufficient nor necessary to install a font. To install a font, one has to take the full path to the font and put it in a value stored under a specific registry key, which is not exactly a documented API either (though it’s something of common knowledge that the key is HKCU\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Fonts). The location %USERPROFILE%\AppData\Local\Microsoft\Windows\Fonts is merely customary; enumerating that directory’s contents is not guaranteed to return all user-owned fonts, and neither is putting fonts inside sufficient to install them. The path alone would be useless to a cross-platform app, because it would need to perform platform-specific steps to install or enumerate user-owned fonts anyway. Which are not yours to manage in the first place.

In other words, it would not be a good API for whatever you might want to accomplish with it, and it is not even clear that they want you to be able to accomplish it, since doing so might create potential for abuse.

user3840170
  • 26,597
  • 4
  • 30
  • 62
  • After reflecting a bit on this, I'm inclined to treat `%userprofile%\AppData\Local\Microsoft\Windows\Fonts` as the user font directory on Windows and ignore the registry bits involved. The additional complexity just isn't worth supporting. Users can look up the dir with the library, then can add fonts to it on their own and will find them again. Good enough for me. – soc Jan 30 '22 at 20:23