Hide Extensions in Vista / Windows 7 WPF FileDialog.Filter

I am using WPF OpenFileDialog and SaveFileDialog in my .NET 4 WPF application. I use the Filter property to allow the user to set various file filters. In .NET 4, it uses the built-in file dialogs introduced with Windows Vista (if possible).

However, these dialogs show the extensions that make up file filters. Since some of them use quite a few extensions, this is pretty ugly.

For example, I have a filter Image files|*.bmp;*.dib;*.jpg;*.jpeg;*.jpe;*.jfif;*.gif;*.tif;*.tiff;*.png;*.ico|All files|*.* , which displays as Image files (*.bmp;*.dib;*.jpg;*.jpeg;*.jpe;*.jfif;*.gif;*.tif;*.tiff;*.png;*.ico) in the dialog box. Everything in brackets is automatically added, that is, in accordance with the Filter line, it should be displayed Image files . But somewhere in parentheses the material is added. I tried to take a look at the code with Reflector to make sure it was done somewhere, but gave up quickly because it is rather confusing.

Running Paint, for example, I see that you can use these file dialogs without content in brackets, i.e. shows Image files .

Does anyone know a workaround for this "feature"?

+6
source share
3 answers

You are on the right way. There are two ways to display an open file dialog box. The newer method uses IFileOpenDialog (which extends IFileDialog ). Using this method, filter descriptions and file specifications are defined using the COMDLG_FILTERSPEC structure. This allows you to divide them into your own fields, which is more than nature.

If you want to remove the file specifications from the combo box using this method, you will have to either add your own custom control or manage the combo control in the dialog box. However, this will be erratic, but should be doable.

The old school method uses the GetOpenFileName and OPENFILENAME structure. The trick with this is that it can display a dialogue with the old look or the new look. The look is determined by the settings in the OPENFILENAME structure, as described here .

The problem with WinForms OpenFileDialog is that they either use IFileOpenDialog when they say AutoUpgradeEnabled is true and GetOpenFileName with the old look when AutoUpgradeEnabled is false.

The WPF version does not give you a choice, but it still uses the same logic as WinForms, but it does this automatically as needed. This is true for WPF in .NET 4, in previous versions it would just use GetOpenFileName with the old look.

The paint most likely uses GetOpenFileName with a new look. Here is a C # example:

 private delegate IntPtr WndProc(IntPtr hWnd, int msg, IntPtr wParam, IntPtr lParam); private const int OFN_ALLOWMULTISELECT = 0x00000200; private const int OFN_CREATEPROMPT = 0x00002000; private const int OFN_DONTADDTORECENT = 0x02000000; private const int OFN_ENABLEHOOK = 0x00000020; private const int OFN_ENABLEINCLUDENOTIFY = 0x00400000; private const int OFN_ENABLESIZING = 0x00800000; private const int OFN_ENABLETEMPLATE = 0x00000040; private const int OFN_ENABLETEMPLATEHANDLE = 0x00000080; private const int OFN_EXPLORER = 0x00080000; private const int OFN_EXTENSIONDIFFERENT = 0x00000400; private const int OFN_FILEMUSTEXIST = 0x00001000; private const int OFN_FORCESHOWHIDDEN = 0x10000000; private const int OFN_HIDEREADONLY = 0x00000004; private const int OFN_LONGNAMES = 0x00200000; private const int OFN_NOCHANGEDIR = 0x00000008; private const int OFN_NODEREFERENCELINKS = 0x00100000; private const int OFN_NOLONGNAMES = 0x00040000; private const int OFN_NONETWORKBUTTON = 0x00020000; private const int OFN_NOREADONLYRETURN = 0x00008000; private const int OFN_NOTESTFILECREATE = 0x00010000; private const int OFN_NOVALIDATE = 0x00000100; private const int OFN_OVERWRITEPROMPT = 0x00000002; private const int OFN_PATHMUSTEXIST = 0x00000800; private const int OFN_READONLY = 0x00000001; private const int OFN_SHAREAWARE = 0x00004000; private const int OFN_SHOWHELP = 0x00000010; [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode)] public class OPENFILENAME_I { public int lStructSize; public IntPtr hwndOwner; public IntPtr hInstance; public string lpstrFilter; public IntPtr lpstrCustomFilter; public int nMaxCustFilter; public int nFilterIndex; public IntPtr lpstrFile; public int nMaxFile = 260; public IntPtr lpstrFileTitle; public int nMaxFileTitle = 260; public string lpstrInitialDir; public string lpstrTitle; public int Flags; public short nFileOffset; public short nFileExtension; public string lpstrDefExt; public IntPtr lCustData; public WndProc lpfnHook; public string lpTemplateName; public IntPtr pvReserved; public int dwReserved; public int FlagsEx; } [DllImport("comdlg32.dll", CharSet = CharSet.Unicode, SetLastError = true)] private static extern bool GetOpenFileName([In, Out] OPENFILENAME_I ofn); private void ShowOpenFileDialog() { OPENFILENAME_I ofn = new OPENFILENAME_I(); ofn.lStructSize = Marshal.SizeOf(typeof(OPENFILENAME_I)); ofn.lpstrFilter = "Text Files (*.txt)\0*.txt\0All Files\0*.*\0\0"; ofn.nFilterIndex = 0; //ofn.Flags = OFN_EXPLORER | OFN_ENABLEHOOK | OFN_ENABLESIZING | OFN_NODEREFERENCELINKS | OFN_HIDEREADONLY | OFN_PATHMUSTEXIST | OFN_FILEMUSTEXIST; ofn.Flags = OFN_ENABLESIZING | OFN_NODEREFERENCELINKS | OFN_HIDEREADONLY | OFN_PATHMUSTEXIST | OFN_FILEMUSTEXIST; GetOpenFileName(ofn); } 

You can try adding the OFN_EXPLORER and / or OFN_ENABLEHOOK , and it will revert to the old look. But as it is, in the above code a dialog box appears with an open file in which all files will not be displayed in the file specification.

+5
source

After a bunch of testing, I got the following result: FileDialog in WPF calls its own IFileDialog :: SetFileTypes method with strings as defined by the filter. Depending on the Windows option, to hide the extension on known file types (in the settings of the Windows Explorer folder), extensions are automatically added or not.

Now the only question remains, how can Paint not show extensions for โ€œimage filesโ€ in the open file dialog box.

+1
source

You might want to go here ...

Hide extensions

+1
source

Source: https://habr.com/ru/post/886327/


All Articles