🚀 go-pugleaf

RetroBBS NetNews Server

Inspired by RockSolid Light RIP Retro Guy

Thread View: borland.public.cppbuilder.nativeapi
13 messages
13 total messages Started by Mehmet Caner Wed, 16 Jul 2008 08:34
Explorer type TreeView in Vista
#229
Author: Mehmet Caner
Date: Wed, 16 Jul 2008 08:34
91 lines
3540 bytes
Hi,

The following code fills TreeView1 component with the drives of the computer 
in Windows XP SP2 successfully, but failed in Vista. What's wrong with the 
code?

Thanks in advance!

void __fastcall TForm1::FirstTree(void)
{
  LPMALLOC lpMalloc;

  if (SUCCEEDED(SHGetMalloc(&lpMalloc))) {
  LPSHELLFOLDER lpsf;
  SHFILEINFO FileInfo;
  unsigned int uSHFlags = SHGFI_SYSICONINDEX | SHGFI_DISPLAYNAME | 
SHGFI_PIDL;
  TTreeNode *TNode;

  if (SUCCEEDED(SHGetDesktopFolder(&lpsf))) {
   LPITEMIDLIST lpidl;
   if (SUCCEEDED(SHGetFolderLocation(Handle, CSIDL_DRIVES, NULL, 0, 
&lpidl))) {
     LPSHELLFOLDER lpsfSub;
     if (SUCCEEDED(lpsf->BindToObject(lpidl, NULL, IID_IShellFolder, 
reinterpret_cast<void **>(&lpsfSub)))) {
      SHGetFileInfo((LPCSTR)lpidl, 0, &FileInfo, sizeof(SHFILEINFO), 
uSHFlags);
      FillTree(lpsfSub, lpidl);
      lpsfSub->Release();
     }
   }
   lpMalloc->Free(lpidl);
   lpsf->Release();
  }
  lpMalloc->Release();
  }
}
//---------------------------------------------------------------------------
void __fastcall TForm1::FillTree (LPSHELLFOLDER lpsf, LPITEMIDLIST lpidl)
{
  LPMALLOC lpMalloc;
  Screen->Cursor = crHourGlass;

  if (SUCCEEDED(SHGetMalloc(&lpMalloc))) {
   LPENUMIDLIST lpeidl;
   HRESULT HRes;

   HRes = lpsf->EnumObjects(NULL, SHCONTF_NONFOLDERS, &lpeidl);

   if (HRes == NOERROR) {
    TreeView1->Items->BeginUpdate();
    LPITEMIDLIST lpidlCurrent;
    unsigned long ulFetched;
    while (lpeidl->Next(1, &lpidlCurrent, &ulFetched) == S_OK) {
     LPITEMIDLIST lpidlFQ = MergeIDLists (lpMalloc, lpidl, lpidlCurrent);
     if (lpidlFQ) {
      SHFILEINFO FileInfo;
      DWORD FileAttrib;
      unsigned int uSHFlags;
      TTreeNode *Node;
      uSHFlags = SHGFI_SYSICONINDEX | SHGFI_DISPLAYNAME | SHGFI_PIDL;
      SHGetFileInfo(reinterpret_cast<LPCSTR>(lpidlFQ), FileAttrib, 
&FileInfo, sizeof(SHFILEINFO), uSHFlags);

      Node = TreeView1->Items->AddChild(NULL, FileInfo.szDisplayName);
      Node->ImageIndex = FileInfo.iIcon;
      Node->SelectedIndex = FileInfo.iIcon;
      Node->Data = reinterpret_cast<void *>(lpidlFQ);
      TTreeNode *ChildNode = TreeView1->Items->AddChild(Node, "");
      ChildNode->ImageIndex = -1;
     }
     lpMalloc->Free(lpidlCurrent);
    }
    TreeView1->Items->EndUpdate();

    lpeidl->Release();
   }
   else {
    ShowMessage ("Error Code: 001");
   }
   lpMalloc->Release();
  }
  else {
 Screen->Cursor = crArrow;

 ShowMessage ("Error Code: 002");
  }
  Screen->Cursor = crArrow;
}
//---------------------------------------------------------------------------
Re: Explorer type TreeView in Vista
#230
Author: Bob Gonder
Date: Wed, 16 Jul 2008 17:30
20 lines
1283 bytes
Mehmet Caner wrote:

