• Using SHGetFileInfo for Icons (VBA Any)

    Home » Forums » AskWoody support » Productivity software by function » Visual Basic for Applications » Using SHGetFileInfo for Icons (VBA Any)

    Author
    Topic
    #457481

    I am trying to use the shell32 API, SHGetFileInfo to load an Image control with a file’s associated icon. Any sample code that I’ve found uses a PictureBox because it has a Window’s handle, but VBA UserForms do not have a PictureBox, they only have Image controls.

    Another option would be to use an ImageList, but I cannot find any code for it either that doesn’t use a PictureBox.

    I wrote a “simple” test to just display an icon on a blank form without any controls. It gives some numbers for the SHGetFileInfo, but the form is blank.

    The data structures go into a module:

    Option Explicit
    Public Const MAX_PATH As Long = 260
    Public Const SHGFI_DISPLAYNAME = &H200
    Public Const SHGFI_EXETYPE = &H2000
    Public Const SHGFI_SYSICONINDEX = &H4000  'system icon index
    Public Const SHGFI_LARGEICON = &H0        'large icon
    Public Const SHGFI_SMALLICON = &H1        'small icon
    Public Const ILD_TRANSPARENT = &H1        'display transparent
    Public Const SHGFI_SHELLICONSIZE = &H4
    Public Const SHGFI_TYPENAME = &H400
    Public Const BASIC_SHGFI_FLAGS = SHGFI_TYPENAME Or _
                 SHGFI_SHELLICONSIZE Or SHGFI_SYSICONINDEX Or _
                 SHGFI_DISPLAYNAME Or SHGFI_EXETYPE
    Public Type SHFILEINFO
       hIcon          As Long
       iIcon          As Long
       dwAttributes   As Long
       szDisplayName  As String * MAX_PATH
       szTypeName     As String * 80
    End Type
    Public Declare Function FindWindow Lib "user32.dll" _
        Alias "FindWindowA" _
        (ByVal lpClassName As String, ByVal lpWindowName As String) As Long
    Public Declare Function ImageList_Draw Lib "comctl32" _
      (ByVal himl&, _
       ByVal i&, _
       ByVal hDCDest&, _
       ByVal x&, _
       ByVal y&, _
       ByVal Flags&) As Long
    
    Public Declare Function SHGetFileInfo Lib "shell32" _
       Alias "SHGetFileInfoA" _
      (ByVal pszPath As String, _
       ByVal dwFileAttributes As Long, _
       psfi As SHFILEINFO, _
       ByVal cbSizeFileInfo As Long, _
       ByVal uFlags As Long) As Long
    Public Declare Function DrawIconEx Lib "user32" _
        (ByVal hdc As Long, _
         ByVal xLeft As Long, _
         ByVal yTop As Long, _
         ByVal hIcon As Long, _
         ByVal cxWidth As Long, _
         ByVal cyWidth As Long, _
         ByVal istepIfAniCur As Long, _
         ByVal hbrFlickerFreeDraw As Long, _
         ByVal diFlags As Long) As Long
    

    The UserForm (I’m in Excel) is blank with the following code:

    Option Explicit
    Private Sub UserForm_Initialize()
        'Get UserForm window handle
        Const C_VBA6_USERFORM_CLASSNAME = "ThunderDFrame"
        Dim hWndForm As Long, hImgSmall As Long
        hWndForm = FindWindow(C_VBA6_USERFORM_CLASSNAME, Me.Caption)
        Dim sFile As String
        sFile = "E:Documents and Settingssbarrett.CACIMy DocumentsA.txt"
        Dim hIconSmall As Long
        Dim shinfo As SHFILEINFO
        hImgSmall = SHGetFileInfo(sFile, ByVal 0&, shinfo, Len(shinfo), BASIC_SHGFI_FLAGS Or SHGFI_SMALLICON)
        Dim ll As Long
        ll = ImageList_Draw(ByVal hImgSmall, ByVal shinfo.iIcon, ByVal hWndForm, ByVal 10&, ByVal 10&, ILD_TRANSPARENT)
    End Sub
    

    Any help would be greatly appreciated! –Sam

    Viewing 0 reply threads
    Author
    Replies
    • #1147257

      I only know a little bit about MS Forms Image controls…

      You can load a picture from disk using control.Picture = LoadPicture(path).

      However, unless you can extract the icon to a file, this might not be useful.

      • #1147284

        That’s the problem. My call to SHGetFileInfo returns the handle of the system image list that contains the small icon images (see http://allapi.mentalis.org/apilist/SHGetFileInfo.shtml%5B/url%5D) and I don’t have a file.

        In addition to LoadPicture you can get the picture from other controls so, for example, if you have an ImageList named ImageList1,
        control.Picture = ImageList1.ListImages(i).Picture
        also works. The Picture property is strange: (1) there no documentation on what sort of object the Picture property returns and (2) intellisense gives a Handle Property fro the Picture property, but
        Image1.Picture.Handle = Image2.Picture.Handle
        crashes with Object doesn’t support this property, so I guess that Handle is readonly.

        Agggggggggggggggg! drop

    Viewing 0 reply threads
    Reply To: Using SHGetFileInfo for Icons (VBA Any)

    You can use BBCodes to format your content.
    Your account can't use all available BBCodes, they will be stripped before saving.

    Your information: