AutoHotkey Tip of the Week: Adding Icons to Menus the Easy Way(?)

Inserting Icons into Your AutoHotkey Menus Makes Options Standout and Easy to Navigate, But You May Need to Prioritize the Methods for Adding Icons

I’ve employed icons in my QuickLink.ahk script for many years, but the process I used for adding them to menu items always felt awkward and messy—too much special-purpose code.

I want the script to standalone without needing much tailoring. Most changes should occur in Windows File Explorer by creating folders or editing shortcuts. Then the QuickLinks.ahk script should read all the Menu items from that folder/file structure—including menu icons. However, my implementation of icons gets a bit sloppy. For my own QuickLinks, I added numerous special lines of code to deal with the inconsistencies in how Windows deals with folder and file icons. I’ve never felt comfortable with how it worked.

My recent work implementing the Switch/Case statements has prompted me to return to my original goal of producing a script needing little or no adapting. That means not only constructing the AutoHotkey menu directly from the folder/file structure shown in Windows File Explorer, but the menu icons themselves should load from those folders and shortcut files without requiring additional unique lines of AutoHotkey code in the script.

Note: The QuickLinks.ahk script does contain specialized snippets that add the God Mode Tools folder and shortcut, as well as, the dynamic time/date insertion menu. However, anyone who doesn’t want those features can easily comment out the pertinent section.

Library Benefits

While implementing the new Switch/Case command, I found better ways to force menus to display the icons I want—without extra code. Rather than embedding icons and icons paths in the AutoHotkey script, I incorporate a few techniques that either add the menu icon automatically from the Windows shortcut (and eventually folder) or, at a minimum, make it easy to find and call an icon without making any changes to the AutoHotkey script itself. In this blog, I concentrate on adding menu icons directly from information embedded in the Windows shortcut—if any. Next time, I’ll deal with the top-level folder icons.

Using Switch/Case Statements

An important feature of the Switch/Case command is its duplication of a series of If-Else statements. Since it uses Short-circuit Boolean Evaluation, AutoHotkey exits the set of conditions after the first match. This saves evaluating the numerous following conditionals (and possibly overwriting an earlier added menu icon). This makes the physical order of the Case statements in the script very important. You must assign a priority to each true condition.

For example, in the Case statements below that target Windows shortcuts, the Case for extracting the icon from an EXE file appears before the Case which uses a shortcut’s manually embedded icon:

Case Instr(QL_OutTarget,"exe"):  ; Use EXE file icon
  Menu, %QL_MainMenu%, Icon, %QL_NewName%, %QL_OutTarget%, 1
Case (QL_OutIcon != ""):         ; Use embedded icon
  Menu, %QL_MainMenu%, Icon, %QL_NewName%
    , %QL_OutIcon%, %QL_OutIconNum%

In the first Case, if the Windows shortcut target (QL_OutTarget) launches an EXE file, then it uses the first icon found in the EXE file. In the second Case, if the shortcut contains a manually assigned icon (QL_OutIcon), then AutoHotkey uses that icon. But, if the first case executes, the second case never occurs—even when you manually embedded a preferred icon in the shortcut. Swapping the location of the two case statements in the script gives higher priority to shortcuts containing special icons.

Extracting Icon Data from Windows Shortcuts

The Windows NewShortcut dialogue creates two types of shortcuts—.lnk (link) and .url (Web address). When you manually create a shortcut by right-clicking in a blank area of a Windows File Explorer window (ideally within the QuickLinks subfolders), you get the option to create a shortcut (NewShortcut):

QuickLinksNewShortcut
To manually create a new shortcut, right-click on a blank area of a Windows File Explorer window (or the Desktop), then select NewShortcut. Enter the target filename or Internet URL. However, using URLs creates the .url type Windows shortcuts constraining icon use.

If you enter a folder or filename, it creates a .lnk shortcut targeting that folder/file. When entering a Web URL, Windows creates a .url shortcut. The only problem is that the AutoHotkey FileGetShortcut command does not read icon information embedded in .url shortcuts while it works just fine for .lnk shortcuts. Ideally, for the purpose of adding icons, we should avoid placing any .url type files in our QuickLinks shortcut folders.

AddLinksMenu
To add new shortcuts to QuickLinks, select a file/folder (including path), or Web address and select Add Links ⇒ [Subfolder].
Tip: Fortunately, when building shortcuts for Web URLs using the AutoHotkey FileCreateShortcut command, it writes a special command readable Internet .lnk file—although, once written, it does not allow manual editing of the URL.

As a best practice, in the QuickLinks script use the Add Links option in the main menu to create Internet shortcuts. The Add Links feature exploits the FileCreateShortcut command. Select the URL in a Web browser or any other document or Web page, activate the QuickLinks menu, then select Add Links [Folder] (the folder where you plan to place the shortcut). This eliminates the deficiencies of the manually created .url shortcut.

*          *          *

CoverImage200
A Multitude of AutoHotkey Tips and Tricks

