 |

|
Do you need to present a folder browser dialog to the user from your WPF app?
Sure, you can use the FolderBrowserDialog Class[^], but what self-respecting WPF
programmer wants to pull in the System.Windows.Forms namespace
and its associated DLL(s)?
Not me.
Here's a simple wrapper around the SHBrowseForFolder Function[^] that I posted
on the WPF board.
I'm not sure it's article-worthy, so for now I'll just keep it here in case
someone asks for it.
On to the code, in its entirety, with an example of its usage following...
using System;
using System.Text;
using System.Runtime.InteropServices;
using System.Windows;
using System.Windows.Interop;
namespace CommonDialogWrappers
{
public class BrowseForFolderDialog
{
#region Public Properties
public string SelectedFolder { get; protected set; }
public string Title
{
get { return BrowseInfo.lpszTitle; }
set { BrowseInfo.lpszTitle = value; }
}
public string InitialFolder { get; set; }
public string InitialExpandedFolder { get; set; }
public string OKButtonText { get; set; }
BROWSEINFOW browseInfo;
public BROWSEINFOW BrowseInfo
{
get { return browseInfo; }
protected set { browseInfo = value; }
}
public BrowseInfoFlags BrowserDialogFlags
{
get { return BrowseInfo.ulFlags; }
set { BrowseInfo.ulFlags = value; }
}
#endregion
#region Public Constructors
public BrowseForFolderDialog()
{
BrowseInfo = new BROWSEINFOW();
BrowseInfo.hwndOwner = IntPtr.Zero;
BrowseInfo.pidlRoot = IntPtr.Zero;
BrowseInfo.pszDisplayName = new String(' ', 260);
BrowseInfo.lpszTitle = "Select a folder:";
BrowseInfo.ulFlags = BrowseInfoFlags.BIF_NEWDIALOGSTYLE;
BrowseInfo.lpfn = new BrowseCallbackProc(BrowseEventHandler);
BrowseInfo.lParam = IntPtr.Zero;
BrowseInfo.iImage = -1;
}
#endregion
#region Public ShowDialog() Overloads
public Nullable<bool> ShowDialog()
{
return PInvokeSHBrowseForFolder(null);
}
public Nullable<bool> ShowDialog(Window owner)
{
return PInvokeSHBrowseForFolder(owner);
}
#endregion
#region PInvoke Stuff
private Nullable<bool> PInvokeSHBrowseForFolder(Window owner)
{
WindowInteropHelper windowhelper;
if (null != owner)
{
windowhelper = new WindowInteropHelper(owner);
BrowseInfo.hwndOwner = windowhelper.Handle;
}
IntPtr pidl = SHBrowseForFolderW(browseInfo);
if (IntPtr.Zero != pidl)
{
StringBuilder pathsb = new StringBuilder(260);
if (false != SHGetPathFromIDList(pidl, pathsb))
{
SelectedFolder = pathsb.ToString();
Marshal.FreeCoTaskMem(pidl);
return true;
}
}
return false;
}
private int BrowseEventHandler(IntPtr hwnd, MessageFromBrowser uMsg, IntPtr lParam, IntPtr lpData)
{
switch (uMsg)
{
case MessageFromBrowser.BFFM_INITIALIZED:
{
if (!string.IsNullOrEmpty(InitialExpandedFolder))
SendMessageW(hwnd, MessageToBrowser.BFFM_SETEXPANDED, new IntPtr(1), InitialExpandedFolder);
else if (!string.IsNullOrEmpty(InitialFolder))
SendMessageW(hwnd, MessageToBrowser.BFFM_SETSELECTIONW, new IntPtr(1), InitialFolder);
if (!string.IsNullOrEmpty(OKButtonText))
SendMessageW(hwnd, MessageToBrowser.BFFM_SETOKTEXT, new IntPtr(1), OKButtonText);
break;
}
case MessageFromBrowser.BFFM_SELCHANGED:
{
StringBuilder pathsb = new StringBuilder(260);
if (false != SHGetPathFromIDList(lParam, pathsb))
{
SelectedFolder = pathsb.ToString();
}
break;
}
case MessageFromBrowser.BFFM_VALIDATEFAILEDA: {
break;
}
case MessageFromBrowser.BFFM_VALIDATEFAILEDW: {
break;
}
case MessageFromBrowser.BFFM_IUNKNOWN:
{
break;
}
}
return 0;
}
public delegate int BrowseCallbackProc(IntPtr hwnd, MessageFromBrowser uMsg, IntPtr lParam, IntPtr lpData);
[Flags]
public enum BrowseInfoFlags : uint
{
BIF_None = 0x0000,
BIF_RETURNONLYFSDIRS = 0x0001, BIF_DONTGOBELOWDOMAIN = 0x0002, BIF_STATUSTEXT = 0x0004, BIF_RETURNFSANCESTORS = 0x0008,
BIF_EDITBOX = 0x0010, BIF_VALIDATE = 0x0020, BIF_NEWDIALOGSTYLE = 0x0040, BIF_USENEWUI = BIF_NEWDIALOGSTYLE | BIF_EDITBOX,
BIF_BROWSEINCLUDEURLS = 0x0080, BIF_UAHINT = 0x0100, BIF_NONEWFOLDERBUTTON = 0x0200, BIF_NOTRANSLATETARGETS = 0x0400, BIF_BROWSEFORCOMPUTER = 0x1000, BIF_BROWSEFORPRINTER = 0x2000, BIF_BROWSEINCLUDEFILES = 0x4000, BIF_SHAREABLE = 0x8000 }
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode)]
public class BROWSEINFOW
{
public IntPtr hwndOwner;
public IntPtr pidlRoot; public string pszDisplayName; public string lpszTitle;
public BrowseInfoFlags ulFlags;
public BrowseCallbackProc lpfn;
public IntPtr lParam;
public int iImage; }
public enum MessageFromBrowser : uint
{
BFFM_INITIALIZED = 1,
BFFM_SELCHANGED = 2,
BFFM_VALIDATEFAILEDA = 3,
BFFM_VALIDATEFAILEDW = 4,
BFFM_IUNKNOWN = 5
}
public enum MessageToBrowser : uint
{
WM_USER = 0x0400,
BFFM_SETSTATUSTEXTA = WM_USER + 100,
BFFM_ENABLEOK = WM_USER + 101,
BFFM_SETSELECTIONA = WM_USER + 102,
BFFM_SETSELECTIONW = WM_USER + 103,
BFFM_SETSTATUSTEXTW = WM_USER + 104,
BFFM_SETOKTEXT = WM_USER + 105, BFFM_SETEXPANDED = WM_USER + 106 }
[DllImport("shell32.dll")]
private static extern IntPtr SHBrowseForFolderW([MarshalAs(UnmanagedType.LPStruct), In, Out] BROWSEINFOW bi);
[DllImport("shell32.dll")]
private static extern bool SHGetPathFromIDList(IntPtr pidl, StringBuilder path);
[DllImport("user32.dll")]
public static extern IntPtr SendMessageW(IntPtr hWnd, uint Msg, IntPtr wParam, IntPtr lParam);
[DllImport("user32.dll")]
public static extern IntPtr SendMessageW(IntPtr hWnd, MessageToBrowser msg, IntPtr wParam, [MarshalAs(UnmanagedType.LPWStr)] string str);
#endregion
}
}
Example:
CommonDialogWrappers.BrowseForFolderDialog dlg = new CommonDialogWrappers.BrowseForFolderDialog();
dlg.Title = "Select a folder and click OK!";
dlg.InitialExpandedFolder = @"c:\";
dlg.OKButtonText = "OK!";
if (true == dlg.ShowDialog(this))
{
MessageBox.Show(dlg.SelectedFolder, "Selected Folder");
}
Mark Salsbery
Microsoft MVP - Visual C++
|
|
|
|

