benners Posted December 28, 2015 Share Posted December 28, 2015 I am trying to add icons to a menu and I am having an issue when it comes to actual .ico files. The function I am using works with dll and exe files and I have tried to modify it to work with .ico with no success.I have cobbled the code together from the help file and this forum and now it's time to ask for help before the dog gets kicked j/k.What I need to know is either where I am going wrong or another way to get a handle to an icon using and actual icon file so that it can be converted to a bitmap and added to a menu. The _WinAPI_ExtractIconEx is successful as $i_Result = 1, for 1 icon extracted but no icon is displayed.I would have thought _WinAPI_ShellExtractIcon would have worked with .ico files but no icon is diplayed. Cheersexpandcollapse popup; #FUNCTION# ==================================================================================================================== ; Name ..........: CreateBitmapFromIcon ; Description ...: Create a bitmap image from an icon ; Syntax ........: CreateBitmapFromIcon($iBackground, $sIcon, $iIndex, $iWidth, $iHeight) ; Return values .: Handle to the bitmap ; Author ........: Yashied ; Modified ......: Benners 28/12/2015 ; Remarks .......: ; Related .......: ; Link ..........: https://www.autoitscript.com/forum/topic/97365-how-to-convert-a-hicon-to-a-32-bit-hbitmap/?do=findComment&comment=700670 ; =============================================================================================================================== Func CreateBitmapFromIcon($sIcon, $iIndex = 0, $iWidth = 16, $iHeight = 16) Local $hDC = _WinAPI_GetDC(0) Local $hBackDC = _WinAPI_CreateCompatibleDC($hDC) Local $hBitmap = _WinAPI_CreateSolidBitmap(0, _WinAPI_GetSysColor($COLOR_MENU), $iWidth, $iHeight) Local $hBackSv = _WinAPI_SelectObject($hBackDC, $hBitmap) Local $hIcon = 0 If StringRight($sIcon, 4) = '.ico' Then Local $tIcon = DllStructCreate("int Handle") Local $i_Result = _WinAPI_ExtractIconEx("C:\Program Files (x86)\AutoIt3\Beta\Icons\au3script_v10.ico", 0, 0, DllStructGetPtr($tIcon), 1) $hIcon = DllStructGetData($tIcon, "Handle") Else $hIcon = _WinAPI_ShellExtractIcon($sIcon, $iIndex, $iWidth, $iHeight) EndIf If Not @error Then _WinAPI_DrawIconEx($hBackDC, 0, 0, $hIcon, 0, 0, 0, 0, $DI_NORMAL) _WinAPI_DestroyIcon($hIcon) EndIf _WinAPI_SelectObject($hBackDC, $hBackSv) _WinAPI_ReleaseDC(0, $hDC) _WinAPI_DeleteDC($hBackDC) Return $hBitmap EndFunc ;==>CreateBitmapFromIcon Link to comment Share on other sites More sharing options...
benners Posted December 28, 2015 Author Share Posted December 28, 2015 OK, I have spent some more time looking at other examples and googling. I have got round the ico file issues by using another way to get the associated icon. This works mostly as I want but the icons look shite when viewed lower than 32x32. This appears to be when the icon are gotten using shell32.dll cal ExtractAssociatedIcon. I found using SHGetFileInfo maybe better but that requires further reading and hair pulling.below is the full code for testing, if anyone has the time to lend a hand with the icon size\display issues and an ini is attached for the program.expandcollapse popup#Region ;**** Directives created by AutoIt3Wrapper_GUI **** #AutoIt3Wrapper_au3check_parameters=-d -w 1 -w 2 -w 3 -w 4 -w 5 -w 6 #AutoIt3Wrapper_Icon=Icons\BennersQL.ico #AutoIt3Wrapper_Res_Description=Shortcut launcher for files #AutoIt3Wrapper_Res_Fileversion=1.0.0.8 #AutoIt3Wrapper_Res_Fileversion_AutoIncrement=y #AutoIt3Wrapper_Res_LegalCopyright=@ Benners Inc 2015 #AutoIt3Wrapper_Res_requestedExecutionLevel=requireAdministrator #EndRegion ;**** Directives created by AutoIt3Wrapper_GUI **** #include <array.au3> #include <ButtonConstants.au3> #include <ComboConstants.au3> #include <FileConstants.au3> #include <GUIConstantsEx.au3> #include <GuiComboBox.au3> #include <GuiMenu.au3> #include <GuiStatusBar.au3> #include <IE.au3> #include <misc.au3> #include <MsgBoxConstants.au3> #include <WindowsConstants.au3> #include 'UDF\Logging_Functions.au3' #include <WinAPIShellEx.au3> If Not $CMDLINE[0] Then If UBound(ProcessList(@ScriptName)) > 2 Then Exit ElseIf $CMDLINE[1] <> '/restart' Then Exit EndIf Opt("GUIOnEventMode", 1) ; global vars Global $g_s_INI = stringtrimright(@ScriptFullPath,3) & 'ini' Global $g_s_DefaultTitle = 'Benners'' Quick Launch' Global $g_a_MenuEvents[50][2] Global $g_i_Dpi = GetDPI() Global $g_h_Main_GUI = 0 Global $g_h_MainMenu = 0 Global $g_h_Status_bar = 0 Global Enum $g_id_FileAdd_mnu = 1000, $g_id_FileOpen_mnu, $g_id_FilePreferences_mnu, $g_id_FileExit_mnu Main_GUI_Draw() ; create the gui ; set the function to run when a menu message is received. GUIRegisterMsg($WM_COMMAND, "WM_COMMAND") ; show the gui GUISetState(@SW_SHOW) While 1 Sleep(100) WEnd Func Main_GUI_Draw() Local $i_Left = IniRead($g_s_INI, 'GUI', 'Left', -1) Local $i_Top = IniRead($g_s_INI, 'GUI', 'Top', -1) $g_h_Main_GUI = GUICreate(IniRead($g_s_INI, 'GUI', 'Title', $g_s_DefaultTitle), 491 * $g_i_Dpi, 130 * $g_i_Dpi, $i_Left, $i_Top) ; set the GUI on top of others WinSetOnTop($g_h_Main_GUI, '', 1) GUISetOnEvent($GUI_EVENT_CLOSE, "Main_GUI_Close") ; create a menu (This is the main menu, others will be added to this) $g_h_MainMenu = _GUICtrlMenu_CreateMenu() #Region #### create the default file menu #### ; create a menu (this will be the File menu added to the main menu) Local $h_File_mnu = _GUICtrlMenu_CreateMenu() ; add items to the file menu _GUICtrlMenu_AddMenuItem($h_File_mnu, "Add To Menu", $g_id_FileAdd_mnu) _GUICtrlMenu_AddMenuItem($h_File_mnu, "Open", $g_id_FileOpen_mnu) _GUICtrlMenu_AddMenuItem($h_File_mnu, "") _GUICtrlMenu_AddMenuItem($h_File_mnu, "Preferences", $g_id_FilePreferences_mnu) _GUICtrlMenu_AddMenuItem($h_File_mnu, "") _GUICtrlMenu_AddMenuItem($h_File_mnu, "Exit", $g_id_FileExit_mnu) ; set the menu icons _GUICtrlMenu_SetItemBmp($h_File_mnu, $g_id_FileAdd_mnu, CreateBitmapFromIcon(@SystemDir & '\imageres.dll', 156, 0), False) _GUICtrlMenu_SetItemBmp($h_File_mnu, $g_id_FileOpen_mnu, CreateBitmapFromIcon(@SystemDir & '\imageres.dll', 7, 0), False) _GUICtrlMenu_SetItemBmp($h_File_mnu, $g_id_FilePreferences_mnu, CreateBitmapFromIcon(@SystemDir & '\imageres.dll', 64, 0), False) _GUICtrlMenu_SetItemBmp($h_File_mnu, $g_id_FileExit_mnu, CreateBitmapFromIcon(@SystemDir & '\shell32.dll', 27, 0), False) ; add the file menu to the main menu _GUICtrlMenu_AddMenuItem($g_h_MainMenu, 'File', 0, $h_File_mnu) #EndRegion #### create the default file menu #### #Region #### create the users main menu #### MainMenu_CreateDynamic($g_a_MenuEvents) #EndRegion #### create the users main menu #### ; Set window menu _GUICtrlMenu_SetMenu($g_h_Main_GUI, $g_h_MainMenu) EndFunc ;==>Main_GUI_Draw Func Main_GUI_Close() Exit EndFunc ;==>Main_GUI_Close Func MainMenu_AddItem() Local $s_GUITitle = 'Add Menu Item' ; get the main guis position Local $a_WindowPos = WinGetPos($g_s_DefaultTitle) ; create the main gui using main gui window positions Local $h_AddItem_GUI = GUICreate($s_GUITitle, 305 * $g_i_Dpi, 300 * $g_i_Dpi, $a_WindowPos[0], $a_WindowPos[1]) #Region #### select a file group ############################ GUICtrlCreateGroup("Select a File", 8 * $g_i_Dpi, 5 * $g_i_Dpi, 289 * $g_i_Dpi, 64 * $g_i_Dpi) Local $id_FileName_lbl = GUICtrlCreateLabel("", 16 * $g_i_Dpi, 32 * $g_i_Dpi, 230 * $g_i_Dpi, 17 * $g_i_Dpi, $DT_END_ELLIPSIS) Local $id_FileSelect_btn = GUICtrlCreateButton("...", 253 * $g_i_Dpi, 28 * $g_i_Dpi, 30 * $g_i_Dpi, 25 * $g_i_Dpi) GUICtrlSetFont(-1, 10, 800, 0, "MS Sans Serif") GUICtrlSetTip(-1, "Select a file to add to the menu") GUICtrlCreateGroup("", -99, -99, 1, 1) #EndRegion #### select a file group ############################ #Region #### select a menu group ############################ GUICtrlCreateGroup("Select a Menu", 8 * $g_i_Dpi, 72 * $g_i_Dpi, 289 * $g_i_Dpi, 80 * $g_i_Dpi) GUICtrlCreateLabel("Current Menu Items", 18 * $g_i_Dpi, 94 * $g_i_Dpi, 96 * $g_i_Dpi, 17 * $g_i_Dpi) Local $id_MainMenuList_cbo = GUICtrlCreateCombo("", 133 * $g_i_Dpi, 92 * $g_i_Dpi, 150 * $g_i_Dpi, 25 * $g_i_Dpi, BitOR($CBS_DROPDOWNLIST, $CBS_AUTOHSCROLL)) GUICtrlSetTip(-1, "Displays list of current menu items") ; set the combo data, read the main menu list from the ini Local $a_MenuItems = IniReadSection($g_s_INI, 'MainMenu') If Not @error Then ; loop through the array and add the strings For $i = 1 To $a_MenuItems[0][0] _GUICtrlComboBox_AddString($id_MainMenuList_cbo, $a_MenuItems[$i][0]) Next EndIf Local $s_AddNew = 'Add New Menu..' ; add new menu option to end of list _GUICtrlComboBox_AddString($id_MainMenuList_cbo, $s_AddNew) Local $id_AddSubMenu_chk = GUICtrlCreateCheckbox("Add Sub Menu", 18 * $g_i_Dpi, 123 * $g_i_Dpi, 90 * $g_i_Dpi, 17 * $g_i_Dpi) GUICtrlSetTip(-1, "Add the menu item under a sub menu") Local $id_AddSubMenu_inp = GUICtrlCreateInput("", 132 * $g_i_Dpi, 121 * $g_i_Dpi, 150 * $g_i_Dpi, 21 * $g_i_Dpi) GUICtrlSetState(-1, $GUI_DISABLE) GUICtrlSetTip(-1, "Type the name of the sub menu") GUICtrlCreateGroup("", -99, -99, 1, 1) #EndRegion #### select a menu group ############################ #Region #### create menu group ############################## GUICtrlCreateGroup("Create Menu Item", 8 * $g_i_Dpi, 156 * $g_i_Dpi, 289 * $g_i_Dpi, 80 * $g_i_Dpi) GUICtrlCreateLabel("Type a Name", 18 * $g_i_Dpi, 178 * $g_i_Dpi, 68 * $g_i_Dpi, 17 * $g_i_Dpi) Local $id_MenuItemText_inp = GUICtrlCreateInput("", 133 * $g_i_Dpi, 176 * $g_i_Dpi, 150 * $g_i_Dpi, 21 * $g_i_Dpi) GUICtrlSetTip(-1, "Type the name for the menu item") Local $id_AddSeparator_chk = GUICtrlCreateCheckbox("Add Separator Line", 18 * $g_i_Dpi, 207 * $g_i_Dpi, 113 * $g_i_Dpi, 17 * $g_i_Dpi) GUICtrlSetTip(-1, "Add a separator line after the menu item") GUICtrlCreateGroup("", -99, -99, 1, 1) #EndRegion #### create menu group ############################## #Region #### action buttons ################################# Local $id_Add_btn = GUICtrlCreateButton("Add", 70 * $g_i_Dpi, 244 * $g_i_Dpi, 75 * $g_i_Dpi, 25 * $g_i_Dpi) GUICtrlSetTip(-1, "Add the menu item") GUICtrlSetState(-1, $GUI_DISABLE) Local $id_Close_btn = GUICtrlCreateButton("Close", 160 * $g_i_Dpi, 244 * $g_i_Dpi, 75 * $g_i_Dpi, 25 * $g_i_Dpi) GUICtrlSetTip(-1, "Fuck It I have changed my mind") #EndRegion #### action buttons ################################# Local $h_StatusBar = _GUICtrlStatusBar_Create($h_AddItem_GUI) _GUICtrlStatusBar_SetText($h_StatusBar, 'Idle...') ; show the gui GUISetState(@SW_SHOW) ; set the gui on top of other windows WinSetOnTop($h_AddItem_GUI, '', 1) ;~ ; switch the gui to the add menu item one Switch_GUI($h_AddItem_GUI, 0, 1, $g_h_Main_GUI) Local $s_FileName = '' Local $s_SelectedMenuText = '' Local $s_SubMenuText = '' Local $s_MenuItemText = '' Local $s_IniKey = 'menuitem' Local $s_IniValue = '' Local $a_Filenames = '' ; array holding the selected file name(s) to add to menu Local $i_ItemCount = 0 ; menuitems info to add to ini section Local $i_NewMenuItems = 1 ; number of items to add Local $i_CurrentElement = 0 ; current element of the array holding the selected file name to add Local $i_FileAddCount = 1 ; number of files added to the menu Local $i_MenuListCurSel = 0 While 1 Switch GUIGetMsg() Case $GUI_EVENT_CLOSE, $id_Close_btn ExitLoop Case $id_FileSelect_btn ; open a file select dialog $s_FileName = FileOpenDialog('Please Select The File(s) To Be Added', "::{20D04FE0-3AEA-1069-A2D8-08002B30309D}", 'All(*.*)', $FD_MULTISELECT, '', $h_AddItem_GUI) If @error Then ContinueLoop ; get the file names $a_Filenames = StringSplit($s_FileName, '|') ; get total number of files to add $i_ItemCount = $a_Filenames[0] ; check if multiple files If Not @error Then ; multiple files ; recreate the file path from the array $s_FileName = $a_Filenames[1] & '\' & $a_Filenames[2] ; set which array element to start from used by add button) $i_CurrentElement = 2 ; subtract 1 from file count (ignore folder path) $i_ItemCount = $a_Filenames[0] - 1 Else ; single file $s_FileName = $a_Filenames[1] ; set which array element to start from used by add button) $i_CurrentElement = 1 EndIf ; update the label with the file path GUICtrlSetData($id_FileName_lbl, $s_FileName) GUICtrlSetTip($id_FileName_lbl, $s_FileName) ; add the file name to the menu item input If GUICtrlRead($id_MainMenuList_cbo) And $s_FileName Then GUICtrlSetState($id_Add_btn, $GUI_ENABLE) $s_FileName = File_GetNameFromString($s_FileName) GUICtrlSetData($id_MenuItemText_inp, StringTrimRight(File_GetNameFromString($s_FileName), 4)) _GUICtrlStatusBar_SetText($h_StatusBar, 'Adding (' & $i_FileAddCount & '/' & $i_ItemCount & '): ' & $s_FileName) Case $id_MainMenuList_cbo ; get the index of the current combo selection $i_MenuListCurSel = _GUICtrlComboBox_GetCurSel($id_MainMenuList_cbo) ; get the selected menu text $s_SelectedMenuText = GUICtrlRead($id_MainMenuList_cbo) If $s_SelectedMenuText = 'Add New Menu..' Then $i_MenuListCurSel = -1 ; get the add menu item gui position $a_WindowPos = WinGetPos($s_GUITitle) ; prompt for menu text $s_SelectedMenuText = InputBox('Create New Menu', 'Please enter the name of the new menu', '', ' M15', _ 350 * $g_i_Dpi, 150 * $g_i_Dpi, $a_WindowPos[0], $a_WindowPos[1], 0, $h_AddItem_GUI) ; check if user cancelled the input If Not @error And $s_SelectedMenuText Then ; set the index for the combo selection $i_MenuListCurSel = 0 ; add the new menu name to the list _GUICtrlComboBox_InsertString($id_MainMenuList_cbo, $s_SelectedMenuText, 0) EndIf ; select the last user selected menu _GUICtrlComboBox_SetCurSel($id_MainMenuList_cbo, $i_MenuListCurSel) EndIf ; check if add button is to be enabled If $s_SelectedMenuText And GUICtrlRead($id_FileName_lbl) Then GUICtrlSetState($id_Add_btn, $GUI_ENABLE) _GUICtrlStatusBar_SetText($h_StatusBar, 'Press add button') Else GUICtrlSetState($id_Add_btn, $GUI_DISABLE) EndIf Case $id_AddSubMenu_chk If GUICtrlRead($id_AddSubMenu_chk) = $GUI_CHECKED Then ; enable the input box GUICtrlSetState($id_AddSubMenu_inp, $GUI_ENABLE) Else ; disable the input and clear entered data GUICtrlSetState($id_AddSubMenu_inp, $GUI_DISABLE) EndIf ; prompt for menu text $s_SubMenuText = InputBox('Create Sub Menu', 'Please enter the name of the sub menu', '', ' M15', _ 350 * $g_i_Dpi, 150 * $g_i_Dpi, $a_WindowPos[0], $a_WindowPos[1], 0, $h_AddItem_GUI) If Not @error Then GUICtrlSetData($id_AddSubMenu_inp, $s_SubMenuText) Else GUICtrlSetState($id_AddSubMenu_chk, $GUI_UNCHECKED) GUICtrlSetState($id_AddSubMenu_inp, $GUI_DISABLE) EndIf Case $id_Add_btn $s_FileName = GUICtrlRead($id_FileName_lbl) ; get the current file location $s_SelectedMenuText = GUICtrlRead($id_MainMenuList_cbo) ; get the user selected menu $s_MenuItemText = GUICtrlRead($id_MenuItemText_inp) ; get the name for the menu item $s_SubMenuText = '' ; check if a sub menu is required If GUICtrlRead($id_AddSubMenu_chk) = $GUI_CHECKED Then $s_SubMenuText = GUICtrlRead($id_AddSubMenu_inp) ; decide whether to write a menuitem or a sub menu If $s_SubMenuText Then $s_IniKey = 'submenu' $s_IniValue = $s_SubMenuText & '|' & $s_MenuItemText & '|' & $s_FileName Else $s_IniKey = 'menuitem' $s_IniValue = $s_MenuItemText & '|' & $s_FileName EndIf ; get any previous menu item entries for the selected menu (enables writing duplicate keys in ini) $a_MenuItems = IniReadSection($g_s_INI, $s_SelectedMenuText) If @error Then ; section may not exist or is empty ; add the menu name to the list of menus to show IniWrite($g_s_INI, 'MainMenu', $s_SelectedMenuText, '') ; add the menu item settings to the ini IniWrite($g_s_INI, $s_SelectedMenuText, $s_IniKey, $s_IniValue) Else ; get the number of menu items currently in the menu section $i_ItemCount = $a_MenuItems[0][0] ; check if a seperator is required If GUICtrlRead($id_AddSeparator_chk) = $GUI_CHECKED Then $i_NewMenuItems = 2 ; resize the array for 1 or 2 new menu items ReDim $a_MenuItems[(($i_ItemCount + $i_NewMenuItems) + 1)][2] ; write the none seperator keys to the array first $a_MenuItems[($i_ItemCount + $i_NewMenuItems)][0] = $s_IniKey $a_MenuItems[($i_ItemCount + $i_NewMenuItems)][1] = $s_IniValue If GUICtrlRead($id_AddSeparator_chk) = $GUI_CHECKED Then ; set the ini key to write (for menuitem) $s_IniValue = '' If $s_SubMenuText Then $s_IniValue = $s_SubMenuText & '|' ; add the seperator info $a_MenuItems[$i_ItemCount + 1][0] = $s_IniKey $a_MenuItems[$i_ItemCount + 1][1] = $s_IniValue EndIf ; update the array row count $a_MenuItems[0][0] = UBound($a_MenuItems) - 1 ; rewrite the ini section from the new array IniWriteSection($g_s_INI, $s_SelectedMenuText, $a_MenuItems) EndIf ; check if all the selected file have been addded If $a_Filenames[0] = 1 Or $i_CurrentElement = $a_Filenames[0] Then ExitLoop #Region #### set data for next file addition #### ; reset how many items are to be added to the array $i_NewMenuItems = 1 ; increase number of files added $i_FileAddCount += 1 ; set next array element to be processed $i_CurrentElement += 1 ; build the file path from the array for the next file $s_FileName = $a_Filenames[1] & '\' & $a_Filenames[$i_CurrentElement] ; add the next file the file name GUICtrlSetData($id_FileName_lbl, $s_FileName) GUICtrlSetTip($id_FileName_lbl, $s_FileName) ; uncheck the sub menu box GUICtrlSetState($id_AddSubMenu_chk, $GUI_UNCHECKED) GUICtrlSetState($id_AddSubMenu_inp, $GUI_DISABLE) ; trim extension and update label GUICtrlSetData($id_MenuItemText_inp, File_GetNameFromString($s_FileName, 0)) ; uncheck the sub menu box GUICtrlSetState($id_AddSeparator_chk, $GUI_UNCHECKED) ; update the status bar text _GUICtrlStatusBar_SetText($h_StatusBar, 'Adding (' & $i_FileAddCount & '/' & ($a_Filenames[0] - 1) & '): ' & File_GetNameFromString($s_FileName)) #EndRegion #### set data for next file addition #### EndSwitch Sleep(10) WEnd GUISetState(@SW_HIDE, $h_AddItem_GUI) GUISetState(@SW_RESTORE, $g_h_Main_GUI) Switch_GUI($g_h_Main_GUI, 1, 0, $h_AddItem_GUI, 1) EndFunc ;==>MainMenu_AddItem Func MainMenu_CreateDynamic(ByRef $a_MenuEvents, $s_IniFile = $g_s_INI) ; get the menu items for the main menu Local $a_MainMenuItems = IniReadSection($s_IniFile, 'MainMenu') ; some error occured when reading skip menu creation If @error Then Return Local $a_MenuItems = '' ; array that holds the menu text and actions Local $a_MenuData = '' ; array that holds data about the menu items Local $h_MenuID = 0 ; main menu id where other menu are created Local $i_ItemID = 2000 ; menu id where the item will be created Local $h_SubmenuID = 0 ; submenu id where the menu item will be created Local $i_MenuItemCount = 0 ; number of menu items. used to resize array later Local $s_MenuText = '' ; text of the menus added to the main menu Local $s_MenuItemText = '' ; initially, menu type i.e menuitem or submenu. changes later Local $s_MenuItemString = '' ; string linked to the menu item, normally a file path Local $s_SubMenus = '' ; string to keep track of created sub menus to stop dupes ; loop through the user supplied menus For $x = 1 To $a_MainMenuItems[0][0] ; set the text for the menu $s_MenuText = $a_MainMenuItems[$x][0] ; create a menu (this will be where the items are added) $h_MenuID = _GUICtrlMenu_CreateMenu() ; now add any menu or sub menu items to the current main menu item $a_MenuItems = IniReadSection($s_IniFile, $s_MenuText) ; some error occured when reading continue with next menu item If @error Then ContinueLoop ; loop through the current main menus items For $y = 1 To $a_MenuItems[0][0] $s_MenuItemText = $a_MenuItems[$y][0] $s_MenuItemString = $a_MenuItems[$y][1] $a_MenuData = StringSplit($s_MenuItemString, '|') ; $a_MenuData[1] is the menu text, $a_MenuData[2] is the file name Switch $s_MenuItemText Case 'menuitem' ; create a menu item _GUICtrlMenu_AddMenuItem($h_MenuID, $a_MenuData[1], $i_ItemID) ; check the string isn't blank (item maybe a seperator) If $s_MenuItemString Then ; set the icon for the entry MainMenu_SetItemIcon($h_MenuID, $i_ItemID, $a_MenuData[2]) ; check the file is there and disable if missing If Not FileExists($a_MenuData[2]) And Not StringInStr($s_MenuItemString, 'http') Then _ _GUICtrlMenu_SetItemDisabled($h_MenuID, $i_ItemID, True, False) EndIf Case 'submenu' ; set the text for the sub menu $s_MenuItemText = $a_MenuData[1] ; check if the sub menu already exists If Not String_SearchForWords($s_SubMenus, $s_MenuItemText) Then $h_SubmenuID = _GUICtrlMenu_CreateMenu() ; add the created sub menu to a string, this is checked later to stop the creation of dupe menus $s_SubMenus &= $s_MenuItemText & '|' EndIf ; create the sub menu items _GUICtrlMenu_AddMenuItem($h_SubmenuID, $a_MenuData[2], $i_ItemID) ; add the menu item to the sub menu ; set the icon for the entry MainMenu_SetItemIcon($h_MenuID, $i_ItemID, $a_MenuData[3]) ; check the file is there and disable if missing If Not FileExists($a_MenuData[3]) And Not StringInStr($s_MenuItemString, 'http') Then _ _GUICtrlMenu_SetItemDisabled($h_SubmenuID, $i_ItemID, True, False) ; add the sub menu to the user selected menu _GUICtrlMenu_AddMenuItem($h_MenuID, $a_MenuData[1], $i_ItemID, $h_SubmenuID) Case Else ContinueLoop EndSwitch ; increase the menu item count $i_MenuItemCount += 1 ; add the item string value to the array $a_MenuEvents[$i_MenuItemCount][0] = $i_ItemID $a_MenuEvents[$i_MenuItemCount][1] = StringRegExpReplace($s_MenuItemString, "^.*\|", "") ; increase the the menu id $i_ItemID += 1 Next ; add the created menu to the main menu _GUICtrlMenu_AddMenuItem($g_h_MainMenu, $s_MenuText, 0, $h_MenuID) Next ; update the array total item count $a_MenuEvents[0][0] = $i_MenuItemCount ; resize array to include only added items ReDim $a_MenuEvents[$i_MenuItemCount + 1][2] ;~ _ArrayDisplay($a_MenuEvents, $i_MenuItemCount) EndFunc ;==>MainMenu_CreateDynamic Func MainMenu_DefaultEvents() Switch @GUI_CtrlId Case $g_id_FileAdd_mnu ; draw the Menu editor MainMenu_AddItem() Case $g_id_FileOpen_mnu ; open a file select dialog Local $s_FileName = FileOpenDialog('Please Select a File', "::{20D04FE0-3AEA-1069-A2D8-08002B30309D}", 'All(*.*)', 0, '', $g_h_Main_GUI) If @error Then Return ; minimize the main GUI GUISetState(@SW_MINIMIZE, $g_h_Main_GUI) ; open the file name ShellExecute($s_FileName) Case $g_id_FilePreferences_mnu ; minimize the main GUI GUISetState(@SW_MINIMIZE, $g_h_Main_GUI) ShellExecute($g_s_INI) EndSwitch EndFunc ;==>MainMenu_DefaultEvents Func MainMenu_DynamicEvents($i_ControlID) ; minimize the main GUI GUISetState(@SW_MINIMIZE, $g_h_Main_GUI) ; loop through the array and look for the clicked menu item For $i = 1 To $g_a_MenuEvents[0][0] If $i_ControlID = $g_a_MenuEvents[$i][0] Then ShellExecute($g_a_MenuEvents[$i][1]) ExitLoop EndIf Next EndFunc ;==>MainMenu_DynamicEvents Func MainMenu_SetItemIcon($h_Menu, $i_ControlID, $s_FilePath) ; set a default icon index (used if exe passsed) Local $i_IconIndex = 0 ; create a bitmap from the file Local $h_Bitmap = CreateBitmapFromIcon($s_FilePath, $i_IconIndex) ; set the menu icon _GUICtrlMenu_SetItemBmp($h_Menu, $i_ControlID, $h_Bitmap, False) EndFunc ;==>MainMenu_SetItemIcon Func StatusBar_SetText($s_Text) _GUICtrlStatusBar_SetText($g_h_Status_bar, $s_Text, 1) EndFunc ;==>StatusBar_SetText #Region #### misc functions ####### ; #FUNCTION# ==================================================================================================================== ; Name ..........: CreateBitmapFromIcon ; Description ...: Create a bitmap image from an icon ; Syntax ........: CreateBitmapFromIcon($iBackground, $sIcon, $iIndex, $iWidth, $iHeight) ; Return values .: Handle to the bitmap ; Author ........: Yashied ; Modified ......: Benners 28/12/2015 ; Remarks .......: ; Related .......: ; Link ..........: https://www.autoitscript.com/forum/topic/97365-how-to-convert-a-hicon-to-a-32-bit-hbitmap/?do=findComment&comment=700670 ; =============================================================================================================================== Func CreateBitmapFromIcon($sIcon, $iIndex = 0, $i_UseAssocIcon = 1, $iWidth = 16, $iHeight = 16) Local $hDC = _WinAPI_GetDC(0) Local $hBackDC = _WinAPI_CreateCompatibleDC($hDC) Local $hBitmap = _WinAPI_CreateSolidBitmap(0, _WinAPI_GetSysColor($COLOR_MENU), $iWidth, $iHeight) Local $hBackSv = _WinAPI_SelectObject($hBackDC, $hBitmap) Local $hIcon = 0 ; check if specific icons are to be used (i.e from shell32.dll) If $i_UseAssocIcon Then $hIcon = ExtractAssociatedIcon($g_h_Main_GUI, $sIcon) Else $hIcon = _WinAPI_ShellExtractIcon($sIcon, $iIndex, $iWidth, $iHeight) EndIf If Not @error Then _WinAPI_DrawIconEx($hBackDC, 0, 0, $hIcon, $iWidth, $iHeight, 0, 0, $DI_NORMAL) _WinAPI_DestroyIcon($hIcon) EndIf _WinAPI_SelectObject($hBackDC, $hBackSv) _WinAPI_ReleaseDC(0, $hDC) _WinAPI_DeleteDC($hBackDC) Return $hBitmap EndFunc ;==>CreateBitmapFromIcon ; #FUNCTION# ==================================================================================================================== ; Name ..........: ExtractAssociatedIcon ; Description ...: Extract the icon associated with a given file ; Syntax ........: ExtractAssociatedIcon($hWnd, $sFile) ; Parameters ....: $hWnd - A handle value. ; $sFile - A string value. ; Return values .: Handle to the icon ; Author ........: Rasim ; Modified ......: ; Remarks .......: ; Link ..........: https://www.autoitscript.com/forum/topic/87409-extractassociatedicon/?do=findComment&comment=627538 ; =============================================================================================================================== Func ExtractAssociatedIcon($hWnd, $sFile) Local $aRet = DllCall("shell32.dll", "hwnd", "ExtractAssociatedIcon", _ "hwnd", $hWnd, _ "str", $sFile, _ "short*", 0) Return $aRet[0] EndFunc ;==>ExtractAssociatedIcon Func File_GetNameFromString($s_Path, $i_Extension = 1) If $i_Extension Then Return StringRegExpReplace($s_Path, "^.*\\", "") Return StringRegExpReplace($s_Path, "^.*\\|\..*$", "") EndFunc ;==>File_GetNameFromString Func File_GetExtensionFromString($s_Path, $i_Period = 1) If $i_Period Then Return StringRegExpReplace($s_Path, "^.*\.", ".$1") Return StringRegExpReplace($s_Path, "^.*\.", "") EndFunc ;==>File_GetExtensionFromString Func GetDPI() ;; Get the current DPI (dots per inch) setting, and the ratio between it and ;; approximately 96 DPI. ;; ;; Return a 1D array of dimension 3. Indices zero is the dimension of the array ;; minus one. Indices 1 = the current DPI (an integer). Indices 2 is the ratio ;; should be applied to all GUI dimensions to make the GUI automatically adjust ;; to suit the various DPI settings. ;; ;; Author: Phillip123Adams ;; Posted: August, 17, 2005, originally developed 6/04/2004, ;; AutoIT 3.1.1.67 (but earlier v3.1.1 versions with DLLCall should work). ;; ;; Note: The dll calls are based upon code from the AutoIt3 forum from a post ;; by this-is-me on Nov 23 2004, 10:29 AM under topic "@Larry, Help!" Thanks ;; to this-is-me and Larry. Prior to that, I was obtaining the current DPI ;; from the Registry: ;; $iDPI = RegRead("HKCU\Control Panel\Desktop\WindowMetrics", "AppliedDPI") ;; Local $iDPIRat, $Logpixelsy = 90, $hWnd = 0 Local $hDC = DllCall("user32.dll", "long", "GetDC", "long", $hWnd) Local $aRet = DllCall("gdi32.dll", "long", "GetDeviceCaps", "long", $hDC[0], "long", $Logpixelsy) Local $iDPI = $aRet[0] $hDC = DllCall("user32.dll", "long", "ReleaseDC", "long", $hWnd, "long", $hDC) ;; Set a ratio for the GUI dimensions based upon the current DPI value. Select Case $iDPI = 0 $iDPI = 96 $iDPIRat = 94 Case $iDPI < 84 $iDPIRat = $iDPI / 105 Case $iDPI < 121 $iDPIRat = $iDPI / 96 Case $iDPI < 145 $iDPIRat = $iDPI / 95 Case Else $iDPIRat = $iDPI / 94 EndSelect ; Return the DPI Ration Return $iDPIRat EndFunc ;==>GetDPI Func String_SearchForWords($sTest, $sSearch) Local $sPattern = '(?i)^(?=.*\b' & StringReplace($sSearch, '|', '\b)(?=.*\b') & '\b)' Return StringRegExp($sTest, $sPattern) EndFunc ;==>String_SearchForWords Func Switch_GUI($h_NewGUI, $i_EventMode = 0, $i_DisableOldGUI = 0, $h_OldGUI = '', $i_DeleteOldGUI = 0) ; Change current GUI ($hwdGUI = GUI to change to, $iEventMode = Set GUIOnEventMode option 0/1, $iDisableMain = Disable the main OI GUI 0/1) Opt("GUIOnEventMode", $i_EventMode) ; Set on event mode. GUISwitch($h_NewGUI) ; Switch control to the specified GUI. GUISetState(@SW_ENABLE, $h_NewGUI) If $i_DisableOldGUI Then GUISetState(@SW_DISABLE, $h_OldGUI) ; Disable the main GUI. If $i_DeleteOldGUI Then GUIDelete($i_DeleteOldGUI) EndFunc ;==>Switch_GUI Func WM_COMMAND($hWnd, $iMsg, $wParam, $lParam) #forceref $hWnd, $iMsg, $lParam Local $i_ControlID = _WinAPI_LoWord($wParam) Switch $i_ControlID Case $g_id_FileAdd_mnu MainMenu_AddItem() Case $g_id_FileOpen_mnu ; open a file select dialog Local $s_FileName = FileOpenDialog('Please Select a File', "::{20D04FE0-3AEA-1069-A2D8-08002B30309D}", 'All(*.*)', 0, '', $g_h_Main_GUI) If @error Then Return ; minimize the main GUI GUISetState(@SW_MINIMIZE, $g_h_Main_GUI) ; open the file name ShellExecute($s_FileName) Case $g_id_FilePreferences_mnu ShellExecute($g_s_INI); Case $g_id_FileExit_mnu Main_GUI_Close() Case $i_ControlID >= 2000 MainMenu_DynamicEvents($i_ControlID) EndSwitch Return $GUI_RUNDEFMSG EndFunc ;==>WM_COMMAND #EndRegion #### misc functions ####### QuickLaunch.ini Link to comment Share on other sites More sharing options...
KaFu Posted December 28, 2015 Share Posted December 28, 2015 Regarding Icon handling I rely on this excellent UDF and let it do the work. OS: Win10-22H2 - 64bit - German, AutoIt Version: 3.3.16.1, AutoIt Editor: SciTE, Website: https://funk.eu AMT - Auto-Movie-Thumbnailer (2022-Nov-26) BIC - Batch-Image-Cropper (2023-Apr-01) COP - Color Picker (2009-May-21) DCS - Dynamic Cursor Selector (2024-Feb-16) HMW - Hide my Windows (2018-Sep-16) HRC - HotKey Resolution Changer (2012-May-16) ICU - Icon Configuration Utility (2018-Sep-16) SMF - Search my Files (2023-Jun-03) - THE file info and duplicates search tool SSD - Set Sound Device (2017-Sep-16) Link to comment Share on other sites More sharing options...
benners Posted December 29, 2015 Author Share Posted December 29, 2015 (edited) Yep, cheers KaFu, I managed to find the udf. The links were down in the original post which is why I went in another direction. I'll have a look through and see if I can make things fit. Edited December 29, 2015 by benners Link to comment Share on other sites More sharing options...
Recommended Posts
Create an account or sign in to comment
You need to be a member in order to leave a comment
Create an account
Sign up for a new account in our community. It's easy!
Register a new accountSign in
Already have an account? Sign in here.
Sign In Now