Three chapters of the e-book Digging Deeper Into AutoHotkey discuss the beginnings of the QuickLinks.ahk script and how it works. Plus, Chapter Thirty of AutoHotkey Applications explains how I originally added icons to AutoHotkey menus. You can find even more features for the QuickLinks.ahk script demonstrated in Chapter 4.1.4 “Automatically Add Windows Shortcuts to the QuickLinks App”, Chapter 4.1.5 “Spice Up AutoHotkey Menus with Icons”, Chapter 4.1.6 “Finding Windows Icons for AutoHotkey Menus”, Chapter 4.1.7 “Add Secret Windows Tools (God Mode) to QuickLinks Menu”, and Chapter 4.1.8 “Using Unique Icons for Specific Windows Shortcuts” of the book Jack’s Motley Assortment of AutoHotkey Tips.

*          *          *

Reading Windows Shortcut and File Data

Two AutoHotkey commands provide the data you need for loading menu icons: FileGetShortcut and FileGetAttrib:

FileGetShortcut
  , C:\Users\%A_UserName%\QuickLinks\%QL_MainMenu%\%QL_NewName%.lnk
  , QL_OutTarget, QL_OutDir, QL_OutArgs, QL_OutDescription
  , QL_OutIcon, QL_OutIconNum, QL_OutRunState
FileGetAttrib, QL_FileAttrib , %QL_OutTarget%

Using these commands, we decipher enough information to determine which icons to load.  Originally created either by hand or via the Add Links option in the QuickLinks menu, the following images display the available Windows shortcut data for different types of shortcuts using the above commands.

LinkProgram

Program Shortcuts

This first Windows shortcut targets a program. Since the variable QL_OutTarget includes the path and name of the program, AutoHotkey can use the icon embedded in that program file. As a rule, using the program icons adds simplicity for both inserting icons into the menu item and later recognizing the program in the QuickLinks menu. When assigning special-purpose parameters to program, such as printing documents, we may not want to use the program icon. Then, assigning a specific icon to the shortcut will overrule the program icon.

Unfortunately, shortcuts targeting document or image files do not provide data for the default launching program. I would guess that I can find it in the Windows Registry—a topic for another time.

LinkURL

Manually Created URL Shortcut

When manually adding a Web address in the New ⇒ Shortcut dialogue (a right-click on a blank area of the Desktop or in Windows File Explorer), Windows defaults to a .url shortcut type of link. The AutoHotkey FileGetShortcut command won’t return any data from this type of shortcut—even if you manually add an icon in the Windows Properties window. Therefore, the shortcut filename provides the only available icon clue.

For Internet addresses, rather than manually creating .url shortcuts, I recommend building the shortcut using the Add Links option in the QuickLinks menu. That option writes an Internet .lnk type file as shown in the next image.

LinkInternet

AutoHotkey Created Internet Shortcut with Readable Embedded Icon

The advantage of creating Internet links using the Add Links option in the QuickLinks menu lies in the fact that AutoHotkey can later extract icon information from the Windows shortcut via the FileGetShortcut command. This allows the manual or programmatic addition of icons to the shortcuts for later use by the QuickLinks menu.

Note: To make them easier to recognize, I’ve inserted code into the QuickLinksTimeDateSubMenuSwitch.ahk script that automatically adds an icon to Web shortcuts IconInternet when first created via the QuickLinks  Add Links option.

LinkEmbeddedIcon

Folder Shortcut with Embedded Icon

Note that the variable QL_FileAttrib now includes the letter “D” designating it as a Windows folder shortcut. Folder shortcuts open the target folder (directory) in Windows File Explorer. As a rule, the icon in Windows defaults to a file folder image. AutoHotkey can use this attribute to add a default icon to the QuickLinks menu for each Windows folder shortcut. Otherwise, only a default icon in the Switch/Case will appear.

Note: A folder shortcut .lnk file points to a folder and should not be confused with the folders found in the top-level of QuickLinks folder/file structure. Folders present special problems for adding icons to AutoHotkey menus. This issue serves as the topic for a future blog.

Of course, you can embed a different icon either manually through the Properties windows or programmatically with the AutoHotkey. (I’m looking at writing a shortcut editing tool to bypass the Properties window for the QuickLinks.ahk script.)

Prioritize Switch/Case Statements

With the exception of the Case statement for .ahk, this set of Switch/Case statements occur in order according to priority:

Switch
{
Case (QL_OutIcon != ""):       ; Embedded icon
  Menu, %QL_MainMenu%, Icon, %QL_NewName%
    , %QL_OutIcon%, %QL_OutIconNum%
Case Instr(QL_OutTarget,"`.ahk"):   ; AutoHotkey script
   Menu, %QL_MainMenu%, Icon, %QL_NewName%
    , C:\Program Files\AutoHotkey\AutoHotkeyU64.exe, 2
Case Instr(QL_FileAttrib,"D"):   ; Folder icon
   Menu, %QL_MainMenu%, Icon, %QL_NewName%
    , %A_Windir%\system32\imageres.dll, 4,
Case Instr(QL_OutTarget,"exe"):  ; Program icon
  Menu, %QL_MainMenu%, Icon, %QL_NewName%, %QL_OutTarget%, 1
Default:
  QL_AddIcon(QL_MainMenu,A_LoopFileName)
}