|
Hello sir,
After searching for a no of sites for this control,I came to this post.
In my opinion U should write an article on this control Because I haven't seen any File Browser Control in WPF till now(if it exists now,plz do let me know ).
Anyways,Coming to point ,Can i use it ?
I am making an open source next generation Media Player(Hope to make it better than existing ones) and i am looking for such control.
If yes for permission to use it,What are the terms?
Will your name and blog reference in the class will make the way.
Great job,
sonam
(sonamsingh_19@yahoo.co.in)
I walk in rain ....so that no one can see me crying.
|
|
|
|
|

|
There is a set of file and folder browser controls (commercial though) for WPF : Shell MegaPack.WPF
|
|
|
|

|
Thanks for posting this Mark.
Maybe you should post this as a short and sweet article. I knew that "someone" had posted this but danged if I could remember who or where.
Why is common sense not common?
Never argue with an idiot. They will drag you down to their level where they are an expert.
Sometimes it takes a lot of work to be lazy
Individuality is fine, as long as we do it together - F. Burns
Help humanity, join the CodeProject grid computing team here
|
|
|
|

|
This is great. The only bug I see that is that there are folders with "." or period characters in them and they don't display the period or anything after.
For example, these show blank
.dia
.eclipse
.idlerc
These only show the first part
Paint.NET (shows Paint instead of Paint.NET)
org.eclipse.platform_3.5.0_920333535 only shows (org.eclipse.platform_3.5)
|
|
|
|

