# Functions

## Table of Contents

- Introduction and Simple Examples
- Parameters
- Optional Parameters
- Returning Values to Caller
- Variadic Functions
- Local Variables
- Dynamically Calling a Function
- Short-circuit Boolean Evaluation
- Using Subroutines Within a Function
- Return, Exit, and General Remarks
- Using #Include to Share Functions Among Multiple Scripts
- Libraries of Functions: Standard Library and User Library
- Built-in Functions

## Introduction and Simple Examples

A function is similar to a subroutine (Gosub) except that it can accept parameters (inputs) from its caller. In addition, a function may optionally return a value to its caller. Consider the following simple function that accepts two numbers and returns their sum:

    Add(x, y)
    {
        return x + y   ; "Return" expects an expression.
    }

The above is known as a function definition because it creates a function named "Add" (not case sensitive) and establishes that anyone who calls it must provide exactly two parameters (x and y). To call the function, assign its result to a variable with the := operator. For example:

    Var := Add(2, 3)  ; The number 5 will be stored in Var.

Also, a function may be called without storing its return value:

    Add(2, 3)

But in this case, any value returned by the function is discarded; so unless the function produces some effect other than its return value, the call would serve no purpose.

Since a function call is an expression, any variable names in its parameter list should not be enclosed in percent signs. By contrast, literal strings should be enclosed in double quotes. For example:

    if InStr(MyVar, "fox")
        MsgBox The variable MyVar contains the word fox.

Finally, functions may be called in the parameters of any command (except OutputVar and InputVar parameters such as those of StringLen). However, parameters that do not support expressions must use the "% " prefix as in this example:

    MsgBox % "The answer is: " . Add(3, 2)

The "% " prefix is also permitted in parameters that natively support expressions, but it is simply ignored.

## Parameters

When a function is defined, its parameters are listed in parentheses next to its name (there must be no spaces between its name and the open-parenthesis). If a function does not accept any parameters, leave the parentheses empty; for example: GetCurrentTimestamp().

ByRef Parameters: From the function's point of view, parameters are essentially the same as local variables unless they are defined as ByRef as in this example:

    Swap(ByRef Left, ByRef Right)
    {
        temp := Left
        Left := Right
        Right := temp
    }

In the example above, the use of ByRef causes each parameter to become an alias for the variable passed in from the caller. In other words, the parameter and the caller's variable both refer to the same contents in memory. This allows the Swap function to alter the caller's variables by moving Left's contents into Right and vice versa.

By contrast, if ByRef were not used in the example above, Left and Right would be copies of the caller's variables and thus the Swap function would have no external effect.

Since return can send back only one value to a function's caller, ByRef can be used to send back extra results. This is achieved by having the caller pass in a variable (usually empty) in which the function stores a value.

When passing large strings to a function, ByRef enhances performance and conserves memory by avoiding the need to make a copy of the string. Similarly, using ByRef to send a long string back to the caller usually performs better than something like `Return HugeString`.

[AHK_L 60+]: If something other than a modifiable variable is passed to a ByRef parameter, the function behaves as though the keyword "ByRef" is absent. For example, `Swap(A_Index, i)` stores the value of A_Index in i, but the value assigned to Left is discarded once the Swap function returns.

[v1.1.01+]: The IsByRef() function can be used to determine whether the caller supplied a variable for a given ByRef parameter.

Known limitations:

- Fields of objects are not considered variables for the purposes of ByRef. For example, if `foo.bar` is passed to a ByRef parameter, it will behave as though ByRef was omitted.
- It is not possible to pass Clipboard, built-in variables, or environment variables to a function's ByRef parameter, even when #NoEnv is absent from the script.
- Although a function may call itself recursively, if it passes one of its own local variables or non-ByRef parameters to itself ByRef, the new layer's ByRef parameter will refer to its own local variable of that name rather than the previous layer's. However, this issue does not occur when a function passes to itself a global variable, static variable, or ByRef parameter.
- If a parameter in a function-call resolves to a variable (e.g. `Var` or `++Var` or `Var*=2`), other parameters to its left or right can alter that variable before it is passed to the function. For example, `func(Var, Var++)` would unexpectedly pass 1 and 0 when Var is initially 0, even when the function's first parameter is not ByRef. Since this behavior is counterintuitive, it might change in a future release.

## Optional Parameters

