{"name":"Function","title":"Function","type":"topic","url":"https://community.bistudio.com/wiki/Function","revid":349916,"updated":"2023-11-20T22:11:06Z","aliases":["Functions - SQF","In-line function","Inline function","function"],"markdown":"> [!IMPORTANT]\n> For a proper writing tutorial, see Writing a Function.\n>\n> See also:\n>\n> - Arma 2: Functions Library\n> - Take On Helicopters: Functions Library\n> - Arma 3: Functions Library\n\nA **function** contains code which usually consists of an *input*, *processing* and *output* part. Functions were first introduced in the Operation Flashpoint: Resistance patch.\nThe main advantages of functions are:\n\n**Improved legibility:** By writing the code once and re-using it by calling the function\n\n**Easier debugging:** If your function contains an error, you only have to fix it in one place\n\n### Types of function\n\n#### Functions-as-files\n\n*See calling functions for how a function-as-file is called.*\n\nFunctions as files are functions stored within a file. These are usually used for larger and more complex functions. The code is evaluated in the same way, however, there are additional commands which must include the file before the function itself can be called.\n\n```sqf\n// Code inside fn_showHint.sqf\nhint \"Function was executed!\"; // Function will show a hint when executed\n```\n\n#### Inline functions\n\nInline functions are functions are technically code which is often stored within a variable or declared as a function parameter. Inline functions operate the same way as functions-as-files as both are evaluated in the same way, but the difference is that inline functions are stored within parentheses `{`}, whereas functions-as-files do not require these.\n\n```sqf\n// Inline function as variable\nTAG_fnc_showHint =\n{\n    hint \"Function was executed!\"; // Function will show a hint when executed\n};\ncall TAG_fnc_showHint;\n```\n\n### Anatomy of a function\n\nWhen scripting, there are two types of functions: functions-as-files and inline functions.\nFunctions-as-files are instances where the a whole file itself is used to house a function, whereas inline functions are either contained within a variable or as a parameter of a function.\nSome built-in functions require functions-as-files, whereas most will support both.\n\n#### Parameters (input)\n\nParameters for functions are available to the function via the magic variable _this.\nDeclaration of parameters can be done using the params command. Common practice for defining parameters is done via the use of private variables and defined variables.\n\n```sqf\n// Code inside fn_showHint.sqf\nparams [\"_text\"];\nhint _text;\n```\n\n```sqf\n// Inline function as variable\nTAG_fnc_showHint =\n{\n    params [\"_text\"];\n    hint _text;\n};\n```\n\n```sqf\n\"Function was executed!\" call TAG_fnc_showHint;\n```\n\nParameters passed to functions are passed **before** the function, rather than after (such as the mathematical or c-like syntax *f(x)*).\n\n```sqf\n// Array variable as parameter\n_myTempParams = [_parameterOne, _parameterTwo];\n_myTempVariableTwo = _myTempParams call myInlineFunction;\n```\n\n```sqf\n// Array as parameter\n_myTempVariable = [_parameterOne,_parameterTwo] call myInlineFunction;\n```\n\n#### Return Values (output)\n\nThe value of the last executed statement in a function is returned to the calling instance.\n\n```sqf\nmy_fnc = {\n    if (_this > 0) exitWith {\n        _this + 1\n    };\n    _this - 1\n};\n\nhint str ( 5 call my_fnc); //  6\nhint str (-5 call my_fnc); // -6\n```\n\nIn the first example \"_this + 1\" is the last executed statement in my_fnc, in the second example it is \"_this - 1\".\n\n> [!NOTE]\n> It was believed at one point that the returning statement should not have a semicolon `;` after it; this is false and having a semicolon does not change anything and is recommended.\n\n```sqf\nmy_fnc = {\n    a = 1;\n    b = 2;\n    c = a + b;\n    c // ← fine\n};\n```\n\n```sqf\nmy_fnc = {\n    a = 1;\n    b = 2;\n    c = a + b;\n    c; // ← better\n};\n```\n\nMore examples:\n\n```sqf\n// myCode.sqf\nprivate _myName = _this select 0;\n\nprivate _returnMe = \"FAIL\";\n\nif (_myName == \"Test\") then\n{\n    _returnMe = \"PASS\";\n};\n_returnMe;\n```\n\n```sqf\n// myCodeInline\nmyCodeReturnValue = {\n    private _myName = _this select 0;\n    private _returnMe = \"FAIL\";\n\n    if (_myName == \"Kaboom\") then\n    {\n        _returnMe = \"PASS\";\n    };\n\n    _returnMe\n};\n\n_myCalledVariable = [\"Kaboom\"] call myCodeReturnValue; // \"PASS\"\n_myCalledVariableFail = [\"Blah\"] call myCodeReturnValue; // \"FAIL\"\n```\n\n```sqf\n// return.sqf\nSTATEMENT 1;\nSTATEMENT 2;\nRETURN_VALUE\n```\n\n```sqf\n// test.sqf\nvalue = call compile preprocessFile \"return.sqf\";\n// value is now RETURN_VALUE\n\ncall compile preprocessFile \"return.sqf\";\n// valid, but RETURN_VALUE is not saved anywhere\n```\n\n#### Execution\n\nFunctions can be executed from several points in the game:\n\n- Other scripts\n- Other functions\n- Scripting lines in the Mission Editor\n- Event Handlers in addon config files\n\nFunctions are first loaded as String from a file via preprocessFile or loadFile. They are then executed via the call or spawn command. Since Armed Assault the loaded String needs to be compiled in order to convert it to Code, which is required for call or spawn.\n\n##### Call\n\nExample (Operation Flashpoint):\n\n```sqf\nmyFunction1 = loadFile \"myFunction1.sqf\";\nmyFunction2 = preprocessFile \"myFunction2.sqf\";\n\ncall myFunction1;\n[1, 2] call myFunction2;\n```\n\nExample (Armed Assault):\n\n```sqf\nmyFunction1 = compile loadFile \"myFunction1.sqf\";\nmyFunction2 = compile preprocessFile \"myFunction2.sqf\";\n\n_result1 = call myFunction1;\n_result2 = [1, 2] call myFunction2;\n```\n\nFunctions executed using call are run *within* the executing instance, which waits for the result of the function.\nUnlike scripts, functions halt all other game engine processes until the function has completed its instructions.\nThis means functions run faster than scripts, and the result of functions is immediate and unambiguous.\nIt can also mean that if a function takes too long to run it will have an adverse effect on game play - large functions or CPU intensive functions can cause the game to seize up until it completes.\nWhen creating a functions you want the function to be short and sweet to achieve the best results.\n\n> [!NOTE]\n> You can still use the special variables and commands of scripts in functions (Armed Assault only)!\n\n##### Spawn\n\nFunctions may also be executed using spawn, but then the function result is not accessible, making it behave more like a procedure.\nSpawned functions will run asynchronously or *alongside* the executing instance. This helps prevent large CPU intensive functions from seizing up the game.\n\nExample (Armed Assault):\n\n```sqf\nmyFunction1 = compile loadFile \"myFunction1.sqf\";\nmyFunction2 = compile preprocessFile \"myFunction2.sqf\";\n\n_param spawn myFunction1;\n[1, 2] spawn myFunction2;\n```\n\n### Examples\n\n#### Example 1: max.sqf\n\nIn this example the function returns maximum of first and second argument.\n\nmax.sqf\n\n```sqf\n//\"Return maximum of first and second argument\";\nparams [\"_a\", \"_b\"];\n[_b, _a] select (_a > _b);\n```\n\nalternative max.sqf (big boys code :))\n\n```sqf\n(_this select 0) max (_this select 1);\n```\n\nexecuting script:\n\n```sqf\nfMax = compile preprocessFile \"max.sqf\";\nmaxValue = [3, 5] call fMax;\n\n// maxValue is now 5\n```\n\n#### Example 2: infantrySafe.sqf\n\nIn this example the function returns no value and switches all units to safe mode.\n\n```sqf\n// Switch all infantry units to safe mode\n{\n    if (vehicle _x == _x) then\n    {\n        _x setBehaviour \"safe\";\n    }\n} forEach _this;\n```\n\n#### Example 3: Inline Function\n\nAn inline-function can be created in any script:\n\n```sqf\nFNC_sayhello = {hint format [\"hello %1\", _this]};\n```\n\nThis function can then be called (in other scripts, functions, unit's init lines, trigger activation fields, etc.) via:\n\n```sqf\nname player call FNC_sayhello\n```\n\nIn case the function doesn't require any arguments you can just call the function.\n\n```sqf\ncall FNC_helloall\n```\n\n### See also\n\n- Scripts\n- SQF Syntax\n- call","sections":[{"heading":null,"level":1,"markdown":"> [!IMPORTANT]\n> For a proper writing tutorial, see Writing a Function.\n>\n> See also:\n>\n> - Arma 2: Functions Library\n> - Take On Helicopters: Functions Library\n> - Arma 3: Functions Library\n\nA **function** contains code which usually consists of an *input*, *processing* and *output* part. Functions were first introduced in the Operation Flashpoint: Resistance patch.\nThe main advantages of functions are:\n\n**Improved legibility:** By writing the code once and re-using it by calling the function\n\n**Easier debugging:** If your function contains an error, you only have to fix it in one place"},{"heading":"Types of function","level":3,"markdown":""},{"heading":"Functions-as-files","level":4,"markdown":"*See calling functions for how a function-as-file is called.*\n\nFunctions as files are functions stored within a file. These are usually used for larger and more complex functions. The code is evaluated in the same way, however, there are additional commands which must include the file before the function itself can be called.\n\n```sqf\n// Code inside fn_showHint.sqf\nhint \"Function was executed!\"; // Function will show a hint when executed\n```"},{"heading":"Inline functions","level":4,"markdown":"Inline functions are functions are technically code which is often stored within a variable or declared as a function parameter. Inline functions operate the same way as functions-as-files as both are evaluated in the same way, but the difference is that inline functions are stored within parentheses `{`}, whereas functions-as-files do not require these.\n\n```sqf\n// Inline function as variable\nTAG_fnc_showHint =\n{\n    hint \"Function was executed!\"; // Function will show a hint when executed\n};\ncall TAG_fnc_showHint;\n```"},{"heading":"Anatomy of a function","level":3,"markdown":"When scripting, there are two types of functions: functions-as-files and inline functions.\nFunctions-as-files are instances where the a whole file itself is used to house a function, whereas inline functions are either contained within a variable or as a parameter of a function.\nSome built-in functions require functions-as-files, whereas most will support both."},{"heading":"Parameters (input)","level":4,"markdown":"Parameters for functions are available to the function via the magic variable _this.\nDeclaration of parameters can be done using the params command. Common practice for defining parameters is done via the use of private variables and defined variables.\n\n```sqf\n// Code inside fn_showHint.sqf\nparams [\"_text\"];\nhint _text;\n```\n\n```sqf\n// Inline function as variable\nTAG_fnc_showHint =\n{\n    params [\"_text\"];\n    hint _text;\n};\n```\n\n```sqf\n\"Function was executed!\" call TAG_fnc_showHint;\n```\n\nParameters passed to functions are passed **before** the function, rather than after (such as the mathematical or c-like syntax *f(x)*).\n\n```sqf\n// Array variable as parameter\n_myTempParams = [_parameterOne, _parameterTwo];\n_myTempVariableTwo = _myTempParams call myInlineFunction;\n```\n\n```sqf\n// Array as parameter\n_myTempVariable = [_parameterOne,_parameterTwo] call myInlineFunction;\n```"},{"heading":"Return Values (output)","level":4,"markdown":"The value of the last executed statement in a function is returned to the calling instance.\n\n```sqf\nmy_fnc = {\n    if (_this > 0) exitWith {\n        _this + 1\n    };\n    _this - 1\n};\n\nhint str ( 5 call my_fnc); //  6\nhint str (-5 call my_fnc); // -6\n```\n\nIn the first example \"_this + 1\" is the last executed statement in my_fnc, in the second example it is \"_this - 1\".\n\n> [!NOTE]\n> It was believed at one point that the returning statement should not have a semicolon `;` after it; this is false and having a semicolon does not change anything and is recommended.\n\n```sqf\nmy_fnc = {\n    a = 1;\n    b = 2;\n    c = a + b;\n    c // ← fine\n};\n```\n\n```sqf\nmy_fnc = {\n    a = 1;\n    b = 2;\n    c = a + b;\n    c; // ← better\n};\n```\n\nMore examples:\n\n```sqf\n// myCode.sqf\nprivate _myName = _this select 0;\n\nprivate _returnMe = \"FAIL\";\n\nif (_myName == \"Test\") then\n{\n    _returnMe = \"PASS\";\n};\n_returnMe;\n```\n\n```sqf\n// myCodeInline\nmyCodeReturnValue = {\n    private _myName = _this select 0;\n    private _returnMe = \"FAIL\";\n\n    if (_myName == \"Kaboom\") then\n    {\n        _returnMe = \"PASS\";\n    };\n\n    _returnMe\n};\n\n_myCalledVariable = [\"Kaboom\"] call myCodeReturnValue; // \"PASS\"\n_myCalledVariableFail = [\"Blah\"] call myCodeReturnValue; // \"FAIL\"\n```\n\n```sqf\n// return.sqf\nSTATEMENT 1;\nSTATEMENT 2;\nRETURN_VALUE\n```\n\n```sqf\n// test.sqf\nvalue = call compile preprocessFile \"return.sqf\";\n// value is now RETURN_VALUE\n\ncall compile preprocessFile \"return.sqf\";\n// valid, but RETURN_VALUE is not saved anywhere\n```"},{"heading":"Execution","level":4,"markdown":"Functions can be executed from several points in the game:\n\n- Other scripts\n- Other functions\n- Scripting lines in the Mission Editor\n- Event Handlers in addon config files\n\nFunctions are first loaded as String from a file via preprocessFile or loadFile. They are then executed via the call or spawn command. Since Armed Assault the loaded String needs to be compiled in order to convert it to Code, which is required for call or spawn."},{"heading":"Call","level":5,"markdown":"Example (Operation Flashpoint):\n\n```sqf\nmyFunction1 = loadFile \"myFunction1.sqf\";\nmyFunction2 = preprocessFile \"myFunction2.sqf\";\n\ncall myFunction1;\n[1, 2] call myFunction2;\n```\n\nExample (Armed Assault):\n\n```sqf\nmyFunction1 = compile loadFile \"myFunction1.sqf\";\nmyFunction2 = compile preprocessFile \"myFunction2.sqf\";\n\n_result1 = call myFunction1;\n_result2 = [1, 2] call myFunction2;\n```\n\nFunctions executed using call are run *within* the executing instance, which waits for the result of the function.\nUnlike scripts, functions halt all other game engine processes until the function has completed its instructions.\nThis means functions run faster than scripts, and the result of functions is immediate and unambiguous.\nIt can also mean that if a function takes too long to run it will have an adverse effect on game play - large functions or CPU intensive functions can cause the game to seize up until it completes.\nWhen creating a functions you want the function to be short and sweet to achieve the best results.\n\n> [!NOTE]\n> You can still use the special variables and commands of scripts in functions (Armed Assault only)!"},{"heading":"Spawn","level":5,"markdown":"Functions may also be executed using spawn, but then the function result is not accessible, making it behave more like a procedure.\nSpawned functions will run asynchronously or *alongside* the executing instance. This helps prevent large CPU intensive functions from seizing up the game.\n\nExample (Armed Assault):\n\n```sqf\nmyFunction1 = compile loadFile \"myFunction1.sqf\";\nmyFunction2 = compile preprocessFile \"myFunction2.sqf\";\n\n_param spawn myFunction1;\n[1, 2] spawn myFunction2;\n```"},{"heading":"Examples","level":3,"markdown":""},{"heading":"Example 1: max.sqf","level":4,"markdown":"In this example the function returns maximum of first and second argument.\n\nmax.sqf\n\n```sqf\n//\"Return maximum of first and second argument\";\nparams [\"_a\", \"_b\"];\n[_b, _a] select (_a > _b);\n```\n\nalternative max.sqf (big boys code :))\n\n```sqf\n(_this select 0) max (_this select 1);\n```\n\nexecuting script:\n\n```sqf\nfMax = compile preprocessFile \"max.sqf\";\nmaxValue = [3, 5] call fMax;\n\n// maxValue is now 5\n```"},{"heading":"Example 2: infantrySafe.sqf","level":4,"markdown":"In this example the function returns no value and switches all units to safe mode.\n\n```sqf\n// Switch all infantry units to safe mode\n{\n    if (vehicle _x == _x) then\n    {\n        _x setBehaviour \"safe\";\n    }\n} forEach _this;\n```"},{"heading":"Example 3: Inline Function","level":4,"markdown":"An inline-function can be created in any script:\n\n```sqf\nFNC_sayhello = {hint format [\"hello %1\", _this]};\n```\n\nThis function can then be called (in other scripts, functions, unit's init lines, trigger activation fields, etc.) via:\n\n```sqf\nname player call FNC_sayhello\n```\n\nIn case the function doesn't require any arguments you can just call the function.\n\n```sqf\ncall FNC_helloall\n```"},{"heading":"See also","level":3,"markdown":"- Scripts\n- SQF Syntax\n- call"}],"categories":["Scripting Topics"],"groups":["Scripting"]}