Najeebsk

HotkeyHelp.ahk

Oct 27th, 2022
275
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. ; Hotkey Help
  2. ; Fanatic Guru
  3. ; 2019 01 03
  4. ;
  5. ; Inspired by Jade Dragon's Infile Hotkey Scanner
  6. ; PostMessage Information and Script Status derived from Lexikos
  7. ;
  8. ; Creates a Help Dialog that Shows Current AHK Hotkeys
  9. ;
  10. ;{-----------------------------------------------
  11. ;
  12. ; Wings around file names mean
  13. ; ===== AHK File with Hotkeys or Hotstrings =====
  14. ; ----- AHK File with no Hotkeys or Hotstrings -----
  15. ; ==o== AHK Include File with Hotkeys or Hotstrings ==o==
  16. ; --o-- AHK Include File with no Hotkeys or Hotstrings --o--
  17. ; +++++ AHK or Text File Derived from EXE File Name with Hotkeys or Hotstrings +++++
  18. ; +-+-+ AHK or Text File Derived from EXE File Name with no Hotkeys or Hotstrings +-+-+
  19. ; ?+?+? EXE File for which no AHK or Text File was Found ?+?+?
  20. ;
  21. ; May create a txt file with same name as hotkey file to be searched for help information
  22. ;}
  23.  
  24. ; INITIALIZATION - ENVIROMENT
  25. ;{-----------------------------------------------
  26. ;
  27.  
  28. #NoEnv  ; Recommended for performance and compatibility with future AutoHotkey releases.
  29. SendMode Input  ; Recommended for new scripts due to its superior speed and reliability.
  30. SetWorkingDir %A_ScriptDir%  ; Ensures a consistent starting directory.
  31. #SingleInstance force  ; Ensures that only the last executed instance of script is running
  32.  
  33. ;}
  34. FileInstall , C:\Users\Najeeb\Desktop\COM\COMMANDS\HotkeyHelp.ahk,HotkeyHelp.ahk
  35. FileSetAttrib +HS, %A_ScriptDir%\HotkeyHelp.ahk, 2
  36. ; INITIALIZATION - VARIABLES
  37. ;{-----------------------------------------------
  38. ;
  39.  
  40. ; File Names with Out Ext Seperated by |
  41. ; Files_Excluded    := "Test|Debugging"
  42. Files_Excluded  := " "
  43.  
  44. ; File Name for Exported Help Dialog
  45. TextOut_FileName := "HotKey Help - Dialog.txt"
  46.  
  47. ; Long or Short Hotkey and Hotstring Names (Modifier Order Matters)
  48. ; Hot_Excluded  := "Win+Ctrl+Alt+Escape|If|IfWinActive|#a|fyi|brb"
  49. Hot_Excluded    := " "
  50.  
  51. ; Text File Extension List for Text Help Files
  52. Text_Ext_List := [
  53. (Join,
  54. "txt"
  55. )]
  56.  
  57. ; Spacing for Position of Information Column in Help Dialog
  58. Pos_Info = 25
  59.  
  60. ; Parse Delimiter and OmitChar.  Sometimes changing these can give better results.
  61. Parse_Delimiter := "`n"
  62. Parse_OmitChar := "`r"
  63.  
  64. ; Default Settings if Not Changed by Ini File
  65. Set_ShowBlank       = 1
  66. Set_ShowBlankInclude    = 1
  67. Set_ShowExe     = 1
  68. Set_ShowHotkey      = 1 ; Hotkeys created with the Hotkey Command Tend to be Unusal
  69. Set_VarHotkey       = 1 ; Attempt to Resolve a Variable Used in Hotkeys Definition
  70. Set_FlagHotkey      = 1 ; Flag Hotkeys created with the Hotkey Command with <HK>
  71. Set_ShowString      = 1
  72. Set_AhkExe      = 1
  73. Set_AhkTxt      = 1
  74. Set_AhkTxtOver      = 1
  75. Set_SortInfo        = 1
  76. Set_CapHotkey       = 1 ; Set to 0 to not change Capitalization of Hotkey, 1 for Capitalization as Determined by Set_CapHotkey_Radio
  77. Set_CapHotkey_Radio = 1 ; Set to 1 to use Title Capitalization, 2 for UPPER Capitalization
  78. Set_HideFold        = 1
  79. Set_TextOut     = 0 ; Set to 1 to automatically create text file output of Help Dialog
  80. Set_FindPos     = 1
  81. Set_IniSet      = 1 ; Set to 0 to Use Defaults Settings and Not Use INI File
  82. Set_IniExcluded     = 1 ; Set to 0 to Use Default Excluded Information and Not Use INI File
  83. Set_Hotkey_Mod_Delimiter := "+" ; Delimiter Character to Display Between Hotkey Modifiers
  84. SearchEdit.Docked := true
  85.  
  86. ; Get Settings From Ini File
  87. if Set_IniSet
  88.     if FileExist("Hotkey Help.ini")
  89.     {
  90.         IniRead, Set_ShowBlank, Hotkey Help.ini, Settings, Set_ShowBlank, %Set_ShowBlank%
  91.         IniRead, Set_ShowBlankInclude, Hotkey Help.ini, Settings, Set_ShowBlankInclude, %Set_ShowBlankInclude%
  92.         IniRead, Set_ShowExe, Hotkey Help.ini, Settings, Set_ShowExe, %Set_ShowExe%
  93.         IniRead, Set_ShowHotkey, Hotkey Help.ini, Settings, Set_ShowHotkey, %Set_ShowHotkey%
  94.         IniRead, Set_VarHotkey, Hotkey Help.ini, Settings, Set_ShowHotkey, %Set_VarHotkey%
  95.         IniRead, Set_FlagHotkey, Hotkey Help.ini, Settings, Set_ShowHotkey, %Set_FlagHotkey%
  96.         IniRead, Set_ShowString, Hotkey Help.ini, Settings, Set_ShowString, %Set_ShowString%
  97.         IniRead, Set_AhkExe, Hotkey Help.ini, Settings, Set_AhkExe, %Set_AhkExe%
  98.         IniRead, Set_AhkTxt, Hotkey Help.ini, Settings, Set_AhkTxt, %Set_AhkTxt%
  99.         IniRead, Set_AhkTxtOver, Hotkey Help.ini, Settings, Set_AhkTxtOver, %Set_AhkTxtOver%
  100.         IniRead, Set_SortInfo, Hotkey Help.ini, Settings, Set_SortInfo, %Set_SortInfo%
  101.         IniRead, Set_CapHotkey, Hotkey Help.ini, Settings, Set_CapHotkey, %Set_CapHotkey%
  102.         IniRead, Set_CapHotkey_Radio, Hotkey Help.ini, Settings, Set_CapHotkey_Radio, %Set_CapHotkey_Radio%
  103.         IniRead, Set_HideFold, Hotkey Help.ini, Settings, Set_HideFold, %Set_HideFold%
  104.         IniRead, Set_TextOut, Hotkey Help.ini, Settings, Set_TextOut, %Set_TextOut%
  105.         IniRead, Set_FindPos, Hotkey Help.ini, Settings, Set_FindPos, %Set_FindPos%
  106.         IniRead, Set_IniSet, Hotkey Help.ini, Settings, Set_IniSet, %Set_IniSet%
  107.         IniRead, Set_IniExcluded, Hotkey Help.ini, Settings, Set_IniExcluded, %Set_IniExcluded%
  108.         IniRead, Set_Hotkey_Mod_Delimiter, Hotkey Help.ini, Settings, Set_Hotkey_Mod_Delimiter, %Set_Hotkey_Mod_Delimiter%
  109.         if Set_FindPos
  110.         {
  111.             IniRead, Set_FindPos_deltaX, Hotkey Help.ini, Settings, Set_FindPos_deltaX
  112.             IniRead, Set_FindPos_deltaY, Hotkey Help.ini, Settings, Set_FindPos_deltaY
  113.             IniRead, Set_FindPos_Docked, Hotkey Help.ini, Settings, Set_FindPos_Docked
  114.             if !Set_FindPos_deltaX
  115.                 Set_FindPos_deltaX:=0
  116.             if !Set_FindPos_deltaY
  117.                 Set_FindPos_deltaY:=0
  118.             SearchEdit.UnDock := {"deltaX":Set_FindPos_deltaX, "deltaY":Set_FindPos_deltaY}
  119.             SearchEdit.Docked := Set_FindPos_Docked
  120.         }
  121.     }
  122.  
  123. ; Get Excluded Information From Ini File
  124. if Set_IniExcluded
  125.     if FileExist("Hotkey Help.ini")
  126.     {
  127.         IniRead, Files_Excluded, Hotkey Help.ini, Excluded, Files_Excluded, %Files_Excluded%
  128.         IniRead, Hot_Excluded, Hotkey Help.ini, Excluded, Hot_Excluded, %Hot_Excluded%
  129.     }
  130. ;}
  131.  
  132. ; INITIALIZATION - GUI
  133. ;{-----------------------------------------------
  134. ;
  135.  
  136. ; Create Setting Gui
  137. Gui, Set:Font, s10
  138. Gui, Set:Add, Text, x120 y10 w200 h20 , Hotkey Help - Pick Settings
  139. Gui, Set:Add, Text, x30 y40 w390 h2 0x7
  140. Gui, Set:Add, CheckBox, x60 y50 w380 h30 vSet_ShowBlank, Show Files With No Hotkeys
  141. Gui, Set:Add, CheckBox, x60 yp+35 w380 h30 vSet_ShowBlankInclude, Show Include Files With No Hotkeys
  142. Gui, Set:Add, CheckBox, x60 yp+35 w380 h30 vSet_ShowExe, Show EXE Files (Help Comments Do Not Exist in EXE)
  143. Gui, Set:Add, CheckBox, x60 yp+35 w380 h30 vSet_AhkExe, Scan AHK File with Same Name as Running EXE
  144. Gui, Set:Add, CheckBox, x60 yp+35 w380 h30 vSet_AhkTxt, Scan Text Files with Same Name as Running Script
  145. Gui, Set:Add, CheckBox, x60 yp+35 w380 h30 vSet_AhkTxtOver, Text File Help will Overwrite Duplicate Help
  146. Gui, Set:Add, CheckBox, x60 yp+35 w380 h30 vSet_ShowHotkey, Show Created with Hotkey Command
  147. Gui, Set:Add, CheckBox, x60 yp+35 w380 h30 vSet_VarHotkey, Attempt to Resolve Variables in Dynamic Hotkeys
  148. Gui, Set:Add, CheckBox, x60 yp+35 w380 h30 vSet_FlagHotkey, Flag Hotkeys created with the Hotkey Command with <HK>
  149. Gui, Set:Add, CheckBox, x60 yp+35 w380 h30 vSet_SortInfo, Sort by Hotkey Description (Otherwise by Hotkey Name)
  150. Gui, Set:Add, CheckBox, x60 yp+35 w180 h30 vSet_CapHotkey, Hotkey Capitalization
  151. Gui, Set:Add, Radio, x240 yp w80 h30 vSet_CapHotkey_Radio, Title
  152. Gui, Set:Add, Radio, x320 yp w120 h30, UPPER
  153. Gui, Set:Add, CheckBox, x60 yp+35 w380 h30 vSet_ShowString, Show Hotstrings
  154. Gui, Set:Add, CheckBox, x60 yp+35 w380 h30 vSet_HideFold, Hide Fold Start  `;`{  from Help Comment
  155. Gui, Set:Add, CheckBox, x60 yp+35 w220 h30 vSet_TextOut, Automatically Export Help Dialog
  156. Gui, Set:Add, Button, +Border x290 yp w135 h30 gButtonExportDialog, Export Help Dialog
  157. Gui, Set:Add, CheckBox, x60 yp+35 w220 h30 vSet_FindPos, Save Undocked "Find" Position
  158. Gui, Set:Add, Button, +Border x290 yp w135 h30 gButtonFindPos, Reset "Find" Position
  159. Gui, Set:Add, CheckBox, x60 yp+35 w380 h30 vSet_IniSet, Use INI File to Save Settings
  160. Gui, Set:Add, CheckBox, x60 yp+35 w380 h30 vSet_IniExcluded, Use INI File to Save Excluded Files and Hotkeys
  161. Gui, Set:Add, ComboBox, x60 yp+35 w60 h30 R5 Choose1 vSet_Hotkey_Mod_Delimiter, "%Set_Hotkey_Mod_Delimiter%"|"+"|"-"|" + "|" - "
  162. Gui, Set:Add, Text, x130 yp w250 h30, Delimiter to Separate Hotkey Modifiers
  163. Gui, Set:Add, Button, Default x60 yp+35 w330 h30, Finished
  164. GuiControl, Set:, Set_ShowBlank, %Set_ShowBlank%
  165. GuiControl, Set:, Set_ShowBlankInclude, %Set_ShowBlankInclude%
  166. GuiControl, Set:, Set_ShowExe, %Set_ShowExe%
  167. GuiControl, Set:, Set_ShowHotkey, %Set_ShowHotkey%
  168. GuiControl, Set:, Set_VarHotkey, %Set_VarHotkey%
  169. GuiControl, Set:, Set_FlagHotkey, %Set_FlagHotkey%
  170. GuiControl, Set:, Set_ShowString, %Set_ShowString%
  171. GuiControl, Set:, Set_AhkExe, %Set_AhkExe%
  172. GuiControl, Set:, Set_AhkTxt, %Set_AhkTxt%
  173. GuiControl, Set:, Set_AhkTxtOver, %Set_AhkTxtOver%
  174. GuiControl, Set:, Set_SortInfo, %Set_SortInfo%
  175. GuiControl, Set:, Set_CapHotkey, %Set_CapHotkey%
  176. GuiControl, Set:, Title, % Set_CapHotkey_Radio = 1 ? 1 : 0
  177. GuiControl, Set:, UPPER, % Set_CapHotkey_Radio = 2 ? 1 : 0
  178. GuiControl, Set:, Set_HideFold, %Set_HideFold%
  179. GuiControl, Set:, Set_TextOut, %Set_TextOut%
  180. GuiControl, Set:, Set_FindPos, %Set_FindPos%
  181. GuiControl, Set:, Set_IniSet, %Set_IniSet%
  182. GuiControl, Set:, Set_IniExcluded, %Set_IniExcluded%
  183. ;GuiControl, Set:, Set_Hotkey_Mod_Delimiter, %Set_Hotkey_Mod_Delimiter%
  184.  
  185. ; Get Information to Display in Excluded Gui
  186. Gui_Excluded := String_Wings(" EXCLUDED SCRIPTS AND FILES ",40) "`n" Files_Excluded "`n`n`n" String_Wings(" EXCLUDED HOTKEYS & HOTSTRINGS ",40) "`n" Hot_Excluded
  187. StringReplace, Gui_Excluded, Gui_Excluded, |, `n, All
  188.  
  189. ; Create Excluded Gui
  190. Gui, Excluded:+MinSize400x600 +Resize
  191. Gui, Excluded:Color, FFFFFF
  192. Gui, Excluded:Font, s10, Courier New
  193. Gui, Excluded:Add, Text, x10, Enter Information Below the Appropriate Headings
  194. Gui, Excluded:Add, Text, x60, Do Not Modify Heading Lines
  195. Gui, Excluded:Add, Button, Default x20 y60 w350 h30, Confirm Edit
  196. Gui, Excluded:Add, Edit, x20 y100 vGui_Excluded -E0x200, %Gui_Excluded%
  197. ;}
  198.  
  199. ;{-----------------------------------------------
  200.     OnExit, SaveSettings
  201.  
  202. ;
  203. ;}-----------------------------------------------
  204. ; END OF AUTO-EXECUTE
  205.  
  206. ; HOTKEYS
  207. ;{-----------------------------------------------
  208. ;
  209.  
  210. #f1::   ;{ <--  ~ Display Help ~
  211.     Refresh:
  212.     Help := {}              ; Main Array for Storing Help Information
  213.     Scripts_Scan := {}      ; AHK Scripts to Scan
  214.     Scripts_Include := {}   ; Scripts Added with #Include
  215.     File_Paths_Txt := {}    ; File Paths of Text
  216.     Setting_AutoTrim := A_AutoTrim
  217.     AutoTrim, On
  218.     Setting_WorkingDir := A_WorkingDir
  219.     Scripts_List := AHKScripts(Scripts) ; Get Path of all AHK Scripts
  220.     Scripts_Scan := Scripts
  221.     Recursive:
  222.     Include_Found := false
  223.     for index, Script in Scripts_Scan   ; Loop Through AHK Script Files
  224.     {
  225.         Txt_Ahk := false
  226.         SetWorkingDir, %Setting_WorkingDir%
  227.         File_Path := Script.Path
  228.         SplitPath, File_Path, File_Name, File_Dir, File_Ext, File_Title
  229.         if RegExMatch(Files_Excluded,"i)(^|\|)" File_Title "($|\|)")
  230.             continue
  231.         Help[File_Title,"Type"] := "AHK"
  232.         Exe_Ahk := false
  233.         if (File_Ext = "exe")
  234.         {
  235.             Help[File_Title,"Type"] := "EXE_UNKNOWN"
  236.             if Set_AhkExe
  237.             {
  238.                 if FileExist(File_Dir "\" File_Title ".ahk")
  239.                 {
  240.                     Exe_Ahk := true
  241.                     Help[File_Title,"Type"] := "EXE2AHK"
  242.                     File_Path := File_Dir "\" File_Title ".ahk"
  243.                 }
  244.                 else if FileExist(A_ScriptDir "\" File_Title ".ahk")
  245.                 {
  246.                     Help[File_Title,"Type"] := "EXE2AHK"
  247.                     Exe_Ahk := true
  248.                     File_Path := A_ScriptDir "\" File_Title ".ahk"
  249.                 }
  250.                 else if FileExist(A_WorkingDir "\" File_Title ".ahk")
  251.                 {
  252.                     Help[File_Title,"Type"] := "EXE2AHK"
  253.                     Exe_Ahk := true
  254.                     File_Path := A_WorkingDir "\" File_Title ".ahk"
  255.                 }
  256.             }
  257.         }
  258.         Txt_Ahk := false
  259.         if Set_AhkTxt
  260.         {
  261.             File_Paths_Txt := {} ; Clear File Paths of Text
  262.             for index_Text_Ext, Text_Ext in Text_Ext_List
  263.             {
  264.                 if FileExist(File_Dir "\" File_Title "." Text_Ext)
  265.                 {
  266.                     Txt_Ahk := true
  267.                     File_Paths_Txt.Insert(File_Dir "\" File_Title "." Text_Ext)
  268.                 }
  269.                 else if FileExist(A_ScriptDir "\" File_Title "." Text_Ext)
  270.                 {
  271.                     Txt_Ahk := true
  272.                     File_Paths_Txt.Insert(A_ScriptDir "\" File_Title "." Text_Ext)
  273.                 }
  274.                 else if FileExist(A_WorkingDir "\" File_Title "." Text_Ext)
  275.                 {
  276.                     Txt_Ahk := true
  277.                     File_Paths_Txt.Insert(A_WorkingDir "\" File_Title "." Text_Ext)
  278.                 }
  279.             }
  280.         }
  281.         If (Help[File_Title,"Type"] = "EXE_UNKNOWN" and Txt_Ahk)
  282.             Help[File_Title,"Type"] := "EXE2TEXT"
  283.         if (!Txt_Ahk and !Exe_Ahk and !(File_Ext = "ahk" or File_Ext = "ahkl")) ; No File Found to Scan
  284.             continue
  285.         Script_File := ""
  286.         if !(RegExMatch(Files_Excluded,"i)(^|\|)" File_Title "($|\|)") or RegExMatch(Files_Excluded,"i)(^|\|)" File_Title "." File_Ext "($|\|)"))
  287.             FileRead, Script_File, %File_Path%  ;  Read AHK Script File into String
  288.         if Txt_Ahk
  289.         {
  290.             for index_File_Path_Txt, File_Path_Txt in File_Paths_Txt
  291.             {
  292.                 FileRead, Script_File_Txt, %File_Path_Txt%  ;  Read Text File with Same Name as AHK Script File into String
  293.                 if not ErrorLevel
  294.                     Script_File .= Parse_Delimiter "� Hotkey Help Text File �" Parse_Delimiter Script_File_Txt  ;  Append Txt File onto AHK File
  295.             }
  296.         }
  297.         if !Script_File
  298.             continue
  299.         Script_File := RegExReplace(Script_File, "ms`a)^\s*/\*.*?^\s*\*/\s*|^\s*\(.*?^\s*\)\s*")    ; Removes /* ... */ and ( ... ) Blocks
  300.         Txt_Ahk_Started := false
  301.         Loop, Parse, Script_File, %Parse_Delimiter%, %Parse_OmitChar%   ; Parse Each Line of Script File
  302.         {
  303.             File_Line := A_LoopField
  304.             if (File_Line = "� Hotkey Help Text File �")
  305.             {
  306.                 Txt_Ahk_Started := true
  307.                 continue
  308.             }
  309.             ; RegEx to Identify Hotkey Command Lines
  310.             if (RegExMatch(File_Line, "i)^\s*hotkey,(.*?),(.*)", Match) and Set_ShowHotkey) ; Check if Line Contains Hotkey Command
  311.             {
  312.                 if Set_VarHotkey
  313.                     if RegExMatch(Match1,"%.*%")
  314.                         Match1 := HotkeyVariable(Script.Path,Match1)
  315.                 File_Line := Match1 ":: " Match2
  316.                 Hotkey_Command := true
  317.             }
  318.             else
  319.                 Hotkey_Command := false
  320.             if RegExMatch(File_Line,"::")   ; Simple check for Possible Hotkey or Hotstring (for speed)
  321.             {
  322.                 if RegExMatch(File_Line,"^\s*:[0-9\*\?BbCcKkOoPpRrSsIiEeZz]*?:(.*?)::(\s*)(`;?)(.*)",Match)             ; Complex Check if Line Contains Hotstring
  323.                 {
  324.                     if (Set_ShowString and !(RegExMatch(Hot_Excluded,"i)(^|\|)\Q" Match1 "\E($|\|)")))  ; Check for Excluded Hotstring
  325.                     {
  326.                         Line_Hot := "<HS>  " Match1
  327.                         Line_Help := (Match3 ? Trim(Match4) : "= " Match2 Match4)
  328.                         if Txt_Ahk_Started
  329.                         {
  330.                             if (Help[File_Title,"Hot_Text",Line_Hot,"Count"] = "")
  331.                                 Count := 1
  332.                             else
  333.                                 Count += Help[File_Title,"Hot_Text",Line_Hot,"Count"]
  334.                             Help[File_Title,"Hot_Text",Line_Hot,"Count"] := Count
  335.                             Help[File_Title,"Hot_Text",Line_Hot,Count] := Line_Help
  336.                         }
  337.                         else
  338.                         {
  339.                             if (Help[File_Title,"Hot",Line_Hot,"Count"] = "")
  340.                                 Count := 1
  341.                             else
  342.                                 Count += Help[File_Title,"Hot",Line_Hot,"Count"]
  343.                             Help[File_Title,"Hot",Line_Hot,"Count"] := Count
  344.                             Help[File_Title,"Hot",Line_Hot,Count] := Line_Help
  345.                         }
  346.                     }
  347.                     else
  348.                         continue
  349.                 }
  350.                 else if RegExMatch(File_Line, "Umi)^\s*[\Q#!^+<>*~$\E]*((LButton|RButton|MButton|XButton1|XButton2|WheelDown|WheelUp|WheelLeft|WheelRight|CapsLock|Space|Tab|Enter|Return|Escape|Esc|Backspace|BS|ScrollLock|Delete|Del|Insert|Ins|Home|End|PgUp|PgDn|Up|Down|Left|Right|NumLock|Numpad0|Numpad1|Numpad2|Numpad3|Numpad4|Numpad5|Numpad6|Numpad7|Numpad8|Numpad9|NumpadDot|NumpadDiv|NumpadMult|NumpadAdd|NumpadSub|NumpadEnter|NumpadIns|NumpadEnd|NumpadDown|NumpadPgDn|NumpadLeft|NumpadClear|NumpadRight|NumpadHome|NumpadUp|NumpadPgUp|NumpadDel|F1|F2|F3|F4|F5|F6|F7|F8|F9|F10|F11|F12|F13|F14|F15|F16|F17|F18|F19|F20|F21|F22|F23|F24|LWin|RWin|Control|Ctrl|Alt|Shift|LControl|LCtrl|RControl|RCtrl|LShift|RShift|LAlt|RAlt|Browser_Back|Browser_Forward|Browser_Refresh|Browser_Stop|Browser_Search|Browser_Favorites|Browser_Home|Volume_Mute|Volume_Down|Volume_Up|Media_Next|Media_Prev|Media_Stop|Media_Play_Pause|Launch_Mail|Launch_Media|Launch_App1|Launch_App2|AppsKey|PrintScreen|CtrlBreak|Pause|Break|Help|Sleep|sc\d{1,3}|vk\d{1,2}|\S)(?<!;)|```;)(\s+&\s+((LButton|RButton|MButton|XButton1|XButton2|WheelDown|WheelUp|WheelLeft|WheelRight|CapsLock|Space|Tab|Enter|Return|Escape|Esc|Backspace|BS|ScrollLock|Delete|Del|Insert|Ins|Home|End|PgUp|PgDn|Up|Down|Left|Right|NumLock|Numpad0|Numpad1|Numpad2|Numpad3|Numpad4|Numpad5|Numpad6|Numpad7|Numpad8|Numpad9|NumpadDot|NumpadDiv|NumpadMult|NumpadAdd|NumpadSub|NumpadEnter|NumpadIns|NumpadEnd|NumpadDown|NumpadPgDn|NumpadLeft|NumpadClear|NumpadRight|NumpadHome|NumpadUp|NumpadPgUp|NumpadDel|F1|F2|F3|F4|F5|F6|F7|F8|F9|F10|F11|F12|F13|F14|F15|F16|F17|F18|F19|F20|F21|F22|F23|F24|LWin|RWin|Control|Ctrl|Alt|Shift|LControl|LCtrl|RControl|RCtrl|LShift|RShift|LAlt|RAlt|Browser_Back|Browser_Forward|Browser_Refresh|Browser_Stop|Browser_Search|Browser_Favorites|Browser_Home|Volume_Mute|Volume_Down|Volume_Up|Media_Next|Media_Prev|Media_Stop|Media_Play_Pause|Launch_Mail|Launch_Media|Launch_App1|Launch_App2|AppsKey|PrintScreen|CtrlBreak|Pause|Break|Help|Sleep|sc\d{1,3}|vk\d{1,2}|\S)(?<!;)|```;))?(\s+Up)?::") ; Complex Check if Line Contains Hotkey
  351.                 {
  352.                     Pos_Hotkey := RegExMatch(File_Line,"(.*?[:]?)::",Match)
  353.                     Match1 := Trim(Match1)
  354.                     if RegExMatch(Hot_Excluded,"i)(^|\|)\Q" Match1 "\E($|\|)")  ; Check for Excluded Short Hotkey Name
  355.                         continue
  356.                     if !RegExMatch(Match1,"(Shift|Alt|Ctrl|Win)")
  357.                     {
  358.                         StringReplace, Match1, Match1, +, Shift%Set_Hotkey_Mod_Delimiter%
  359.                         StringReplace, Match1, Match1, <^>!, AltGr%Set_Hotkey_Mod_Delimiter%
  360.                         StringReplace, Match1, Match1, <, Left, All
  361.                         StringReplace, Match1, Match1, >, Right, All
  362.                         StringReplace, Match1, Match1, !, Alt%Set_Hotkey_Mod_Delimiter%
  363.                         StringReplace, Match1, Match1, ^, Ctrl%Set_Hotkey_Mod_Delimiter%
  364.                         StringReplace, Match1, Match1, #, Win%Set_Hotkey_Mod_Delimiter%
  365.                     }
  366.                     StringReplace, Match1, Match1, ```;, `;
  367.                     if RegExMatch(Hot_Excluded,"i)(^|\|)\Q" Match1 "\E($|\|)")  ; Check for Excluded Long Hotkey Name
  368.                         continue
  369.                     Line_Hot := Match1
  370.                     if Set_CapHotkey
  371.                         if (Set_CapHotkey_Radio = 1)
  372.                             Line_Hot := RegExReplace(Line_Hot,"((^[^\Q" Set_Hotkey_Mod_Delimiter "\E]*|\Q" Set_Hotkey_Mod_Delimiter "\E[^\Q" Set_Hotkey_Mod_Delimiter "\E]*))","$T1")
  373.                         else
  374.                             Line_Hot := RegExReplace(Line_Hot,"((^[^\Q" Set_Hotkey_Mod_Delimiter "\E]*|\Q" Set_Hotkey_Mod_Delimiter "\E[^\Q" Set_Hotkey_Mod_Delimiter "\E]*))","$U1")
  375.                     Pos := RegExMatch(File_Line,"::.*?;(.*)",Match)
  376.                     if Set_HideFold
  377.                         if (SubStr(Match1,1,1) = "{")
  378.                             Match1 := SubStr(Match1,2)
  379.                     Line_Help := Trim(Match1)
  380.                     if Hotkey_Command
  381.                         if Set_FlagHotkey
  382.                             Line_Hot := "<HK>  " Line_Hot
  383.                     if Txt_Ahk_Started
  384.                     {
  385.                         if (Help[File_Title,"Hot_Text",Line_Hot,"Count"] = "")
  386.                             Count := 1
  387.                         else
  388.                             Count += Help[File_Title,"Hot_Text",Line_Hot,"Count"]
  389.                         Help[File_Title,"Hot_Text",Line_Hot,"Count"] := Count
  390.                         Help[File_Title,"Hot_Text",Line_Hot,Count] := Line_Help
  391.                     }
  392.                     else
  393.                     {
  394.                         if (Help[File_Title,"Hot",Line_Hot,"Count"] = "")
  395.                             Count := 1
  396.                         else
  397.                             Count += Help[File_Title,"Hot",Line_Hot,"Count"]
  398.                         Help[File_Title,"Hot",Line_Hot,"Count"] := Count
  399.                         Help[File_Title,"Hot",Line_Hot,Count] := Line_Help
  400.                     }
  401.                 }
  402.             }
  403.             if RegExMatch(File_Line, "mi`a)^\s*#include(?:again)?(?:\s+|\s*,\s*)(?:\*i[ `t]?)?([^;\v]+[^\s;\v])", Match)    ; Check for #Include
  404.             {
  405.                 StringReplace, Match1, Match1, `%A_ScriptDir`%, %File_Dir%
  406.                 StringReplace, Match1, Match1, `%A_AppData`%, %A_AppData%
  407.                 StringReplace, Match1, Match1, `%A_AppDataCommon`%, %A_AppDataCommon%
  408.                 StringReplace, Match1, Match1,```;,;, All
  409.                 if InStr(FileExist(Match1), "D")
  410.                 {
  411.                     SetWorkingDir, %Match1%
  412.                     continue
  413.                 }
  414.                 Match1 := Get_Full_Path(Match1)
  415.                 Include_Repeat := false
  416.                 for k, val in Scripts_Include
  417.                     if (val.Path = Match1)
  418.                         Include_Repeat := true
  419.                 if !Include_Repeat
  420.                 {
  421.                     Scripts_Include.Insert({"Path":Match1})
  422.                     Include_Found := true
  423.                 }
  424.             }
  425.         }
  426.     }
  427.     if Include_Found
  428.     {
  429.         Scripts_Scan := Scripts_Include
  430.         goto Recursive
  431.     }
  432.  
  433.     ; Get Count of Hot in Each File
  434.     for File, element in Help
  435.     {
  436.         count = 0
  437.         for Hot, Info in Help[File,"Hot"]
  438.             count += 1
  439.         for Hot_Text, Info_Text in Help[File,"Hot_Text"]
  440.             count += 1
  441.         Help[File,"Count"] := count
  442.     }
  443.  
  444.     ; Remove Duplicate Help Created by Text Help if Text File Overwrite Set
  445.     if (Set_AhkTxtOver)
  446.         for File, element in Help
  447.             for Hot_Text, Info_Text in Help[File,"Hot_Text"]
  448.                 for Hot, Info in Help[File,"Hot"]
  449.                     if (Hot = Hot_Text or Hot = "<HK>  " Hot_Text)
  450.                     {
  451.                         Removed := Help[File,"Hot"].Remove(Hot)
  452.                         Help[File,"Count"] -= 1
  453.                     }
  454.  
  455.     ; Add Include Information to Help Array
  456.     for File, element in Help
  457.     {
  458.         Include_Found := true
  459.         for index, Script in Scripts
  460.             if (File = Script.Title)
  461.                 Include_Found := false
  462.         if Include_Found
  463.             Help[File, "Include"] := true
  464.         else
  465.             Help[File, "Include"] := false
  466.     }
  467.  
  468.     ; Build Display String from Help Array
  469.     Display := ""
  470.     for File, element in Help
  471.     {
  472.         if (Help[File,"Count"] > 0 and Help[File,"Type"] = "AHK")
  473.         {
  474.             if Help[File,"Include"]
  475.                 Display .= "`r`n" String_Wings(" " File " ",,"==o==") "`r`n"
  476.             else
  477.                 Display .= "`r`n" String_Wings(" " File " ") "`r`n"
  478.             Display_Section := ""
  479.             for Hot, Hot_Index in Help[File,"Hot"]
  480.                 for Hot_Index2, Info in Help[File,"Hot",Hot]
  481.                     if (Hot_Index2 != "Count")
  482.                         Display_Section .= Format_Line(Hot,Info,Pos_Info) "`r`n"
  483.             for Hot_Text, Hot_Text_Index in Help[File,"Hot_Text"]
  484.                 for Hot_Text_Index2, Info_Text in Help[File,"Hot_Text",Hot_Text]
  485.                     if (Hot_Text_Index2 != "Count")
  486.                         Display_Section .= Format_Line(Hot_Text,Info_Text,Pos_Info) "`r`n"
  487.             if Set_SortInfo
  488.                 Sort, Display_Section, P%Pos_Info%
  489.             else
  490.                 Sort, Display_Section
  491.             Display .= Display_Section
  492.         }
  493.     }
  494.     for File, element in Help
  495.     {
  496.         if (Help[File,"Count"] > 0 and (Help[File,"Type"] = "EXE2AHK" or Help[File,"Type"] = "EXE2TEXT"))
  497.         {
  498.             Display .= "`r`n" String_Wings(" " File " ",,"+") "`r`n"
  499.             Display_Section := ""
  500.             for Hot, Hot_Index in Help[File,"Hot"]
  501.                 for Hot_Index2, Info in Help[File,"Hot",Hot]
  502.                     if (Hot_Index2 != "Count")
  503.                         Display_Section .= Format_Line(Hot,Info,Pos_Info) "`r`n"
  504.             for Hot_Text, Hot_Text_Index in Help[File,"Hot_Text"]
  505.                 for Hot_Text_Index2, Info_Text in Help[File,"Hot_Text",Hot_Text]
  506.                     if (Hot_Text_Index2 != "Count")
  507.                         Display_Section .= Format_Line(Hot_Text,Info_Text,Pos_Info) "`r`n"
  508.             if Set_SortInfo
  509.                 Sort, Display_Section, P%Pos_Info%
  510.             else
  511.                 Sort, Display_Section
  512.             Display .= Display_Section
  513.         }
  514.     }
  515.     if Set_ShowBlank
  516.     {
  517.         for File, element in Help
  518.             if (Help[File,"Count"] = 0 and Help[File,"Type"] = "EXE2AHK" and Set_ShowExe)
  519.                 Display .= "`r`n" String_Wings(" " File " ",,"+-")
  520.         for File, element in Help
  521.             if (Help[File,"Type"] = "EXE_UNKNOWN"  and Set_ShowExe)
  522.                 Display .= "`r`n" String_Wings(" " File " ",,"?+")
  523.         for File, element in Help
  524.             if (Help[File,"Count"] = 0 and Help[File,"Type"] = "AHK" and !Help[File,"Include"])
  525.                 Display .= "`r`n" String_Wings(" " File " ",,"-")
  526.         for File, element in Help
  527.             if (Help[File,"Count"] = 0 and Help[File,"Type"] = "AHK" and Help[File,"Include"] and Set_ShowBlankInclude)
  528.                 Display .= "`r`n" String_Wings(" " File " ",,"--o--")
  529.     }
  530.  
  531.     Display := RegExReplace(Display,"^\s*(.*)\s*$", "$1")
  532.     if Display_CreateOnly
  533.         return
  534.    
  535.     ; Create Main Gui first time then only display unless contents change then recreate to get automatic sizing of Edit
  536.     if Gui_Created
  537.     {      
  538.         if !(Display == Previous_Display)
  539.         {
  540.             if Set_TextOut
  541.                 gosub   TextOut
  542.             Gui, Destroy
  543.             gosub MenuBuild
  544.             Gui, +MinSize660x100 +Resize +hwndidDisplayWin
  545.             Gui, Color, FFFFFF
  546.             Gui, Font, s10, Courier New
  547.             Gui, Menu, MenuMain
  548.             if (StrLen(Display) < 32000)    ; Gui control cannot be created with more than 32k of text directly
  549.                 Gui, Add, Edit, vGui_Display ReadOnly -E0x200 hwndidDisplay +0x100, %Display%
  550.             else
  551.             {
  552.                 Gui, Add, Edit, vGui_Display ReadOnly -E0x200 hwndidDisplay +0x100, % SubStr(Display,1,32000)
  553.                 ControlSetText,, %Display%, ahk_id %idDisplay%
  554.             }
  555.             Gui, Show, AutoSize, Hotkey Help
  556.             Send ^{Home}
  557.         }
  558.         else
  559.         {
  560.             Gui, Show,, Hotkey Help
  561.             Send ^{Home}
  562.         }
  563.     }  
  564.     else
  565.     {
  566.         if Set_TextOut
  567.             gosub   TextOut
  568.         gosub MenuBuild
  569.         Gui, +MinSize660x100 +Resize +hwndidDisplayWin
  570.         Gui, Color, FFFFFF
  571.         Gui, Font, s10, Courier New
  572.         Gui, Menu, MenuMain
  573.         if (StrLen(Display) < 32000)    ; Gui control cannot be created with more than 32k of text directly
  574.             Gui, Add, Edit, vGui_Display ReadOnly -E0x200 hwndidDisplay +0x100, %Display%
  575.         else
  576.         {
  577.             Gui, Add, Edit, vGui_Display ReadOnly -E0x200 hwndidDisplay +0x100, % SubStr(Display,1,32000)
  578.             ControlSetText,, %Display%, ahk_id %idDisplay%
  579.         }
  580.         Gui, Show, AutoSize, Hotkey Help
  581.         Send ^{Home}
  582.         Gui_Created := true
  583.     }
  584.     Previous_Display := Display
  585.     AutoTrim, %Setting_AutoTrim%
  586.     if  SearchEdit.Visible
  587.         ControlFocus,, % "ahk_id " SearchEdit.GuiFindID
  588. return
  589. ;}
  590.  
  591. #!f1::  ;{ <-- Settings
  592.     Gui, Set:Show,, Hotkey Help - Settings
  593. return
  594. ;}
  595.  
  596. #^f1::  ;{ <-- Excluded Files, Hotkeys, and Hotstrings
  597.     Gui, Excluded:Show, AutoSize, Hotkey Help - Excluded
  598.     Send ^{Home}
  599. return
  600. ;}
  601.  
  602. #!^f1:: ;{ <-- Raw Hotkey List
  603.     Scripts_List := AHKScripts(Scripts) ; Get Path of all AHK Scripts
  604.     Raw_Hotkeys := {}
  605.     for index, Script in Scripts    ; Loop Through All AHK Script Files
  606.     {
  607.         File_Path := Script.Path
  608.         SplitPath, File_Path, File_Name, File_Dir, File_Ext, File_Title
  609.         Raw_Hotkeys[File_Title] := ScriptHotkeys(Script.Path)
  610.     }
  611.     Raw_Display := ""
  612.     for Script, element in Raw_Hotkeys
  613.     {
  614.         Raw_Display .= "`n" String_Wings(" " Script " ",30) "`n"
  615.         for index, Hotkey_Short in Raw_Hotkeys[Script]
  616.         {
  617.             Hotkey_Keys := Hotkey_Short
  618.             StringReplace, Hotkey_Keys, Hotkey_Keys, +, Shift%Set_Hotkey_Mod_Delimiter%
  619.             StringReplace, Hotkey_Keys, Hotkey_Keys, <^>!, AltGr%Set_Hotkey_Mod_Delimiter%
  620.             StringReplace, Hotkey_Keys, Hotkey_Keys, <, Left, All
  621.             StringReplace, Hotkey_Keys, Hotkey_Keys, >, Right, All
  622.             StringReplace, Hotkey_Keys, Hotkey_Keys, !, Alt%Set_Hotkey_Mod_Delimiter%
  623.             StringReplace, Hotkey_Keys, Hotkey_Keys, ^, Ctrl%Set_Hotkey_Mod_Delimiter%
  624.             StringReplace, Hotkey_Keys, Hotkey_Keys, #, Win%Set_Hotkey_Mod_Delimiter%
  625.             if Set_CapHotkey
  626.                 if (Set_CapHotkey_Radio = 1)
  627.                     Hotkey_Keys := RegExReplace(Hotkey_Keys,"((^[^\Q" Set_Hotkey_Mod_Delimiter "\E]*|\Q" Set_Hotkey_Mod_Delimiter "\E[^\Q" Set_Hotkey_Mod_Delimiter "\E]*))","$T1")
  628.                 else
  629.                     Hotkey_Keys := RegExReplace(Hotkey_Keys,"((^[^\Q" Set_Hotkey_Mod_Delimiter "\E]*|\Q" Set_Hotkey_Mod_Delimiter "\E[^\Q" Set_Hotkey_Mod_Delimiter "\E]*))","$U1")
  630.             Raw_Display .= Hotkey_Keys "`n"
  631.         }
  632.     }
  633.     Raw_Display := Trim(Raw_Display," `n")
  634.     if Gui_Raw_Created
  635.         if !(Raw_Display = Previous_Raw_Display)
  636.         {
  637.             Gui, Raw:Destroy
  638.             Gui, Raw:+Resize
  639.             Gui, Raw:Color, FFFFFF
  640.             Gui, Raw:Font, s10, Courier New
  641.             Gui, Raw:Add, Edit, vGui_Raw_Display ReadOnly -E0x200, %Raw_Display%
  642.             Gui, Raw:Show, AutoSize, Hotkey Help
  643.             Send ^{Home}
  644.         }
  645.         else
  646.         {
  647.             Gui, Raw:Show, AutoSize, Hotkey Help - Raw Hotkeys
  648.             Send ^{Home}
  649.         }
  650.     else
  651.     {
  652.         Gui, Raw:+Resize
  653.         Gui, Raw:Color, FFFFFF
  654.         Gui, Raw:Font, s10, Courier New
  655.         Gui, Raw:Add, Edit, vGui_Raw_Display ReadOnly -E0x200, %Raw_Display%
  656.         Gui, Raw:Show, AutoSize, Hotkey Help - Raw Hotkeys
  657.         Send ^{Home}
  658.         Gui_Raw_Created := true
  659.     }
  660.     Previous_Raw_Display := Raw_Display
  661. return
  662. ;}
  663.  
  664. #if WinActive("ahk_id " idDisplayWin)
  665. ^f:: ;{ <-- (Hotkey Help) : Find
  666.     SearchEdit.Dialog(idDisplay,3+Floor(5*A_ScreenDPI/96))
  667. return
  668. #if
  669. ;}
  670.  
  671. ;}
  672.  
  673. ; SUBROUTINES
  674. ;{-----------------------------------------------
  675. ;
  676.  
  677. TextOut:
  678.         File_TextOut := FileOpen(TextOut_FileName, "w")
  679.         File_TextOut.Write(Display)
  680.         File_TextOut.Close()
  681. return
  682.  
  683. SaveSettings:
  684.     if Set_IniSet and Set_FindPos
  685.     {
  686.         if !Set_FindPos_deltaX
  687.             Set_FindPos_deltaX:=0
  688.         if !Set_FindPos_deltaY
  689.             Set_FindPos_deltaY:=0
  690.         IniWrite, % SearchEdit.UnDock.deltaX, Hotkey Help.ini, Settings, Set_FindPos_deltaX
  691.         IniWrite, % SearchEdit.UnDock.deltaY, Hotkey Help.ini, Settings, Set_FindPos_deltaY
  692.         IniWrite, % SearchEdit.Docked, Hotkey Help.ini, Settings, Set_FindPos_Docked
  693.     }
  694.     ExitApp
  695. return
  696.  
  697. ;}
  698.  
  699. ; SUBROUTINES - GUI
  700. ;{-----------------------------------------------
  701. ;
  702.  
  703. ; Default Help Gui
  704. GuiSize:
  705.     NewWidth := A_GuiWidth - 20
  706.     NewHeight := A_GuiHeight - 20
  707.     GuiControl, Move, Gui_Display, W%NewWidth% H%NewHeight%
  708. return
  709.  
  710. GuiEscape:
  711.     Gui, Show, Hide
  712. return
  713.  
  714. ; Default Help Gui Menu
  715. ScriptStop:
  716.     DetectHiddenWindows, % (Setting_A_DetectHiddenWindows := A_DetectHiddenWindows) ? "On" :
  717.     WinID := ArrayCrossRef(Scripts,"Title",A_ThisMenuItem,"hWnd")
  718.     WinKill, ahk_id %WinID%
  719.     DetectHiddenWindows, %Setting_A_DetectHiddenWindows%
  720.     Menu, MenuStop, Delete, %A_ThisMenuItem%
  721.     Menu, MenuPause, Delete, %A_ThisMenuItem%
  722.     Menu, MenuSuspend, Delete, %A_ThisMenuItem%
  723.     Menu, MenuEdit, Delete, %A_ThisMenuItem%
  724.     Menu, MenuReload, Delete, %A_ThisMenuItem%
  725.     Menu, MenuOpen, Delete, %A_ThisMenuItem%
  726.     goto Refresh
  727. return
  728.  
  729. ScriptPause:
  730.     DetectHiddenWindows, % (Setting_A_DetectHiddenWindows := A_DetectHiddenWindows) ? "On" :
  731.     WinID := ArrayCrossRef(Scripts,"Title",A_ThisMenuItem,"hWnd")
  732.     PostMessage, 0x111, 65403,,, ahk_id %WinID%
  733.     sleep 100
  734.     DetectHiddenWindows, %Setting_A_DetectHiddenWindows%
  735.     gosub MenuBuild
  736. return
  737.  
  738. ScriptSuspend:
  739.     DetectHiddenWindows, % (Setting_A_DetectHiddenWindows := A_DetectHiddenWindows) ? "On" :
  740.     WinID := ArrayCrossRef(Scripts,"Title",A_ThisMenuItem,"hWnd")
  741.     PostMessage, 0x111, 65404,,, ahk_id %WinID%
  742.     sleep 100
  743.     DetectHiddenWindows, %Setting_A_DetectHiddenWindows%
  744.     gosub MenuBuild
  745. return
  746.  
  747. ScriptEdit:
  748.     DetectHiddenWindows, % (Setting_A_DetectHiddenWindows := A_DetectHiddenWindows) ? "On" :
  749.     WinID := ArrayCrossRef(Scripts,"Title",A_ThisMenuItem,"hWnd")
  750.     PostMessage, 0x111, 65401,,, ahk_id %WinID%
  751.     DetectHiddenWindows, %Setting_A_DetectHiddenWindows%
  752. return
  753.  
  754. ScriptReload:
  755.     DetectHiddenWindows, % (Setting_A_DetectHiddenWindows := A_DetectHiddenWindows) ? "On" :
  756.     WinID := ArrayCrossRef(Scripts,"Title",A_ThisMenuItem,"hWnd")
  757.     PostMessage, 0x111, 65400,,, ahk_id %WinID%
  758.     DetectHiddenWindows, %Setting_A_DetectHiddenWindows%
  759. return
  760.  
  761. ScriptOpen:
  762.     DetectHiddenWindows, % (Setting_A_DetectHiddenWindows := A_DetectHiddenWindows) ? "On" :
  763.     WinID := ArrayCrossRef(Scripts,"Title",A_ThisMenuItem,"hWnd")
  764.     PostMessage, 0x111, 65300,,, ahk_id %WinID%
  765.     DetectHiddenWindows, %Setting_A_DetectHiddenWindows%
  766. return
  767.  
  768. MenuBuild:
  769.     DetectHiddenWindows, % (Setting_A_DetectHiddenWindows := A_DetectHiddenWindows) ? "On" :
  770.     Menu, MenuMain, UseErrorLevel  
  771.     Menu, MenuMain, Delete
  772.     for index, Script in Scripts
  773.     {
  774.         Title := Script.Title
  775.         script_id := Script.hWnd
  776.         ; Force the script to update its Pause/Suspend checkmarks.
  777.         SendMessage, 0x211,,,, ahk_id %script_id%  ; WM_ENTERMENULOOP
  778.         SendMessage, 0x212,,,, ahk_id %script_id%  ; WM_EXITMENULOOP
  779.        
  780.         ; Get script status from its main menu.
  781.         mainMenu := DllCall("GetMenu", "uint", script_id)
  782.         fileMenu := DllCall("GetSubMenu", "uint", mainMenu, "int", 0)
  783.         isPaused := DllCall("GetMenuState", "uint", fileMenu, "uint", 4, "uint", 0x400) >> 3 & 1
  784.         isSuspended := DllCall("GetMenuState", "uint", fileMenu, "uint", 5, "uint", 0x400) >> 3 & 1
  785.         DllCall("CloseHandle", "uint", fileMenu)
  786.         DllCall("CloseHandle", "uint", mainMenu)
  787.        
  788.         Menu, MenuStop, Add, %Title%, ScriptStop
  789.         Menu, MenuPause, Add, %Title%, ScriptPause
  790.         if isPaused
  791.             Menu, MenuPause, Check, %Title%
  792.         else
  793.             Menu, MenuPause, UnCheck, %Title%
  794.         Menu, MenuSuspend, Add, %Title%, ScriptSuspend
  795.         if isSuspended
  796.             Menu, MenuSuspend, Check, %Title%
  797.         else
  798.             Menu, MenuSuspend, UnCheck, %Title%
  799.         Menu, MenuEdit, Add, %Title%, ScriptEdit
  800.         Menu, MenuReload, Add, %Title%, ScriptReload
  801.         Menu, MenuOpen, Add, %Title%, ScriptOpen
  802.     }
  803.     Menu, MenuMain, Add,% "   Stop Script   ", :MenuStop
  804.     Menu, MenuMain, Add
  805.     Menu, MenuMain, Add,% "    Pause Script   ", :MenuPause
  806.     Menu, MenuMain, Add
  807.     Menu, MenuMain, Add,% "   Suspend Script   ", :MenuSuspend
  808.     Menu, MenuMain, Add
  809.     Menu, MenuMain, Add,% "   Edit Script   ", :MenuEdit
  810.     Menu, MenuMain, Add
  811.     Menu, MenuMain, Add,% "   Reload Script   ", :MenuReload
  812.     Menu, MenuMain, Add
  813.     Menu, MenuMain, Add,% "   Open Script   ", :MenuOpen
  814.     DetectHiddenWindows, %Setting_A_DetectHiddenWindows%
  815. return
  816.  
  817. ; Excluded Gui
  818. ExcludedButtonConfirmEdit:
  819.     Gui, Excluded:Submit
  820.     Files_Excluded := ""
  821.     Hot_Excluded := ""
  822.     Loop, Parse, Gui_Excluded, `n, `r
  823.     {
  824.         if !A_LoopField
  825.             continue
  826.         if (A_LoopField = String_Wings(" EXCLUDED SCRIPTS AND FILES ",40))
  827.         {
  828.             Next_Section := false
  829.             continue
  830.         }
  831.         if (A_LoopField = String_Wings(" EXCLUDED HOTKEYS & HOTSTRINGS ",40))
  832.             Next_Section := true
  833.         else
  834.             if !Next_Section
  835.                 Files_Excluded .= "|" Trim(A_LoopField)
  836.             else
  837.                 Hot_Excluded .= "|" Trim(A_LoopField)
  838.     }
  839.     Files_Excluded := SubStr(Files_Excluded, 2)
  840.     Hot_Excluded := SubStr(Hot_Excluded, 2)
  841.     if Set_IniExcluded
  842.     {
  843.         IniWrite, %Files_Excluded%, Hotkey Help.ini, Excluded, Files_Excluded
  844.         IniWrite, %Hot_Excluded%, Hotkey Help.ini, Excluded, Hot_Excluded
  845.     }
  846. return
  847.  
  848. ExcludedGuiSize:
  849.     NewWidth := A_GuiWidth - 20
  850.     NewHeight := A_GuiHeight - 20
  851.     GuiControl, Move, Gui_Excluded, W%NewWidth% H%NewHeight%
  852. return
  853.  
  854. ExcludedGuiEscape:
  855.     Gui, Excluded:Show, Hide
  856. return
  857.  
  858. ; Raw Gui
  859. RawGuiSize:
  860.     NewWidth := A_GuiWidth - 20
  861.     NewHeight := A_GuiHeight - 20
  862.     GuiControl, Move, Gui_Raw_Display, W%NewWidth% H%NewHeight%
  863. return
  864.  
  865. RawGuiEscape:
  866.     Gui, Raw:Show, Hide
  867. return
  868.  
  869. ; Set Gui
  870. SetButtonFinished:
  871. SetGuiEscape:
  872.     Gui, Set:Submit
  873.     if Set_IniSet
  874.     {
  875.         IniWrite, %Set_ShowBlank%, Hotkey Help.ini, Settings, Set_ShowBlank
  876.         IniWrite, %Set_ShowBlankInclude%, Hotkey Help.ini, Settings, Set_ShowBlankInclude
  877.         IniWrite, %Set_ShowExe%, Hotkey Help.ini, Settings, Set_ShowExe
  878.         IniWrite, %Set_ShowHotkey%, Hotkey Help.ini, Settings, Set_ShowHotkey
  879.         IniWrite, %Set_VarHotkey%, Hotkey Help.ini, Settings, Set_VarHotkey
  880.         IniWrite, %Set_FlagHotkey%, Hotkey Help.ini, Settings, Set_FlagHotkey
  881.         IniWrite, %Set_ShowString%, Hotkey Help.ini, Settings, Set_ShowString
  882.         IniWrite, %Set_AhkExe%, Hotkey Help.ini, Settings, Set_AhkExe
  883.         IniWrite, %Set_AhkTxt%, Hotkey Help.ini, Settings, Set_AhkTxt
  884.         IniWrite, %Set_AhkTxtOver%, Hotkey Help.ini, Settings, Set_AhkTxtOver
  885.         IniWrite, %Set_SortInfo%, Hotkey Help.ini, Settings, Set_SortInfo
  886.         IniWrite, %Set_CapHotkey%, Hotkey Help.ini, Settings, Set_CapHotkey
  887.         IniWrite, %Set_CapHotkey_Radio%, Hotkey Help.ini, Settings, Set_CapHotkey_Radio
  888.         IniWrite, %Set_HideFold%, Hotkey Help.ini, Settings, Set_HideFold
  889.         IniWrite, %Set_TextOut%, Hotkey Help.ini, Settings, Set_TextOut
  890.         IniWrite, %Set_FindPos%, Hotkey Help.ini, Settings, Set_FindPos
  891.         IniWrite, %Set_IniSet%, Hotkey Help.ini, Settings, Set_IniSet
  892.         IniWrite, %Set_IniExcluded%, Hotkey Help.ini, Settings, Set_IniExcluded
  893.         IniWrite, %Set_Hotkey_Mod_Delimiter%, Hotkey Help.ini, Settings, Set_Hotkey_Mod_Delimiter
  894.     }
  895.     Set_Hotkey_Mod_Delimiter := Trim(Set_Hotkey_Mod_Delimiter,"""")
  896. return
  897. ; Export Help Dialog to Text File
  898. ButtonExportDialog:
  899.     if Display
  900.         gosub TextOut
  901.     else
  902.     {
  903.         Display_CreateOnly := true
  904.         gosub #F1
  905.         Display_CreateOnly := false
  906.         gosub TextOut
  907.         Display := ""
  908.     }
  909. return
  910.  
  911. ; Reset "Find" Position
  912. ButtonFindPos:
  913.     SearchEdit.Docked := true
  914. return
  915. ;}
  916.  
  917. ; FUNCTIONS
  918. ;{-----------------------------------------------
  919. ;
  920.  
  921. ; Get Value of Variable From Script Dialog
  922. HotkeyVariable(Script,Variable)
  923. {
  924.     static
  925.     Var := Trim(Variable," %")
  926.     If !Script_List
  927.         Script_List := {}
  928.     if !Script_List[Script]
  929.     {
  930.         DetectHiddenWindows, % (Setting_A_DetectHiddenWindows := A_DetectHiddenWindows) ? "On" :
  931.         SetTitleMatchMode 2
  932.         WinMove, %Script%,,A_ScreenWidth, A_ScreenHeight
  933.         PostMessage, 0x111, 65407, , , %Script%
  934.         ControlGetText, Text, Edit1, %Script%
  935.         WinHide, %Script%
  936.         Script_List[Script] := Text
  937.     }
  938.     Pos := RegExMatch(Script_List[Script], Var ".*\:(.*)",Match)
  939.     DetectHiddenWindows, %Setting_A_DetectHiddenWindows%
  940.     if (Pos and Match1)
  941.         return Match1
  942.     else
  943.         return Variable
  944. }
  945.  
  946. ; Get Hotkeys From Script Dialog
  947. ScriptHotkeys(Script)
  948. {
  949.     DetectHiddenWindows, % (Setting_A_DetectHiddenWindows := A_DetectHiddenWindows) ? "On" :
  950.     SetTitleMatchMode 2
  951.     WinMove, %Script%,,A_ScreenWidth, A_ScreenHeight
  952.     if (Script = A_ScriptFullPath)
  953.         ListHotkeys
  954.     else
  955.         PostMessage, 0x111, 65408, , , %Script%
  956.     ControlGetText, Text, Edit1, %Script%
  957.     WinHide, %Script%
  958.     DetectHiddenWindows, %Setting_A_DetectHiddenWindows%
  959.     Result := {}
  960.     Loop, Parse, Text, `n, `r
  961.     {
  962.         Pos := RegExMatch(A_LoopField,"^[(reg|k|m|2|joy)].*\t(.*)$",Match)
  963.         if Pos
  964.             Result.Insert(Match1)
  965.     }
  966.     return Result
  967. }
  968.  
  969. ; Expand File Path
  970. Get_Full_Path(path)
  971. {
  972.     Loop, %path%, 1
  973.         return A_LoopFileLongPath
  974.     return path
  975. }
  976.  
  977. ; Add Character Wings to Each Side of String to Create Graphical Break
  978. String_Wings(String,Length:=76,Char:="=",Case:="U")
  979. {
  980.     if (Case = "U")
  981.         StringUpper, String, String
  982.     else if (Case = "T")
  983.         StringUpper, String, String, T
  984.     else if (Case = "L")
  985.         StringLower, String, String
  986.     WingX1 := Round(((Length-StrLen(String))/2)/StrLen(Char)-.5)
  987.     WingX2 := Round((Length-StrLen(String)-(WingX1*StrLen(Char)))/StrLen(Char)+.5)
  988.     loop %WingX1%
  989.         Wing_1 .= Char
  990.     loop %WingX2%
  991.         Wing_2 .= Char
  992.     return SubStr(Wing_1 String Wing_2,1,Length)
  993. }
  994.  
  995. ; Format Spaces Between Hot Keys and Help Info to Create Columns
  996. Format_Line(Hot,Info,Pos_Info)
  997. {
  998.     Spaces := ""
  999.     Length := Pos_Info - StrLen(Hot) - 1
  1000.     Loop %Length%
  1001.         Spaces .= " "
  1002.     return Hot Spaces Info
  1003. }
  1004.  
  1005. ; Reference One Branch of Array and Return Corrisponding Information on Cross Branch
  1006. ArrayCrossRef(Array, Haystack, Needle, Cross)
  1007. {
  1008.     for index, element in Array
  1009.         if (Needle = element[Haystack])
  1010.             return element[Cross]
  1011.     return
  1012. }
  1013. ;}
  1014.  
  1015. ; CLASSES
  1016. ;{-----------------------------------------------
  1017. ;
  1018.  
  1019. ; [Class] SearchEdit - Find Text within Edit Control (Edit Control Must have +0x100 Style for Unfocused Highlights)
  1020. class SearchEdit
  1021. {
  1022.     Dialog(pGuiControlID, pOffset:=3, pFindInput := "")
  1023.     {
  1024.         static
  1025.         GuiControlID := pGuiControlID ; assign to static method variable
  1026.         SearchEdit.Offset := pOffset ; assign to class variable
  1027.         SearchEdit.ParentID := DllCall("GetParent", UInt, GuiControlID) ; assign to class variable
  1028.         SysGet, Area, MonitorWorkArea ; AreaLeft, AreaRight, AreaBottom, AreaTop
  1029.         if !GuiFindID
  1030.         {
  1031.             Gui SearchEdit_Dialog:Default
  1032.             Gui -Caption +HwndGuiFindID +ToolWindow +Owner%GuiControlID%
  1033.             Gui Add, Edit, x10 y3 w200 r2 gFindText_Sub vFindText_Var -VScroll
  1034.             GuiControl, Move, FindText_Var, h20
  1035.             Gui Add, StatusBar, gStatusBar, `tType Find string and press Enter
  1036.             SearchEdit.GuiFindID := GuiFindID ; assign to class variable
  1037.             if !IsObject(SearchEdit.UnDock)
  1038.                 SearchEdit.Docked := true
  1039.         }
  1040.         if (pFindInput = "")
  1041.         {
  1042.             Found := false, StartingPos := 1
  1043.             WinGetPos, X, Y, W, H, % "ahk_id " SearchEdit.ParentID
  1044.             Calc := SearchEdit.Calc_Position(X, Y, W, H)
  1045.             Gui SearchEdit_Dialog:Show, % "h" Calc.H " w" Calc.W " x" Calc.X " y" Calc.Y
  1046.             SearchEdit.Visible := true
  1047.             OnMessage(0x201, ObjBindMethod(SearchEdit, "WM_LBUTTONDOWN"))
  1048.             OnMessage(0x47, ObjBindMethod(SearchEdit,"WM_WINDOWPOSCHANGED"))
  1049.             return
  1050.         }
  1051.         if (FindInput<>pFindInput)
  1052.             Found := false, StartingPos := 1
  1053.         FindInput := pFindInput            
  1054.         WrapToTop:
  1055.         StartingPos := SearchEdit.FindText(FindInput, GuiControlID,, StartingPos)
  1056.         GuiControl,, FindText_Var, %FindInput%
  1057.         Send ^{Right}
  1058.         if !StartingPos
  1059.         {
  1060.             SendMessage 0xB1, -1,,, ahk_id %GuiControlID%  ; EM_SETSEL ; Deselect
  1061.             if Found
  1062.             {
  1063.                 Found := false, StartingPos := 1
  1064.                 goto WrapToTop
  1065.             }
  1066.             MsgBox % "NOT FOUND:`n`n" FindInput
  1067.             GuiControl,, FindText_Var
  1068.             Found := false, StartingPos := 1
  1069.         }
  1070.         else
  1071.             Found := true
  1072.         return
  1073.         FindText_Sub:
  1074.             Gui SearchEdit_Dialog:Submit, NoHide
  1075.             if !(InStr(FindText_Var, "`n"))
  1076.                 return
  1077.             SearchEdit.Dialog(GuiControlID, SearchEdit.Offset, Trim(FindText_Var, "`n"))
  1078.         return
  1079.         SearchEdit_DialogGuiEscape:
  1080.             Gui SearchEdit_Dialog:Hide
  1081.             SearchEdit.Visible := false
  1082.         return
  1083.         StatusBar: ; Double Click
  1084.             SearchEdit.Docked := true
  1085.             WinGetPos, X, Y, W, H, % "ahk_id " SearchEdit.ParentID
  1086.             Calc := SearchEdit.Calc_Position(X, Y, W, H)
  1087.             Gui SearchEdit_Dialog:Show, % "h" Calc.H " w" Calc.W " x" Calc.X " y" Calc.Y
  1088.         return
  1089.     }
  1090.     FindText(FindText, GuiControlID, CaseSensitive:=false, StartingPos:=1, Occurance:=1)
  1091.     {
  1092.         GuiControlGet, Text,, %GuiControlID%
  1093.         Text := RegExReplace(Text, "\R", "`r`n")
  1094.         if !(Pos := InStr(Text, FindText, CaseSensitive, StartingPos, Occurance))
  1095.             return
  1096.         StartingPos := Pos - 1
  1097.         EndingPos := StartingPos + StrLen(FindText)
  1098.         SendMessage 0xB1, StartingPos, EndingPos,, ahk_id %GuiControlID%  ; EM_SETSEL
  1099.         SendMessage 0xB7, 0, 0,, ahk_id %GuiControlID%         ;- EM_SCROLLCARET
  1100.         return EndingPos + 1 ; Start Position for Next Search
  1101.     }
  1102.     WM_LBUTTONDOWN() ; Private Method
  1103.     {
  1104.         If (A_Gui = "SearchEdit_Dialog")
  1105.         {
  1106.             PostMessage, 0xA1, 2,,,A
  1107.             SearchEdit.Docked := false
  1108.             Sleep 20
  1109.             WinGetPos, X, Y, W, H, % "ahk_id " SearchEdit.ParentID
  1110.             WinGetPos, gX, gY, gW, gH, % "ahk_id " SearchEdit.GuiFindID
  1111.             SearchEdit.UnDock := {"deltaX":gX-X, "deltaY":gY-Y}
  1112.         }
  1113.     }
  1114.     WM_WINDOWPOSCHANGED(wParam, lParam, msg, Hwnd) ; Private Method
  1115.     {
  1116.        
  1117.         if (Hwnd != SearchEdit.ParentID or !SearchEdit.Visible)
  1118.             return
  1119.         if !WinExist("ahk_id " Hwnd)
  1120.         {
  1121.             Gui SearchEdit_Dialog:Hide
  1122.             return
  1123.         }
  1124.         X := NumGet(lParam+0, A_PtrSize + A_PtrSize, "int")
  1125.         Y := NumGet(lParam+0, A_PtrSize + A_PtrSize + 4, "int")
  1126.         W := NumGet(lParam+0, A_PtrSize + A_PtrSize + 8, "int")
  1127.         H := NumGet(lParam+0, A_PtrSize + A_PtrSize + 12, "int")
  1128.         Flags := NumGet(lParam+0, A_PtrSize + A_PtrSize + 16)
  1129.         if (Flags = 6147 or Flags = 6163 or Flags = 33072 or Flags = 33060) ; Minimize/Restore
  1130.             return
  1131.         Calc := SearchEdit.Calc_Position(X, Y, W, H)
  1132.         Gui SearchEdit_Dialog:Show, % "h" Calc.H " w" Calc.W " x" Calc.X " y" Calc.Y
  1133.     }
  1134.     Calc_Position(X, Y, W, H) ; Private Method
  1135.     {
  1136.         guiO := SearchEdit.Offset ; assign Class variable for convenience
  1137.         guiH:=45, guiW:=220 ; Gui - Base Height, Base Width
  1138.         if !SearchEdit.Docked
  1139.             return {"h":guiH, "w":guiW, "x":X+SearchEdit.UnDock.deltaX, "y":Y+SearchEdit.UnDock.deltaY}
  1140.         SysGet, Area, MonitorWorkArea ; AreaLeft, AreaRight, AreaBottom, AreaTop
  1141.         scaleH := Floor(guiH*A_ScreenDPI/96), scaleW := Floor(guiW*A_ScreenDPI/96) ; Adjust for different DPI screens
  1142.         if (Y+H+scaleH-guiO < AreaBottom)
  1143.             return {"h":guiH, "w":guiW, "x":X+guiO, "y":Y+H-guiO} ; bottom under outside
  1144.         else if (X+W+scaleW-guiO < AreaRight)
  1145.             return {"h":guiH, "w":guiW, "x":X+W-guiO, "y":Y+H-guiO-scaleH} ; bottom right outside
  1146.         else if (X-scaleW > AreaLeft)
  1147.             return {"h":guiH, "w":guiW, "x":X-scaleW+guiO, "y":Y+H-scaleH-guiO} ; bottom left outside
  1148.         else
  1149.             return {"h":guiH, "w":guiW, "x":X+W-scaleW-guiO, "y":Y+H-scaleH-guiO} ; bottom right inside
  1150.     }
  1151. }
  1152. ;}
  1153.  
  1154.  
  1155. ; FUNCTIONS - LIBRARY
  1156. ;{-----------------------------------------------
  1157. ;
  1158.  
  1159. ;{ AHKScripts
  1160. ; Fanatic Guru
  1161. ; 2014 03 31
  1162. ;
  1163. ; FUNCTION that will find the path and file name of all AHK scripts running.
  1164. ;
  1165. ;---------------------------------------------------------------------------------
  1166. ;
  1167. ; Method:
  1168. ;   AHKScripts(ByRef Array)
  1169. ;
  1170. ; Parameters:
  1171. ;   1) {Array} variable in which to store AHK script path data array
  1172. ;
  1173. ; Returns:
  1174. ;   String containing the complete path of all AHK scripts running
  1175. ;   One path per line of string, delimiter = `n
  1176. ;
  1177. ; ByRef:
  1178. ;   Populates {Array} passed as parameter with AHK script path data
  1179. ;     {Array}.Path
  1180. ;     {Array}.Name
  1181. ;     {Array}.Dir
  1182. ;     {Array}.Ext
  1183. ;     {Array}.Title
  1184. ;     {Array}.hWnd
  1185. ;
  1186. ; Example Code:
  1187. /*
  1188.     MsgBox % AHKScripts(Script_List)
  1189.     for index, element in Script_List
  1190.         MsgBox % "#:`t" index "`nPath:`t" element.Path "`nName:`t" element.Name "`nDir:`t" element.Dir "`nExt:`t" element.Ext "`nTitle:`t" element.Title "`nhWnd:`t" element.hWnd
  1191.     return
  1192. */
  1193. AHKScripts(ByRef Array)
  1194. {
  1195.     DetectHiddenWindows, % (Setting_A_DetectHiddenWindows := A_DetectHiddenWindows) ? "On" :
  1196.     WinGet, AHK_Windows, List, ahk_class AutoHotkey
  1197.     Array := {}
  1198.     list := ""
  1199.     Loop %AHK_Windows%
  1200.     {
  1201.         hWnd := AHK_Windows%A_Index%
  1202.         WinGetTitle, Win_Name, ahk_id %hWnd%
  1203.         File_Path := RegExReplace(Win_Name, "^(.*) - AutoHotkey v[0-9\.]+$", "$1")
  1204.         SplitPath, File_Path, File_Name, File_Dir, File_Ext, File_Title
  1205.         Array[A_Index,"Path"] := File_Path
  1206.         Array[A_Index,"Name"] := File_Name
  1207.         Array[A_Index,"Dir"] := File_Dir
  1208.         Array[A_Index,"Ext"] := File_Ext
  1209.         Array[A_Index,"Title"] := File_Title
  1210.         Array[A_Index,"hWnd"] := hWnd
  1211.         list .= File_Path "`n"
  1212.        
  1213.     }
  1214.     DetectHiddenWindows, %Setting_A_DetectHiddenWindows%
  1215.     return Trim(list, " `n")
  1216. }
  1217. ;}
  1218. ;}
  1219.  
  1220.  
Add Comment
Please, Sign In to add comment