>The following code fills TreeView1 component with the drives of the computer 
>in Windows XP SP2 successfully, but failed in Vista. What's wrong with the 
>code?

I would start by replacing the SUCCEEDED macro
with a function that reports what the error is.

>  if (SUCCEEDED(SHGetDesktopFolder(&lpsf))) {

BOOL SUCCEEDED( HRESULT code )
{
	if( code < 0 )
	{
		//report error;
		return FALSE;
	}
	return TRUE;
}
Re: Explorer type TreeView in Vista
#231
Author: Remy Lebeau (TeamB)
Date: Wed, 16 Jul 2008 18:45
20 lines
1573 bytes
"Mehmet Caner" <mcaner40@hotmail.com> wrote in message 
news:487db2ae$1@newsgroups.borland.com...

> The following code fills TreeView1 component with the drives of the
> computer in Windows XP SP2 successfully, but failed in Vista.
> What's wrong with the code?

You did not say where it is failing.  Can you step through the code and find 
the particular line that is not working?

Have you tried using Vista's new KNOWNFOLDERIDs instead of CSIDLs?  In this 
case, CSIDL_DRIVES maps to FOLDERID_ComputerFolder.  Have a look at MSDN for 
more details:

    Known Folders
    http://msdn.microsoft.com/en-us/library/bb776911(VS.85).aspx


Gambit 
Re: Explorer type TreeView in Vista
#240
Author: Mehmet Caner
Date: Thu, 17 Jul 2008 12:41
122 lines
4725 bytes
Hi Remy,

Thank you very much for your quick answer.

> You did not say where it is failing.  Can you step through the code and 
> find the particular line that is not working?

The code does not enter the while loop in function FillTree:

//  while (lpeidl->Next(1, &lpidlCurrent, &ulFetched) == S_OK) {

void __fastcall TForm1::FirstTree(void)
{
  LPMALLOC lpMalloc;

  if (SUCCEEDED(SHGetMalloc(&lpMalloc))) {
   LPSHELLFOLDER lpsf;
   SHFILEINFO FileInfo;
   unsigned int uSHFlags = SHGFI_SYSICONINDEX | SHGFI_DISPLAYNAME | 
SHGFI_PIDL;
   TTreeNode *TNode;

   if (SUCCEEDED(SHGetDesktopFolder(&lpsf))) {
    LPITEMIDLIST lpidl;
    if (SUCCEEDED(SHGetFolderLocation(Handle, CSIDL_DRIVES, NULL, 0, 
&lpidl))) {
     LPSHELLFOLDER lpsfSub;
     if (SUCCEEDED(lpsf->BindToObject(lpidl, NULL, IID_IShellFolder, 
reinterpret_cast<void **>(&lpsfSub)))) {
      SHGetFileInfo((LPCSTR)lpidl, 0, &FileInfo, sizeof(SHFILEINFO), 
uSHFlags);
      FillTree(lpsfSub, lpidl);
      lpsfSub->Release();
     }
     else ErrorFunc();
    }
    else ErrorFunc();
    lpMalloc->Free(lpidl);
    lpsf->Release();
   }
   else ErrorFunc();
   lpMalloc->Release();
  }
  else ErrorFunc();
}
//---------------------------------------------------------------------------
void __fastcall TForm1::FillTree (LPSHELLFOLDER lpsf, LPITEMIDLIST lpidl)
{
  LPMALLOC lpMalloc;
  Screen->Cursor = crHourGlass;

  if (SUCCEEDED(SHGetMalloc(&lpMalloc))) {
   LPENUMIDLIST lpeidl;
   HRESULT HRes;

   HRes = lpsf->EnumObjects(NULL, SHCONTF_NONFOLDERS, &lpeidl);

   if (HRes == NOERROR) {
    TreeView1->Items->BeginUpdate();
    LPITEMIDLIST lpidlCurrent;
    unsigned long ulFetched;
    while (lpeidl->Next(1, &lpidlCurrent, &ulFetched) == S_OK) { //////// 
failing line
     LPITEMIDLIST lpidlFQ = MergeIDLists (lpMalloc, lpidl, lpidlCurrent);
     if (lpidlFQ) {
      SHFILEINFO FileInfo;
      DWORD FileAttrib;
      unsigned int uSHFlags;
      TTreeNode *Node;
      uSHFlags = SHGFI_SYSICONINDEX | SHGFI_DISPLAYNAME | SHGFI_PIDL;
      SHGetFileInfo(reinterpret_cast<LPCSTR>(lpidlFQ), FileAttrib, 
&FileInfo, sizeof(SHFILEINFO), uSHFlags);

      Node = TreeView1->Items->AddChild(NULL, FileInfo.szDisplayName);
      Node->ImageIndex = FileInfo.iIcon;
      Node->SelectedIndex = FileInfo.iIcon;
      Node->Data = reinterpret_cast<void *>(lpidlFQ);
      TTreeNode *ChildNode = TreeView1->Items->AddChild(Node, "");
      ChildNode->ImageIndex = -1;
     }
     lpMalloc->Free(lpidlCurrent);
    }
    ErrorFunc();
    TreeView1->Items->EndUpdate();

    lpeidl->Release();
   }
   else {
    ErrorFunc();
   }
   lpMalloc->Release();
  }
  else {
 Screen->Cursor = crArrow;
 ErrorFunc();
  }
  Screen->Cursor = crArrow;
}
//---------------------------------------------------------------------------
void __fastcall TForm1::ErrorFunc (void)
{
  LPTSTR MsgBuf;

  FormatMessage (FORMAT_MESSAGE_ALLOCATE_BUFFER | 
FORMAT_MESSAGE_FROM_SYSTEM, NULL,
     GetLastError(), MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
     (LPTSTR) &MsgBuf, 0, NULL);

  MessageBox (NULL, MsgBuf, "Error Message", MB_OK|MB_ICONINFORMATION);
  LocalFree (MsgBuf);
}
//-----------------------------------------------------------------------------

> Have you tried using Vista's new KNOWNFOLDERIDs instead of CSIDLs?  In 
> this case, CSIDL_DRIVES maps to FOLDERID_ComputerFolder.  Have a look at 
> MSDN for more details:
>
>    Known Folders
>    http://msdn.microsoft.com/en-us/library/bb776911(VS.85).aspx

Thanks for the tip. I think it requires Vista SDK. I have download and 
installed it. I have begun studying on KNOWNFOLDERID. 
Re: Explorer type TreeView in Vista
#244
Author: Remy Lebeau (TeamB)
Date: Thu, 17 Jul 2008 18:05
12 lines
1448 bytes
"Mehmet Caner" <mcaner40@hotmail.com> wrote in message 
news:487f3e1b@newsgroups.borland.com...

> The code does not enter the while loop in function FillTree:

Is FillTree() being entered at all?  If so, then the binding to CSIDL_DRIVES 
is fine, but either SHGetMalloc() failed or the drives cannot be enumerated. 
You need to more specific.


Gambit 
Re: Explorer type TreeView in Vista
#245
Author: Mehmet Caner
Date: Thu, 17 Jul 2008 19:48
12 lines
1524 bytes
> Is FillTree() being entered at all?  If so, then the binding to 
> CSIDL_DRIVES is fine, but either SHGetMalloc() failed or the drives cannot 
> be enumerated. You need to more specific.

I stepped through the code. FillTree() function is called.

SHGetMalloc() and EnumObjects() functions are successfully called in 
FillTree().

The code only does not enter the while loop:

while (lpeidl->Next(1, &lpidlCurrent, &ulFetched) == S_OK) {
Re: Explorer type TreeView in Vista
#246
Author: Bob Gonder
Date: Thu, 17 Jul 2008 20:00
12 lines
1528 bytes
Mehmet Caner wrote:

>SHGetMalloc() and EnumObjects() functions are successfully called in 
>FillTree().

I suppose it might be the second case in this note:

http://msdn.microsoft.com/en-us/library/bb775066(VS.85).aspx
If the folder contains no suitable subobjects, then the IShellFolder::EnumObjects method
is permitted either to set *ppenumIDList to NULL and return S_FALSE, or to set
*ppenumIDList to an enumerator that produces no objects and return S_OK. Calling
applications must be prepared for both success cases.
Re: Explorer type TreeView in Vista
#250
Author: Remy Lebeau (TeamB)
Date: Thu, 17 Jul 2008 20:36
17 lines
1591 bytes
"Mehmet Caner" <mcaner40@hotmail.com> wrote in message 
news:487fa20b@newsgroups.borland.com...

> EnumObjects() functions are successfully called in FillTree().

If that were the case, then your while loop would be entered.

> The code only does not enter the while loop:
>
> while (lpeidl->Next(1, &lpidlCurrent, &ulFetched) == S_OK) {

Are you saying that Next() returns something other than S_OK?  That would 
mean the drives are not enumerable.


Gambit 
Re: Explorer type TreeView in Vista
#251
Author: Mehmet Caner
Date: Thu, 17 Jul 2008 21:27
5 lines
1359 bytes
> Are you saying that Next() returns something other than S_OK?  That would 
> mean the drives are not enumerable.

Next() returns S_OK, but the while loop is not entered. It is really very 
interesting. 
Re: Explorer type TreeView in Vista
#252
Author: Mehmet Caner
Date: Thu, 17 Jul 2008 21:30
14 lines
1603 bytes
Hi Bob,

Thanks for your answer.

> http://msdn.microsoft.com/en-us/library/bb775066(VS.85).aspx
> If the folder contains no suitable subobjects, then the 
> IShellFolder::EnumObjects method
> is permitted either to set *ppenumIDList to NULL and return S_FALSE, or to 
> set
> *ppenumIDList to an enumerator that produces no objects and return S_OK. 
> Calling
> applications must be prepared for both success cases.

EnumObjects() returns S_OK. 
Re: Explorer type TreeView in Vista
#253
Author: Remy Lebeau (TeamB)
Date: Thu, 17 Jul 2008 21:54
11 lines
1406 bytes
"Mehmet Caner" <mcaner40@hotmail.com> wrote in message 
news:487fb940@newsgroups.borland.com...

> Next() returns S_OK

If EnumObjects() return S_OK and Next() return S_OK, then your while() loop 
is guaranteed to be entered.


Gambit 
Re: Explorer type TreeView in Vista
#258
Author: Mehmet Caner
Date: Fri, 18 Jul 2008 01:23
4 lines
1290 bytes
> If EnumObjects() return S_OK and Next() return S_OK, then your while() 
> loop is guaranteed to be entered.

Sorry. It was a big mistake. Next() return S_FALSE. 
Re: Explorer type TreeView in Vista
#259
Author: Remy Lebeau (TeamB)
Date: Fri, 18 Jul 2008 01:44
10 lines
1459 bytes
"Mehmet Caner" <mcaner40@hotmail.com> wrote in message 
news:487ff0aa@newsgroups.borland.com...

> Sorry. It was a big mistake. Next() return S_FALSE.

There you go then.  That means the CSIDL_DRIVES enumerator is empty.


Gambit 
Thread Navigation

This is a paginated view of messages in the thread with full content displayed inline.

Messages are displayed in chronological order, with the original post highlighted in green.

Use pagination controls to navigate through all messages in large threads.

Back to All Threads