Class to select directory

. Lot of you may recognize him from the lots of helpful posts on the mfc usenet groups.

CDirDialog : this class encapsulates the SHBrowseForFolder API. You can use this class to browse for folders. I had seen many posting asking this question. So, I put together this small wrapper class. In order to use it , Set the title by setting the text in m_strTitle. If you dont set this the title will have "Open".

Set the initial directory to start from using m_strInitDir. If you dont set this, it will start from desktop.

Then call DoBrowse (). If it returns TRUE, you can see the m_strPath for the selected directory. If it returns FALSE, user has dismissed the dialog with a cancel OR there was some problem retrieving the folder. I have not put in any error code. If, somebody wants to they are welcome to do it.
////////////////////////////////////////////////////////////////////////
// DirDialog.h: interface for the CDirDialog class.
//
//////////////////////////////////////////////////////////////////////

#if
!defined(AFX_DIRDIALOG_H__62FFAC92_1DEE_11D1_B87A_0060979CDF6D__INCLUDED_)
#define AFX_DIRDIALOG_H__62FFAC92_1DEE_11D1_B87A_0060979CDF6D__INCLUDED_

#if _MSC_VER >= 1000
#pragma once
#endif // _MSC_VER >= 1000

class CDirDialog
{
public:
     CDirDialog();
     virtual ~CDirDialog();
     int DoBrowse ();
     CString m_strPath;
     CString m_strInitDir;
     CString m_strTitle;
     int  m_iImageIndex;

};

#endif //
!defined(AFX_DIRDIALOG_H__62FFAC92_1DEE_11D1_B87A_0060979CDF6D__INCLUDED_)


///////////////////////////////////////////////////////////////////////////
// DirDialog.cpp: implementation of the CDirDialog class.
//
//////////////////////////////////////////////////////////////////////

#include "stdafx.h"
#include "DirDialog.h"
#include "shlobj.h"
#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif

//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////

CDirDialog::CDirDialog()
{////////////////////////////////////////////

}

CDirDialog::~CDirDialog()
{///////////////////////////////////////////

}

int CDirDialog::DoBrowse ()
{/////////////////////////////////////////

    LPMALLOC pMalloc;
    if (SHGetMalloc (&pMalloc)!= NOERROR)
    {
        return 0;
    }

    BROWSEINFO bInfo;
    LPITEMIDLIST pidl;
    ZeroMemory ( (PVOID) &bInfo,sizeof (BROWSEINFO));

     if (!m_strInitDir.IsEmpty ())
     {
          OLECHAR       olePath[MAX_PATH];
          ULONG         chEaten;
          ULONG         dwAttributes;
          HRESULT       hr;
          LPSHELLFOLDER pDesktopFolder;
          // // Get a pointer to the Desktop's IShellFolder interface. //
          if (SUCCEEDED(SHGetDesktopFolder(&pDesktopFolder)))
          {

               //
               // IShellFolder::ParseDisplayName requires the file name be in Unicode.
               //
               MultiByteToWideChar(CP_ACP, MB_PRECOMPOSED, m_strInitDir.GetBuffer (MAX_PATH), -1,
                    olePath, MAX_PATH);

               m_strInitDir.ReleaseBuffer (-1);
               //
               // Convert the path to an ITEMIDLIST.
               //
               hr = pDesktopFolder->ParseDisplayName(NULL,
                    NULL,
                    olePath,
                    &chEaten,
                    &pidl,
                    &dwAttributes);
               if (FAILED(hr))
               {
                    pMalloc ->Free (pidl);
                    pMalloc ->Release ();
                    return 0;
               }
               bInfo.pidlRoot = pidl;
          }
     }
          bInfo.hwndOwner = NULL;
          bInfo.pszDisplayName = m_strPath.GetBuffer (MAX_PATH);
          bInfo.lpszTitle = (m_strTitle.IsEmpty()) ? "Open":m_strTitle;
          bInfo.ulFlags = BIF_RETURNFSANCESTORS|BIF_RETURNONLYFSDIRS;


          if ((pidl = ::SHBrowseForFolder (&bInfo)) == NULL)
          {
               return 0;
          }
          m_strPath.ReleaseBuffer ();
          m_iImageIndex = bInfo.iImage;

          if (::SHGetPathFromIDList(pidl,m_strPath.GetBuffer (MAX_PATH)) == FALSE)
          {
               pMalloc ->Free (pidl);
               pMalloc ->Release ();
               return 0;
          }

    m_strPath.ReleaseBuffer ();

    pMalloc ->Free (pidl);
    pMalloc ->Release ();
     return 1;
}

