Show icon for creator code on OSX - cocoa

How could I display a custom icon depending on a files creator code/type code. For example I have an application that opens files with the creator code 'TSTx', how would I set the icon for that creator code?
I'm guessing that's how apps like Cyberduck show a progress icon when a file is being downloaded without changing the file extension and that's the behaviour I'm trying to replicate.
Thanks,
J

You shouldn’t rely on creator and type codes for this. Not all files have them assigned. In fact, not even all apps have unique creator codes, so that’s guaranteed to break.
If they files do exist in the file system and have proper path extensions, -[NSWorkspace iconForFile:] should do the trick. (I think that will also work with custom icons.) If the file doesn’t exist in the file system (e. g. because it’s stored in a database), -[NSWorkspace iconForFileType:] is the way to go. You can supply it with a path extension or, if you insist, with an HFS type code (which you must wrap in a string with the NSFileTypeForHFSTypeCode function).
To set a custom icon to be used by the Finder, you don’t need type and creator codes. Use -[NSWorkspace setIcon:forFile:options:].

Related

Is it possible to assign a custom icon to a custom file extension?

I am trying to make my own coding language and I want to have a custom file extension for it. I need to have a custom icon, and a way to check for text editors (vscode etc.). So it can run on any computer with the custom icon and and a way to check for a text editor that it will automatically open when you open the file, included. I am willing to use any coding languages as long as you help me out with it and dont just tell me what to do.
I have tried using the whole HKEY stuff and since I am using a custom file extension that is not associated with windows it doesn't show up in HKEY_CLASSES_ROOT like file extensions that are associated with windows do.
Let's say you want to have an icon associated with file extension .xyz. And your icon is resource ID #0 in Resources.dll.
These registry keys become relevant:
[HKEY_CLASSES_ROOT\.xyz]
#="XYZ"
[HKEY_CLASSES_ROOT\XYZ\DefaultIcon]
#="C:\\Path\\To\\File\\With\\Resources\\Resources.dll, 0"

Qt on Mac: how to get a file dialog that allows to write the desired file path manually?

On Mac OS-X, usually directory dialogues are shown without the possibility to enter the path with the keyboard. This seems to be the default behaviour when I build a Qt application on OS-X.
How can I specify that I do want the path to be manually entered?
I'd recommend using the native dialog obtained thought he QFileDialog's static methods. With the new sandboxing requirements from apple, you must use the standard dialogs for your application to get access to the file system. Its interesting actually, the actual dialog given to the user in a sandboxed application is though something called Powerbox. You can read more about it here in the NSPanel documentation.
Also as elmigranto pointed out in all the file dialogs on the Mac, you can hit command + shift + g to enter the path to navigate to.
Note: In the newer Qt versions the documentation implies that they corrected this such that using the static functions on QFileDialog gets you a native dialog that also goes through PowerBox. I haven't tried it myself though and the bug on the issue remains open against Qt 5.5.0 and 5.6.0. Overriding QFileDialog doesn't get you a native dialog however. If you need a customized dialog, going the NSSavePanel route is the way to go.
If you use the static functions of QFileDialog, such as getExistingDirectory() and getOpenFileName() you get native OS X file dialogs. However, if you create your own QFileDialog without using the static functions you should get a Qt file dialog for which you can specify what the user must select in the dialog by calling setFileMode(). I think the Qt file dialog will let the user manually change the path in the dialog.
Of course if you only want to have the user manually type in a directory path you could also use a simple QInputDialog.

How do I assign an icon to a custom file type?

Is there any way to do so in C or C++ (I know that it can be done in C#, so if you know how to, it'd also help!)?
What I want is a way to, automatically and through my own application, associate a custom file extension with a custom icon. For example, something that would make all current and subsequent .foo files have an image of their own, instead of the bland white paper sheet default. Just like what Java does to .jar files and Dev-C++ to .c and .cpp upon them being installed.
Through my researches I've found a lot of related information about a thing called Shell or something. I wound up myself at this page, and as viable what it says may seem, I have no idea on how to implement it at all, nor grasp what exactly it is about. Sorry if I sound noobish!
OS is Windows.
First you need to know how to modify registry in c++, here is a post that explains that:
Registry and c++
In the link you provided you have the keys that you need to update
HKEY_CLASSES_ROOT/[yourextension]
the call to SHChangeNotify is only needed to tell explorer to refresh once you modified the icon.

How to set the kMDItemKind of a saved document on Mac OS X?

I have a legacy app (minimally ported from Mac System 7 to Carbon to Cocoa) where users are reporting that the kMDItemKind metadata, as reported my mdls, of text files saved by the app seem to be set to "Microsoft Excel 97-2004 workbook". The legacy file creator and type should have been set to 'cBaS' and 'TEXT' (as was registered with Apple in ye ole ancient days), and the legacy file extension is ".bas".
What sets the kMDItemKind metadata of saved files under Mac OS X?
How do I make sure that the kMDItemKind is set correctly when saving these text files, so that my app will open them?
You can't directly set the kMDItemKind of a file. It is derived from other metadata. The file type code 'TEXT' is quite generic. The creator code is ignored these days. The file extension is probably what the system is relying on.
Unfortunately, in your case, you have multiple apps which handle .bas files. Which of those the system picks is somewhat arbitrary and subject to change. Launch Services is assigning the kind based on which would actually be used and how that app defines the document type or UTI that's matching the file extension.
Normally, you should leave the association of files with specific applications to the user. If they want to change it, they can do so with Always Open With accessible in the Finder's File menu or context menu when the Option key is held down. Or they can use the Get Info menu.
Your best bet would be to switch to using a more-likely-to-be-unique file extension

How does Windows associate icons to files in explorer shell?

I have both InDesign CS2 and CS3 installed. Both use files with .indd extension. How does Windows know which icon to use? It uses correct icons i.e. CS2 files have cs2 icon and CS3 files have CS3 icon.
How does Windows know how to do this?
And how can I extract or use this version-detection system in my programs?
Edit:
Thank you for your shell-extension-icon-handler answers. Something new to me. But is there any way I could connect to IconHandler that InDesign provides and use it to detect version of the InDesign file?
You need to write an Icon Handler shell extension. See the MSDN documentation for IExtractIcon. The basic mechanism is that you create a shell extension and register the icon handler for the file type you want (look in HKEY_CLASSES_ROOT/.indd) and then the shell loads your handler, passes the file information and requests an icon in return. There's also the IExtractImage method if you want to provide a thumbnail bitmap rather than just an icon.
Note that you need to be especially careful writing shell extension handlers as any memory leaks or crashes can nuke the explorer and any other applications that display a file open/save dialog.
For some files it's HKEY_CLASSES_ROOT\<file extension here>\DefaultIcon registry entry, but most files map to a more friendly name, e.g. .pdf\(Default) -> AcroExch.Document (if Adobe Reader is installed).
In that case you have to go along the registry to AcroExch.Document and see that either
DefaultIcon is right there or
AcroExch.Document\CLSID\(Default) is some GUID. Then, follow HKEY_CLASSES_ROOT\CLSID\<insert that guid here> and you'll notice that this key contains DefaultIcon
... and DefaultIcon is where the icon is loaded from.
Hope that was clear enough ;). I don't know about your special case but there should be a distinction in the registry.
It almost certainly installs a shell icon extension handler. Writing your own and knowing how to detect the version in a file format that isn't documented well or at all is quite tricky.

Resources