|
rhyous wrote: This is great. The only bug I see that is that there are folders with "." or period characters in them and they don't display the period or anything after.
I'm unable to reproduce that on Windows 7.
Is it something you see in my wrapper code?Mark Salsbery
Microsoft MVP - Visual C++
|
|
|
|

|
I am on Windows 7 64 bit using Visual Studio 2008.
Don't worry, I have what I need using Ookii Dialogs.
Thanks,
Jared
|
|
|
|

|
This works really well. Thanks. I looked at a lot of other solutions and nothing was half as good as this.
|
|
|
|
|
|

|
Thanks,
I wish you had made a TIP or a small article with this code in there.
This is a great approach if you can live with a non styled Common Dialog box.
|
|
|
|
| |

|
Check...Check One...Check...Is this thing on?
|
|
|
|

|
I got caught fishing[^] with a McDonalds employee
I think I should have seen this one coming and not responded to the original post.
|
|
|
|
|

|
Mark, we have a Problem[^]
Many are stubborn in pursuit of the path they have chosen, few in pursuit of the goal - Friedrich Nietzsche
.·´¯`·->Rajesh<-·´¯`·.
[Microsoft MVP - Visual C++]
|
|
|
|
|

|
I just read the thread - my head is still spinning trying to comprehend where he was coming from, without leaping to the conclusion that he was an idiot.
¡El diablo está en mis pantalones! ¡Mire, mire!
Real Mentats use only 100% pure, unfooled around with Sapho Juice(tm)!
SELECT * FROM User WHERE Clue > 0
0 rows returned
Save an Orange - Use the VCF!
VCF Blog
|
|
|
|
|

|
Jim, how the heck did you come to this thread? Just curious.
|
|
|
|

|
If memory serves, I think I came across a reply Mark made to my post from a few days ago. I thought it was amusing and checked out an article of his, then came across his profile, and then this thread I think.
¡El diablo está en mis pantalones! ¡Mire, mire!
Real Mentats use only 100% pure, unfooled around with Sapho Juice(tm)!
SELECT * FROM User WHERE Clue > 0
0 rows returned
Save an Orange - Use the VCF!
VCF Blog
|
|
|
|

|
led mike wrote: Jim, how the heck did you come to this thread? Just curious.
Now you may wonder how I'm here too.
Nobody can give you wiser advice than yourself. - Cicero
.·´¯`·->Rajesh<-·´¯`·.
Codeproject.com: Visual C++ MVP
|
|
|
|

|
Look at this[^]
I recognize this guy. He has been on here for months now and does not seem to be making progress. I think he needs a career change.
|
|
|
|

|
2 or 3 days of this[^] has me wondering if this person is real (sadly) or just a joker.
Mark Salsbery
Microsoft MVP - Visual C++
|
|
|
|

|
He is either a troll or suffering severe bouts of the ID Ten T condition.
|
|
|
|

|
Mark Salsbery wrote: Check...Check One...Check...Is this thing on?
Yeh it's working.. TIC TIC TIC!
"Opinions are neither right nor wrong. I cannot change your opinion. I can, however, change what influences your opinion." - David Crow
cheers,
Alok Gupta
VC Forum Q&A :- I/ IV
Support CRY- Child Relief
|
|
|
|

|
Wow the first page of the C++ forum is almost entirely people that won't RTFM. That Programm3r a**hole is the same bullsh*t every time he posts. This site is close to becoming worthless as far as the forums are concerned.
|
|
|
|

|
led mike wrote: Another fishing derby day
Heh. They come in waves....maybe it has something to do with tides?
Mark Salsbery
Microsoft MVP - Visual C++
|
|
|
|

|
Just came from the C# forum.... there just are not very many people you can help here any longer since most of them are completely hopeless. It may be time to for me to formulate a CodeProject Exit Strategy
|
|
|
|

|
Man....I'm only through a couple pages of the Visual C++ board...
I had to pause and just say W T F
Thanks for listening
Mark Salsbery
Microsoft MVP - Visual C++
|
|
|
|