Enhancement

This enhancement was sent by Lars Klose.

I downloaded Girish Bharadwaj's wrapper class for SHBrowseForFolder, CDirDialog, a few days ago. Because it seems useful to me to set the selected folder to a default value other than 'desktop' when the dialog opens, I extended Girish Bharadwaj's implementation with a callback function that sets the selected folder when the dialog is initialized. It's set to the value stored in the new member variable m_strSelDir or defaults to 'desktop' if m_strSelDir was not set. The attached zip contains the changed files DirDialog.h and .cpp.

Download file (2KB)



Comments

  • Thank you!

    Posted by Legacy on 02/05/2004 12:00am

    Awesome work! I've tried for hours to send those callback messages without any result! Keep the great work!

    Jenya.

    Reply
  • Terrific!

    Posted by Legacy on 12/06/2003 12:00am

    Originally posted by: Tommy S.

    Thanx man!

    You just saved me alot of time that I now intend to spend
    in bed with my girlfriend ;)


    Reply
  • Nice work. Thanks.

    Posted by Legacy on 08/22/2003 12:00am

    Originally posted by: MT

    I appreciate the work.  Easily integrated in my project in just a few minutes.  Easily expandable.  Thanks for the organization.
    
    

    MT

    Reply
  • Great but doesn't show other computers on network

    Posted by Legacy on 01/16/2003 12:00am

    Originally posted by: Standa

    Hi, I use that class and I'm satisfied, but what doesn't work for me, is that I cant browse through computers on network, even when I browse them eg. with Servant Salamander or with Windows Explorer. When I want to expand "Other Computers" (or how is it written in english), it doesn't show me any computer...

    Does anybody know how to solve this ??

    Thanks Standa.

    Reply
  • useful class.. but wrong class design

    Posted by Legacy on 10/23/2002 12:00am

    Originally posted by: Juice

    this class is useful. but had wrong design

    this class have not initial method, too..

    what's wrong?

    for example, I can't specify owner window...

    kkkkk...

    Reply
  • Just to say THANKS for an excellent contribution

    Posted by Legacy on 07/29/2002 12:00am

    Originally posted by: Darren

    Reply
  • very good ,I had made some change too!

    Posted by Legacy on 11/14/2001 12:00am

    Originally posted by: zzg_han

    I want to use this class not use MFC,so I change some thing
    of it.But it had give me some Ideas.

    Reply
Leave a Comment
  • Your email address will not be published. All fields are required.

Top White Papers and Webcasts

  • While virtual desktop infrastructure (VDI) comes with many potential advantages, adoption of VDI has been slow. The reality is that the path to achieving the VDI promise land is a difficult one, mostly due to high expense, poor end-user experience, and management difficulties. More often than not, the root cause of all three of these failure modes is storage. This white paper explores how a new, 100%-flash based approach to VDI can overcome the key VDI failure traps and deliver a VDI solution that both …

  • Mobile is introducing sweeping changes throughout your workplace. As a senior stakeholder driving mobile initiatives in your organization, you may be lost in a sea of technologies and claims from vendors promising rapid delivery of applications to your employees, customers, and partners. To help explain some of the topics you will need to be aware of, and to separate the must-haves from the nice-to-haves, this reference guide can help you with applying a mobile strategy in the context of application …

Most Popular Programming Stories

More for Developers

Latest Developer Headlines

RSS Feeds