The MASM Forum

Projects => MasmBasic & the RichMasm IDE => Topic started by: jj2007 on January 21, 2020, 01:58:17 AM

Title: Icon Explorer
Post by: jj2007 on January 21, 2020, 01:58:17 AM
Building this snippet requires MasmBasic of January 20, 2020 (http://masm32.com/board/index.php?topic=94.0):

GuiParas equ "Check the icon", w200, h100, bGrey, icon moricons:50     ; width 300px, height 200px, grey background
GuiMenu equ @File, &Open, &Save, -, E&xit, @Edit, Undo, Copy, Paste    ; creates a menu -> Event Menu
include \masm32\MasmBasic\Res\MbGui.asm
GuiControl MyEdit, "edit", "Hello World"
GuiEnd


(http://www.jj2007.eu/pics/CheckTheIcon.png)

Looks easy but finding the icons is not trivial. Therefore I made (attached, with source) a little program that shows the available icons together with their ID. 25 icon files are predefined, but you can open any file by putting a ? into the edit box and hitting Return:

(http://www.jj2007.eu/pics/IconExplorer.png)

Tested with WinXP, Win7-64 and Win10. You may read on the Internet that imageres.dll has no longer icons in Win10, but that's not correct. It has actually many more icons than the Win7 version. There are also some nice new icons in Win10, like e.g. icon shell32:51380. For the football fans I suggest icon pifmgr:26
Title: Re: Icon Explorer
Post by: Biterider on January 21, 2020, 02:41:58 AM
Hi jj
The application works here too.  :thumbsup:
It shows the icons as expected but it requires some time to show them all. That makes it "feeling" a bit sluggish.
There is a graphic glitch at the right side. The controls overlap the area where the icons are displayed, hiding some of them partially.

Regards, Biterider
Title: Re: Icon Explorer
Post by: jj2007 on January 21, 2020, 02:47:49 AM
Yes, I know. LoadIcon is not the fastest API, and a file can by definition have 65536 icons... that takes time.

Re overlap, if you put e.g. Shell32:1000, it starts counting at ID 1000, thus showing the higher ones, too. A hack :cool:
Title: Change icon at runtime?
Post by: jj2007 on January 21, 2020, 04:52:19 AM
Any idea why this would not work? I get an icon handle with LoadIcon or LoadImage, WM_SETICON returns zero but GetLastError says all is fine. The icons get registered, i.e. a second WM_SETICON message returns them, but the window does not display the new icon. There are several examples in stackoverflow etc, it seems to work there.

.if rv(LoadIcon, hDll, someID)
; no luck with invoke LoadImage, 0, Chr$("test.bmp"), IMAGE_BITMAP, 16, 16, LR_LOADFROMFILE
push eax
invoke SendMessage, hWnd, WM_SETICON, ICON_BIG, eax
pop eax
invoke SendMessage, hWnd, WM_SETICON, ICON_SMALL, eax

Title: Re: Icon Explorer
Post by: Vortex on January 21, 2020, 05:29:29 AM
Hi Jochen,

xandaz recommended using the API function CreateIconIndirect to convert a bitmap to an icon :

include SetIcon.inc

DlgProc     PROTO :DWORD,:DWORD,:DWORD,:DWORD

ICON_ID     equ 100

ICON_SIZE   equ 32

.data

DlgBox  db 'DLGBOX',0
szBmp   db 'Smiley.bmp',0

.data?

hInst   dd ?
hIcon   dd ?

.code

start:

    invoke  GetModuleHandle,0
    mov     hInst,eax
    xor     ecx,ecx
    invoke  DialogBoxParam,eax,ADDR DlgBox,ecx,ADDR DlgProc,ecx
    invoke  ExitProcess,eax

DlgProc PROC hWnd:HWND,uMsg:UINT,wParam:WPARAM,lParam:LPARAM

LOCAL ii:ICONINFO

    .IF uMsg==WM_INITDIALOG

        ; Code portion from xandaz

        invoke  LoadImage,hInst,ADDR szBmp,IMAGE_BITMAP,\
                ICON_SIZE,ICON_SIZE,LR_LOADFROMFILE

        mov     ii.fIcon,TRUE
        mov     ii.hbmMask,eax
        mov     ii.hbmColor,eax
        invoke  CreateIconIndirect,ADDR ii
        mov     hIcon,eax

        invoke  SendMessage,hWnd,WM_SETICON,ICON_SMALL,eax

    .ELSEIF uMsg==WM_CLOSE

        invoke  DestroyIcon,hIcon
        invoke  EndDialog,hWnd,0

    .ELSE

        xor eax,eax
        ret

    .ENDIF

    mov    eax,1
    ret

DlgProc ENDP

END start
Title: Re: Icon Explorer
Post by: jj2007 on January 21, 2020, 01:03:05 PM
Thanks, Erol. Your version works fine - and mine, too. I had used the handle of the edit control, so the OS tried to set the icon to the edit control; a dumb error that unfortunately doesn't get flagged by Windows :biggrin:

Now you can test the icons directly. Just put the index into the green edit box and hit Return. With Alt Tab, you can see the big version of the selected icon.

.if rv(LoadIcon, hDll, someID)
push eax
invoke SendMessage, hGui, WM_SETICON, ICON_SMALL, eax
pop eax
invoke SendMessage, hGui, WM_SETICON, ICON_BIG, eax
.endif
Title: Re: Icon Explorer
Post by: Vortex on January 22, 2020, 05:25:12 AM
Hi Jochen,

Thanks, nice work :thumbsup:

Title: Re: Icon Explorer
Post by: jj2007 on January 22, 2020, 11:01:15 PM
Thanks, Erol :tongue:

This is now a full-fledged Windows application with a nice Butterfly icon alias shell32:239 (requires MB 22.1. (http://masm32.com/board/index.php?topic=94.0)):
GuiParas equ "Check the icon", w200, h100, bGrey, icon Butterfly  ; width 300px, height 200px, grey background
include \masm32\MasmBasic\Res\MbGui.asm
GuiEnd


For now, predefined names are Apple, Ball, Bluetooth, Bulb, Butterfly, Dice, Flower, Football, Joystick, Keys, Lens, Newspaper,  Painting, Printer, Star, Swords, Trafficlight, Tree, Trumpet, Umbrella, and Wall

The only downside is that these icons are barely documented, and some might change if Microsoft decides to do so. That is quite unlikely, though - some of these Dlls are over 20 years old, for moricons it's almost 30 years, see Wikipedia on Moricons.dll (https://en.wikipedia.org/wiki/Moricons.dll). Same for pifmgr.dll, which has some really nice icons.