Перейти к содержимому раздела
Серый форум
разработка скриптов
Вы не вошли. Пожалуйста, войдите или зарегистрируйтесь.
Страницы 1
Чтобы отправить ответ, вы должны войти или зарегистрироваться
1 2021-06-14 09:39:48 (изменено: Publipor, 2021-06-14 13:30:32)
- Publipor
- Участник
- Неактивен
- Рейтинг : [0|0]
Тема: AHK:Помогите разобраться в ошибке.The script contains syntax errors.
Здравствуйте. Возникла в проблема в написании простенького кода. Планировал заменить в определенной программе сочетаний клавиш «ctrl+alt» на «Xbutton2» , но что-то не получилось. Не могли б Вы, объяснить в чем я допустил ошибку
#If WinActive("ahk_exe acad.exe")
Xbutton1::vkA2
return
Xbutton2::vkA2 & vkA4
return
PgUp::
{
SendInput, {⌀}
return
}
Post’s attachments
Screenshot 2021-06-14 083811.png
Screenshot 2021-06-14 083811.png 7.47 kb, file has never been downloaded.
You don’t have the permssions to download the attachments of this post.
2 Ответ от teadrinker 2021-06-14 13:00:38
- teadrinker
- Администратор
- Неактивен
Re: AHK:Помогите разобраться в ошибке.The script contains syntax errors.
Publipor, ознакомьтесь, пожалуйста, с правилами форума. Обратите внимание на оформление заголовков и кода. Отредактируйте свой пост.
Разработка AHK-скриптов:
e-mail dfiveg@mail.ru
Telegram jollycoder
3 Ответ от teadrinker 2021-06-14 18:44:18
- teadrinker
- Администратор
- Неактивен
Re: AHK:Помогите разобраться в ошибке.The script contains syntax errors.
Попробуйте так:
#If WinActive("ahk_exe acad.exe")
Xbutton2::
Send {Ctrl Down}{Alt Down}
KeyWait, Xbutton2
Send {Ctrl Up}{Alt Up}
Return
Разработка AHK-скриптов:
e-mail dfiveg@mail.ru
Telegram jollycoder
4 Ответ от Publipor 2021-06-16 09:15:33 (изменено: Publipor, 2021-06-16 09:15:53)
- Publipor
- Участник
- Неактивен
- Рейтинг : [0|0]
Re: AHK:Помогите разобраться в ошибке.The script contains syntax errors.
teadrinker Огромное спасибо, этот скрипт заработал))
5 Ответ от Publipor 2021-06-16 12:50:38 (изменено: Publipor, 2021-06-16 12:58:21)
- Publipor
- Участник
- Неактивен
- Рейтинг : [0|0]
Re: AHK:Помогите разобраться в ошибке.The script contains syntax errors.
teadrinker Дополнительный вопрос, в данном скрипте я смогу заменить Xbutton2 к примеру на сочинение ctrl+num1 (ctrl & Numpad1), скрип будет работать?
6 Ответ от teadrinker 2021-06-16 13:04:12
- teadrinker
- Администратор
- Неактивен
Re: AHK:Помогите разобраться в ошибке.The script contains syntax errors.
Да, только нужно будет KeyWait изменить.
Разработка AHK-скриптов:
e-mail dfiveg@mail.ru
Telegram jollycoder
7 Ответ от Publipor 2021-06-16 13:05:16 (изменено: Publipor, 2021-06-16 13:07:26)
- Publipor
- Участник
- Неактивен
- Рейтинг : [0|0]
Re: AHK:Помогите разобраться в ошибке.The script contains syntax errors.
teadrinker, таким образом?
ctrl & Numpad1::
Send {Ctrl Down}{Alt Down}{shift Down}{Alt Down}
KeyWait, ctrl & Numpad1
Send {shift Up}
Return
8 Ответ от teadrinker 2021-06-16 13:34:45
- teadrinker
- Администратор
- Неактивен
Re: AHK:Помогите разобраться в ошибке.The script contains syntax errors.
Не, совсем не так. Сейчас не у компьютера.
Разработка AHK-скриптов:
e-mail dfiveg@mail.ru
Telegram jollycoder
9 Ответ от Publipor 2021-06-16 15:33:42
- Publipor
- Участник
- Неактивен
- Рейтинг : [0|0]
Re: AHK:Помогите разобраться в ошибке.The script contains syntax errors.
teadrinker, Хорошо, мне не срочно.)
10 Ответ от teadrinker 2021-06-16 17:05:34
- teadrinker
- Администратор
- Неактивен
Re: AHK:Помогите разобраться в ошибке.The script contains syntax errors.
Во-первых, саму горячую клавишу проще определять так: ^Numpad1::. Во-вторых, у вас что-то непонятное посылается здесь:
Send {Ctrl Down}{Alt Down}{shift Down}{Alt Down}
Зачем {Alt Down} два раза?
В-третьих, в KeyWait можно прописывать только одну клавишу. В четвёртых, здесь
должны отжиматься все клавиши, до этого нажатые, иначе они так и останутся нажатыми после выполнения скрипта.
Разработка AHK-скриптов:
e-mail dfiveg@mail.ru
Telegram jollycoder
11 Ответ от Publipor 2021-06-16 17:09:32
- Publipor
- Участник
- Неактивен
- Рейтинг : [0|0]
Re: AHK:Помогите разобраться в ошибке.The script contains syntax errors.
teadrinker Спасибо за ответ. По поводу 2 и 4 замечания. Это механическая ошибка.я экспериментировал с горячими клавишами и допустил оплошность.
Сообщения 11
Страницы 1
Чтобы отправить ответ, вы должны войти или зарегистрироваться
Hi guys,
I’ve got plenty of problems trying to make a script work. And at this stage need your help and eye balls to point out whatever I’m doing wrong.
I wanted to use some functionality only available in AHK V2.
I’m tearing my hair out, as as far as my eyes can tell, the syntax is exactly the same as in the AHK V2 documentation, but if I try to compile the script it says that the script contains errors:
1) WinGetCont
Error: The script contains syntax errors.
Specifically:
C:\Dropbox\GTD portable\MindMap\dualmindmapper.ahk (74) : ==> Call to nonexistent function.
Specifically: WinGetCount(«WorkFlowy»)
But the documentation here:
https lexikos.github.io /v2/docs/commands/WinGetCount.htm Broken Link for safety
says:
Count := WinGetCount(WinTitle, WinText, ExcludeTitle, ExcludeText)
and I wrote:
WINDOWZ := WinGetCount(«WorkFlowy»)
2) SendMode Input
C:\Dropbox\GTD portable\MindMap\dualmindmapper.ahk (13) : ==> Call to nonexistent function.
Specifically: SendMode(«Input»)
but the doc https lexikos.github.io /v2/docs/commands/SendMode.htm Broken Link for safety says:
SendMode «Input»
And I wrote
SendMode «Input»
3) SetTitleMatchMode(«RegEx») or SetTitleMatchMode RegEx
C:\Dropbox\GTD portable\MindMap\dualmindmapper.ahk (141) : ==> Parameter #1 invalid.
Specifically: «RegEx»
The documentation https lexikos.github.io /v2/docs/commands/SetTitleMatchMode.htm Broken Link for safety says:
SetTitleMatchMode «RegEx»
I wrote
SetTitleMatchMode «RegEx»
If you want the whole source code, here it is: https www.dropbox.com /s/ypbx7148uo2kowt/dualmindmapper.ahk?dl=0 Broken Link for safety
Please, I would seriously appreciate ya’lls help.
Thanks for this! Unfortunately, I’m running into a couple other issues updating to the latest compiled version in this repo.
These were all tested pre-compile using the AutoHotkey.exe
, AutoHotkey.dll
, and vcruntime140.dll
in x64w
of this repo.
Hotkey("F1", "createMessageBox") ; <--- Error: Invalid callback function
; Hotkey("F1", createMessageBox) ; <--- Warning: This variable appears to never be assigned a value. Specifically: global createMessageBox -> Error: Nonexistent hotkey. Specifically: F1
; Hotkey("F1", createMessageBox()) ; <--- Immediately invokes MsgBox with asdasd. Upon pressing OK it throws: Error: Nonexistent hotkey. Specifically: F1
Return
createMessageBox() {
global
MsgBox("asdasd")
Return
}
defaultObject := {
testVar: "yay, it worked"
}
CritObj := CriticalObject(defaultObject)
additionalThread := "
(
CritObj := CriticalObject(A_Args[1])
CritObj.testVar := "Manipulated CritObj String"
MsgBox(CritObj.testVar)
)"
; exampleThread := AHKThread(additionalThread, &CritObj "", "testSecondThread", false) ; <-- Error: Syntax error Specifically &CritObj ""
exampleThread := AHKThread(additionalThread, &CritObj, "testSecondThread", false) ; <-- Error: Syntax error Specifically &CritObj
; exampleThread := AHKThread(additionalThread, CritObj, "testSecondThread", false) ; <-- Error in #include file This value of type "Object" has no property named "Ptr".
; exampleThread := AHKThread(additionalThread, CritObj "", "testSecondThread", false) ; <-- Error: Expected a String but got an Object.
Sleep(10000) ; Janky Test
Return
Thanks for your time,
Deafwave
Здравствуйте. Возникла в проблема в написании простенького кода. Планировал заменить в определенной программе сочетаний клавиш «ctrl+alt» на «Xbutton2» , но что-то не получилось. Не могли б Вы, объяснить в чем я допустил ошибку
Screenshot 2021-06-14 083811.png
Screenshot 2021-06-14 083811.png 7.47 kb, file has never been downloaded.
You don’t have the permssions to download the attachments of this post.
Re: AHK:Помогите разобраться в ошибке.The script contains syntax errors.
Publipor, ознакомьтесь, пожалуйста, с правилами форума. Обратите внимание на оформление заголовков и кода. Отредактируйте свой пост.
Источник
Scripts
- Using the Program: How to use AutoHotkey, in general.
- Concepts and Conventions: General explanation of various concepts utilised by AutoHotkey.
- Scripting Language: Specific details about syntax (how to write scripts).
Table of Contents
- Introduction
- Script Startup (the Auto-execute Thread): Taking action immediately upon starting the script, and changing default settings.
- Splitting a Long Line into a Series of Shorter Ones: This can improve a script’s readability and maintainability.
- Script Library Folders
- Convert a Script to an EXE (Ahk2Exe): Convert a .ahk script into a .exe file that can run on any PC.
- Passing Command Line Parameters to a Script: The variable A_Args contains the incoming parameters.
- Script File Codepage: Using non-ASCII characters safely in scripts.
- Debugging a Script: How to find the flaws in a misbehaving script.
Introduction
Each script is a plain text file containing lines to be executed by the program (AutoHotkey.exe). A script may also contain hotkeys and hotstrings, or even consist entirely of them. However, in the absence of hotkeys and hotstrings, a script will perform its functions sequentially from top to bottom the moment it is launched.
The program loads the script into memory line by line. During loading, the script is optimized and validated. Any syntax errors will be displayed, and they must be corrected before the script can run.
Script Startup (the Auto-execute Thread)
After the script has been loaded, the auto-execute thread begins executing at the script’s top line, and continues until instructed to stop, such as by Return, ExitApp or Exit. The physical end of the script also acts as Exit.
The script will terminate after completing startup if it lacks hotkeys, hotstrings, visible GUIs, active timers, clipboard monitors and InputHooks, and has not called the Persistent function. Otherwise, it will stay running in an idle state, responding to events such as hotkeys, hotstrings, GUI events, custom menu items, and timers. If these conditions change after startup completes (for example, the last timer is disabled), the script may exit when the last running thread completes or the last GUI closes.
Whenever any new thread is launched (whether by a hotkey, hotstring, timer, or some other event), the following settings are copied from the auto-execute thread. If not set by the auto-execute thread, the standard defaults will apply (as documented on each of the following pages): CoordMode, Critical, DetectHiddenText, DetectHiddenWindows, FileEncoding, ListLines, SendLevel, SendMode, SetControlDelay, SetDefaultMouseSpeed, SetKeyDelay, SetMouseDelay, SetRegView, SetStoreCapsLockMode, SetTitleMatchMode, SetWinDelay, and Thread.
Each thread retains its own collection of the above settings, so changes made to those settings will not affect other threads.
The «default setting» for one of the above functions usually refers to the current setting of the auto-execute thread, which starts out the same as the program-defined default setting.
Traditionally, the top of the script has been referred to as the auto-execute section. However, the auto-execute thread is not limited to just the top of the script. Any functions which are called on the auto-execute thread may also affect the default settings. As directives and function, hotkey, hotstring and class definitions are skipped when encountered during execution, it is possible for startup code to be placed throughout each file. For example, a global variable used by a group of hotkeys may be initialized above (or even below) those hotkeys rather than at the top of the script.
Splitting a Long Line into a Series of Shorter Ones
Long lines can be divided up into a collection of smaller ones to improve readability and maintainability. This does not reduce the script’s execution speed because such lines are merged in memory the moment the script launches.
There are three methods, and they can generally be used in combination:
- Continuation operator: Start or end a line with an expression operator to join it to the previous or next line.
- Continuation by enclosure: A sub-expression enclosed in (), [] or <> can automatically span multiple lines in most cases.
- Continuation section: Mark a group of lines to be merged together, with additional options such as what text (or code) to insert between lines.
Continuation operator: A line that starts with a comma or any other expression operator (except ++ and —) is automatically merged with the line directly above it. Similarly, a line that ends with an expression operator is automatically merged with the line below it. In the following example, the second line is appended to the first because it begins with a comma:
Similarly, the following lines would get merged into a single line because the last two start with «and» or «or»:
The ternary operator is also a good candidate:
The following examples are equivalent to those above:
Although the indentation used in the examples above is optional, it might improve clarity by indicating which lines belong to ones above them. Also, blank lines or comments may be added between or at the end of any of the lines in the above examples.
A continuation operator cannot be used with an auto-replace hotstring or directive other than #HotIf.
Continuation expressions may contain both types of comments.
Continuation expressions may contain normal continuation sections. Therefore, as with any line containing an expression, if a line begins with a non-escaped open parenthesis ( ( ), it is considered to be the start of a continuation section unless there is a closing parenthesis ( ) ) on the same line.
Quoted strings cannot span multiple lines using this method alone. However, see above.
Continuation by enclosure can be combined with a continuation operator. For example:
- A brace is never interpreted as the beginning of a block if it is preceded by an unclosed ( / [ / < , since that would produce an invalid expression. For example, the brace in If (< is the start of an object literal.
- An object literal cannot legally follow ) or ] , so if the brace follows either of those symbols (excluding whitespace), it is interpreted as the beginning of a block (such as for a function or property definition).
- For control flow statements which require a body (and therefore support OTB), the brace can be the start of an object literal only if it is preceded by an operator, such as := < or for x in< . In particular, the brace in Loop < is always block-begin, and If < and While < are always errors.
A brace can be safely used for line continuation with any function call, expression or control flow statement which does not require a body. For example:
Continuation section: This method should be used to merge a large number of lines or when the lines are not suitable for the other methods. Although this method is especially useful for auto-replace hotstrings, it can also be used with any expression. For example:
In the examples above, a series of lines is bounded at the top and bottom by a pair of parentheses. This is known as a continuation section. Notice that any code after the closing parenthesis is also joined with the other lines (without any delimiter), but the opening and closing parentheses are not included.
If the line above the continuation section ends with a name character and the section does not start inside a quoted string, a single space is automatically inserted to separate the name from the contents of the continuation section.
Quote marks are automatically escaped (i.e. they are interpreted as literal characters) if the continuation section starts inside a quoted string, as in the examples above. Otherwise, quote marks act as they do normally; that is, continuation sections can contain expressions with quoted strings.
By default, leading spaces or tabs are omitted based on the indentation of the first line inside the continuation section. If the first line mixes spaces and tabs, only the first type of character is treated as indentation. If any line is indented less than the first line or with the wrong characters, all leading whitespace on that line is left as is.
The default behavior of a continuation section can be overridden by including one or more of the following options to the right of the section’s opening parenthesis. If more than one option is present, separate each one from the previous with a space. For example: ( LTrim Join| .
Join: Specifies how lines should be connected together. If this option is omitted, each line except the last will be followed by a linefeed character (`n). If the word Join is specified by itself, lines are connected directly to each other without any characters in between. Otherwise, the word Join should be followed immediately by as many as 15 characters. For example, Join`s would insert a space after each line except the last. Another example is Join`r`n , which inserts CR+LF between lines. Similarly, Join| inserts a pipe between lines. To have the final line in the section also ended by a join-string, include a blank line immediately above the section’s closing parenthesis.
LTrim: Omits all spaces and tabs at the beginning of each line. This is usually unnecessary because of the default «smart» behaviour.
LTrim0 (LTrim followed by a zero): Turns off the omission of spaces and tabs from the beginning of each line.
RTrim0 (RTrim followed by a zero): Turns off the omission of spaces and tabs from the end of each line.
Comments (or Comment or Com or C): Allows semicolon comments inside the continuation section (but not /*..*/ ). Such comments (along with any spaces and tabs to their left) are entirely omitted from the joined result rather than being treated as literal text. Each comment can appear to the right of a line or on a new line by itself.
` (accent): Treats each backtick character literally rather than as an escape character. This also prevents the translation of any explicitly specified escape sequences such as `r and `t .
( or ): If an opening or closing parenthesis appears to the right of the initial opening parenthesis (except as a parameter of the Join option), the line is reinterpreted as an expression instead of the beginning of a continuation section. This enables expressions like (x.y)[z]() to be used at the start of a line, and also allows multi-line expressions to start with a line like (( or (MyFunc( .
Escape sequences such as `n (linefeed) and `t (tab) are supported inside the continuation section except when the accent (`) option has been specified.
When the comment option is absent, semicolon and /*..*/ comments are not supported within the interior of a continuation section because they are seen as literal text. However, comments can be included on the bottom and top lines of the section. For example:
As a consequence of the above, semicolons never need to be escaped within a continuation section.
Since a closing parenthesis indicates the end of a continuation section, to have a line start with literal closing parenthesis, precede it with an accent/backtick: `) . However, this cannot be combined with the accent (`) option.
A continuation section can be immediately followed by a line containing the open-parenthesis of another continuation section. This allows the options mentioned above to be varied during the course of building a single line.
The piecemeal construction of a continuation section by means of #Include is not supported.
Script Library Folders
The library folders provide a few standard locations to keep shared scripts which other scripts utilise by means of #Include. A library script typically contains a function or class which is designed to be used and reused in this manner. Placing library scripts in one of these locations makes it easier to write scripts that can be shared with others and work across multiple setups. The library locations are:
The library folders are searched in the order shown above.
For example, if a script includes the line #Include , the program searches for a file named «MyLib.ahk» in the local library. If not found there, it searches for it in the user library, and then the standard library. If a match is still not found and the library’s name contains an underscore (e.g. MyPrefix_MyFunc ), the program searches again with just the prefix (e.g. MyPrefix.ahk ).
Although by convention a library file generally contains only a single function or class of the same name as its filename, it may also contain private functions that are called only by it. However, such functions should have fairly distinct names because they will still be in the global namespace; that is, they will be callable from anywhere in the script.
Convert a Script to an EXE (Ahk2Exe)
A script compiler (courtesy of fincs, with additions by TAC109) is included with the program.
Once a script is compiled, it becomes a standalone executable; that is, AutoHotkey.exe is not required in order to run the script. The compilation process creates an executable file which contains the following: the AutoHotkey interpreter, the script, any files it includes, and any files it has incorporated via the FileInstall function. Additional files can be included using compiler directives.
Compiler Topics
Running the Compiler
Ahk2Exe can be used in the following ways:
GUI Interface: Run the «Convert .ahk to .exe» item in the Start Menu. (After invoking the GUI, there may be a pause before the window is shown; see Background Information for more details.)
Right-click: Within an open Explorer window, right-click any .ahk file and select «Compile Script» (only available if the script compiler option was chosen when AutoHotkey was installed). This creates an EXE file of the same base filename as the script, which appears after a short time in the same directory. Note: The EXE file is produced using the same custom icon, .bin file and compression setting that were last saved in Method #1 above, or as specified by any relevant compiler directive in the script.
Command Line: The compiler can be run from the command line by using the parameters shown below. If any command line parameters are used, the script is compiled immediately unless /gui is used. All parameters are optional, except that there must be one /gui or /in parameter.
Parameter pair | Meaning |
---|---|
/in script_name | The path and name of the script to compile. This is mandatory if any other parameters are used, unless /gui is used. |
/out exe_name | The pathname of the output .exe to be created. Default is the directorybase_name of the input file plus extension of .exe, or any relevant compiler directive in the script. |
/icon icon_name | The icon file to be used. Default is the last icon saved in the GUI interface, or any SetMainIcon compiler directive in the script. |
/base file_name | The base file to be used (a .bin or .exe file). Default is the last base file name saved in the GUI interface, or any Base compiler directive in the script. |
/resourceid name | Assigns a non-standard resource ID to be used for the main script for compilations which use an .exe base file (see Embedded Scripts). Numeric resource IDs should consist of a hash sign (#) followed by a decimal number. Default is #1, or any ResourceID compiler directive in the script. |
/cp codepage | Overrides the default codepage used to read script files. For a list of possible values, see Code Page Identifiers. Note that Unicode scripts should begin with a byte-order-mark (BOM), rendering the use of this parameter unnecessary. |
/compress n | Compress the exe? 0 = no, 1 = use MPRESS if present, 2 = use UPX if present. Default is the last setting saved in the GUI interface. |
/gui | Shows the GUI instead of immediately compiling. The other parameters can be used to override the settings last saved in the GUI. /in is optional in this case. |
/silent [verbose] | Disables all message boxes and instead outputs errors to the standard error stream (stderr); or to the standard output stream (stdout) if stderr fails. Other messages are also output to stdout. Optionally enter the word verbose to output status messages to stdout as well. |
Deprecated: /ahk file_name |
The pathname of AutoHotkey.exe to be used as a utility when compiling the script. |
Deprecated: /mpress 0or1 |
Compress the exe with MPRESS? 0 = no, 1 = yes. Default is the last setting used in the GUI interface. |
Deprecated: /bin file_name |
The .bin file to be used. Default is the last .bin file name saved in the GUI interface. |
- Parameters containing spaces must be enclosed in double quotes.
- Compiling does not typically improve the performance of a script.
- #NoTrayIcon and A_AllowMainWindow affect the behavior of compiled scripts.
- The built-in variable A_IsCompiled contains 1 if the script is running in compiled form. Otherwise, it is blank.
- When parameters are passed to Ahk2Exe, a message indicating the success or failure of the compiling process is written to stdout. Although the message will not appear at the command prompt, it can be «caught» by means such as redirecting output to a file.
- Additionally in the case of a failure, Ahk2Exe has exit codes indicating the kind of error that occurred. These error codes can be found at GitHub (ErrorCodes.md).
The compiler’s source code and newer versions can be found at GitHub.
Base Executable File
Each compiled script .exe is based on an executable file which implements the interpreter. The base files included in the Compiler directory have the «.bin» extension; these are versions of the interpreter which do not include the capability to load external script files. Instead, the program looks for a Win32 (RCDATA) resource named «>AUTOHOTKEY SCRIPT /compress parameter or the GUI setting.
MPRESS official website (downloads and information): http://www.matcode.com/mpress.htm
MPRESS mirror: https://www.autohotkey.com/mpress/
UPX official website (downloads and information): https://upx.github.io/
Note: While compressing the script executable prevents casual inspection of the script’s source code using a plain text editor like Notepad or a PE resource editor, it does not prevent the source code from being extracted by tools dedicated to that purpose.
Background Information
The following folder structure is supported, where the running version of Ahk2Exe.exe is in the first Compiler directory shown below:
The base file search algorithm runs for a short amount of time when Ahk2Exe starts, and works as follows:
Qualifying AutoHotkey .exe files and all .bin files are searched for in the compiler’s directory, the compiler’s parent directory, and any of the compiler’s sibling directories with directory names that start with AutoHotkey or V , but do not start with AutoHotkey_H . The selected directories are searched recursively. Any AutoHotkey.exe files found are excluded, leaving files such as AutoHotkeyA32.exe, AutoHotkey64.exe, etc. plus all .bin files found. All .exe files that are included must have a name starting with AutoHotkey and a file description containing the word AutoHotkey , and must have a version of 1.1.34+ or 2.0-a135+ .
A version of the AutoHotkey interpreter is also needed (as a utility) for a successful compile, and one is selected using a similar algorithm. In most cases the version of the interpreter used will match the version of the base file selected by the user for the compile.
Passing Command Line Parameters to a Script
Scripts support command line parameters. The format is:
And for compiled scripts, the format is:
Switches: Zero or more of the following:
Send syntax errors that prevent a script from launching to the standard error stream (stderr) rather than displaying a dialog. See #ErrorStdOut for details.
An encoding can optionally be specified. For example, /ErrorStdOut=UTF-8 encodes messages as UTF-8 before writing them to stderr.
Overrides the default codepage used to read script files. For more details, see Script File Codepage.
AutoHotkey loads the script and then exits instead of running it.
By default, load-time errors and warnings are displayed as usual. The /ErrorStdOut switch can be used to suppress or capture any error messages.
The process exit code is zero if the script successfully loaded, or non-zero if there was an error.
Deprecated: Use /validate instead.
AutoHotkey loads the script but does not run it. In previous versions of AutoHotkey, filenames of auto-included files were written to the file specified by OutFile, formatted as #Include directives.
If the output file exists, it is overwritten. OutFile can be * to write the output to stdout.
If the script contains syntax errors, the output file may be empty. The process exit code can be used to detect this condition; if there is a syntax error, the exit code is 2. The /ErrorStdOut switch can be used to suppress or capture the error message.
Includes a file prior to the main script. Only a single file can be included by this method. When the script is reloaded, this switch is automatically passed to the new instance.
When used with a compiled script based on an .exe file, this switch causes the program to ignore the main embedded script. This allows a compiled script .exe to execute external script files or embedded scripts other than the main one. Other switches not normally supported by compiled scripts can be used but must be listed to the right of this switch. For example:
If the current executable file does not have an embedded script, this switch is permitted but has no effect.
This switch is not supported by compiled scripts which are based on a .bin file.
Script Filename: This can be omitted if there are no Script Parameters. If omitted, it defaults to the path and name of the AutoHotkey executable, replacing «.exe» with «.ahk». For example, if you rename AutoHotkey.exe to MyScript.exe, it will attempt to load MyScript.ahk. If you run AutoHotkey32.exe without parameters, it will attempt to load AutoHotkey32.ahk.
Specify an asterisk (*) for the filename to read the script text from standard input (stdin). This also puts the following into effect:
For an example, see ExecScript().
If the current executable file has embedded scripts, this parameter can be an asterisk followed by the resource name or ID of an embedded script. For compiled scripts (i.e. if an embedded script with the ID #1 exists), this parameter must be preceded by the /script switch.
Script Parameters: The string(s) you want to pass into the script, with each separated from the next by one or more spaces. Any parameter that contains spaces should be enclosed in quotation marks. If you want to pass an empty string as a parameter, specify two consecutive quotation marks. A literal quotation mark may be passed in by preceding it with a backslash (»). Consequently, any trailing slash in a quoted parameter (such as «C:My Documents » ) is treated as a literal quotation mark (that is, the script would receive the string C:My Documents » ). To remove such quotes, use A_Args[1] := StrReplace(A_Args[1], ‘»‘)
Incoming parameters, if present, are stored as an array in the built-in variable A_Args, and can be accessed using array syntax. A_Args[1] contains the first parameter. The following example exits the script when too few parameters are passed to it:
If the number of parameters passed into a script varies (perhaps due to the user dragging and dropping a set of files onto a script), the following example can be used to extract them one by one:
If the parameters are file names, the following example can be used to convert them to their case-corrected long names (as stored in the file system), including complete/absolute path:
Script File Codepage
In order for non-ASCII characters to be read correctly from file, the encoding used when the file was saved (typically by the text editor) must match what AutoHotkey uses when it reads the file. If it does not match, characters will be decoded incorrectly. AutoHotkey uses the following rules to decide which encoding to use:
- If the file begins with a UTF-8 or UTF-16 (LE) byte order mark, the appropriate codepage is used and the /CPn switch is ignored.
- If the /CPn switch is passed on the command-line, codepage n is used. For a list of possible values, see Code Page Identifiers.
- In all other cases, UTF-8 is used (this default differs from AutoHotkey v1).
Note that this applies only to script files loaded by AutoHotkey, not to file I/O within the script itself. FileEncoding controls the default encoding of files read or written by the script, while IniRead and IniWrite always deal in UTF-16 or ANSI.
As all text is converted (where necessary) to the native string format, characters which are invalid or don’t exist in the native codepage are replaced with a placeholder: ‘�’. This should only occur if there are encoding errors in the script file or the codepages used to save and load the file don’t match.
RegWrite may be used to set the default for scripts launched from Explorer (e.g. by double-clicking a file):
This assumes AutoHotkey has already been installed. Results may be less than ideal if it has not.
Debugging a Script
Built-in functions such as ListVars and Pause can help you debug a script. For example, the following two lines, when temporarily inserted at carefully chosen positions, create «break points» in the script:
When the script encounters these two lines, it will display the current contents of all variables for your inspection. When you’re ready to resume, un-pause the script via the File or Tray menu. The script will then continue until reaching the next «break point» (if any).
It is generally best to insert these «break points» at positions where the active window does not matter to the script, such as immediately before a WinActivate function. This allows the script to properly resume operation when you un-pause it.
The following functions are also useful for debugging: ListLines, KeyHistory, and OutputDebug.
Some common errors, such as typos and missing «global» declarations, can be detected by enabling warnings.
Interactive Debugging
Interactive debugging is possible with a supported DBGp client. Typically the following actions are possible:
- Set and remove breakpoints on lines — pause execution when a breakpoint is reached.
- Step through code line by line — step into, over or out of functions.
- Inspect all variables or a specific variable.
- View the stack of running threads and functions.
Note that this functionality is disabled for compiled scripts which are based on a BIN file. For compiled scripts based on an EXE file, /debug must be specified after /script.
To enable interactive debugging, first launch a supported debugger client then launch the script with the /Debug command-line switch.
SERVER and PORT may be omitted. For example, the following are equivalent:
To attach the debugger to a script which is already running, send it a message as shown below:
Once the debugger client is connected, it may detach without terminating the script by sending the «detach» DBGp command.
Источник
Adblock
detector
Switch | Meaning | Works compiled? |
---|---|---|
/force | Launch unconditionally, skipping any warning dialogs. This has the same effect as #SingleInstance Off. | Yes |
/restart | Indicate that the script is being restarted and should attempt to close a previous instance of the script (this is also used by the Reload function, internally). | Yes |
/ErrorStdOut
/ErrorStdOut=Encoding |
No | |
/Debug | Connect to a debugging client. For more details, see Interactive Debugging. | No |
/CPn |
SyntaxError
— это ошибка, которая легко может ввести в ступор начинающего программиста. Стоит забыть одну запятую или не там поставить кавычку и Python наотрез откажется запускать программу. Что ещё хуже, по выводу в консоль сложно сообразить в чём дело. Выглядят сообщения страшно и непонятно. Что с этим делать — не ясно. Вот неполный список того, что можно встретить:
SyntaxError: invalid syntax
SyntaxError: EOL while scanning string literal
SyntaxError: unexpected EOF while parsing
Эта статья о том, как справиться с синтаксической ошибкой SyntaxError
. Дочитайте её до конца и получите безотказный простой алгоритм действий, что поможет вам в трудную минуту — ваш спасательный круг.
Работать будем с программой, которая выводит на экран список учеников. Её код выглядит немного громоздко и, возможно, непривычно. Если не всё написанное вам понятно, то не отчаивайтесь, чтению статьи это не помешает.
students = [
['Егор', 'Кузьмин'],
['Денис', 'Давыдов'],
]
for first_name, last_name in students:
label = 'Имя ученика: {first_name} {last_name}'.format(
first_name = first_name
last_name = last_name
)
print(label)
Ожидается примерно такой результат в консоли:
$ python script.py
Имя ученика: Егор Кузьмин
Имя ученика: Денис Давыдов
Но запуск программы приводит к совсем другому результату. Скрипт сломан:
$ python script.py
File "script.py", line 9
last_name = last_name
^
SyntaxError: invalid syntax
Ошибки в программе бывают разные и каждой нужен свой особый подход. Первым делом внимательно посмотрите на вывод программы в консоль. На последней строчке написано SyntaxError: invalid syntax
. Если эти слова вам не знакомы, то обратитесь за переводом к Яндекс.Переводчику:
SyntaxError: недопустимый синтаксис
SyntaxError: неверный синтаксис
Первое слово SyntaxError
Яндекс не понял. Помогите ему и разделите слова пробелом:
Syntax Error: invalid syntax
Синтаксическая ошибка: неверный синтаксис
Теория. Синтаксические ошибки
Программирование — это не магия, а Python — не волшебный шар. Он не умеет предсказывать будущее, у него нет доступа к секретным знаниями, это просто автомат, это программа. Узнайте как она работает, как ищет ошибки в коде, и тогда легко найдете эффективный способ отладки. Вся необходимая теория собрана в этом разделе, дочитайте до конца.
SyntaxError
— это синтаксическая ошибка. Она случается очень рано, еще до того, как Python запустит программу. Вот что делает компьютер, когда вы запускаете скрипт командой python script.py
:
- запускает программу
python
python
считывает текст из файлаscript.py
python
превращает текст программы в инструкцииpython
исполняет инструкции
Синтаксическая ошибка SyntaxError
возникает на четвёртом этапе в момент, когда Python разбирает текст программы на понятные ему компоненты. Сложные выражения в коде он разбирает на простейшие инструкции. Вот пример кода и инструкции для него:
person = {'name': 'Евгений'}
Инструкции:
- создать строку
'Евгений'
- создать словарь
- в словарь добавить ключ
'name'
со значением'Евгений'
- присвоить результат переменной
person
SyntaxError
случается когда Python не смог разбить сложный код на простые инструкции. Зная это, вы можете вручную разбить код на инструкции, чтобы затем проверить каждую из них по отдельности. Ошибка прячется в одной из инструкций.
1. Найдите поломанное выражение
Этот шаг сэкономит вам кучу сил. Найдите в программе сломанный участок кода. Его вам предстоит разобрать на отдельные инструкции. Посмотрите на вывод программы в консоль:
$ python script.py
File "script.py", line 9
last_name = last_name
^
SyntaxError: invalid syntax
Вторая строчка сообщает: File "script.py", line 9
— ошибка в файле script.py
на девятой строчке. Но эта строка является частью более сложного выражения, посмотрите на него целиком:
label = 'Имя ученика: {first_name} {last_name}'.format(
first_name = first_name
last_name = last_name
)
«Девман» — авторская методика обучения программированию. Готовим к работе крутых программистов на Python. Станьте программистом, пройдите продвинутый курс Python.
2. Разбейте выражение на инструкции
В прошлых шагах вы узнали что сломан этот фрагмент кода:
label = 'Имя ученика: {first_name} {last_name}'.format(
first_name = first_name
last_name = last_name
)
Разберите его на инструкции:
- создать строку
'Имя ученика: {first_name} {last_name}'
- получить у строки метод
format
- вызвать функцию с двумя аргументами
- результат присвоить переменной
label
Так выделил бы инструкции программист, но вот Python сделать так не смог и сломался. Пора выяснить на какой инструкции нашла коса на камень.
Теперь ваша задача переписать код так, чтобы в каждой строке программы исполнялось не более одной инструкции из списка выше. Так вы сможете тестировать их по отдельности и облегчите себе задачу. Так выглядит отделение инструкции по созданию строки:
# 1. создать строку
template = 'Имя ученика: {first_name} {last_name}'
label = template.format(
first_name = first_name
last_name = last_name
)
Сразу запустите код, проверьте что ошибка осталась на прежнему месте. Приступайте ко второй инструкции:
# 1. создать строку
template = 'Имя ученика: {first_name} {last_name}'
# 2. получить у строки метод
format = template.format
label = format(
first_name = first_name
last_name = last_name
)
Строка format = template.format
создает новую переменную format
и кладёт в неё функцию. Да, да, это не ошибка! Python разрешает класть в переменные всё что угодно, в том числе и функции. Новая переменная переменная format
теперь работает как обычная функция, и её можно вызвать: format(...)
.
Снова запустите код. Ошибка появится внутри format
. Под сомнением остались две инструкции:
- вызвать функцию с двумя аргументами
- результат присвоить переменной
label
Скорее всего, Python не распознал вызов функции. Проверьте это, избавьтесь от последней инструкции — от создания переменной label
:
# 1. создать строку
template = 'Имя ученика: {first_name} {last_name}'
# 2. получить у строки метод
format = template.format
# 3. вызвать функцию
format(
first_name = first_name
last_name = last_name
)
Запустите код. Ошибка снова там же — внутри format
. Выходит, код вызова функции написан с ошибкой, Python не смог его превратить в инструкцию.
3. Проверьте синтаксис вызова функции
Теперь вы знаете что проблема в коде, вызывающем функцию. Можно помедитировать еще немного над кодом программы, пройтись по нему зорким взглядом еще разок в надежде на лучшее. А можно поискать в сети примеры кода для сравнения.
Запросите у Яндекса статьи по фразе “Python синтаксис функции”, а в них поищите код, похожий на вызов format
и сравните. Вот одна из первых статей в поисковой выдаче:
- Функции в Python
Уверен, теперь вы нашли ошибку. Победа!
Have you ever seen the message “syntax error near unexpected token” while running one of your Bash scripts?
In this guide I will show you why this error occurs and how to fix it.
Why the Bash unexpected token syntax error occurs?
As the error suggests this is a Bash syntax error, in other words it reports bad syntax somewhere in your script or command. There are many things that can go wrong in a Bash script and cause this error. Some common causes are missing spaces next to commands and lack of escaping for characters that have a special meaning for the Bash shell.
Finding the syntax error reported when you execute your script is not always easy. This process often requires you to change and retest your script multiple times.
To make your life easier I have analysed different scenarios in which this syntax error can occur. For every scenario I will show you the script or command with the error and the fix you need to apply to solve the problem.
Let’s get started!
One Approach to Fix Them All
Considering that this syntax error can occur in multiple scenarios you might not be able to find your exact error in the list below.
Don’t worry about it, what matters is for you to learn the right approach to identify what’s causing the error and knowing how to fix it.
And going through the examples below you will learn how to do that.
In some of the examples I will show you how to fix this error if it happens while executing a single command in a Bash shell.
In other examples we will look at Bash scripts that when executed fail with the “unexpected token” error.
To fix the error in a single command it’s usually enough to add or remove some incorrect characters that cause the syntax error in the command.
Knowing how to fix the error in a script can take a bit more time, and for that I will use the following 5-step process:
- Run the script that contains the syntax error.
- Take note of the line mentioned by the Bash error.
- Execute the line with the error in a Bash shell to find the error fast (without having to change the script and rerun it multiple times).
- Update your script with the correct line of code.
- Confirm the script works.
Makes sense?
It’s time for the first scenario.
Let’s say I have the following file on my Linux system:
-rw-r--r-- 1 ec2-user ec2-user 28 Jun 28 22:29 report(july).csv
And I want to rename it to report_july.csv.
I can use the following command, right?
mv report(july).csv report_july.csv
When I run it I get the following error:
-bash: syntax error near unexpected token `('
But, why?
Because parentheses () are used in Bash to create a subshell. In other words they are special characters.
And Bash special character need to be escaped if used as normal characters in a command. The backslah is used to escape characters.
I will update the command to include the backslash before both parentheses:
mv report(july).csv report_july.csv
No errors this time:
-rw-r--r-- 1 ec2-user ec2-user 28 Jun 28 22:29 report_july.csv
Lesson 1: Remember to escape Bash special characters when you use them as normal characters (literals) in a filename or string in general.
First error fixed!
Syntax Error Near Unexpected Token Then (Example 1)
And here is the second scenario.
When I run the following script:
#!/bin/bash
DAY="Monday"
if[ $DAY == "Monday" ]; then
echo "Today is Monday"
else
echo "Today is not Monday"
fi
I get back the error below:
(localhost)$ ./unexpected_token.sh
./unexpected_token.sh: line 5: syntax error near unexpected token `then'
./unexpected_token.sh: line 5: `if[ $DAY == "Monday" ]; then'
Can you see why?
The error is caused by the missing space between if and the open square bracket ( [ ).
And the reason is the following:
if is a shell builtin command and you might be thinking you are using if here. But in reality the shell sees if[ that is not a known command to the shell.
At that point the shell doesn’t know how to handle then given that it hasn’t found if before, and it stops the script with the error above.
The correct script is:
#!/bin/bash
DAY="Monday"
if [ $DAY == "Monday" ]; then
echo "Today is Monday"
else
echo "Today is not Monday"
fi
I have just added a space between if and [ so the shell can see the if command.
And the output of the script is correct:
(localhost)$ ./unexpected_token.sh
Today is Monday
Lesson 2: Spaces are important in Bash to help the shell identify every command.
Syntax Error Near Unexpected Token Then (Example 2)
While writing Bash scripts, especially at the beginning, it’s common to do errors like the one below:
(localhost)$ for i in {0..10} ; do echo $i ; then echo "Printing next number" ; done
When you run this one-liner here’s what you get:
-bash: syntax error near unexpected token `then'
Let’s find out why…
The syntax of a for loop in Bash is:
for VARIABLE in {0..10}
do
echo command1
echo command2
echo commandN
done
And using a single line:
for VARIABLE in {0..10}; do echo command1; echo command2; echo commandN; done
So, as you can see the semicolon is used in Bash to separate commands when you want to write them on a single line.
The reason why the semicolons were not required in the first version of the script is that the newline is a command separator too.
Now, let’s go back to our error…
The one-liner that was failing with an error contains the then statement that as you can see is not part of the structure of a for loop.
The error is telling us:
- There is a syntax error.
- The token ‘then‘ is unexpected.
Let’s confirm the one-liner runs well after removing then:
(localhost)$ for i in {0..10} ; do echo $i ; echo "Printing next number" ; done
0
Printing next number
1
Printing next number
2
Printing next number
3
Printing next number
4
Printing next number
5
Printing next number
6
Printing next number
7
Printing next number
8
Printing next number
9
Printing next number
10
Printing next number
All good!
Lesson 3: When you see a syntax error verify that you are using Bash loops or conditional constructs in the right way and you are not adding any statements that shouldn’t be there.
Syntax Error Near Unexpected Token Done
I have created a simple script in which an if statement is nested inside a while loop. It’s a very common thing to do in Bash.
#!/bin/bash
COUNTER=0
while true
do
if [ $COUNTER -eq 0 ]; then
echo "Stopping the script..."
exit 1
done
fi
This script might seem ok, but when I run it I get the following…
./unexpected_token.sh: line 8: syntax error near unexpected token `done'
./unexpected_token.sh: line 8: ` done'
Why?
The done and fi statements are correctly used to close the while loop and the if conditional statement. But they are used in the wrong order!
The if statement is nested into the while loop so we should be closing the if statement first, using fi. And after that we can close the while loop using done.
Let’s try the script:
(localhost)$ ./unexpected_token.sh
Stopping the script...
All good now.
Lesson 4: Nested loops and conditional statements need to be closed in the same order in which they are opened.
Syntax Error Near Unexpected Token fi
Let’s look at another scenario in which this syntax error can occur with the fi token:
#!/bin/bash
for NAME in 'John' 'Mark' 'Kate'
do
if [ "$NAME" == 'Mark' ] then
echo 'Hello Mark!'
fi
done
And this is what I get when I run it:
./unexpected_token.sh: line 7: syntax error near unexpected token `fi'
./unexpected_token.sh: line 7: ` fi'
In this case the Bash shell identifies the if statement and because of that it expects then after it.
As you can see then is there, so what’s the problem?
There is no command separator between the [ ] command (yes….it’s a command) and the then statement.
So, what’s the fix?
Add a command separator immediately after the closing square bracket. We will use the semicolon ( ; ) as command separator.
Our script becomes:
#!/bin/bash
for NAME in 'John' 'Mark' 'Kate'
do
if [ "$NAME" == 'Mark' ]; then
echo 'Hello Mark!'
fi
done
And if I run it I get the correct output:
(localhost)$ ./unexpected_token.sh
Hello Mark!
Lesson 5: Remember to specify command separators in your Bash scripts. Either the semicolon or the newline.
Conclusion
You now have what you need to understand what causes this syntax error in your scripts. You can apply the 5 lessons I have explained in this guide to find a fix.
Take the time to review the lessons at the end of each section so they become part of your Bash knowledge.
If you have any questions please feel free to write them in the comments below.
Now, let’s say you have saved your Bash script using Windows.
And when you run it in Linux you are seeing a syntax error that you can’t really explain because the script looks correct to you.
You might be having the problem explained in this article.
Enjoy your scripting!
Related FREE Course: Decipher Bash Scripting
I’m a Software Engineer and Programming Coach. I want to help you in your journey to become a Super Developer!
Scripts
Table of Contents
- Introduction
- The Top of the Script (the Auto-execute Section): This portion executes automatically when the script starts.
- Escape Sequences: When to use `% and `, to indicate a literal percent sign or comma.
- Comments in Scripts: The use of semicolon and the symbols /*…*/ to add remarks to a script.
- Splitting a Long Line into a Series of Shorter Ones: This can improve a script’s readability and maintainability.
- Convert a Script to an EXE (ahk2exe): Convert a .ahk script into a .exe file that can run on any PC.
- Passing Command Line Parameters to a Script: The variable A_Args contains the incoming parameters.
- Script File Codepage: Using non-ASCII characters safely in scripts.
- Debugging a Script: How to find the flaws in a misbehaving script.
- Portability of AutoHotkey.exe: Having a copy of AutoHotkey.exe is enough to execute any .ahk file.
- Installer Options: How to do unattended/silent installations or uninstallations.
Introduction
Each script is a plain text file containing lines to be executed by the program (AutoHotkey.exe). A script may also contain hotkeys and hotstrings, or even consist entirely of them. However, in the absence of hotkeys and hotstrings, a script will perform its commands sequentially from top to bottom the moment it is launched.
The program loads the script into memory line by line, and each line may be up to 16,383 characters long. During loading, the script is optimized and validated. Any syntax errors will be displayed, and they must be corrected before the script can run.
The Top of the Script (the Auto-execute Section)
After the script has been loaded, it begins executing at the top line, continuing until a Return, Exit, hotkey/hotstring label, or the physical end of the script is encountered (whichever comes first). This top portion of the script is referred to as the auto-execute section.
A script that lacks hotkeys, hotstrings, visible GUIs, active message monitors, active timers, active OnClipboardChange callback functions, custom tray menu items and the #Persistent directive will terminate after the auto-execute section has completed. Otherwise, it will stay running in an idle state, responding to events such as hotkeys, hotstrings, GUI events, custom menu items, and timers. If these conditions change after the auto-execute section completes (for example, the last timer is disabled), the script may exit when the last running thread completes or the last GUI closes.
Every thread launched by a hotkey, hotstring, menu item, GUI event, or timer starts off fresh with the default values for the following attributes as set in the auto-execute section. If unset, the standard defaults will apply (as documented on each of the following pages): DetectHiddenWindows, DetectHiddenText, SetTitleMatchMode, SendMode, SetKeyDelay, SetMouseDelay,
SetWinDelay,
SetControlDelay,
SetDefaultMouseSpeed,
CoordMode,
SetStoreCapslockMode, StringCaseSense, Thread, and Critical.
If the auto-execute section takes a long time to complete (or never completes), the default values for the above settings will be put into effect after 100 milliseconds. When the auto-execute section finally completes (if ever), the defaults are updated again to be those that were in effect at the end of the auto-execute section. Thus, it’s usually best to make any desired changes to the defaults at the top of scripts that contain hotkeys, hotstrings, timers, or custom menu items. Also note that each thread retains its own collection of the above settings. Changes made to those settings will not affect other threads.
Escape Sequences
AutoHotkey’s escape character is accent/backtick (`), which is at the upper left corner of most English keyboards. Using this character rather than backslash avoids the need for double blackslashes in file paths.
A quote mark can be escaped to include it inside a quoted string. For example, the expressions "`""
, '"'
and Chr(34)
all produce a string containing a double quote mark.
Certain special characters are also produced by means of an escape sequence. The most common ones are `t
(tab), `n
(linefeed), and `r
(carriage return).
Scripts can be commented by using a semicolon at the beginning of a line. For example:
; This entire line is a comment.
Comments may also be added to the end of a command, in which case the semicolon must have at least one space or tab to its left. For example:
Run "Notepad" ; This is a comment on the same line as a command.
In addition, the /*
and */
symbols can be used to comment out an entire section, as in this example:
/* MsgBox "This line is commented out (disabled)." MsgBox "This one too." */
Excluding whitespace, /*
must appear at the start of the line, while */
can appear only at the start or end of a line. It is also valid to omit */
, in which case the remainder of the file is commented out.
Since comments are ignored when a script is launched, they do not impact performance or memory utilization.
Splitting a Long Line into a Series of Shorter Ones
Long lines can be divided up into a collection of smaller ones to improve readability and maintainability. This does not reduce the script’s execution speed because such lines are merged in memory the moment the script launches.
Method #1: A line that starts with «and», «or», ||, &&, a comma, or a period is automatically merged with the line directly above it (the same is true for all other expression operators except ++ and —). In the following example, the second line is appended to the first because it begins with a comma:
FileAppend "This is the text to append.`n" ; A comment is allowed here. , A_ProgramFiles "SomeApplicationLogFile.txt" ; Comment.
Similarly, the following lines would get merged into a single line because the last two start with «and» or «or»:
if (Color = "Red" or Color = "Green" or Color = "Blue" ; Comment. or Color = "Black" or Color = "Gray" or Color = "White") ; Comment. and ProductIsAvailableInColor(Product, Color) ; Comment.
The ternary operator is also a good candidate:
ProductIsAvailable := (Color = "Red") ? false ; We don't have any red products, so don't bother calling the function. : ProductIsAvailableInColor(Product, Color)
Although the indentation used in the examples above is optional, it might improve clarity by indicating which lines belong to ones above them. Also, it is not necessary to include extra spaces for lines starting with the words «AND» and «OR»; the program does this automatically. Finally, blank lines or comments may be added between or at the end of any of the lines in the above examples.
Method #2: This method should be used to merge a large number of lines or when the lines are not suitable for Method #1. Although this method is especially useful for auto-replace hotstrings, it can also be used with any command or expression. For example:
; EXAMPLE #1: Var := " ( Line 1 of the text. Line 2 of the text. By default, a linefeed (`n) is present between lines. )" ; EXAMPLE #2: FileAppend " ( A line of text. By default, the hard carriage return (Enter) between the previous line and this one will be written to the file. This line is indented with a tab; by default, that tab will also be written to the file. )", A_Desktop "My File.txt"
In the examples above, a series of lines is bounded at the top and bottom by a pair of parentheses. This is known as a continuation section. Notice that the bottom line contains FileAppend’s last parameter after the closing parenthesis. This practice is optional; it is done in cases like this so that the comma will be seen as a parameter-delimiter rather than a literal comma.
By default, quote marks inside the continuation section act as if they have been escaped (i.e. they are interpreted as literal characters). Additionally, leading spaces or tabs are omitted based on the indentation of the first line inside the continuation section. If the first line mixes spaces and tabs, only the first type of character is treated as indentation. If any line is indented less than the first line or with the wrong characters, all leading whitespace on that line is left as is.
The default behavior of a continuation section can be overridden by including one or more of the following options to the right of the section’s opening parenthesis. If more than one option is present, separate each one from the previous with a space. For example: ( LTrim Join|
.
Join: Specifies how lines should be connected together. If this option is omitted, each line except the last will be followed by a linefeed character (`n). If the word Join is specified by itself, lines are connected directly to each other without any characters in between. Otherwise, the word Join should be followed immediately by as many as 15 characters. For example, Join`s
would insert a space after each line except the last («`s» indicates a literal space — it is a special escape sequence recognized only by Join). Another example is Join`r`n
, which inserts CR+LF between lines. Similarly, Join|
inserts a pipe between lines. To have the final line in the section also ended by a join-string, include a blank line immediately above the section’s closing parenthesis.
Known limitation: If the Join string ends with a colon, it must not be the last option on the line. For example, (Join:
is treated as the label «(Join» and (LTrim Join:
is unsupported, but (Join: C
is okay.
LTrim: Omits all spaces and tabs at the beginning of each line. This is usually unnecessary because of the default «smart» behaviour.
LTrim0 (LTrim followed by a zero): Turns off the omission of spaces and tabs from the beginning of each line.
RTrim0 (RTrim followed by a zero): Turns off the omission of spaces and tabs from the end of each line.
Quotes (or Q): Restores the ability to terminate quoted strings when an expression is used in a continuation section.
` (accent): Treats each backtick character literally rather than as an escape character. This also prevents commas and percent signs from being explicitly and individually escaped. In addition, it prevents the translation of any explicitly specified escape sequences such as `r and `t.
): If a closing parenthesis appears in the continuation section’s options (except as a parameter of the Join option), the line is reinterpreted as an expression instead of the beginning of a continuation section. This allows expressions like (x.y)[z]()
to work without the need to escape the opening parenthesis.
Escape sequences such as `n (linefeed) and `t (tab) are supported inside the continuation section except when the accent (`) option has been specified.
When the comment option is absent, semicolon and /*..*/ comments are not supported within the interior of a continuation section because they are seen as literal text. However, comments can be included on the bottom and top lines of the section. For example:
FileAppend " ; Comment. ; Comment. ( LTrim Join ; Comment. ; This is not a comment; it is literal. Include the word Comments in the line above to make it a comment. )", "C:File.txt" ; Comment.
As a consequence of the above, semicolons never need to be escaped within a continuation section.
A continuation section cannot produce a line whose total length is greater than 16,383 characters (if it tries, the program will alert you the moment the script is launched). One way to work around this is to do a series of concatenations into a variable. For example:
Var := " ( ... )" Var .= "`n ; Add more text to the variable via another continuation section. ( ... )" FileAppend Var, "C:My File.txt"
Since a closing parenthesis indicates the end of a continuation section, to have a line start with literal closing parenthesis, precede it with an accent/backtick: `)
.
A continuation section can be immediately followed by a line containing the open-parenthesis of another continuation section. This allows the options mentioned above to be varied during the course of building a single line.
The piecemeal construction of a continuation section by means of #Include is not supported.
Convert a Script to an EXE (ahk2exe)
A script compiler (courtesy of fincs) is included with the program.
Once a script is compiled, it becomes a standalone executable; that is, AutoHotkey.exe is not required in order to run the script. The compilation process creates an executable file which contains the following: the AutoHotkey interpreter, the script, any files it includes, and any files it has incorporated via the FileInstall command.
Ahk2Exe can be used in the following ways:
- GUI Interface: Run the «Convert .ahk to .exe» item in the Start Menu.
- Right-click: Within an open Explorer window, you can right-click any .ahk file and select «Compile Script» (only available if the script compiler option was chosen when AutoHotkey was installed). This creates an EXE file of the same base filename as the script, which appears after a short time in the same directory. Note: The EXE file is produced using the same custom icon, .bin file and use MPRESS setting that were last used by Method #1 above.
- Command Line: The compiler can be run from the command line with the following parameters:
Ahk2Exe.exe /in MyScript.ahk [/out MyScript.exe] [/icon MyIcon.ico] [/bin AutoHotkeySC.bin] [/mpress 0or1]
For example:
Ahk2Exe.exe /in "MyScript.ahk" /icon "MyIcon.ico"
Usage:
- Parameters containing spaces should be enclosed in double quotes.
- If the «out» file is omitted, the EXE will have the same base filename as the script itself.
Notes:
- Compiling does not typically improve the performance of a script.
- The commands #NoTrayIcon and «Menu, Tray, ShowMainWindow» affect the behavior of compiled scripts.
- Custom version info (as seen in Explorer’s file-properties dialog) can be added to your compiled scripts by using a utility such as Resource Hacker (freeware) to edit the file «AutoHotkeySC.bin». This file is contained in the «Compiler» subfolder where AutoHotkey was installed. Compile_AHK II can be used to facilitate this process. The compiled script can be edited instead of AutoHotkeySC.bin.
- The method above can also be used to change existing icons or add new ones to all compiled scripts.
- The built-in variable A_IsCompiled contains 1 if the script is running in compiled form. Otherwise, it is blank.
- When parameters are passed to Ahk2Exe, a message indicating the success or failure of the compiling process is written to stdout. Although the message will not appear at the command prompt, it can be «caught» by means such as redirecting output to a file.
- Additionally in the case of a failure, Ahk2Exe has exit codes indicating the kind of error that occurred. These error codes can be found at GitHub (ErrorCodes.md).
- Resources can be compressed to reduce size of the program.
- You can compile scripts with AutoHotkey.exe or AutoHotkey.dll.
- Main Script can be encrypted for protection, but you should recompile AutoHotkey_H in Visual Studio with a different password or technique to have proper protection. Best is to use dynamic password generator or similar.
- WinApi functions are automatically declared for AutoHotkeySC.bin in compiled script using #DllImport.
The compiler’s source code and newer versions can be found at GitHub.
Compressing Compiled Scripts
Ahk2Exe optionally uses MPRESS (a freeware program by MATCODE Software) to compress compiled scripts. If mpress.exe is present in the «Compiler» subfolder where AutoHotkey was installed, it is used automatically unless it is disabled via /mpress 0
or the GUI setting.
Official website (was offline in March 2016): http://www.matcode.com/mpress.htm
Mirror (downloads and information): https://autohotkey.com/mpress/
Note: While compressing the script executable prevents casual inspection of the script’s source code using a plain text editor like Notepad or a PE resource editor, it does not prevent the source code from being extracted by tools dedicated to that purpose.
Passing Command Line Parameters to a Script
Scripts support command line parameters. The format is:
AutoHotkey.exe [Switches] [Script Filename] [Script Parameters]
And for compiled scripts, the format is:
CompiledScript.exe [Switches] [Script Parameters]
Switches: Zero or more of the following:
Switch | Meaning |
---|---|
/f or /force | Launch unconditionally, skipping any warning dialogs. This has the same effect as #SingleInstance Off. |
/r or /restart | Indicate that the script is being restarted (this is also used by the Reload command, internally). |
/ErrorStdOut | Send syntax errors that prevent a script from launching to stderr rather than displaying a dialog. See #ErrorStdOut for details. This can be combined with /iLib to validate the script without running it. |
Not supported by compiled scripts: | |
/Debug | Connect to a debugging client. For more details, see Interactive Debugging. |
/CPn | Overrides the default codepage used to read script files. For more details, see Script File Codepage. |
/iLib «OutFile» |
AutoHotkey loads the script but does not run it. For each script file which is auto-included via the library mechanism, two lines are written to the file specified by OutFile. These lines are written in the following format, where LibDir is the full path of the Lib folder and LibFile is the filename of the library: #Include LibDir #IncludeAgain LibDirLibFile.ahk If the output file exists, it is overwritten. OutFile can be If the script contains syntax errors, the output file may be empty. The process exit code can be used to detect this condition; if there is a syntax error, the exit code is 2. The /ErrorStdOut switch can be used to suppress or capture the error message. |
Script Filename: This can be omitted if there are no Script Parameters. If omitted (such as if you run AutoHotkey directly from the Start menu), the program looks for a script file called AutoHotkey.ahk
in the following locations, in this order:
- The directory which contains the AutoHotkey executable.
- The current user’s Documents folder.
The filename AutoHotkey.ahk
depends on the name of the executable used to run the script. For example, if you rename AutoHotkey.exe to MyScript.exe, it will attempt to find MyScript.ahk
. If you run AutoHotkeyU32.exe without parameters, it will look for AutoHotkeyU32.ahk.
Specify an asterisk (*) for the filename to read the script text from standard input (stdin). For an example, see ExecScript().
Script Parameters: The string(s) you want to pass into the script, with each separated from the next by a space. Any parameter that contains spaces should be enclosed in quotation marks. A literal quotation mark may be passed in by preceding it with a backslash («). Consequently, any trailing slash in a quoted parameter (such as «C:My Documents«) is treated as a literal quotation mark (that is, the script would receive the string C:My Documents«). To remove such quotes, use A_Args[1] := StrReplace(A_Args[1], '"')
Incoming parameters, if present, are stored as an array in the built-in variable A_Args, and can be accessed using array syntax. A_Args[1]
contains the first parameter. The following example exits the script when too few parameters are passed to it:
if A_Args.Length() < 3 { MsgBox "This script requires at least 3 parameters but it only received " argc "." ExitApp }
If the number of parameters passed into a script varies (perhaps due to the user dragging and dropping a set of files onto a script), the following example can be used to extract them one by one:
for n, param in A_Args ; For each parameter: { MsgBox "Parameter number " n " is " param "." }
If the parameters are file names, the following example can be used to convert them to their case-corrected long names (as stored in the file system), including complete/absolute path:
for n, GivenPath in A_Args ; For each parameter (or file dropped onto a script): { Loop Files, GivenPath, "FD" ; Include files and directories. LongPath := A_LoopFileFullPath MsgBox "The case-corrected long path name of file`n" GivenPath "`nis:`n" LongPath }
Known limitation: dragging files onto a .ahk script may fail to work properly if 8-dot-3 (short) names have been turned off in an NTFS file system. One work-around is to compile the script then drag the files onto the resulting EXE.
Script File Codepage
The characters a script file may contain are restricted by the codepage used to load the file.
- If the file begins with a UTF-8 or UTF-16 (LE) byte order mark, the appropriate codepage is used and the /CPn switch is ignored.
- If the /CPn switch is passed on the command-line, codepage n is used. For a list of valid numeric codepage identifiers, see MSDN.
- In all other cases, the system default ANSI codepage is used.
Note that this applies only to script files loaded by AutoHotkey, not to file I/O within the script itself. FileEncoding controls the default encoding of files read or written by the script, while IniRead and IniWrite always deal in UTF-16 or ANSI.
As all text is converted (where necessary) to the native string format, characters which are invalid or don’t exist in the native codepage are replaced with a placeholder: ‘�’. This should only occur if there are encoding errors in the script file or the codepages used to save and load the file don’t match.
RegWrite may be used to set the default for scripts launched from Explorer (e.g. by double-clicking a file):
; Uncomment the appropriate line below or leave them all commented to ; reset to the default of the current build. Modify as necessary: ; codepage := 0 ; System default ANSI codepage ; codepage := 65001 ; UTF-8 ; codepage := 1200 ; UTF-16 ; codepage := 1252 ; ANSI Latin 1; Western European (Windows) if (codepage != "") codepage := " /CP" . codepage cmd := '"' A_AhkPath '" ' codepage ' "%1" %*' key := "AutoHotkeyScriptShellOpenCommand" if A_IsAdmin ; Set for all users. RegWrite cmd, "REG_SZ", "HKCR" key else ; Set for current user only. RegWrite cmd, "REG_SZ", "HKCUSoftwareClasses" key
This assumes AutoHotkey has already been installed. Results may be less than ideal if it has not.
Debugging a Script
Commands such as ListVars and Pause can help you debug a script. For example, the following two lines, when temporarily inserted at carefully chosen positions, create «break points» in the script:
ListVars
Pause
When the script encounters these two lines, it will display the current contents of all variables for your inspection. When you’re ready to resume, un-pause the script via the File or Tray menu. The script will then continue until reaching the next «break point» (if any).
It is generally best to insert these «break points» at positions where the active window does not matter to the script, such as immediately before a WinActivate command. This allows the script to properly resume operation when you un-pause it.
The following commands are also useful for debugging: ListLines, KeyHistory, and OutputDebug.
Some common errors, such as typos and missing «global» declarations, can be detected by enabling warnings.
Interactive Debugging
Interactive debugging is possible with a supported DBGp client. Typically the following actions are possible:
- Set and remove breakpoints on lines — pause execution when a breakpoint is reached.
- Step through code line by line — step into, over or out of functions and subroutines.
- Inspect all variables or a specific variable.
- View the stack of running subroutines and functions.
Note that this functionality is disabled for compiled scripts.
To enable interactive debugging, first launch a supported debugger client then launch the script with the /Debug command-line switch.
AutoHotkey.exe /Debug[=SERVER:PORT] ...
SERVER and PORT may be omitted. For example, the following are equivalent:
AutoHotkey /Debug "myscript.ahk" AutoHotkey /Debug=localhost:9000 "myscript.ahk"
To attach the debugger to a script which is already running, send it a message as shown below:
ScriptPath := "" ; SET THIS TO THE FULL PATH OF THE SCRIPT A_DetectHiddenWindows := true if WinExist(ScriptPath " ahk_class AutoHotkey") ; Optional parameters: ; wParam = the IPv4 address of the debugger client, as a 32-bit integer. ; lParam = the port which the debugger client is listening on. PostMessage DllCall("RegisterWindowMessage", "str", "AHK_ATTACH_DEBUGGER")
Once the debugger client is connected, it may detach without terminating the script by sending the «detach» DBGp command.
Portability of AutoHotkey.exe
The file AutoHotkey.exe is all that is needed to launch any .ahk script.
Renaming AutoHotkey.exe also changes which script it runs by default, which can be an alternative to compiling a script for use on a computer without AutoHotkey installed. For instance, MyScript.exe automatically runs MyScript.ahk if a filename is not supplied, but is also capable of running other scripts.
Installer Options
To silently install AutoHotkey into the default directory (which is the same directory displayed by non-silent mode), pass the parameter /S to the installer. For example:
AutoHotkey110800_Install.exe /S
A directory other than the default may be specified via the /D parameter (in the absence of /S, this changes the default directory displayed by the installer). For example:
AutoHotkey110800_Install.exe /S /D=C:Program FilesAutoHotkey
Version: If AutoHotkey was previously installed, the installer automatically detects which version of AutoHotkey.exe to set as the default. Otherwise, the default is Unicode 32-bit or Unicode 64-bit depending on whether the OS is 64-bit. To override which version of AutoHotkey.exe is set as the default, pass one of the following switches:
/A32
or/ANSI
: ANSI 32-bit./U64
or/x64
: Unicode 64-bit (only valid on 64-bit systems)./U32
: Unicode 32-bit.
For example, the following installs silently and sets ANSI 32-bit as the default:
AutoHotkey110800_Install.exe /S /A32
Uninstall: To silently uninstall AutoHotkey, pass the /Uninstall
parameter to Installer.ahk. For example:
"C:Program FilesAutoHotkeyAutoHotkey.exe" "C:Program FilesAutoHotkeyInstaller.ahk" /Uninstall
For AutoHotkey versions older than 1.1.08.00, use uninst.exe /S
. For example:
"C:Program FilesAutoHotkeyuninst.exe" /S
Note: Installer.ahk must be run as admin to work correctly.
Extract: Later versions of the installer include a link in the bottom-right corner to extract setup files without installing. If this function is present, the /E
switch can be used to invoke it from the command line. For example:
AutoHotkey110903_Install.exe /D=F:AutoHotkey /E
Restart scripts [v1.1.19.02+]: In silent install/uninstall mode, running scripts are closed automatically, where necessary. Pass the /R
switch to automatically reload these scripts using whichever EXE they were running on, without command line args. Setup will attempt to launch the scripts via Explorer, so they do not run as administrator if UAC is enabled.
Taskbar buttons [v1.1.08+]: On Windows 7 and later, taskbar buttons for multiple scripts are automatically grouped together or combined into one button by default. The Separate taskbar buttons option disables this by registering each AutoHotkey executable as a host app (IsHostApp).
[v1.1.24.02+]: For command-line installations, specify /IsHostApp
or /IsHostApp=1
to enable the option and /IsHostApp=0
to disable it.
Run with UI Access [v1.1.24.02+]
The installer GUI has an option «Add ‘Run with UI Access’ to context menus». This context menu option provides a workaround for common UAC-related issues by allowing the script to automate administrative programs — without the script running as admin. To achieve this, the installer does the following:
- Copies AutoHotkeyA32.exe, AutoHotkeyU32.exe and (if present) AutoHotkeyU64.exe to AutoHotkey*_UIA.exe.
- Sets the uiAccess attribute in each UIA file’s embedded manifest.
- Creates a self-signed digital certificate named «AutoHotkey» and signs each UIA file.
- Registers the context menu option to run the appropriate exe file.
If any these UIA files are present before installation, the installer will automatically update them even if the UI Access option is not enabled.
For command-line installations, specify /uiAccess
or /uiAccess=1
to enable the option and /uiAccess=0
to disable it. By default, the installer will enable the option if UAC is enabled and the UI Access context menu option was present before installation.
Scripts which need to run other scripts with UI access can simply Run the appropriate UIA.exe file with the normal command line parameters.
Known limitations:
- UIA is only effective if the file is in a trusted location; i.e. a Program Files sub-directory.
- UIA.exe files created on one computer cannot run on other computers without first installing the digital certificate which was used to sign them.
- UIA.exe files cannot be started via CreateProcess due to security restrictions. ShellExecute can be used instead. Run tries both.
- UIA.exe files cannot be modified, as it would invalidate the file’s digital signature.
- Because UIA programs run at a different «integrity level» than other programs, they can only access objects registered by other UIA programs. For example,
ComObjActive("Word.Application")
will fail because Word is not marked for UI Access. - The script’s own windows can’t be automated by non-UIA programs/scripts for security reasons.
- Running a non-UIA script which uses a mouse hook (even as simple as
#InstallMouseHook
) may prevent all mouse hotkeys from working when the mouse is pointing at a window owned by a UIA script, even hotkeys implemented by the UIA script itself. A workaround is to ensure UIA scripts are loaded last.
For more details, see Enable interaction with administrative programs on the archive forum.
Script Showcase
See this page for some useful scripts.