iShellFolder, BindToObjects and IiEnumIdList in VB.Net

N

Nicola Garone

Hi all,
I need to enumerate pidl in a directory which I got (I think) the rigt
pidl, but I don't know how to procede.

here is a piece of code (folder is a IShellFolder object and it seems to
work correctly)

Dim idEnum As IEnumIDList
Dim pidEnum As IntPtr
folder.EnumObjects(IntPtr.Zero, _
COM.ShellAPI.API.SHCONTF.SHCONTF_FOLDERS Or _
COM.ShellAPI.API.SHCONTF.SHCONTF_NONFOLDERS, _
pidEnum)

Now pidEnum got a value and this make me thind folder.EnumObjects works
well
but OF COURSE idEnum (which I must use) is Nothing since is not initialized
so I can't use
Dim hRes As Integer
hRes = idEnum.Next(1, pidl, fetched)

I tried:
Dim idEnum As IEnumIDList
Dim pidEnum As IntPtr =
Marshal.AllocHGlobal(Marshal.SizeOf(idEnum))
' this give me an error "Value can't be null"

I also tried:
Dim idEnum As IEnumIDList
Dim pidEnum As IntPtr
folder.EnumObjects(IntPtr.Zero, ... bla bla bla)
Marshal.StructureToPtr(idEnum, pidEnum, False)
' this also give me an error "Value can't be null"

I also tried:
Dim idEnum As IEnumIDList
Dim pidEnum As IntPtr
Marshal.PtrToStructure(pidEnum, idEnum)
' this also give me an error "Value can't be null"


this is how I defined EnumObjects
<PreserveSig()> _
Function EnumObjects(ByVal hwnd As IntPtr, ByVal grfFlags As
COM.ShellAPI.SHCONTF, ByRef ppenumIDList As IntPtr) As Int32

what am I missing?

Thanks in advance
Nicola Garone
 
R

Robin Tucker

This is what my implementation looks like - of course, it might not be
optimal, but EnumObjects should return a pointer to an IEnumIDList. If it
returns nothing, then the object is not enumerable and perhaps your
IShellFolder is not correct.

Public Shared Function GetIEnum(ByRef theFolder As COM.IShellFolder) As
COM.IEnumIDList

Dim ptrRet As IntPtr

' Get the pidl enumerator

theFolder.EnumObjects(IntPtr.Zero, COM.ShellAPI.SHCONTF.SHCONTF_FOLDERS,
ptrRet)

' if its null, we don't have an enumerator (we are not enumerable!)

If ptrRet.Equals(IntPtr.Zero) Then
Return Nothing
End If

' Get the shell enum type

Dim shellEnumType As System.Type =
System.Type.GetType("CR.COM.IEnumIDList")

' COM cast to an IEnumIDList

Dim obj As [Object] = Marshal.GetTypedObjectForIUnknown(CType(ptrRet,
IntPtr), shellEnumType)

' and cast to the interface

Return DirectCast(obj, COM.IEnumIDList)
End Function
 
N

Nicola Garone

Since also your code dind't work (on my pc) I supposed interface definition
and finally I discovered the value of SHCONTF_FOLDER was wrong, Sigh!!
Thanks a lot for your help. I'm afraid I'll need again for next steps :)
Nicola.

Robin Tucker said:
This is what my implementation looks like - of course, it might not be
optimal, but EnumObjects should return a pointer to an IEnumIDList. If it
returns nothing, then the object is not enumerable and perhaps your
IShellFolder is not correct.

Public Shared Function GetIEnum(ByRef theFolder As COM.IShellFolder) As
COM.IEnumIDList

Dim ptrRet As IntPtr

' Get the pidl enumerator

theFolder.EnumObjects(IntPtr.Zero, COM.ShellAPI.SHCONTF.SHCONTF_FOLDERS,
ptrRet)

' if its null, we don't have an enumerator (we are not enumerable!)

If ptrRet.Equals(IntPtr.Zero) Then
Return Nothing
End If

' Get the shell enum type

Dim shellEnumType As System.Type =
System.Type.GetType("CR.COM.IEnumIDList")

' COM cast to an IEnumIDList

Dim obj As [Object] = Marshal.GetTypedObjectForIUnknown(CType(ptrRet,
IntPtr), shellEnumType)

' and cast to the interface

Return DirectCast(obj, COM.IEnumIDList)
End Function


Nicola Garone said:
Hi all,
I need to enumerate pidl in a directory which I got (I think) the rigt
pidl, but I don't know how to procede.

here is a piece of code (folder is a IShellFolder object and it seems to
work correctly)

Dim idEnum As IEnumIDList
Dim pidEnum As IntPtr
folder.EnumObjects(IntPtr.Zero, _
COM.ShellAPI.API.SHCONTF.SHCONTF_FOLDERS Or _
COM.ShellAPI.API.SHCONTF.SHCONTF_NONFOLDERS, _
pidEnum)

Now pidEnum got a value and this make me thind folder.EnumObjects works
well
but OF COURSE idEnum (which I must use) is Nothing since is not initialized
so I can't use
Dim hRes As Integer
hRes = idEnum.Next(1, pidl, fetched)

I tried:
Dim idEnum As IEnumIDList
Dim pidEnum As IntPtr =
Marshal.AllocHGlobal(Marshal.SizeOf(idEnum))
' this give me an error "Value can't be null"

I also tried:
Dim idEnum As IEnumIDList
Dim pidEnum As IntPtr
folder.EnumObjects(IntPtr.Zero, ... bla bla bla)
Marshal.StructureToPtr(idEnum, pidEnum, False)
' this also give me an error "Value can't be null"

I also tried:
Dim idEnum As IEnumIDList
Dim pidEnum As IntPtr
Marshal.PtrToStructure(pidEnum, idEnum)
' this also give me an error "Value can't be null"


this is how I defined EnumObjects
<PreserveSig()> _
Function EnumObjects(ByVal hwnd As IntPtr, ByVal grfFlags As
COM.ShellAPI.SHCONTF, ByRef ppenumIDList As IntPtr) As Int32

what am I missing?

Thanks in advance
Nicola Garone
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top