shbrowseforfolder in my folder

Hi,
Herre follows my function that let's me
browse for a folder on the disk.
My problem is that I want to start the
browsing in a specified directory.
How can I add that ?
I don't want to browse ONLY starting
from that dir. I want to browse the whole
computer, but when the dialog opens I
want my folder to be already selected.
Working code would be nice.
Stay simple, I have the rxlib that comes
with a nice component that does all the
stuff. But it is doing too much. Maybe
we can do it by only adding one or two lines.

I know that we have to send a message
to the dialog with
procedure TBrowseFolderDlg.SetSelPath(const Path: string);
begin
  if FHandle <> 0 then
    SendMessage(FHandle, BFFM_SETSELECTION, 1, Longint(PChar(Path)));
end;

But I don't know where to call it.
If you know how to do add the following
things :
-start browse with my dir selected
-enable the ok button only if a dir is
selected.

Thanks in advance.



-------------------------------
procedure TSelectFolder.Execute;
var
  pMAlloc: IMalloc;
begin
  wBrowseInfo.hwndOwner := TCustomForm(GetOwner).Handle;
  wBrowseInfo.pidlRoot := nil;
  wBrowseInfo.pszDisplayName := wPath;
  wBrowseInfo.lpszTitle := PChar('Tri2 Tool');
  wBrowseInfo.ulFlags := 0;
  wBrowseInfo.lpfn := nil;
  wBrowseInfo.lParam := 0;
  wBrowseInfo.iImage := 0;

  try
    CoGetMalloc(MEMCTX_TASK, pMAlloc);
    GetMem(wPath, MAX_PATH);

    wItemIDList := SHBrowseForFolder(wBrowseInfo);

    if wItemIDList <> nil then
      if SHGetPathFromIDList(wItemIDList, wPath) then
        FPath := wPath
      else
        FPath := ''
    else
      FPath := '';
  finally
    FreeMem(wPath);
    pMalloc._Release;
  end; // try
end;
LVL 4
jeurkAsked:
Who is Participating?
 
LischkeConnect With a Mentor Commented:
Hi Jeurk,

here's how to do it:

function BrowseCallbackProc(hwnd: HWND; uMsg: UINT; lParam, lpData: LPARAM): Integer; stdcall;

// callback function used in SelectDirectory to set the status text and choose an initial dir

var Path: array[0..MAX_PATH] of Char;

begin
  case uMsg of
    BFFM_INITIALIZED:
      begin
        // Initialization has been done, now set our initial directory which is passed in lpData
        // (and set btw. the status text too).
        // Note: There's no need to cast lpData to a PChar since the following call needs a
        //       LPARAM parameter anyway.
        SendMessage(hwnd, BFFM_SETSELECTION, 1, lpData);
        SendMessage(hwnd, BFFM_SETSTATUSTEXT, 0, lpData);
      end;
    BFFM_SELCHANGED:
      begin
        // Set the status window to the currently selected path.
        if SHGetPathFromIDList(Pointer(lParam), Path) then SendMessage(hwnd, BFFM_SETSTATUSTEXT, 0, Integer(@Path));
      end;
  end;
  Result := 0;
end;

//-----------------------------------------------------------------------------

function SelectDirectory(const Caption, InitialDir: String; const Root: WideString;
                         ShowStatus: Boolean; out Directory: String): Boolean;

// Another (overloaded) browse-for-folder function with the ability to select an intial directory
// (other SelectDirectory functions are in FileCtrl.pas).
// I had to make this overloading unambiguous in its parameter list so I included a flag which
// indicates whether or not to show a status text line in the dialog (which will receive the
// currently selected path if enabled).

var BrowseInfo: TBrowseInfo;
    Buffer: PChar;
    RootItemIDList,
    ItemIDList: PItemIDList;
    ShellMalloc: IMalloc;
    IDesktopFolder: IShellFolder;
    Eaten, Flags: LongWord;
    Windows: Pointer;
    Path: String;

begin
  Result := False;
  Directory := '';
  Path := InitialDir;
  if (Length(Path) > 0) and (Path[Length(Path)] = '\') then Delete(Path, Length(Path), 1);
  FillChar(BrowseInfo, SizeOf(BrowseInfo), 0);
  if (ShGetMalloc(ShellMalloc) = S_OK) and (ShellMalloc <> nil) then
  begin
    Buffer := ShellMalloc.Alloc(MAX_PATH);
    try
      SHGetDesktopFolder(IDesktopFolder);
      IDesktopFolder.ParseDisplayName(Application.Handle, nil, PWideChar(Root), Eaten, RootItemIDList, Flags);
      with BrowseInfo do
      begin
        hwndOwner := Application.Handle;
        pidlRoot := RootItemIDList;
        pszDisplayName := Buffer;
        lpszTitle := PChar(Caption);
        ulFlags := BIF_RETURNONLYFSDIRS;
        if ShowStatus then ulFlags := ulFlags or BIF_STATUSTEXT;
        lParam := Integer(PChar(Path));
        lpfn := BrowseCallbackProc;
      end;

      // make the browser dialog modal
      Windows := DisableTaskWindows(Application.Handle);
      try
        ItemIDList := ShBrowseForFolder(BrowseInfo);
      finally
        EnableTaskWindows(Windows);
      end;

      Result :=  ItemIDList <> nil;
      if Result then
      begin
        ShGetPathFromIDList(ItemIDList, Buffer);
        ShellMalloc.Free(ItemIDList);
        Directory := Buffer;
      end;
    finally
      ShellMalloc.Free(Buffer);
    end;
  end;
end;

//-----------------------------------------------------------------------------



Ciao, Mike
0
 
intheCommented:
well its possible see this comp (wrapper around shbrowse.. with source):

http://www.delphifreestuff.com/cgi-bin/dfs_components.cgi?browsedr

might help some..
0
 
intheCommented:
whoops a bit slow :-)
0
[Webinar] Improve your customer journey

A positive customer journey is important in attracting and retaining business. To improve this experience, you can use Google Maps APIs to increase checkout conversions, boost user engagement, and optimize order fulfillment. Learn how in this webinar presented by Dito.

 
jeurkAuthor Commented:
Hi,
works fine, just what I wanted. thanks.

inthe : I was aware of that componant
thanks. But i just wanted to add the
minimum code to do my stuff, thanks
anyway...

regards.
0
 
jeurkAuthor Commented:
Inthe : happens everyday ;)
I missed some 1000 yesterday ;)
0
 
LischkeCommented:
:-)))
0
 
intheCommented:
yep i noticed :-)
dont worry it happens to us all
0
All Courses

From novice to tech pro — start learning today.