When defining a function, one or more of its parameters can be marked as optional. This is done by appending an equal sign (or `:=` in v1.1.09+) followed by a default value. The following function has its Z parameter marked optional:

    Add(X, Y, Z:=0) {
        return X + Y + Z
    }

As of v1.1.09, both `=` and `:=` are supported. The latter is recommended for consistency with expression assignments and compatibility with future versions of AutoHotkey.

When the caller passes three parameters to the function above, Z's default value is ignored. But when the caller passes only two parameters, Z automatically receives the value 0.

It is not possible to have optional parameters isolated in the middle of the parameter list. In other words, all parameters that lie to the right of the first optional parameter must also be marked optional. [AHK_L 31+]: Optional parameters may be omitted from the middle of the parameter list when calling the function, unless the function call is dynamic:

    Func(1,, 3)
    Func(X, Y:=2, Z:=0) {  ; Note that Z must still be optional in this case.
        MsgBox %X%, %Y%, %Z%
    }

In v1.0.46.13+, ByRef parameters also support default values; for example: `Func(ByRef p1 = "")`. Whenever the caller omits such a parameter, the function creates a local variable to contain the default value; in other words, the function behaves as though the keyword "ByRef" is absent.

A parameter's default value must be one of the following: true, false, a literal integer, a literal floating point number, or a quoted/literal string such as "fox" or "" (but strings in versions prior to 1.0.46.13+ support only "").

## Returning Values to Caller

As described in introduction, a function may optionally return a value to its caller.

    Test := returnTest()
    MsgBox % Test

    returnTest() {
      return 123
    }

If you want to return extra results from a function, you may also use ByRef:

    returnByRef(A,B,C)
    MsgBox % A "," B "," C

    returnByRef(ByRef val1, ByRef val2, ByRef val3)
    {
      val1 := "A"
      val2 := 100
      val3 := 1.1
      return
    }

[v1.0.97+]: Objects and Arrays can be used to return multiple values or even named values:

    Test1 := returnArray1()
    MsgBox % Test1[1] "," Test1[2]

    Test2 := returnArray2()
    MsgBox % Test2[1] "," Test2[2]

    Test3 := returnObject()
    MsgBox % Test3.id "," Test3.val

    returnArray1() {
      Test := [123,"ABC"]
      return Test
    }

    returnArray2() {
      x := 456
      y := "EFG"
      return [x, y]
    }

    returnObject() {
      Test := {id: 789, val: "HIJ"}
      return Test
    }

## Variadic Functions [AHK_L 60+]

When defining a function, write an asterisk after the final parameter to mark the function as variadic, allowing it to receive a variable number of parameters:

    Join(sep, params*) {
        for index,param in params
            str .= param . sep
        return SubStr(str, 1, -StrLen(sep))
    }
    MsgBox % Join("`n", "one", "two", "three")

When a variadic function is called, surplus parameters can be accessed via an object which is stored in the function's final parameter. The first surplus parameter is at `params[1]`, the second at `params[2]` and so on. As with any standard object, `params.MaxIndex()` can be used to determine the highest numeric index (in this case the number of parameters). However, if there are no parameters, MaxIndex returns an empty string.

Notes:

- The "variadic" parameter can only appear at the end of the formal parameter list.
- RegEx callouts cannot be variadic; the "variadic" parameter is tolerated but left blank.
- Callbacks pass surplus parameters by address rather than via an array.

### Variadic Function Calls

While variadic functions can accept a variable number of parameters, an array of parameters can be passed to any function by applying the same syntax to a function-call:

    substrings := ["one", "two", "three"]
    MsgBox % Join("`n", substrings*)

Notes:

- Numbering of parameters within the source array begins at 1.
- Optional parameters may be entirely omitted from the array.
- The array of parameters may contain named items when directly calling a user-defined function.
- The target function may also be variadic, in which case named items are copied even if they have no corresponding formal parameter.
- This syntax can also be used when calling methods or retrieving properties of objects; for example, `Object.Property[Params*]`.

Known limitations:

- Only the last physical parameter can be expanded this way. For example, `Func(x, y*)` is supported but `Func(x*, y)` is not.
- This syntax cannot be used when setting properties of objects, since the last physical parameter is actually the value being assigned.
- There must not be any non-whitespace characters between the asterisk (`*`) and the symbol which ends the parameter list.

## Local and Global Variables

### Local Variables