This Switch/Case command allows you to manually embed icons in your shortcuts, then automatically add those icons to your menu items. Note: I placed the shortcut icon Case first to prevent EXE shortcut Case from preempting manually selected icons.

When a Case statement evaluates True, AutoHotkey takes action and exits the Switch/Case statements:

  1. If the script finds an icon embedded in the Windows shortcut (QL_OutIcon != “”), it loads that icon into the menu, then exits…else
  2. If the script finds that the target file uses the .ahk extension (Instr(QL_OutTarget,”`.ahk”)), it applies the second icon from the AutoHotkey EXE program file to the menu item, then exits…else
  3. If the script finds that the shortcut targets a folder (Instr(QL_FileAttrib,”D”)), it applies a folder icon to the menu, then exits…else
  4. If the script targets a program (Instr(QL_OutTarget,”exe”)), it loads the first icon from that program file, then exits…else
  5. If none of the previous conditions evaluate true, the Switch Defaults to the function QL_AddIcon(QL_MainMenu, A_LoopFileName).

I originally wrote the QL_AddIcon(menuitem,submenu) function to add menu icons to the main folders at the top-level of the QuickLinks menu. Folder icons do not work in the same manner as Windows shortcuts. (Ultimately, I want to eliminate most of this function since almost every aspect of it consists of specially tailored code):

QL_AddIcon(menuitem,submenu)
{
  submenu1 := StrReplace(submenu, ".lnk")
  submenu2 := StrReplace(submenu, ".url")
  Switch
  {
  Case Instr(submenu,"AutoHotkey"):
    If Instr(submenu,".lnk")
      Menu, %menuitem%, Icon, %submenu1%
        , C:\Program Files\AutoHotkey\AutoHotkeyU64.exe, 2
    Else
      Menu, %menuitem%, Icon, %submenu2%
        , %A_Windir%\system32\SHELL32.dll, 14,
  Case Instr(submenu,"Tools"):
    Menu, %menuitem%
      , Icon, %submenu1%, %A_Windir%\system32\SHELL32.dll, 36,
  Case Instr(submenu,"Text"):
    Menu, %menuitem%
      , Icon, %submenu1%, %A_Windir%\system32\SHELL32.dll, 2,
  Case Instr(submenu,"Photos"):
    Menu, %menuitem%
      , Icon, %submenu1%, %A_Windir%\system32\SHELL32.dll, 140;,
  Case Instr(submenu,"E-Book"):
    Menu, %menuitem%
      , Icon, %submenu1%, Books.ico
  Case Instr(submenu,"EPUB"):
    Menu, %menuitem%
      , Icon, %submenu1%, Books.ico
  Case Instr(submenu,"print"):
    Menu, %menuitem%, Icon
      , %submenu1%,%A_Windir%\system32\SHELL32.dll, 17,
  Case Instr(submenu,"Graphics"):
    Menu, %menuitem%
      , Icon, %submenu1%, %A_Windir%\system32\SHELL32.dll, 142,
  Case Instr(submenu,"favorite"):
    Menu, %menuitem%
      , Icon, %submenu1%, %A_Windir%\system32\SHELL32.dll, 44,
  Case Instr(submenu,"browser"):
    Menu, %menuitem%
      , Icon, %submenu1%, %A_Windir%\system32\SHELL32.dll, 14,
  Case Instr(submenu,"misc"):
    Menu, %menuitem%, Icon
       , %submenu1%, %A_Windir%\system32\SHELL32.dll, 93,
  Case Instr(submenu,"url"):
    Menu, %menuitem%, Icon, %submenu2%
      , %A_Windir%\system32\SHELL32.dll, 14,
  Default:
    Menu, %menuitem%, Icon, %submenu1%
      , %A_Windir%\system32\SHELL32.dll, 85,
  }
}

As I said, I wrote the function above primarily to deal with the folders—which don’t provide easy-to-find icon information—at the top-level of the QuickLinks menu. AutoHotkey does not offer a command for reading folder data. However, another Windows trick makes it possible to retrieve information about manually set folder icons. I’ll do that in the next blog while attempting to eliminate most of the code in the above function.

Click the Follow button at the top of the sidebar on the right of this page for e-mail notification of new blogs. (If you’re reading this on a tablet or your phone, then you must scroll all the way to the end of the blog—pass any comments—to find the Follow button.)

jack

This post was proofread by Grammarly
(Any other mistakes are all mine.)

(Full disclosure: If you sign up for a free Grammarly account, I get 20¢. I use the spelling/grammar checking service all the time, but, then again, I write a lot more than most people. I recommend Grammarly because it works and it’s free.)

One thought on “AutoHotkey Tip of the Week: Adding Icons to Menus the Easy Way(?)

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google photo

You are commenting using your Google account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s