|
Did you see that Nelek guys reply to the double conversion post? *rolleyes*
Did you see the thread in past few weeks talking about the quality of posts in the forums. The OP started complaining about answers and a bunch of us quickly hyjacked it into complaining about questions. Anyway one of our regulars said something like "people not having the requisite knowledge to warrant launching Visual Studio." I should have captured it because his version was funnier.
|
|
|
|
|

|
Can I join the fishing club? This is one of the worst I've seen:
http://www.codeproject.com/script/Forums/View.aspx?fid=1647&msg=2740568[^]
I have my application in MFC which is working fine on Windows Operating system. Now i want to run the same application on Macintosh. I want to know do i need to make changes in my code. If yes what all things needs to be changed. Or it can work perfectly alright without making any changes.
The title of the post is "Operating System Problem"
Alright stone, I give up.
Many are stubborn in pursuit of the path they have chosen, few in pursuit of the goal - Friedrich Nietzsche
.·´¯`·->Rajesh<-·´¯`·.
[Microsoft MVP - Visual C++]
|
|
|
|
|

|
So I stayed in for a change on Friday night. I went into the forums for a couple hours.... good grief what joke, it's even worse than during the weekdays.
One guy wants to convert .exe and .jpg files into binary so he can write them as text files and then convert them back.
Another guy wants to draw a transparent rectangle and a guy replied telling him to draw 4 lines.
Another guy developed a report to print labels and it works Great! Oh but sometimes you need to start in the middle of the page... clearly not a requirement you want to know "before" you start developing the solution... oh and his data comes from a database because that is significant to the printing problem.
And this last gem, the guy wants to run the same .exe on Windows, Linus and Solaris because "it could be better".
That's all the code and fix jackassary I can take for a Friday night, I doubt I will do this again anytime soon.
|
|
|
|
|

|
led mike wrote: One guy wants to convert .exe and .jpg files into binary so he can write them as text files and then convert them back.
led mike wrote: Another guy wants to draw a transparent rectangle and a guy replied telling him to draw 4 lines.
led mike wrote: And this last gem, the guy wants to run the same .exe on Windows, Linus and Solaris because "it could be better".
Must be carved in sandalwood.
Many are stubborn in pursuit of the path they have chosen, few in pursuit of the goal - Friedrich Nietzsche
.·´¯`·->Rajesh<-·´¯`·.
[Microsoft MVP - Visual C++]
|
|
|
|
|
|

|
it's like you've revoked my fishing license or something
|
|
|
|

|
I'm busy fishing myself!
I'm trying to find a new drumming gig. You look a lot like Jimmy Page....looking for a drummer?
Mark Salsbery
Microsoft MVP - Visual C++
|
|
|
|

|
Mark Salsbery wrote: looking for a drummer?
most people have more musical ability in the dirt under there right hand thumbnail than I have in my entire body.
|
|
|
|

|
led mike wrote: most people have more musical ability in the dirt under there right hand thumbnail than I have in my entire body.
Heh...hmmm I'll take that as a "no" then
Mark Salsbery
Microsoft MVP - Visual C++
|
|
|
|

|
I can't believe how they butchered the site. I finally read Maunders post in the lounge and it explains a few things but overall... WOW OMG WTF. If I did work like this I would go back to herding cattle, seriously... I mean that... really.
Notice the message here I am replying to, I can't even add a new thread to your blog! I have only posted I think one reply since this mess started and I couldn't make a link in my reply. None of the commands work like "quote" etc. There are missing forums. They did this over the weekend I guess and I had like 10 email replies from Friday threads and on monday I couldn't use the email links to get to any of them.
I doubt you will get an email notification of this so you probably won't even see it.
WOW... I can't even think of what to say about it, just... WOW I would never have guessed this would happen... WOW.
|
|
|
|

|
I should have posted:
Yes your process is still running and you better come get it because it just ran past my window.
led mike
|
|
|
|

|
http://www.codeproject.com/script/Forums/View.aspx?fid=12076&msg=2758401[^]
AND look at the guys BIO. I remember one of the first threads I read here in CP was about the industry and how every software has bugs. Not about how you can't achieve ZERO but just how in general the industry is OK with buggy software while of course users are NOT.
If this guys BIO is not fiction it is a great example of how much trouble the industry is in and how the current buggy situation has no chance of improving any time soon.
Just a thought. Sorry to bother you. *peace*
led mike
|
|
|
|
 |