All variables accessed or created inside a function are local by default (except super-global variables and built-in variables such as Clipboard, ErrorLevel, and A_TimeIdle). Each local variable's contents are visible only to lines that lie inside the function. Consequently, a local variable may have the same name as a global variable and both will have separate contents. Finally, all local variables start off blank each time the function is called.

### Global variables

To refer to an existing global variable inside a function (or create a new one), declare the variable as global prior to using it. For example:

    LogToFile(TextToLog)
    {
        global LogFileName  ; This global variable was previously given a value somewhere outside this function.
        FileAppend, %TextToLog%`n, %LogFileName%
    }

Assume-global mode: If a function needs to access or create a large number of global variables, it can be defined to assume that all its variables are global (except its parameters) by making its first line either the word "global" or the declaration of a local variable. For example:

    SetDefaults()
    {
        global  ; This word may be omitted if the first line of this function will be something like "local MyVar".
        MyGlobal := 33  ; Assigns 33 to a global variable, first creating the variable if necessary.
        local x, y:=0, z  ; Local variables must be declared in this mode, otherwise they would be assumed global.
    }

This assume-global mode can also be used by a function to create a global array, such as a loop that assigns values to `Array%A_Index%`.

Super-global variables [v1.1.05+]: If a global declaration appears outside of any function, it takes effect for all functions by default. This avoids the need to redeclare the variable in each function. However, if a function parameter or local variable with the same name is declared, it takes precedence over the global variable. Variables created by the class keyword are also super-global.

### Static variables

Static variables are always implicitly local, but differ from locals because their values are remembered between calls. For example:

    LogToFile(TextToLog)
    {
        static LoggedLines = 0
        LoggedLines += 1  ; Maintain a tally locally (its value is remembered between calls).
        global LogFileName
        FileAppend, %LoggedLines%: %TextToLog%`n, %LogFileName%
    }

Static Initializers: In versions prior to 1.0.46, all static variables started off blank; so the only way to detect that one was being used for the first time was to check whether it was blank. In v1.0.46+, a static variable may be initialized to something other than `""` by following it with `:=` or `=` followed by one of the following: true, false, a literal integer, a literal floating point number, or a literal/quoted string such as `"fox"`. For example: `static X:=0, Y:="fox"`. Each static variable is initialized only once (before the script begins executing).

[AHK_L 58+]: `Static var := expression` is supported. All such expressions are evaluated immediately before the script's auto-execute section in the order they are encountered in the script.

Assume-static mode [v1.0.48+]: A function may be defined to assume that all its variables are static (except its parameters) by making its first line the word "static". For example:

    GetFromStaticArray(WhichItemNumber)
    {
        static
        static FirstCallToUs := true  ; A static declaration's initializer still runs only once (upon startup).
        if FirstCallToUs  ; Create a static array during the first call, but not on subsequent calls.
        {
            FirstCallToUs := false
            Loop 10
                StaticArray%A_Index% := "Value #" . A_Index
        }
        return StaticArray%WhichItemNumber%
    }

In assume-static mode, any variable that should not be static must be declared as local or global.

### More about locals and globals

Multiple variables may be declared on the same line by separating them with commas as in these examples:

    global LogFileName, MaxRetries := 5
    static TotalAttempts = 0, PrevResult

In v1.0.46+, a local or global variable may be initialized on the same line as its declaration by following it with `:=` or `=` followed by any expression (the `=` operator behaves the same as `:=` in declarations). Unlike static initializers, the initializers of locals and globals execute every time the function is called, but only if/when the flow of control actually reaches them. In other words, a line like `local x = 0` has the same effect as writing two separate lines: `local x` followed by `x = 0`.

Because the words local, global, and static are processed immediately when the script launches, a variable cannot be conditionally declared by means of an IF statement. In other words, a declaration inside an IF's or ELSE's block takes effect unconditionally for all lines between the declaration and the function's closing brace. Also note that it is not currently possible to declare a dynamic variable such as `global Array%i%`.

For commands that create arrays (such as StringSplit), the resulting array is local if the assume-global mode is not in effect or if the array's first element has been declared as a local variable (this is also true if one of the function's parameters is passed -- even if that parameter is ByRef -- because parameters are similar to local variables). Conversely, if the first element has been declared global, a global array is created. However, the common source of confusion below applies even in these cases. The first element for StringSplit is ArrayName0. For other array-creating commands such as WinGet List, the first element is ArrayName (i.e. without the number).

Within a function, any dynamic variable reference such as `Array%i%` always resolves to a local variable unless no variable of that name exists, in which case a global is used if it exists. If neither exists and the usage requires the variable to be created, it is created as a local variable unless the assume-global mode is in effect. Consequently, a function can create a global array manually (by means such as `Array%i% := A_Index`) only if it has been defined as an assume-global function.

Common source of confusion: Any non-dynamic reference to a variable creates that variable the moment the script launches. For example, when used outside a function, `MsgBox %Array1%` creates Array1 as a global the moment the script launches. Conversely, when used inside a function `MsgBox %Array1%` creates Array1 as one of the function's locals the moment the script launches (unless assume-global is in effect), even if Array and Array0 are declared global.

## Dynamically Calling a Function

In v1.0.47.06+, a function (even a built-in function) may be called dynamically via percent signs. For example, `%Var%(x, "fox")` would call the function whose name is contained in Var. Similarly, `Func%A_Index%()` would call Func1() or Func2(), etc., depending on the current value of A_Index.

In v1.1.07.00+, Var in `%Var%()` can contain a function name, function reference or object imitating a function. If the function does not exist, the default base object's __Call meta-function is invoked instead.

If the function cannot be called due to one of the reasons below, the evaluation of the expression containing the call stops silently and prematurely, which may lead to inconsistent results:

- Calling a nonexistent function, which can be avoided by using `If IsFunc(VarContainingFuncName)`. Except for built-in functions, the called function's definition must exist explicitly in the script by means such as #Include or a non-dynamic call to a library function.
- Passing too few parameters, which can be avoided by checking IsFunc()'s return value (which is the number of mandatory parameters plus one). Note: In v1.0.48+, passing too many parameters is tolerated; each extra parameter is fully evaluated (including any calls to functions) and then discarded.

Finally, a dynamic call to a function is slightly slower than a normal call because normal calls are resolved (looked up) before the script begins running.

## Short-circuit Boolean Evaluation

When AND, OR, and the ternary operator are used within an expression, they short-circuit to enhance performance (regardless of whether any function calls are present). Short-circuiting operates by refusing to evaluate parts of an expression that cannot possibly affect its final result. To illustrate the concept, consider this example:

    if (ColorName <> "" AND not FindColor(ColorName))
        MsgBox %ColorName% could not be found.

In the example above, the FindColor() function never gets called if the ColorName variable is empty. This is because the left side of the AND would be false, and thus its right side would be incapable of making the final outcome true.

Because of this behavior, it's important to realize that any side-effects produced by a function (such as altering a global variable's contents) might never occur if that function is called on the right side of an AND or OR.

It should also be noted that short-circuit evaluation cascades into nested ANDs and ORs. For example, in the following expression, only the leftmost comparison occurs whenever ColorName is blank. This is because the left side would then be enough to determine the final answer with certainty:

    if (ColorName = "" OR FindColor(ColorName, Region1) OR FindColor(ColorName, Region2))
        break   ; Nothing to search for, or a match was found.

As shown by the examples above, any expensive (time-consuming) functions should generally be called on the right side of an AND or OR to enhance performance. This technique can also be used to prevent a function from being called when one of its parameters would be passed a value it considers inappropriate, such as an empty string.

In v1.0.46+, the ternary conditional operator (?:) also short-circuits by not evaluating the losing branch.

## Using Subroutines Within a Function

Although a function cannot contain definitions of other functions, it can contain subroutines. As with other subroutines, use Gosub to launch them and Return to return (in which case the Return would belong to the Gosub and not the function).

Known limitation: Currently, the name of each subroutine (label) must be unique among those of the entire script. The program will notify you upon launch if there are duplicate labels.

If a function uses Gosub to jump to a public subroutine (one that lies outside of the function's braces), all variables outside are global and the function's own local variables are not accessible until the subroutine returns. However, A_ThisFunc will still contain the name of the function.

Although Goto cannot be used to jump from inside a function to outside, it is possible for a function to Gosub an external/public subroutine and then do a Goto from there.

Although the use of Goto is generally discouraged, it can be used inside a function to jump to another position within the same function. This can help simplify complex functions that have many points of return, all of which need to do some clean-up prior to returning.

A function may contain externally-called subroutines such as timers, GUI g-labels, and menu items. This is generally done to encapsulate them in a separate file for use with #Include, which prevents them from interfering with the script's auto-execute section. However, the following limitations apply:

- Such subroutines should use only static and global variables (not locals) if their function is ever called normally. This is because a subroutine thread that interrupts a function-call thread (or vice versa) would be able to change the values of local variables seen by the interrupted thread. Furthermore, any time a function returns to its caller, all of its local variables are made blank to free their memory.
- Such subroutines should use only global variables (not static variables) as GUI control variables.
- When a function is entered by a subroutine thread, any references to dynamic variables made by that thread are treated as globals (including commands that create arrays).

## Return, Exit, and General Remarks

If the flow of execution within a function reaches the function's closing brace prior to encountering a Return, the function ends and returns a blank value (empty string) to its caller. A blank value is also returned whenever the function explicitly omits Return's parameter.

When a function uses the Exit command to terminate the current thread, its caller does not receive a return value at all. For example, the statement `Var := Add(2, 3)` would leave Var unchanged if Add() exits. The same thing happens if a function causes a runtime error such as running a nonexistent file (when UseErrorLevel is not in effect).

A function may alter the value of ErrorLevel for the purpose of returning an extra value that is easy to remember.

To call a function with one or more blank values (empty strings), use an empty pair of quotes as in this example: `FindColor(ColorName, "")`

Since calling a function does not start a new thread, any changes made by a function to settings such as SendMode and SetTitleMatchMode will go into effect for its caller too.

The caller of a function may pass a nonexistent variable or array element to it, which is useful when the function expects the corresponding parameter to be ByRef. For example, calling `GetNextLine(BlankArray%i%)` would create the variable `BlankArray%i%` automatically as a local or global (depending on whether the caller is inside a function and whether it has the assume-global mode in effect).

When used inside a function, ListVars displays a function's local variables along with their contents. This can help debug a script.

## Style and Naming Conventions

You might find that complex functions are more readable and maintainable if their special variables are given a distinct prefix. For example, naming each parameter in a function's parameter list with a leading "p" or "p_" makes their special nature easy to discern at a glance, especially when a function has several dozen local variables competing for your attention. Similarly, the prefix "r" or "r_" could be used for ByRef parameters, and "s" or "s_" could be used for static variables.

The One True Brace (OTB) style may optionally be used to define functions. For example:

    Add(x, y) {
        return x + y
    }

## Using #Include to Share Functions Among Multiple Scripts

The #Include directive may be used (even at the top of a script) to load functions from an external file.

Explanation: When the script's flow of execution encounters a function definition, it jumps over it (using an instantaneous method) and resumes execution at the line after its closing brace. Consequently, execution can never fall into a function from above, nor does the presence of one or more functions at the very top of a script affect the auto-execute section.

## Libraries of Functions: Standard Library and User Library [v1.0.47+]

A script may call a function in an external file without having to use #Include. For this to work, a file of the same name as the function must exist in one of the following library directories:

    %A_ScriptDir%\Lib\  ; Local library - requires AHK_L 42+.
    %A_MyDocuments%\AutoHotkey\Lib\  ; User library.
    path-to-the-currently-running-AutoHotkey.exe\Lib\  ; Standard library.

For example, if a script calls a nonexistent function MyFunc(), the program searches for a file named MyFunc.ahk in the user library. If not found there, it searches for it in the standard library. If a match is still not found and the function's name contains an underscore (e.g. MyPrefix_MyFunc), the program searches both libraries for a file named MyPrefix.ahk and loads it if it exists. This allows MyPrefix.ahk to contain both the function MyPrefix_MyFunc and other related functions whose names start with MyPrefix_.

[AHK_L 42+]: The local library is supported and is searched before the user library and standard library.

Although a library file generally contains only a single function of the same name as its filename, it may also contain private functions and subroutines 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.

If a library file uses #Include, the working directory for #Include is the library file's own directory. This can be used to create a redirect to a larger library file that contains that function and others related to it.

The script compiler (ahk2exe) also supports library functions. However, it requires that a copy of AutoHotkey.exe exist in the directory above the compiler directory (which is normally the case). If AutoHotkey.exe is absent, the compiler still works but library functions are not automatically included.

Functions included from a library perform just as well as other functions because they are pre-loaded before the script begins executing.

## Built-in Functions

Any optional parameters at the end of a built-in function's parameter list may be completely omitted. For example, `WinExist("Untitled - Notepad")` is valid because its other three parameters would be considered blank.

A built-in function is overridden if the script defines its own function of the same name. For example, a script could have its own custom WinExist() function that is called instead of the standard one. However, the script would then have no way to call the original function.

External functions that reside in DLL files may be called with DllCall().

### Frequently-used Functions

FileExist(FilePattern): Returns a blank value (empty string) if FilePattern does not exist (FilePattern is assumed to be in A_WorkingDir if an absolute path isn't specified). Otherwise, it returns the attribute string (a subset of "RASHNDOCT") of the first matching file or folder. If the file has no attributes (rare), "X" is returned. FilePattern may be the exact name of a file or folder, or it may contain wildcards (* or ?). Since an empty string is seen as "false", the function's return value can always be used as a quasi-boolean value. For example, the statement `if FileExist("C:\My File.txt")` would be true if the file exists and false otherwise. Similarly, the statement `if InStr(FileExist("C:\My Folder"), "D")` would be true only if the file exists and is a directory. Corresponding commands: IfExist and FileGetAttrib.

GetKeyState(KeyName [, "P" or "T"]): Unlike the GetKeyState command -- which returns D for down and U for up -- this function returns true (1) if the key is down and false (0) if it is up. If KeyName is invalid, an empty string is returned. See GetKeyState for other return values and other usage information.

InStr(Haystack, Needle [, CaseSensitive = false, StartingPos = 1, Occurrence = 1]): Returns the position of an occurrence of the string Needle in the string Haystack. Unlike StringGetPos, position 1 is the first character; this is because 0 is synonymous with "false", making it an intuitive "not found" indicator. If the parameter CaseSensitive is omitted or false, the search is not case sensitive (the method of insensitivity depends on StringCaseSense); otherwise, the case must match exactly. If StartingPos is omitted, it defaults to 1 (the beginning of Haystack). Otherwise, specify 2 to start at Haystack's second character, 3 to start at the third, etc. If StartingPos is beyond the length of Haystack, 0 is returned. If StartingPos is 0 or negative, the search is conducted in reverse (right-to-left) beginning at that offset from the end. Regardless of the value of StartingPos, the returned position is always relative to the first character of Haystack. For example, the position of "abc" in "123abc789" is always 4. Specify 2 for Occurrence to return the position of the second match, 3 for the third match, etc. Related items: RegExMatch(), IfInString, and StringGetPos.

RegExMatch(Haystack, NeedleRegEx [, UnquotedOutputVar = "", StartingPos = 1]): See RegExMatch().

RegExReplace(Haystack, NeedleRegEx [, Replacement = "", OutputVarCount = "", Limit = -1, StartingPos = 1]): See RegExReplace().

SubStr(String, StartingPos [, Length]) [v1.0.46+]: Copies a substring from String starting at StartingPos and proceeding rightward to include at most Length characters (if Length is omitted, it defaults to "all characters"). For StartingPos, specify 1 to start at the first character, 2 to start at the second, and so on (if StartingPos is beyond String's length, an empty string is returned). If StartingPos is less than 1, it is considered to be an offset from the end of the string. For example, 0 extracts the last character and -1 extracts the two last characters (but if StartingPos tries to go beyond the left end of the string, the extraction starts at the first character). Length is the maximum number of characters to retrieve (fewer than the maximum are retrieved whenever the remaining part of the string is too short). Specify a negative Length to omit that many characters from the end of the returned string (an empty string is returned if all or too many characters are omitted). Related items: RegExMatch(), StringMid, StringLeft/Right, StringTrimLeft/Right.

StrLen(String): Returns the length of String. If String is a variable to which ClipboardAll was previously assigned, its total size is returned. Corresponding command: StringLen.

WinActive([WinTitle, WinText, ExcludeTitle, ExcludeText]): Returns the Unique ID (HWND) of the active window if it matches the specified criteria. If it does not, the function returns 0. Since all non-zero numbers are seen as "true", the statement `if WinActive("WinTitle")` is true whenever WinTitle is active. The parameter WinTitle supports ahk_id, ahk_class, and other special strings. See IfWinActive for details about these and other aspects of window activation. Note: An easy way to retrieve the unique ID of the active window is with `ActiveHwnd := WinExist("A")`

WinExist([WinTitle, WinText, ExcludeTitle, ExcludeText]): Returns the Unique ID (HWND) of the first matching window (0 if none) as a hexademinal integer. Since all non-zero numbers are seen as "true", the statement `if WinExist("WinTitle")` is true whenever WinTitle exists. The parameter WinTitle supports ahk_id, ahk_class, and other special strings. See IfWinExist for details about these and other aspects of window searching.

### Miscellaneous Functions

Asc(String): Returns the character code (a number between 1 and 255 (in ANSI builds) or 65535 (in Unicode builds)) for the first character in String. If String is empty, 0 is returned.

Chr(Number): Returns the single character corresponding to the character code indicated by Number. If Number is not in the valid range of character codes, an empty string is returned. Common character codes include 9 (tab), 10 (linefeed), 13 (carriage return), 32 (space), 48-57 (the digits 0-9), 65-90 (uppercase A-Z), and 97-122 (lowercase a-z).

DllCall(): See DllCall().

FileOpen(): Provides object-oriented file I/O. See FileOpen() for more details.

Func(FunctionName) [v1.1.00+]: If FunctionName does not exist explicitly in the script (by means such as #Include or a non-dynamic call to a library function), Func() returns 0. Otherwise, it returns a reference to the function. This can be used to call the function or retrieve information such as the minimum and maximum number of parameters.

GetKeyName(Key), GetKeyVK(Key), GetKeySC(Key) [v1.1.01+]: Retrieves the name/text, virtual key code or scan code of a key. Key can be a VK or SC code, such as "vkA2" or "sc01D", a combination of both, or a key name. For example, both `GetKeyName("vk1B")` and `GetKeyName("Esc")` return "Escape", while `GetKeyVK("Esc")` returns 27.

IsByRef(Var) [v1.1.01+]: Returns 1 if Var is a ByRef parameter and the caller supplied a variable; or 0 if Var is any other kind of variable.

IsFunc(FunctionName) [v1.0.48+]: If FunctionName does not exist explicitly in the script (by means such as #Include or a non-dynamic call to a library function), IsFunc() returns 0. Otherwise, it returns one plus the minimum number parameters (e.g. 1 for a function that requires zero parameters, 2 for a function that requires 1 parameter, etc.). For example, the statements `if IsFunc("MyFunc")` and `if IsFunc(VarContainingFunctionName)` would be true if the function exists, and false otherwise. In v1.1.00+, FunctionName can be a function reference instead of a name. See also: Dynamic function-call, A_ThisFunc

IsLabel(LabelName): Returns a non-zero number if LabelName exists in the script as a subroutine, hotkey, or hotstring (do not include the trailing colon(s) in LabelName). For example, the statement `if IsLabel(VarContainingLabelName)` would be true if the label exists, and false otherwise. This is useful to avoid runtime errors when specifying a dynamic label in commands such as Gosub, Hotkey, Menu, and Gui. See also: Labels.

IsObject() [AHK_L 31+]: Determines if a value is an object. See also: Objects.

ListView and TreeView functions: See the ListView and TreeView pages for details.

NumGet(VarOrAddress [, Offset = 0][, Type = "UPtr"]) [v1.0.47+]: Returns the binary number stored at the specified address+offset. For VarOrAddress, passing `MyVar` is equivalent to passing `&MyVar`. However, omitting the "&" performs better and ensures that the target address is valid (invalid addresses return ""). By contrast, anything other than a naked variable passed to VarOrAddress is treated as a raw address; consequently, specifying `MyVar+0` forces the number in MyVar to be used instead of the address of MyVar itself. For Type, specify UInt, Int, Int64, Short, UShort, Char, UChar, Double, Float or Ptr (though unlike DllCall, these must be enclosed in quotes when used as literal strings); for details see DllCall Types. [AHK_L 57+]: Offset may be omitted entirely; for instance, `NumGet(var, "int")` is valid.

NumPut(Number, VarOrAddress [, Offset = 0][, Type = "UPtr"]) [v1.0.47+]: Stores Number in binary format at the specified address+offset and returns the address to the right of the item just written. For VarOrAddress, passing `MyVar` is equivalent to passing `&MyVar`. However, omitting the "&" performs better and ensures that the target address is valid (invalid addresses return ""). By contrast, anything other than a naked variable passed to VarOrAddress is treated as a raw address; consequently, specifying `MyVar+0` forces the number in MyVar to be used instead of the address of MyVar itself. For Type, specify UInt, Int, Int64, Short, UShort, Char, UChar, Double, Float or Ptr (though unlike DllCall, these must be enclosed in quotes when used as literal strings) (UInt64 is supported in v1.0.48+); for details see DllCall Types. If an integer is too large to fit in the specified Type, its most significant bytes are ignored; e.g. `NumPut(257, var, 0, "Char")` would store the number 1. [AHK_L 57+]: Offset may be omitted entirely; for instance, `NumPut(x, var, "int")` is valid.

OnMessage(MsgNumber [, "FunctionName"]): Monitors a message/event. See OnMessage() for details.

StrGet(Address [, Length] [, Encoding = None ] ) [AHK_L 46+]: Copies a string from a memory address, optionally converting it between code pages. See StrGet() for details.

StrPut(String, Address [, Length] [, Encoding = None ] ) [AHK_L 46+]: Copies a string to a memory address, optionally converting it between code pages. See StrPut() for details.

RegisterCallback(): See RegisterCallback().

Trim() [AHK_L 31+]: See Trim().

VarSetCapacity(UnquotedVarName [, RequestedCapacity, FillByte]): Enlarges a variable's holding capacity or frees its memory. See VarSetCapacity() for details.

### General Math

Note: Math functions generally return a blank value (empty string) if any of the incoming parameters are non-numeric.

Abs(Number): Returns the absolute value of Number. The return value is the same type as Number (integer or floating point).

Ceil(Number): Returns Number rounded up to the nearest integer (without any .00 suffix). For example, `Ceil(1.2)` is 2 and `Ceil(-1.2)` is -1.

Exp(N): Returns e (which is approximately 2.71828182845905) raised to the Nth power. N may be negative and may contain a decimal point. To raise numbers other than e to a power, use the ** operator.

Floor(Number): Returns Number rounded down to the nearest integer (without any .00 suffix). For example, `Floor(1.2)` is 1 and `Floor(-1.2)` is -2.

Log(Number): Returns the logarithm (base 10) of Number. The result is formatted as floating point. If Number is negative, an empty string is returned.

Ln(Number): Returns the natural logarithm (base e) of Number. The result is formatted as floating point. If Number is negative, an empty string is returned.

Mod(Dividend, Divisor): Modulo. Returns the remainder when Dividend is divided by Divisor. The sign of the result is always the same as the sign of the first parameter. For example, both `mod(5, 3)` and `mod(5, -3)` yield 2, but `mod(-5, 3)` and`mod(-5, -3)` yield -2. If either input is a floating point number, the result is also a floating point number. For example, `mod(5.0, 3)` is 2.0 and `mod(5, 3.5)` is 1.5. If the second parameter is zero, the function yields a blank result (empty string).

Round(Number [, N]): If N is omitted or 0, Number is rounded to the nearest integer. If N is positive number, Number is rounded to N decimal places. If N is negative, Number is rounded by N digits to the left of the decimal point. For example, `Round(345, -1)` is 350 and Round (345, -2) is 300. Unlike Transform Round, the result has no .000 suffix whenever N is omitted or less than 1. In v1.0.44.01+, a value of N greater than zero displays exactly N decimal places rather than obeying SetFormat. To avoid this, perform another math operation on Round()'s return value; for example: `Round(3.333, 1)+0`.

Sqrt(Number): Returns the square root of Number. The result is formatted as floating point. If Number is negative, the function yields a blank result (empty string).

### Trigonometry

Sin(Number) | Cos(Number) | Tan(Number) : Returns the trigonometric sine|cosine|tangent of Number. Number must be expressed in radians.

ASin(Number): Returns the arcsine (the number whose sine is Number) in radians. If Number is less than -1 or greater than 1, the function yields a blank result (empty string).

ACos(Number): Returns the arccosine (the number whose cosine is Number) in radians. If Number is less than -1 or greater than 1, the function yields a blank result (empty string).

ATan(Number): Returns the arctangent (the number whose tangent is Number) in radians.

Note: To convert a radians value to degrees, multiply it by 180/pi (approximately 57.29578). To convert a degrees value to radians, multiply it by pi/180 (approximately 0.01745329252). The value of pi (approximately 3.141592653589793) is 4 times the arctangent of 1.

### Other Functions

Polyethene's Command Functions: Provides a callable function for each AutoHotkey command that has an OutputVar. This library can be included in any script via #Include.