# Lua/Functions

< Lua

This is a comprehensive list of all functions that can be utilized by Lua scripting, excluding those that are part of userdata structures.

In the "function" column of each table below, bolded text is the actual name of the function, text in italics represents argument types (e.g.: `int`, `mobj_t` or `boolean`) which should not be written in actual Lua scripts when using the function, while arguments surrounded by brackets ( `[ ]` ) are optional and can be omitted when using the function. Unless noted otherwise, the argument names can be chosen freely; the argument names used in this article have no special meaning and are only there to simplify the explanations. Some functions have an alternative syntax, using a different number of arguments or different argument types, for instance.

## Math library

These are the functions included in SRB2's math library. These are generally simple functions that are meant to be used in mathematical contexts.

### Basic math

These are basic mathematical functions that can be used in any context.

Function Return value(s) Description
`abs(int a)` int Returns the absolute value (the number's distance from zero) of `a`.

Note: `abs(INT32_MIN)` does not have a corresponding value, since it would be out of the 32-bit integer range.

`min(int a, int b)` int Returns the smaller value of `a` or `b`.
`max(int a, int b)` int Returns the larger value of `a` or `b`.

### Angle math

These are mathematical functions that are designed to be used with angles. In SRB2, angles are usually represented by large integers where an angle of 1° is represented by the constant `ANG1`, which is equivalent to 11930465 – see Constants > Angles for a full list of constants used to represent angles in this scale. Sometimes, angles may also be represented as fixed-point integers (see below for information on these), where an angle of 1° is represented by the constant `FRACUNIT`.

Some of the functions listed below can be used to convert between these two different representations. Also included here are the basic trigonometric functions (sin, cos and tan), which return values in the fixed-point scale.

Function Return value(s) Description
`sin(angle_t a)` fixed_t Returns the sine of the given angle as a fixed-point value. Output values range from `-FRACUNIT` to `FRACUNIT`.
`cos(angle_t a)` fixed_t Returns the cosine of the given angle as a fixed-point value. Output values range from `-FRACUNIT` to `FRACUNIT`.
`tan(angle_t a)` fixed_t Returns the tangent of the given angle as a fixed-point value. Output values range from about `-1303*FRACUNIT` to about `1303*FRACUNIT`. Undefined values, such as tan(90°) or tan(270°), are represented by `INT32_MIN`.
`asin(fixed_t x)` angle_t
`acos(fixed_t x)` angle_t
`FixedAngle(fixed_t a)`

`fixangle(fixed_t a)`

angle_t Converts an integer in the fixed-point scale to an angle value.

Example: `FixedAngle(90*FRACUNIT)` will return `ANGLE_90`.

`AngleFixed(angle_t a)`

`anglefix(angle_t a)`

fixed_t Converts an angle value to an integer in the fixed-point scale.

'Example: `AngleFixed(ANGLE_90)` will return `90*FRACUNIT`.

`InvAngle(angle_t a)` angle_t Returns the "inverse" of the given angle, i.e., 360° - `a`.

Example: `InvAngle(ANGLE_45)` will return `ANGLE_315`.

### Fixed-point math

These are mathematical functions that are designed to be used with fixed-point integers – i.e., integers expressed as multiples of the constant `FRACUNIT`, or integers bit-shifted to the left by `FRACBITS` (`FRACUNIT` is the same as `1<<FRACBITS`). In this system, `FRACUNIT` itself is treated as 1, `2*FRACUNIT` (or `FRACUNIT*2`) is treated as 2, and so on.

Note: As Lua in SRB2 does not support floating-point numbers (e.g., 0.5, 0.25, 1.1, etc.), non-integer multiples of `FRACUNIT` should instead be written as fractions with the numerator and denominator surrounding the constant – e.g., 0.5 is written as `FRACUNIT/2`, and 1.25 (or 5/4) is written as `5*FRACUNIT/4`.

Function Return value(s) Description
`FixedMul(fixed_t a, fixed_t b)`

`fixmul(fixed_t a, fixed_t b)`

fixed_t Returns the result of multiplying `a` by `b` in the fixed-point scale.

Example: `FixedMul(2*FRACUNIT, 3*FRACUNIT)` will return `6*FRACUNIT`.

`FixedInt(fixed_t a)`

`fixint(fixed_t a)`

int Returns the integer component of `a` as a normal integer.

Example: `FixedInt(45*FRACUNIT)` will return 45.

`FixedDiv(fixed_t a, fixed_t b)`

`fixdiv(fixed_t a, fixed_t b)`

fixed_t Returns the result of dividing `a` by `b` in the fixed-point scale.

Example: `FixedDiv(6*FRACUNIT, 3*FRACUNIT)` will return `2*FRACUNIT`.

`FixedRem(fixed_t a, fixed_t b)`

`fixrem(fixed_t a, fixed_t b)`

fixed_t Returns the remainder of dividing `a` by `b` in the fixed-point scale.

Note: Negative values for `b` are not handled correctly and may slow down the game.

`FixedSqrt(fixed_t a)`

`fixsqrt(fixed_t a)`

fixed_t Returns the square root of `a` in the fixed-point scale.

Example: `FixedSqrt(16*FRACUNIT)` will return `4*FRACUNIT`.

`FixedHypot(fixed_t a, fixed_t b)`

`fixhypot(fixed_t a, fixed_t b)`

fixed_t Returns the hypotenuse of `a` and `b` in the fixed-point scale (i.e., the length of the longest side of a right-angled triangle where the other sides have lengths `a` and `b`).

Example: `FixedHypot(3*FRACUNIT, 4*FRACUNIT)` will return `5*FRACUNIT`.

`FixedFloor(fixed_t a)`

`fixfloor(fixed_t a)`

fixed_t Returns the floor of `a` (the largest integer that is not larger than `a`) in the fixed-point scale.
`FixedTrunc(fixed_t a)`

`fixtrunc(fixed_t a)`

fixed_t Returns the value of `a` rounded to the nearest whole number towards 0 (or `a` truncated to zero decimal digits) in the fixed-point scale.
`FixedCeil(fixed_t a)`

`fixceil(fixed_t a)`

fixed_t Returns the ceiling of `a` (the smallest integer that is not smaller than `a`) in the fixed-point scale.
`FixedRound(fixed_t a)`

`fixround(fixed_t a)`

fixed_t Returns the value of `a` rounded to the nearest whole number away from 0 in the fixed-point scale.

### Miscellaneous

These are simple yet specialized functions that do not fit within the base library.

Function Return value(s) Description
`GetSecSpecial(int special, int section)` int For a given sector type number `special` and a sector type group `section` (expected to be a value between 1 and 4), returns the number of the sector effect from `section` that `special` uses, or 0 if no effect from this group is used. The output values range from 0 to 15 – see Sector types for a list of sector effects and their corresponding effect numbers.

Example: If the sector `sector` uses the Damage (Fire) sector special from Group 1, `GetSecSpecial(sector.special, 1)` will return 3.

`All7Emeralds(int flags)` boolean Returns true if `flags` contains all the emerald flags from `EMERALD1` to `EMERALD7`. Intended to be used for checking either the Single Player/Co-op emeralds collected by all players (`emeralds`), or the multiplayer emeralds (for gametypes Match, CTF and Tag) collected by a particular player (`player.powers[pw_emeralds]`).
`ColorOpposite(int color)` int, int Returns both the opposite skin color for `color`, and the associated sprite frame number for the opposite color (the latter is used for the Level End Sign).

Example: `ColorOpposite(SKINCOLOR_WHITE)` will return the values `SKINCOLOR_BLACK` and 10.

### Easing functions

These are interpolation functions meant to simulate movement between two different points in time in varying degrees of smoothness. Their main use is in the animation of graphics and objects, but there are other applications. Learn more here.

In all of these functions, `t` is the interpolation ratio, ranging from 0 to `FRACUNIT`. `start` is the value where the movement should start and `end` where it's supposed to end: the function then returns the interpolated value corresponding to the provided `t`.

The `start` argument is optional and defaults to 0, with the exception of `ease.inback`, `ease.outback` and `ease.inoutback`, where it is mandatory if the `param` argument needs to be specified as well.

Function Return value(s) Description
`ease.linear(fixed_t t, [[fixed_t start], fixed_t finish])` fixed_t Linear interpolation. The movement speed will be constant throughout the entire duration of the movement.
`ease.insine(fixed_t t, [[fixed_t start], fixed_t finish])` fixed_t InSine function. Movement starts slow and accelerates in a sine function rate.
`ease.outsine(fixed_t t, [[fixed_t start], fixed_t finish])` fixed_t OutSine function. Movement starts fast and decelerates in a sine function rate.
`ease.inoutsine(fixed_t t, [[fixed_t start], fixed_t finish])` fixed_t InOutSine function. Movement starts slow, accelerates and decelerates again near the end, in a sine function rate.
`ease.inquad(fixed_t t, [[fixed_t start], fixed_t finish])` fixed_t InQuad function. Movement starts slow and accelerates in a quadratic function rate.
`ease.outquad(fixed_t t, [[fixed_t start], fixed_t finish])` fixed_t OutQuad function. Movement starts fast and decelerates in a quadratic function rate.
`ease.inoutquad(fixed_t t, [[fixed_t start], fixed_t finish])` fixed_t InOutQuad function. Movement starts slow, accelerates and decelerates again near the end, in a quadratic function rate.
`ease.incubic(fixed_t t, [[fixed_t start], fixed_t finish])` fixed_t InCubic function. Movement starts slow and accelerates in a cubic function rate.
`ease.outcubic(fixed_t t, [[fixed_t start], fixed_t finish])` fixed_t OutCubic function. Movement starts fast and decelerates in a cubic function rate.
`ease.inoutcubic(fixed_t t, [[fixed_t start], fixed_t finish])` fixed_t InOutCubic function. Movement starts slow, accelerates and decelerates again near the end, in a cubic function rate.
`ease.inquart(fixed_t t, [[fixed_t start], fixed_t finish])` fixed_t InQuart function. Movement starts slow and accelerates in a quartic function rate.
`ease.outquart(fixed_t t, [[fixed_t start], fixed_t finish])` fixed_t OutQuart function. Movement starts fast and decelerates in a quartic function rate.
`ease.inoutquart(fixed_t t, [[fixed_t start], fixed_t finish])` fixed_t InOutQuart function. Movement starts slow, accelerates and decelerates again near the end, in a quartic function rate.
`ease.inquint(fixed_t t, [[fixed_t start], fixed_t finish])` fixed_t InQuint function. Movement starts slow and accelerates in a quintic function rate.
`ease.outquint(fixed_t t, [[fixed_t start], fixed_t finish])` fixed_t OutQuint function. Movement starts fast and decelerates in a quintic function rate.
`ease.inoutquint(fixed_t t, [[fixed_t start], fixed_t finish])` fixed_t InOutQuint function. Movement starts slow, accelerates and decelerates again near the end, in a quintic function rate.
`ease.inexpo(fixed_t t, [[fixed_t start], fixed_t finish])` fixed_t InExpo function. Movement starts slow and accelerates in an exponential function rate.
`ease.outexpo(fixed_t t, [[fixed_t start], fixed_t finish])` fixed_t OutExpo function. Movement starts fast and decelerates in an exponential function rate.
`ease.inoutexpo(fixed_t t, [[fixed_t start], fixed_t finish])` fixed_t InOutExpo function. Movement starts slow, accelerates and decelerates again near the end, in an exponential function rate.
`ease.inback(fixed_t t, [[fixed_t start], fixed_t finish, [fixed_t param]])` fixed_t InBack function. Movement initially recoils towards `param`, then accelerates towards the end.
`ease.outback(fixed_t t, [[fixed_t start], fixed_t finish, [fixed_t param]])` fixed_t OutBack function. Movement decelerates towards the end and recoils towards `param`.
`ease.inoutback(fixed_t t, [[fixed_t start], fixed_t finish, [fixed_t param]])` fixed_t InOutBack function. Movement recoils towards `param` both at the start and the end.

## HUD library

These are the functions included in SRB2's HUD library. These functions relate to the head-up display, and are all prefixed with hud. (aside from the patch/string drawing functions). Where they are required, the coordinates provided to these functions should be for the base 320×200 pixel resolution – such that x is a value between 0 and 320 (measured from the left of the screen), y is a value between 0 and 200 (measured from the top of the screen), and x = 0, y = 0 is the top-left corner of the screen. These values will automatically be adjusted by the game for other resolutions.

### Main

Function Return value(s) Description
`hud.enable(string huditem)` nil Enables `huditem` (see below for a list of valid options) if it was disabled by `hud.disable`.
`hud.disable(string huditem)` nil Disables `huditem` (see below for a list of valid options), preventing the game from drawing it.
`hud.enabled(string huditem)` boolean Returns true if `huditem` (see below for a list of valid options) is enabled, false if it was disabled by `hud.disable`.
`hud.add(function func, [string hook])` nil Adds a new HUD drawing function. `hook` determines when the contents of the function are run. See below for a list of valid options for `hook` and the format functions for them take.

Will assume `"game"` if `hook` is not given.

#### Togglable HUD items

Valid huditem string options, for the functions `hud.enable`, `hud.disable` and `hud.enabled`:

Huditem name Description
`"stagetitle"` Stage title card
`"textspectator"` Information text as a spectator
`"crosshair"` Crosshair in first-person
`"score"` Score text and counter
`"time"` Time text and counter
`"rings"` Rings text and counter
`"lives"` Lives picture and counter
`"teamscores"` Team Match/CTF – Team scores
`"weaponrings"` Match/CTF – Weapon ring icons
`"powerstones"` Match/CTF – Chaos Emerald icons
`"nightslink"` NiGHTS link counter
`"nightsdrill"` NiGHTS drill bar
`"nightsrings"` NiGHTS ring counter
`"nightsscore"` NiGHTS score counter
`"nightstime"` NiGHTS time counter
`"nightsrecords"` NiGHTS screen text (Bonus time start, "Get n [more] Spheres", Ending bonuses)
`"rankings"` Rankings/Scores HUD – Multiplayer rankings (all gametypes)
`"coopemeralds"` Rankings/Scores HUD – Single Player Chaos Emerald icons
`"tokens"` Rankings/Scores HUD – Single Player Tokens icon and counter
`"tabemblems"` Rankings/Scores HUD – Single Player Emblems icon and counter
`"intermissiontally"` Intermission – Score tally
`"intermissionmessages"` Intermission – Information text
`"intermissiontitletext"` Intermission – Co-Op/Special Stage title text
`"intermissionemeralds"` Intermission – Special Stage emeralds

#### HUD hooks

Valid hook string options for the function `hud.add`:

Hook name Function format Description
`"game"` `function(drawer v, [player_t stplyr, [camera_t cam]])` The function is run when the Game HUD is displayed. (Default value)

Notes:

• `stplyr` is the player the HUD is being shown for
• `cam` is the camera used by `stplyr`
`"scores"` `function(drawer v)` The function is run when the Rankings/Scores HUD is displayed.
`"title"` `function(drawer v)` The function is run when the Title Screen is displayed.
`"titlecard"` `function(drawer v, [player_t stplyr, [int ticker, [int endtime]]])` The function is run when the stage's level title card is displayed.

Notes:

• `ticker` is the amount of time, in tics, that the title card has been displayed
• `endtime` is the value of `ticker` at which the title card will stop displaying
`"intermission"` `function(drawer v)` The function is run when intermissions between levels are displayed.

### Patch/string drawing functions

These functions can only be used within functions hooked with `hud.add`. Note that the `v` prefix given to all functions listed here is adjustable – this can be any name you like, e.g., `drawer.draw` can be used instead of `v.draw`, if the name of the first argument in the `hud.add` function is given as `drawer` instead of `v`.

Function Return value(s) Description
`v.patchExists(string name)` boolean Returns true if a graphic lump `name` exists in any WAD file loaded, returns false if not.
`v.cachePatch(string name)` `patch_t` Caches a new patch using a graphic with `name` as the name. Returns nil if the graphic does not exist.
`v.draw(int x, int y, patch_t patch, [int flags, [colormap c]])` nil Draws a patch at the screen coordinates given.

Notes:

• `flags` determines the video flags given, which control extra effects such as translucency.
• `c` determines the colormap applied to the patch – use `v.getColormap` or `v.getStringColormap` to obtain a value that can be used here.
`v.getSpritePatch(string/int sprite, [int frame, [int rotation, [angle_t rollangle]]])` `patch_t`, boolean Returns a patch corresponding to the arguments given, and a boolean specifying whether the patch should be flipped. `sprite` may be a sprite number (`SPR_POSS`) or sprite prefix (`"POSS"`). `rotation` is a number between 1 and 8 (1 to 16 for 16 angle sprites). `0` is equivalent to `1` for `rotation` as well. `rollangle` is an angle to rotate the patch counter clockwise.
`v.getSprite2Patch(string/int skin, string/int sprite2, [boolean super?,] [int frame, [int rotation, [angle_t rollangle]]])` `patch_t`, boolean Returns a patch corresponding to the arguments given, and a boolean specifying whether the patch should be flipped. For a description of some of these parameters, see `v.getSpritePatch`.

Notes:

• This is specific to sprites belonging to a Skin, as Skins use a special naming system to avoid naming conflicts between themselves.
• `super?` determines whether to get the super form sprites. This overrides the FF_SPR2SUPER flag from sprite2 if it was also set there
`v.drawScaled(fixed_t x, fixed_t y, fixed_t scale, patch_t patch, [int flags, [colormap c]])` nil Draws a patch at the screen coordinates given, but at a specific scale (e.g.: `FRACUNIT` is normal scale, `FRACUNIT/2` is half normal scale, `2*FRACUNIT` is twice normal scale, etc).

Notes:

• Coordinates are required to be fixed point values (e.g.: `FRACUNIT` is one pixel, `FRACUNIT/2` is half a pixel, `2*FRACUNIT` is two pixels, etc).
• `flags` determines the video flags given, which control extra effects such as translucency.
• `c` determines the colormap applied to the patch – use `v.getColormap` or `v.getStringColormap` to obtain a value that can be used here.
`v.drawStretched(fixed_t x, fixed_t y, fixed_t hscale, fixed_t vscale, patch_t patch, [int flags, [colormap c]])` nil Draws a patch at the screen coordinates given, but at a specific horizontal (`hscale`) and vertical (`vscale`) scale (e.g.: `FRACUNIT` is normal scale, `FRACUNIT/2` is half normal scale, `2*FRACUNIT` is twice normal scale, etc).

Notes:

• Coordinates are required to be fixed point values (e.g.: `FRACUNIT` is one pixel, `FRACUNIT/2` is half a pixel, `2*FRACUNIT` is two pixels, etc).
• `flags` determines the video flags given, which control extra effects such as translucency.
• `c` determines the colormap applied to the patch – use `v.getColormap` or `v.getStringColormap` to obtain a value that can be used here.
`v.drawCropped(fixed_t x, fixed_t y, fixed_t hscale, fixed_t vscale, patch_t patch, int flags, colormap c, fixed_t sx, fixed_t sy, fixed_t w, fixed_t h)` nil Draws a patch at the screen coordinates given, but at a specific horizontal (`hscale`) and vertical (`vscale`) scale, with the sides cut off (`sx`, `sy`, `w`, `h`).

Notes:

• Coordinates are required to be fixed point values (e.g.: `FRACUNIT` is one pixel, `FRACUNIT/2` is half a pixel, `2*FRACUNIT` is two pixels, etc).
• `flags` determines the video flags given, which control extra effects such as translucency – use `0` if you don't want any flags.
• `c` determines the colormap applied to the patch – use `v.getColormap` or `v.getStringColormap` to obtain a value that can be used here, or use `nil` if you don't want a colormap.
• `sx` and `sy` determine how many pixels to cut off the left and top sides of the patch, respectively, (moving the remaining area left and up in the process,) and `w` and `h` determine how wide and tall an area of the patch to draw, not how much to cut off the right and bottom sides.
• `sx`, `sy`, `w`, and `h` select a region of the patch to draw regardless of `hscale` and `vscale` – if you set `w` to `5*FRACUNIT` and set `hscale` to `2*FRACUNIT`, the patch will take up 10 pixels of the screen, as the 5 pixels of the patch are doubled in size. The 5 pixels of the patch that get used will be the same regardless of `hscale` and `vscale`'s values, referring to the patch itself.
`v.drawNum(int x, int y, int num, [int flags])` nil Draws a number at the screen coordinates given.

Notes:

• Numbers drawn by this function will use the same font as numbers from the score/time/rings area of the normal HUD.
• `flags` determines the video flags given, which control extra effects such as color and translucency.
• Unlike `v.drawPaddedNum`, this can also handle negative numbers.
`v.drawPaddedNum(int x, int y, int num, [int digits, [int flags]])` nil Draws a number at the screen coordinates given with a set number of digits. Leading zeros will be added as padding if the number is not large enough to fit the number of digits specified.

Notes:

• Numbers drawn by this function will use the same font as numbers from the score/time/rings area of the normal HUD.
• `flags` determines the video flags given, which control extra effects such as color and translucency.
• Unlike `v.drawNum` this will not handle negative numbers.
`v.drawFill([int x, [int y, [int width, [int height, [int color]]]]])` nil Fills a box of dimensions width by height with a single palette color number at the screen coordinates given. If no parameters are given, this will default to a black box covering the entire screen.

`color` also determines the video flags given, if they are added to the palette color number – only the flags `V_NOSCALESTART`, `V_SNAPTOTOP`, `V_SNAPTOBOTTOM`, `V_SNAPTOLEFT` and `V_SNAPTORIGHT` will have any effect, however.

`v.drawString(int x, int y, string text, [int flags, [string align]])` nil Draws text on the screen at the screen coordinates given.

Notes:

• `flags` determines the video flags given, which control extra effects such as color and translucency.
• `align` determines the alignment of the text or otherwise miscellaneous traits – see below for a full list of valid options.
`v.drawNameTag(int x, int y, string text, [int flags, [int basecolor, [int outlinecolor]]])` nil Draws text in the style of the Character Select name tags at the screen coordinates given.

Notes:

• `basecolor` and `outlinecolor` should be `SKINCOLOR_*` constants.
• `flags` determines the video flags given, which control extra effects such as alignment and translucency.
`v.drawScaledNameTag(fixed_t x, fixed_t y, string text, [int flags, [int scale, [int basecolor, [int outlinecolor]]]])` nil Draws text in the style of the Character Select name tags at the screen coordinates given, but at a specific scale.

Notes:

• `basecolor` and `outlinecolor` should be `SKINCOLOR_*` constants.
• `flags` determines the video flags given, which control extra effects such as alignment and translucency.
`v.drawLevelTitle(int x, int y, string text, [int flags])` nil Draws text in the style of the titlecard level titles on the screen at the screen coordinates given.

Notes:

• `flags` determines the video flags given, which control extra effects such as color and translucency.
`v.stringWidth(string text, [int flags, [string widthtype])` int Returns what the width of the text displayed as graphics on the screen would be.

Notes:

• `flags` determines the video flags given to the string, though only the scaling flags will have any effect on the size of the width returned by the function.
• `widthtype` determines what font the string is in, which can also affect the size of the width returned by the function – see below for a full list of valid options.
`v.nameTagWidth(string text)` int Returns what the width of the text would be if displayed in the style of the Character Select name tag on the screen.
`v.levelTitleWidth(string text)` int Returns what the width of the text would be if displayed in the style of the titlecard level titles on the screen.
`v.levelTitleHeight(string text)` int Returns what the height of the text would be if displayed in the style of the titlecard level titles on the screen. This is affected by whether or not the text has capital characters in it.
`v.getColormap([string/int skin, [int color]])` colormap Returns the colormap to apply to a patch for a particular character skin and/or skin color, as a special type of userdata which can only be used by `v.draw` or `v.drawScaled`. Skin names such as `"sonic"` or `"tails"` can be used, but their skin slot numbers can also be used (e.g., 0 for `"sonic"`, 1 for `"tails"`, etc). If either of these are used, the skin's startcolor value can affect the range of palette colors replaced by the given skin color's palette colors.

Certain skin values have special effects on the colormap returned for a patch to use. They are represented by the following constants:

Value Description
`TC_DEFAULT` Default – this is used by default if no skin is supplied, defaulting to remapping palette colors 160–175 (green) to the given skin color's palette colors.
`TC_BOSS` Boss flash – the colormap used when a boss is flashing in pain; palette color 31 (black) is remapped to palette color 0 (near-white). Overrides the effects of skin colors.
`TC_METALSONIC` Metal Sonic flash – the colormap used when Metal Sonic (Battle) is flashing in pain; palette color 239 (dark blue) is remapped to palette color 0 (near-white). Overrides the effects of skin colors.
`TC_ALLWHITE` All-white flash – the colormap used when Brak Eggman is flashing in pain; all palette colors are remapped to palette color 0 (near-white). Overrides the effects of skin colors.
`TC_RAINBOW` Rainbow flash – same as the default, except it is applied to all palette colors.
`TC_BLINK` Blink flash – all palette colors are remapped to the given skin color's fourth-brightest palette color.
`TC_DASHMODE` Metal Sonic flash – the colormap used when Metal Sonic (Battle) is dashing during pinch phase; multiple colors are remapped. In general, green colors turn into ketchup colors, reds into steel blues, steel blues into oranges. Overrides the effects of skin colors.
`v.getStringColormap(int textcolor)` colormap Returns the colormap to apply to a patch for a particular text color code as a special type of userdata which can only be used by `v.draw` or `v.drawScaled`.

See Lua > Text colors for a list of text colors.

`v.fadeScreen(int color, int strength)` nil Fades the screen to a certain palette color.

Notes:

• If `color` is a palette index, the maximum value of `strength` is 10; otherwise, if `color` is one of the special values in the table below, then the maximum value of `strength` is 31.
• Additionally, certain values of `color` have special effects on the resulting color of the screen pixel:
Value Description
`0xFF00` Fade to black.
`0xFA00` Blue-tinted fade to black.
`0xFB00` Yellow-tinted fade to white.
`v.width()` int Returns the screen width.
`v.height()` int Returns the screen height.
`v.dupx()` int, int Returns the screen's X scale, as both an integer and fixed-point value.
`v.dupy()` int, int Returns the screen's Y scale, as both an integer and fixed-point value.
`v.renderer()` string Returns the renderer used, as a string.

Possible return values:

`v.userTransFlag()` int Returns the value of `translucenthud`, as an alpha video flag, i.e., `V_**TRANS` (see Video flags > Alpha).
`v.localTransFlag()` int Returns the maximum recommended translucency value for HUD items, as an alpha video flag, i.e., `V_**TRANS` (see Video flags > Alpha).

Notes:

• This function differs from `v.userTransFlag` in that `v.userTransFlag` is specified by the user, but `v.localTransFlag` is specified by the game itself.

#### Alignment types

 To doCan someone find a way to represent ALL the new string rendering types? Maybe a nice hierarchical table or something..

Valid alignment string options for `v.drawString`:

Alignment name Description
`"left"` (Default value) The string is left-aligned; the X coordinate is the left edge of the string graphic.
`"right"` The string is right-aligned; the X coordinate is the right edge of the string graphic.
`"center"` The string is center-aligned; the X coordinate is the center of the string graphic.
`"fixed"` The string is left-aligned; the X coordinate is the left edge of the string graphic and coordinates are required to be treated as fixed-point values instead of normal integers, allowing for positions at fractions of a pixel on the screen. (e.g., `FRACUNIT` is one pixel, `FRACUNIT/2` is half a pixel, `2*FRACUNIT` is two pixels, etc.).
`"fixed-center"` The string is center-aligned; the X coordinate is the center of the string graphic and coordinates are required to be treated as fixed-point values instead of normal integers, allowing for positions at fractions of a pixel on the screen. (e.g., `FRACUNIT` is one pixel, `FRACUNIT/2` is half a pixel, `2*FRACUNIT` is two pixels, etc.).
`"fixed-right"` The string is right-aligned; the X coordinate is the right edge of the string graphic and coordinates are required to be treated as fixed-point values instead of normal integers, allowing for positions at fractions of a pixel on the screen. (e.g., `FRACUNIT` is one pixel, `FRACUNIT/2` is half a pixel, `2*FRACUNIT` is two pixels, etc.).
`"small"` The string is drawn in a small font, and is left-aligned.
`"small-center"` The string is drawn in a small font, and is center-aligned.
`"small-right"` The string is drawn in a small font, and is right-aligned.
`"small-fixed"` The string is drawn in a small font, and is left-aligned and coordinates are required to be treated as fixed-point values instead of normal integers, allowing for positions at fractions of a pixel on the screen. (e.g., `FRACUNIT` is one pixel, `FRACUNIT/2` is half a pixel, `2*FRACUNIT` is two pixels, etc.).
`"small-fixed-center"` The string is drawn in a small font, and is center-aligned and coordinates are required to be treated as fixed-point values instead of normal integers, allowing for positions at fractions of a pixel on the screen. (e.g., `FRACUNIT` is one pixel, `FRACUNIT/2` is half a pixel, `2*FRACUNIT` is two pixels, etc.).
`"small-fixed-right"` The string is drawn in a small font, and is right-aligned and coordinates are required to be treated as fixed-point values instead of normal integers, allowing for positions at fractions of a pixel on the screen. (e.g., `FRACUNIT` is one pixel, `FRACUNIT/2` is half a pixel, `2*FRACUNIT` is two pixels, etc.).
`"small-thin"` The string is drawn in a small and thin font, and is left-aligned.
`"small-thin-center"` The string is drawn in a small and thin font, and is center-aligned.
`"small-thin-right"` The string is drawn in a small and thin font, and is right-aligned.
`"small-thin-fixed"` The string is drawn in a small and thin font, and is left-aligned and coordinates are required to be treated as fixed-point values instead of normal integers, allowing for positions at fractions of a pixel on the screen. (e.g., `FRACUNIT` is one pixel, `FRACUNIT/2` is half a pixel, `2*FRACUNIT` is two pixels, etc.).
`"small-thin-fixed-center"` The string is drawn in a small and thin font, and is center-aligned and coordinates are required to be treated as fixed-point values instead of normal integers, allowing for positions at fractions of a pixel on the screen. (e.g., `FRACUNIT` is one pixel, `FRACUNIT/2` is half a pixel, `2*FRACUNIT` is two pixels, etc.).
`"small-thin-fixed-right"` The string is drawn in a small and thin font, and is right-aligned and coordinates are required to be treated as fixed-point values instead of normal integers, allowing for positions at fractions of a pixel on the screen. (e.g., `FRACUNIT` is one pixel, `FRACUNIT/2` is half a pixel, `2*FRACUNIT` is two pixels, etc.).
`"thin"` The string is drawn in a thin font, and is left-aligned.
`"thin-center"` The string is drawn in a thin font, and is center-aligned.
`"thin-right"` The string is drawn in a thin font, and is right-aligned.
`"thin-fixed"` The string is drawn in a thin font, and is left-aligned and coordinates are required to be treated as fixed-point values instead of normal integers, allowing for positions at fractions of a pixel on the screen. (e.g., `FRACUNIT` is one pixel, `FRACUNIT/2` is half a pixel, `2*FRACUNIT` is two pixels, etc.).
`"thin-fixed-center"` The string is drawn in a thin font, and is center-aligned and coordinates are required to be treated as fixed-point values instead of normal integers, allowing for positions at fractions of a pixel on the screen. (e.g., `FRACUNIT` is one pixel, `FRACUNIT/2` is half a pixel, `2*FRACUNIT` is two pixels, etc.).
`"thin-fixed-right"` The string is drawn in a thin font, and is right-aligned and coordinates are required to be treated as fixed-point values instead of normal integers, allowing for positions at fractions of a pixel on the screen. (e.g., `FRACUNIT` is one pixel, `FRACUNIT/2` is half a pixel, `2*FRACUNIT` is two pixels, etc.).

#### Width types

Valid widthtype options for `v.stringWidth`:

Alignment name Description
`"normal"` (Default value) The string is drawn in a normal font.
`"small"` The string is drawn in a small font.
`"thin"` The string is drawn in a thin font.

### Random functions

These functions can only be used within functions hooked with `hud.add`. Note that the `v` prefix given to all functions listed here is adjustable – this can be any name you like, e.g., `drawer.RandomFixed` can be used instead of `v.RandomFixed`, if the name of the first argument in the `hud.add` function is given as `drawer` instead of `v`.

Function Return value(s) Description
`v.RandomFixed()` fixed_t Returns a random integer between 0 and `FRACUNIT-1` (65535).
`v.RandomByte()` int Returns a random integer between 0 and 255.
`v.RandomKey(int a)` int Returns a random integer between 0 and `a - 1`.

Note: `a` should not be larger than 65536. Otherwise, there will be only 65536 possible different results this function can return, which will be spread out across the full range given; the rest of the numbers will be skipped.

`v.RandomRange(int a, int b)` int Returns a random integer between `a` and `b`, inclusive.

Note: The difference between `a` and `b` should not be larger than 65536. Otherwise, there will be only 65536 possible different results this function can return, which are spread out across the full range given; the rest of the numbers will be skipped.

`v.SignedRandom()` int Returns a random integer between -128 and 127.
`v.RandomChance(fixed_t p)` boolean Returns true `p`% of the time, where `p` is a fixed-point number between 0 and `FRACUNIT`. For example, `v.RandomChance(FRACUNIT/2)` returns true 50% of the time.

## Console library

These are the functions included in SRB2's console library. These functions relate to the console and/or commands/variables to be executed by the console.

Function Return value(s) Description
`COM_AddCommand(string name, function fn, [int flags])` nil Format of `fn`: `function(player_t player, [string arg, [...]])`

Registers a console command with the name `name` that executes the specified function when called. The first argument of the function is the player who executed the command, and all subsequent arguments are arguments passed to the command.

`flags` may be any of the flags listed below, OR'ed together, or none.

Flag Description
COM_SPLITSCREEN The command is only available in splitscreen, and the splitscreen player is passed to `fn`.
COM_LOCAL Local execution, does not send over the network buffer (Technical comment: `COM_LOCAL` makes your commands NetXCmd free).
`COM_BufAddText(player_t player, string text)` nil Adds the specified text to `player`'s console buffer, but does not actually execute the command.
`COM_BufInsertText(player_t player, string text)` nil Executes a console command in `player`'s console.
`CV_RegisterVar(table t)` `consvar_t` Format of `t`: `table{string name, string defaultvalue, int flags, table PossibleValue, function(consvar_t var) func}`

Registers a console variable with the name `name` for use in the console and returns the console variable created. `defaultvalue` is the default value for the console variable in string form. `PossibleValue` is a list or range of possible values that are allowed for the variable. `flags` is an integer storing the flags to be given to the console variable; see Constants > Console variable flags for a list of them. If the `CV_CALL` flag is set, the function `func` is executed when the variable is changed: the sole argument passed to such function is the console variable itself.

`PossibleValue` can either be set to the name of one of the pre-existing PossibleValue ranges listed below, or a table listing possible values, or set to nil if not needed:

Name Range
`CV_OnOff` `{Off = 0, On = 1}`
`CV_YesNo` `{No = 0, Yes = 1}`
`CV_Unsigned` `{MIN = 0, MAX = 999999999}`
`CV_Natural` `{MIN = 1, MAX = 999999999}`
`CV_TrueFalse` `{False = 0, True = 1}`

Custom PossibleValue tables need to be formatted as such:

```{string1=value1, string2=value2, [...]}
```

This gives each possible value listed in the table a string name of its own, which can be used in the console itself when the variable is in use.

If `MIN` and `MAX` are used as string names for possible value entries, these will act as the minimum and maximum of a bounded range of possible values, allowing any value in-between the two to be picked as well. Otherwise, the selectable values for the console variable are limited explicitly only to the possible value entries listed in the table. Example of custom `MIN` and `MAX` values:

```{MIN = 20, MAX = 50}
```

The contents of `CV_RegisterVar` can alternatively be laid out as such:

```CV_RegisterVar({name = , defaultvalue = , flags = , PossibleValue = , func = })
```

Or:

```CV_RegisterVar({
name = ,
defaultvalue = ,
flags = ,
PossibleValue = ,
func =
})
```

In the above two layouts, the names of the variables of the table are written out, and so do not need to be placed in any particular order unlike as in the above.

`CV_FindVar(string var)` `consvar_t` Returns the corresponding console variable named `var`.
`CV_Set(consvar_t cvar, string/int value)` nil Sets the value of the target console variable `cvar` to `value`.

This will call the console variable's callback function, if it has one.

`CV_StealthSet(consvar_t cvar, string/int value)` nil Sets the value of the target console variable `cvar` to `value` without calling its callback function.
`CV_AddValue(consvar_t cvar, int increment)` nil Adds the value `increment` to the console variable `cvar`. `increment` can also be a negative number.

If performing the addition causes the variable's value to go below its minimum or above its maximum, the final value will wrap around those bounds.

There are special cases for some console variables:

• `pointlimit`: If gametype is `GT_MATCH`, `increment` is multiplied by 50.
• `forceskin`: Cycles through usable skins. Follows the same conditions as `R_SkinUsable` for the resulting value.
`CONS_Printf(player_t player, string text)` nil Prints the text given to the console for `player`. This is similar to `print(text)`, but this will only print for one player.

Certain ASCII characters will have special effects when printed out to the console by this function. These can either be given using decimal (`\nnn`) or hexadecimal codes (`\xnn` or `\xnnnn`), e.g.: `\130` and `\x82` will both cause text following the code to turn yellow. See Lua > Special characters for a list of these.

## Blockmap search library

These are the functions included in SRB2's Blockmap search library. This consists of only one function, `searchBlockmap`.

Function Return value(s) Description
`searchBlockmap(string searchtype, function fn, mobj_t refmobj, [fixed_t x1, fixed_t x2, fixed_t y1, fixed_t y2])` boolean Does a search through a specified area of the blockmap. This can be used to find Objects or linedefs in the area and run a function for each them. This function returns `true` if the search was not interrupted at any point, and `false` if it was.

`searchtype` determines what is being searched for:

• `"objects"` – search for Objects (`mobj_t`) in the blockmap. Note that Objects with `MF_NOBLOCKMAP` are not in the blockmap, and so will not be found by this function.
• `"lines"` – search for linedefs (`line_t`) in the blockmap.

`fn` is the function to be used on each found Object/linedef. The format of the function depends on the `searchtype`:

• `"objects"` search – `function(mobj_t refmobj, mobj_t foundmobj)`
• `"lines"` search – `function(mobj_t refmobj, line_t foundline)`

In both cases, `refmobj` is the same Object given in `searchBlockmap` arguments, while `foundmobj`/`foundline` are an Object/linedef found in the blockmap.

The return value of `fn` affects how searching continues afterwards:

• `nil` – Continue searching as normal.
• `false` – Stop searching in the current block and move on to the next block.
• `true` – End the search entirely.

If `fn` returns `true` or `false` at any point, `searchBlockmap` will return `false`.

`refmobj` is a reference Object of your choice used within searching. If you do not supply X/Y ranges to search in, it defaults to checking within the Object's radius in both axes (relative to its current X/Y position in the map). If `refmobj` was removed mid-search, the search stops and `searchBlockmap` will return `false`. However, `refmobj` is not an optional argument (a dummy Object can be used if necessary).

`x1`, `x2`, `y1`, and `y2` are optional arguments, determining the range of X and Y coordinates in the map to search the blockmap between, if given. They determine the left, right, bottom and top block positions of the blockmap to search in, specifically. If not given, `refmobj` is used to set the range by default. Note that all Objects or linedefs in each block spanned by the range will be checked, not just those within the range itself. To force searching within an exact range, manual position or distance checking needs to be added to the searching function.

## Input library

These are functions included in SRB2's input library. They relate to client-side input events and are all prefixed with input. The `keynum` or `keyname` arguments required for some of these functions are obtainable from `keyevent_t` variables provided by KeyUp or KeyDown hooks.

Function Return value(s) Description
`input.gameControlDown(int gc)` boolean Returns whether the game control `gc` (a `GC_*` constant) is currently pressed for the first player.
`input.gameControl2Down(int gc)` boolean Returns whether the game control `gc` (a `GC_*` constant) is currently pressed for the second player.
`input.gameControlToKeyNum(int gc)` int,int Returns the numbers of the keys bound to the game control `gc` (a `GC_*` constant) for the first player.
`input.gameControl2ToKeyNum(int gc)` int,int Returns the numbers of the keys bound to the game control `gc` (a `GC_*` constant) for the second player.
`input.joyAxis(int axissel)` int Returns the first player's joystick's position on the axis specified by `axissel` (a `JA_*` constant).
`input.joy2Axis(int axissel)` int Returns the second player's joystick's position on the axis specified by `axissel` (a `JA_*`) constant).
`input.keyNumToName(int keynum)` string Returns the name of the key specified by the key number `keynum`.
`input.keyNameToNum(string keyname)` int Returns the number of the key specified by the key name `keyname`.
`input.keyNumPrintable(string keynum)` boolean Returns whether the key specified by the key number `keynum` corresponds to a printable character.
`input.shiftKeyNum(string keynum)` int Returns the capitalized form of key number `keynum`.
`input.getMouseGrab()` boolean Returns whether the first player's mouse is grabbed (locked and invisible) by the window.
`input.setMouseGrab(boolean grab)` nil Sets whether the first player's mouse is grabbed (locked and invisible) by the window.
`input.getCursorPosition()` int, int Returns the position of the cursor relative to the top-left corner of the window.

## Base library

These are the functions included in SRB2's Base library. All of these functions except for the ones listed under "Base functions" are internal functions from SRB2's source code that are made available for Lua usage. They are grouped here according to their location in the source code.

### Base functions

Function Return value(s) Description
`print(string output, [string output2, [...]])` nil Outputs text in the console. Each output string will be separated into different lines.

Certain ASCII characters will have special effects when printed out to the console by this function. These can either be given using decimal (`\nnn`) or hexadecimal codes (`\xnn` or `\xnnnn`). For example, `\130` and `\x82` will both cause text following the code to turn yellow. See Lua > Special characters for a list of these.

`chatprint(string output, [boolean sound])` nil Outputs text in the chat window (or the console if it cannot be output in the chat window). Each output string will be separated into different lines. If `sound` is set to true (defaults to false), a sound will be played when sent.

Certain ASCII characters will have special effects when printed out to the chat window or console by this function. These can either be given using decimal (`\nnn`) or hexadecimal codes (`\xnn` or `\xnnnn`).For example, `\130` and `\x82` will both cause text following the code to turn yellow. See Lua > Special characters for a list of these.

`chatprintf(player_t player, string output, [boolean sound])` nil Outputs text in the chat window (or the console if it cannot be output in the chat window). Unlike `chatprint`, the text will only be output for the player supplied in `player`. Each output string will be separated into different lines. If `sound` is set to true (defaults to false), a sound will be played when sent.

Certain ASCII characters will have special effects when printed out to the chat window or console by this function. These can either be given using decimal (`\nnn`) or hexadecimal codes (`\xnn` or `\xnnnn`). For example, `\130` and `\x82` will both cause text following the code to turn yellow. See Lua > Special characters for a list of these.

`freeslot(string resource, [string resource2, [...]])` int × amount of arguments Automatically initializes a new named resource based on the name given, declaring the name for the next freeslot available for the appropriate resource type. (e.g.: `"MT_NEWOBJECT"` will add a new Object type). (See Freeslot for more information.) This function will return the integer representing each resource successfully allocated; unsuccessful allocations will not be returned (e.g. one failed freeslot allocation out of a list of four will only return the successful three).

Example: `freeslot("MT_NEWOBJECT", "S_NEWSTATE")` will return `MT_NEWOBJECT`, `S_NEWSTATE`.

Note: Resources that begin with `MT_` (Object type), `S_` (state), or `SPR_` must be in all capital letters, while `sfx_` resources must be all lowercase.

`addHook(string hook, function fn, [int/string extra])` nil Binds a function to a hook (i.e., the function will be run when a particular event happens). See Lua/Hooks for more information on using this function.
`super(mobj_t actor, int var1, int var2)` nil Only use this inside of an overridden `A_` action. Calls the original version of the action.
`IsPlayerAdmin(player_t player)` boolean Returns true if the player has been given administrative privileges by the server via the `promote` command, or has logged as an admin via a preset password; false if not. Note that the host themselves will not necessarily return true to this function, since their administrative powers are there by default.
`userdataType(* v)` string Returns the userdata type of `v` as a string.

Possible strings that may be returned by this function:

• `"unknown"`
• `"state_t"`
• `"mobjinfo_t"`
• `"sfxinfo_t"`
• `"skincolor_t"`
• `"skincolor_t.ramp"`
• `"spriteinfo_t"`
• `"spriteframepivot_t[]"`
• `"spriteframepivot_t"`
• `"taglist"`
• `"mobj_t"`
• `"mapthing_t"`
• `"player_t"`
• `"ticcmd_t"`
• `"skin_t"`
• `"player_t.powers"`
• `"skin_t.soundsid"`
• `"skin_t.sprites"`
• `"skin_t.sprites[]"`
• `"vertex_t"`
• `"line_t"`
• `"side_t"`
• `"subsector_t"`
• `"sector_t"`
• `"ffloor_t"`
• `"pslope_t"`
• `"vector2_t"`
• `"vector3_t"`
• `"mapheader_t"`
• `"polyobj_t"`
• `"consvar_t"`
• `"sector_t.lines"`
• `"sector_t.taglist"`
• `"line_t.sidenum"`
• `"line_t.args"`
• `"line_t.stringargs"`
• `"mapthing_t.args"`
• `"mapthing_t.stringargs"`
• `"bbox"`
• `"hudinfo_t"`
• `"patch_t"`
• `"colormap"`
• `"camera_t"`
• `"action"`
• `"luabanks[]"`
`reserveLuabanks()` `luabanks[]` Reserves and then returns a `luabanks` array.

`Luabanks` is a method to save and load custom information in a savefile.
The indexes 0 through 15 in the `luabanks` array contains `UINT32` integers, which are freely modifiable by the modder.

When reserved in an addon with custom gamedata, this array is automatically updated when a save file is loaded, and saved alongside the normal save information when the game writes the save to a file, akin to saving the emeralds collected in a save.

Trying to call this function in a hook or otherwise calling it more than once, including if another mod has already called it before, will result in an error. As such, only one `luabanks` mod can be loaded in at any one time.

`registerMetatable(table metatable)` nil
 To doRephrase. See merge request for original description.

Registers the metatable `metatable`.

Currently, tables passed through NetVars hooks or stored in custom player/mobj fields will not keep their metatable, because SRB2 does not keep track of them by default.

This issue can be solved by calling this function during script loading to have SRB2 register the given `metatable`, in such a way that the tables/userdata this metatable is attached to (via `setmetatable()`) will not lose their metatable when sent to a client connecting to the server.

`userdataMetatable(string userdataname)` table or nil Takes a string as only argument and returns the metatable

associated to the userdata type this string refers to. Returns nil if the string does not refer to a valid userdata type.

`getTimeMicros()` `int`
 To doRephrase? See merge request.

Returns a modified value of SDL's high resolution counter.

This is used as a profiling timer function: Two values returned by this function can be substracted from each other to find out how much time (in microseconds) is between them. This can be used to measure the performance of Lua code, and as such shouldn't be used for anything else other than performance measurements.

Warning about OpenGL and HUD hooks: measuring Lua API calls that contain OpenGL API calls can give unreliable/confusing results because of the asynchronous nature of OpenGL. This applies to measuring HUD drawing functions in OpenGL mode.

Example:

```-- Get the time before the code to be profiled
local first = getTimeMicros()

-- Run a slow function/block, like:
local nums = {}
for i = 1,10000 do
nums[i] = 0

for j = 1,i do
nums[j] = \$ + 1
end
end

-- Get the time after the code to be profiled
local second = getTimeMicros()

-- Substract the newest time against the oldest time
local result = second - first
-- This result will represent the time between [first] and [second], in microseconds
```

### G_Game

Function Return value(s) Description
`G_BuildMapName([int map])` string Converts the given map number to a map name in `MAPXX` format, where XX is the extended map number. If no map number is given, the current map's number will be used.

Example: `G_BuildMapName(100)` will return `"MAPA0"`.

`G_BuildMapTitle([int map])` string Returns the name and act number of map number `map`.

Example: `G_BuildMapTitle(1)` will return `"Greenflower Zone 1"`.

`G_FindMap(string query)` INT32, string, table
 To doImprove the description

Returns:

```[1] => map number
[2] => map title
[3] => search frequency table
```

The frequency table is unsorted. It has the following format:

```{
['mapnum'],

['matchd'] => matches in map title string
['keywhd'] => matches in map keywords

The above two tables have the following format:

{
['pos'] => offset from start of string
['siz'] => length of match
}...

['total'] => the total matches
}...
```
`G_FindMapByNameOrCode(string query)` INT32, string or nil
 To doImprove the description

Returns:

```[1] => map number
[2] => map title
```
`G_DoReborn(int playernum)` nil Respawns the player whose player number is `playernum`. Avoid calling this function directly in Single Player; set the player's `player.playerstate` to `PST_REBORN` instead.
`G_EnoughPlayersFinished()` boolean Checks if the required players to exit the level is reached. The requirement depends of `playersforexit`.
`G_SetCustomExitVars([int nextmap, [int skipstats]])` nil Alternative version:
• `G_SetCustomExitVars()`

Changes the settings that will apply when the current level is exited, but does not actually exit the level. If a value for `nextmap` is given, it sets the map number the game will change to once the level ends. If `skipstats` is set to 1 (defaults to 0), the statistics screen will be skipped. If set to 2, it will additionally skip the level end cutscene, if applicable. Calling the function with no arguments will clear the custom settings.

`G_ExitLevel()` nil Immediately exits the level.

If `G_SetCustomExitVars` was called beforehand, the level will exit using the custom settings set.

`G_IsSpecialStage([int map])` boolean Returns true if the map with the given map number is a Special Stage; otherwise returns false. If no map number is given, the current map's number will be used.
`G_AddGametype(table t)` nil Registers a custom gametype into the game. See Custom gametypes for more information on using this function.
`G_GametypeUsesLives()` boolean Returns true if the current gametype uses lives (Single Player, Coop or Competition); otherwise returns false. If in Record Attack or a NiGHTS level, this returns false regardless of gametype.
`G_GametypeUsesCoopLives()` boolean Returns true if the current gametype uses the cooplives command, otherwise it returns false.
`G_GametypeUsesCoopStarposts()` boolean Returns true if the current gametype uses the coopstarposts command, otherwise it returns false.
`G_GametypeHasTeams()` boolean Returns true if the current gametype has teams (Team Match or CTF); otherwise returns false.
`G_GametypeHasSpectators()` boolean Returns true if the current gametype supports spectators (Match, CTF or Tag); otherwise returns false.
`G_RingSlingerGametype()` boolean Returns true if the current gametype supports firing rings (Match, CTF or Tag) or if `ringslinger` is enabled; otherwise returns false.
`G_PlatformGametype()` boolean Returns true if the current gametype is a "platformer" gametype (Single Player, Coop, Race or Competition); otherwise returns false.
`G_CoopGametype()` boolean
`G_TagGametype()` boolean
 To doRewrite the description to take into account the gametype rules

Returns true if the current gametype is Tag or Hide and Seek; otherwise returns false.

`G_CompetitionGametype()` boolean
`G_AddPlayer(int skin, int color, string name, int bottype)` player_t
 To doRephrase? See merge request.

Adds a bot to the game. `skin`, `color` and `name` specify how bot will look like. `bottype` can be one of the following values:

• `BOT_NONE` – Player is not bot
• `BOT_2PAI` – Bot acts like Tails from SinglePlayer
• `BOT_2PHUMAN` – Bot acts like Tails but his controls can be taken by human Player 2
• `BOT_MPAI` – Bot has unique AI. It can be modded with LUA through `BotTiccmd` hook

Note: Console commands (COM_BufInsertText) can't be executed as a bot at the moment.

`G_RemovePlayer(int playernum)` nil Removes the bot. (Cannot be applied to human players.)
`G_SetUsedCheats(boolean silent?)` nil
`G_TicsToHours(int tics)` int Converts the given time in tics to hours.
`G_TicsToMinutes(int tics, [boolean full?])` int Converts the given time in tics to minutes. By default, this returns only values between 0 and 59, assuming the return value is used for timers with both "hours" and "minutes" displays (e.g., hours:minutes:seconds). If `full?` is given and set to true, then hours (or multiples of 60 minutes) will not be truncated, allowing for return values over 59. This latter case is used for timers without an "hours" display (e.g., minutes:seconds).
`G_TicsToSeconds(int tics)` int Converts the given time in tics to seconds. This returns only values between 0 and 59, assuming the return value is used for timers with both "minutes" and "seconds" displays (e.g., hours:minutes:seconds).
`G_TicsToCentiseconds(int tics)` int Converts the given time in tics to centiseconds. This returns only values between 0 and 99, assuming the return value is used for timers with both "seconds" and "centiseconds" displays (e.g., minutes:seconds.centiseconds).
`G_TicsToMilliseconds(int tics)` int Converts the given time in tics to milliseconds. This returns only values between 0 and 999.

### M_Random

Function Return value(s) Description
`P_RandomFixed()` fixed_t Returns a random integer between 0 and `FRACUNIT-1` (65535).
`P_RandomByte()` int Returns a random integer between 0 and 255.
`P_RandomKey(int a)` int Returns a random integer between 0 and `a - 1`.

Note: `a` should not be larger than 65536. Otherwise, there will be only 65536 possible different results this function can return, which will be spread out across the full range given; the rest of the numbers will be skipped.

`P_RandomRange(int a, int b)` int Returns a random integer between `a` and `b`, inclusive.

Note: The difference between `a` and `b` should not be larger than 65536. Otherwise, there will be only 65536 possible different results this function can return, which are spread out across the full range given; the rest of the numbers will be skipped.

`P_SignedRandom()` int Returns a random integer between -128 and 127.
`P_RandomChance(fixed_t p)` boolean Returns true `p`% of the time, where `p` is a fixed-point number between 0 and `FRACUNIT`. For example, `P_RandomChance(FRACUNIT/2)` returns true 50% of the time.

Function Return value(s) Description
`M_MoveColorAfter(UINT16 color, UINT16 target)` nil Shifts the given `color` skincolor ahead of the `target` skincolor. Reflected in the multiplayer setup menu and other functions, but will not affect `color`'s index value.
`M_MoveColorBefore(UINT16 color, UINT16 target)` nil Shifts the given `color` skincolor behind the `target` skincolor. Reflected in the multiplayer setup menu and other functions, but will not affect `color`'s index value.
`M_GetColorAfter(UINT16 color)` UINT16 Returns the skincolor after `color` as a `UINT16` value.
`M_GetColorBefore(UINT16 color)` UINT16 Returns the skincolor before `color` as a `UINT16` value.

### M_Map

Function Return value(s) Description
`M_MapNumber(string name)` INT32 Returns the map number for a map identified by the last two characters in its name, or 0 if no map corresponds to these characters.

### P_Enemy

Function Return value(s) Description
`P_CheckMeleeRange(mobj_t actor)` boolean Returns true if `actor`'s target is within the actor's melee range, false if not.
`P_JetbCheckMeleeRange(mobj_t actor)` boolean Same as `P_CheckMeleeRange`, except the melee range is adjusted for use with the Jetty-Syn Bomber.
`P_FaceStabCheckMeleeRange(mobj_t actor)` boolean Same as `P_CheckMeleeRange`, except the melee range is adjusted for use with the CastleBot FaceStabber.
`P_SkimCheckMeleeRange(mobj_t actor)` boolean Same as `P_CheckMeleeRange`, except the melee range is adjusted for use with the Skim.
`P_CheckMissileRange(mobj_t actor)` boolean Returns true if `actor` is able to shoot its target at the moment. Returns false if `actor.reactiontime` has not reached 0 or `actor` cannot see the target. Otherwise, the result is randomly decided based on the distance between them.
`P_NewChaseDir(mobj_t actor)` nil Changes `actor.movedir` to be the decided best direction of the actor to be in relation to its target (provided it has one, of course).

Note: These directions include only the 8 basic cardinal directions (N, S, E, W, NE etc.; also see the `DI_` constants).

`P_LookForPlayers(mobj_t actor, [fixed_t dist, [boolean allaround?, [boolean tracer?]]])` boolean Can `actor` find a player with the conditions provided? If yes, this returns true and the actor's target is set to the first player found. Otherwise this returns false and the actor's target is unchanged.
• `dist` determines the distance limit for the actor to check for players in. If dist is set to 0, the distance limit will be infinite.
• `allaround?` determines whether the actor will look all around itself for players or just within 90° of the direction it is currently facing.
• `tracer?` determines whether to use `actor.tracer` instead of `actor.target`. This is useful for homing missiles such as the Deton, since missiles set their target to the Object who shot them and thus cannot harm it.

`dist` defaults to 0 if not given, while `allaround?` and `tracer` both default to false if not given.

### P_Inter

Function Return value(s) Description
`P_RemoveShield(player_t player)` nil Removes any shield `player` may be carrying. This will not throw back the player nor play a sound.
`P_DamageMobj(mobj_t target, [mobj_t inflictor, [mobj_t source, [int damage, [int damagetype]]]])` boolean Inflicts damage on the `target` Object, causing it to lose a certain amount of health and use the state determined by `target.info.painstate`. However, if `target` has lost all health as a result of this function, `P_KillMobj` is called by this function instead. The return value of this function depends on whether `target` was damaged or not – if it was, this returns true; if not, this returns false.

`inflictor` and `source` determine where the damage came from: `inflictor` is the Object that dealt the damage, `source` is the source of the damage (or where `inflictor` came from). For instance, when a projectile fired by a player or enemy damages `target`, `inflictor` should be set the projectile itself, and `source` to the Object that fired the projectile. However, in situations where a player or enemy directly damages `target`, `inflictor` and `source` are usually both set to the same Object. If the damage comes from a level hazard such as damaging sector specials or crushers (or otherwise from nowhere at all), it is best to set both these arguments to nil.

`damage` determines the amount of damage to deal to `target`, or the number of health points removed from it. `damagetype` determines the damage type that will be dealt. Should the damage type have the death flag set, the `target` will be killed.

Note that, if not given, `inflictor` and `source` both default to nil, `damage` defaults to 1 and `damagetype` to 0. The hooks `ShouldDamage` and `MobjDamage` can be used modify or replace some of the effects of this function.

A list of damage types can be found here.

`P_KillMobj(mobj_t target, [mobj_t inflictor, [mobj_t source, [int damagetype]]])` nil Kills the `target` Object, making it become intangible as well as using the state determined by `target.info.deathstate` (if set to nil, the Object will be removed from existence). If `target` is an enemy or boss, and the Object that killed it was a player or one of their projectiles, points may be awarded to this player. Flickies (and/or other items) will also be spawned by enemies killed by this function. `damagetype` determines the damage type that was dealt.

`inflictor` and `source` follow the same meanings as in `P_DamageMobj`, and both default to nil if not given. `damagetype` defaults to 0. The hook `MobjDeath` can be used to modify or replace some of the effects of this function.

A list of damage types can be found here.

Note: This function is not designed to be used to kill players directly; use `P_DamageMobj` with a special damage type instead.

`P_PlayerRingBurst(player_t player, [int numrings])` nil Spills the specified number of rings. Also spills all weapon panels, ammo and emeralds `player` may be carrying at the time, but does not throw back `player`. If `numrings` is not given (or set to -1), it will default to the player's current ring count (i.e. `player.rings`).

In normal gameplay, up to 32 rings will be spilled by this function; the remainder will not be spawned. The speed at which the rings are flung depends on the duration since the last time this function was used (determined by `player.losstime`). In NiGHTS levels, however, the player will drop all rings if they have the player flag `PF_NIGHTSFALL` (given when the player has run out of time as Super Sonic). In addition, the rings will always be flung at the same speed regardless of `player.losstime`'s value.

Note that this function does not actually affect `player.rings`; this must be modified manually in order for the player to actually lose rings. This does not apply to any weapon panels, ammo and/or emeralds also spilled by this function.

`P_PlayerWeaponPanelBurst(player_t player)` nil Spills all weapon panels that `player` is carrying, but does not throw back `player`. Unlike the rings in `P_PlayerRingBurst`, the player will actually lose the weapon panels spilled by this function.
`P_PlayerWeaponAmmoBurst(player_t player)` nil Spills all weapon panels and ammo that `player` is carrying, but does not throw back `player`. Unlike the rings in `P_PlayerRingBurst`, the player will actually lose the weapon ammo spilled by this function.
`P_PlayerWeaponPanelOrAmmoBurst(player_t player)` nil Spills weapon panels/ammo depending of what `player` is carrying, but does not throw back `player`. If `player` doesn't have a weapon but it's ammo, then the ammo is spilled instead. Otherwise, if `player` does have the weapon then the weapon is spilled. Unlike the rings in `P_PlayerRingBurst`, the player will actually lose the weapon panels/ammo spilled by this function.
`P_PlayerEmeraldBurst(player_t player, [boolean toss?])` nil Spills all emeralds that `player` is carrying, but does not throw back `player`. If `toss` is true, all the emeralds are thrown in the player's forward direction and a toss delay of 2 seconds is set (for players tossing emeralds). Otherwise, the emeralds are spilled around the player (for players dropping emeralds after being hurt). Unlike the rings in `P_PlayerRingBurst`, the player will actually lose the emeralds spilled by this function.
`P_PlayerFlagBurst(player_t player, [boolean toss?])` nil Spills any CTF flags that `player` is carrying, but does not throw back `player`. If `toss` is true, the flag is thrown in the player's forward direction and a toss delay of 2 seconds is set (for players tossing a flag). Otherwise, the direction is random (for players dropping a flag after being hurt).
`P_PlayRinglossSound(mobj_t source, [player_t player])` nil Plays one of the 4 player ring spill sounds randomly, which can vary depending on the skin, or plays the Mario ring loss sound if in Mario mode. `source` is the Object the sound came from.
`P_PlayDeathSound(mobj_t source, [player_t player])` nil Plays one of the 4 player death sounds randomly, which can vary depending on the skin. `source` is the Object the sound came from.
`P_PlayVictorySound(mobj_t source, [player_t player])` nil Plays one of the 4 player victory taunt sounds randomly, which can vary depending on the skin. `source` is the Object the sound came from.
`P_PlayLivesJingle(player_t player)` nil Plays the extra life jingle. By default this is the extra life music, but in Mario mode maps or if `Use1upSound` is enabled in the `MainCfg` block, this is instead a sound effect. If the music is used, the player's `pw_extralife` timer is set to `ExtraLifeTics + 1`.
`P_CanPickupItem(player_t player, [boolean weapon?])` boolean Returns true if `player` can pick up the item, returns false if `player` is a bot or is flashing after being hurt.
`P_DoNightsScore(player_t player)` nil Awards score to `player` NiGHTS-style; spawns a floating score item which changes appearance depending on the player's current link count and whether the player is in bonus time.
`P_DoMatchSuper(player_t player)` nil Gives invincibility, speed shoes, and steals score from others if `player` has all 7 Match Emeralds. Will remove the emeralds afterwards.

### P_Map

Function Return value(s) Description
`P_CheckPosition(mobj_t mobj, fixed_t x, fixed_t y)` boolean, `mobj_t` Checks if the position `(x, y)` is valid for the Object `mobj`. Note that this does not actually teleport the Object to the given coordinates; it only tests what would happen if it was at that position.

This function returns false if either a) the Object has been blocked by a wall or another Object, or b) the Object has been removed from the map during checking; otherwise it will return true to signal the position is not blocked. This function additionally returns the "tmthing" Object set during the run of the function, which in the majority of cases will be `mobj` itself.

The blockmap is checked for any Objects or walls to collide with; any Objects with `MF_NOBLOCKMAP` cannot be collided with by this function. Note that Objects using this function that have the `MF_NOCLIP` will not clip with other Objects or walls at all, while Objects with `MF_NOCLIPTHING` will not clip with Objects but can still be blocked by walls.

`P_TryMove(mobj_t mobj,fixed_t x, fixed_t y, [boolean allowdropoff?])` boolean, `mobj_t` Tries to move the Object `mobj` to the X/Y coordinates supplied (all done in the same tic), checking each position to make sure the Object is not blocked on the way there. If it is blocked by a wall or another Object, or the height of the sector is too small to fit in, this will return false and leave the Object where it was to begin with (i.e., the move failed); otherwise this will return true with the Object at the coordinates supplied. This function additionally returns the "tmthing" Object set during the run of the function, which in the majority of cases will be `mobj` itself.

`allowdropoff` determines whether to stop the Object from falling off a platform too low to step-down when moving, or let it continue regardless of this – if `allowdropoff` is false and the Object would be falling off a platform if it continued, this will return false.

Note: Pushable Objects will also move along anything on top with them when they are moved. Objects with `MF_NOCLIP` will be able to move straight to the specified position without being blocked by anything, and `allowdropoff` will not affect them.

`P_Move(mobj_t actor, int speed)` boolean, `mobj_t` Moves the `actor` Object in its current direction (using `actor.movedir` rather than the angle), moving forward a distance of `speed*FRACUNIT` (`speed` does not need to be multiplied by `FRACUNIT`). Returns true when the actor has moved; returns false if the actor cannot move, does not have a direction to move in or is dead. This function additionally returns the "tmthing" Object set during the run of the function, which in the majority of cases will be `actor` itself.
`P_TeleportMove(mobj_t mobj, fixed_t x, fixed_t y, fixed_t z)` boolean, `mobj_t` Teleports the Object straight to the `x`, `y`, and `z` coordinates supplied, but does not account for whether the Object will be stuck in this position, and will always return true. This function additionally returns the "tmthing" Object set during the run of the function, which in the majority of cases will be `mobj` itself.

Note: This function has been deprecated since the introduction of 2.2.11, we recommend you use the P_SetOrigin or P_MoveOrigin instead.

`P_SetOrigin(mobj_t mobj, fixed_t x, fixed_t y, fixed_t z)` boolean, `mobj_t` Teleports the Object to the `x`, `y`, and `z` coordinates supplied without any positional checks. As all interpolation values of the Object are reset, this function should be used for instant movement. It will always return true, plus the "tmthing" Object set during the run of the function, which in the majority of cases will be `mobj` itself.
`P_MoveOrigin(mobj_t mobj, fixed_t x, fixed_t y, fixed_t z)` boolean, `mobj_t` Teleports the Object to the `x`, `y`, and `z` coordinates supplied without any positional checks. As all interpolation values of the Object are kept, this function should be used for continuous movement. This function additionally returns the "tmthing" Object set during the run of the function, which in the majority of cases will be `mobj` itself.
`P_SlideMove(mobj_t mo)` nil Slides `mo` along a wall using its current X/Y momentum. This assumes that `mo` has already been blocked by a wall, so this searches for the wall that blocked it before sliding.
`P_BounceMove(mobj_t mo)` nil Bounces `mo` off a wall using its current X/Y momentum. This assumes that `mo` has already been blocked by a wall, so this searches for the wall that blocked it before bouncing.
`P_CheckSight(mobj_t source, mobj_t target)` boolean Checks if `target` is visible from `source`'s position – if it is, this returns true; otherwise it returns false. This function is also able to check if FOFs are blocking the line of sight. Note that the angles the Objects are facing are not taken into consideration, only their map coordinates and heights.
`P_CheckHoopPosition(mobj_t hoop, fixed_t x, fixed_t y, fixed_t z, fixed_t radius)` nil Optimized version of `P_CheckPosition` specifically designed for `MT_HOOPCOLLIDE`. `radius` is unused.
`P_RadiusAttack(mobj_t inflictor, mobj_t source, fixed_t radius, [int damagetype, [boolean sightcheck]])` nil Damages all damageable Objects in the blockmap around `inflictor`, with `source` being the Object that `inflictor` came from (if not the same as `inflictor` itself). `radius` is the distance limit around `inflictor` to damage other Objects in, which will automatically be scaled with `inflictor`'s scale. `damagetype` determines the type of damage dealt to Objects hit by the attack. If `sightcheck` is true or not set, the target objects will only be damaged if they have line of sight with the `inflictor`'s position; If false, the attack will be able to harm objects behind walls.

Objects that cannot be damaged by `P_RadiusAttack` include: any Objects sharing the same type as `inflictor`, the `source` Object itself, monitors, bosses, non-shootable Objects (`MF_SHOOTABLE` is not set), or any Objects not within the blockmap at all (`MF_NOBLOCKMAP` is set).

`P_FloorzAtPos(fixed_t x, fixed_t y, fixed_t z, fixed_t height)` fixed_t Returns what would be the floorz (the absolute Z position of the floor) at the `x`, `y`, and `z` coordinates supplied. `height` should be the height of the Object you want to check this for (needed for checking solid/quicksand FOFs). Keep in mind the coordinates and perhaps even the height do not necessarily have to be the actual position of an existing Object.
`P_CeilingzAtPos(fixed_t x, fixed_t y, fixed_t z, fixed_t height)` fixed_t Returns what would be the ceilingz (the absolute Z position of the ceiling) at the `x`, `y`, and `z` coordinates supplied. `height` should be the height of the Object you want to check this for (needed for checking solid/quicksand FOFs). Keep in mind the coordinates and perhaps even the height do not necessarily have to be the actual position of an existing Object.
`P_DoSpring(mobj_t spring, mobj_t object)` nil The `spring` Object sends `object` into the air like a spring. `spring` does not necessarily have to be an Object with the `MF_SPRING` flag, but it should have least all the same attributes as one; see the Spring article for more details. Note that `object` will also be given the `MFE_SPRUNG` flag, marking it as having already touched a spring this tic; the flag will automatically be removed the next tic. If this function is called while `object` has this flag set, it will have no effect.
`P_TryCameraMove(camera_t camera, fixed_t x, fixed_t y)` boolean Tries to move the Camera `camera` to the X/Y coordinates supplied (all done in the same tic), checking each position to make sure the Camera is not blocked on the way there. If it is blocked by a wall, or the height of the sector is too small to fit in, this will return false and leave the Camera where it was to begin with (i.e., the move failed); otherwise this will return true with the Camera at the coordinates supplied.
`P_TeleportCameraMove(camera_t camera, fixed_t x, fixed_t y, fixed_t z)` nil Teleports the Camera straight to the `x`, `y`, and `z` coordinates supplied, but does not account for whether the Camera will be stuck in this position.

### P_Maputl

Function Return value(s) Description
`P_AproxDistance(fixed_t dx, fixed_t dy)` fixed_t Returns the approximate distance between two points, where `dx` is the distance between the X coordinates and `dy` is the distance between the Y coordinates.

Note: This function will normally return a positive value, except if the distance is 38768 fracunits or larger, in which case it will return negative values.

`P_ClosestPointOnLine(fixed_t x, fixed_t y, line_t line)` fixed_t, fixed_t Alternative version: `P_ClosestPointOnLine(fixed_t x, fixed_t y, fixed_t x1, fixed_t y1, fixed_t x2, fixed_t y2)`

Returns the X and Y coordinate (as two separate returned values) of the closest point to the point `(x,y)` on the line `line`.

If a set of 4 fixed-point integers (`x1`, `y1`, `x2`, `y2`) is given instead of a `line_t` variable, these become the coordinates of a custom-defined line that goes through the points `(x1,y1)` and `(x2,y2)`.

`P_PointOnLineSide(fixed_t x, fixed_t y, line_t line)` int Alternative version: `P_PointOnLineSide(fixed_t x, fixed_t y, fixed_t x1, fixed_t y1, fixed_t x2, fixed_t y2)`

Returns 0 if the point `(x,y)` is on the "front" side of the given line, or 1 if it is on the "back" side.

If a set of 4 fixed-point integers (`x1`, `y1`, `x2`, `y2`) is given instead of a `line_t` variable, these become the coordinates of a custom-defined line that goes through the points `(x1,y1)` and `(x2,y2)`.

### P_Mobj

Function Return value(s) Description
`P_SpawnMobj(fixed_t x, fixed_t y, fixed_t z, int type)` `mobj_t` Creates and returns a new Object of the given type at the given coordinates `x`, `y`, and `z`. Various attributes may be given to it as soon as it is spawned, such as a skin color or secondary Object flags. Further Objects may be spawned within this function to be linked to the new Object if necessary. If the new Object is given the `MF_RUNSPAWNFUNC` flag during this function, the action set for the Object type's `SpawnState` property will be run by this function.

The hook `MobjSpawn` can be used to modify or replace some of the effects of this function.

Note: This is the basic function for spawning all Objects in SRB2. All other listed Lua functions (including actions) that spawn an Object therefore use this function internally to spawn them, and any changes made to this function by the `MobjSpawn` hook will affect them as well.

`P_SpawnMobjFromMobj(mobj_t origin, fixed_t x, fixed_t y, fixed_t z, int type)` `mobj_t` Same as `P_SpawnMobj`, except the coordinates given are relative to the `origin` Object. The spawned object's scale and vertical flip are inherited from the origin object.
`P_RemoveMobj(mobj_t mobj)` nil Removes the Object and its thinker from existence. The hook `MobjRemoved` can be used to apply additional effects to this function.

Note: The removed Object cannot be referenced again in Lua after using this function.

Note 2: This function will produce an error if it attempts to remove an Object belonging to a player (i.e.: `mobj.player` must be nil for this function to work).

`P_IsValidSprite2(mobj_t mobj, int sprite2)` boolean Returns true if `mobj` can display `sprite2`, false if not. This is specific to objects that have a Skin, as Skins use a special naming system to avoid naming conflicts between themselves.
`P_SpawnLockOn(player_t player, mobj_t target, state_t state)` nil Spawns MT_LOCKON in `state` above `mobj`. Lua exclusive.
`P_SpawnMissile(mobj_t source, mobj_t dest, int type)` `mobj_t` Spawns a missile Object with the default missile positioning, sending it forward to `dest` at the value of its `Speed` Object type property. This returns the Object spawned by the function.
`P_SpawnXYZMissile(mobj_t source, mobj_t dest, int type, fixed_t x, fixed_t y, fixed_t z)` `mobj_t` Spawns a missile Object at specific `x`, `y`, and `z` coordinates, sending it forward to `dest` at the value of its `Speed` Object type property. This returns the Object spawned by the function.
`P_SpawnPointMissile(mobj_t source, fixed_t dest_x, fixed_t dest_y, fixed_t dest_z, int type, fixed_t x, fixed_t y, fixed_t z)` `mobj_t` Same as `P_SpawnXYZMissile`, except the destination is given via the coordinates `dest_x`, `dest_y` and `dest_z` instead of a destination Object `dest`. This returns the Object spawned by the function.
`P_SpawnAlteredDirectionMissile(mobj_t source, int type, fixed_t x, fixed_t y, fixed_t z, int angle_shift)` `mobj_t` Spawns a missile Object at the value of its `Speed` Object type property, but with an angle relative to the direction its source Object is facing. The source Object must be a missile itself and must have a target set – the spawned missile will also use this target. This returns the Object spawned by the function.
`P_ColorTeamMissile(mobj_t missile, player_t player)` nil In Team Match or CTF, this changes `missile`'s color to match the player's team color (red if player is in the red team, or steel blue if in the blue team). In any other gametype, this will do nothing.
`P_SPMAngle(mobj_t source, int type, angle_t angle, [int allowaim, [int flags2]])` `mobj_t` Spawns a missile Object at the value of its `Speed` Object type property, assuming `source` is a player. `angle` sets what direction to fire the missile in. If `allowaim` is set to a non-zero value, the player's vertical aiming angle determines the vertical angle the missile is fired at. Otherwise, it is fired straight forward. `flags2` allows additional flags to be added on to the missile's secondary Object flags (such as `MF2_RAILRING` to make the missile act like the rail ring weapon). This returns the Object spawned by the function.
`P_SpawnPlayerMissile(mobj_t source, int type, [int flags2])` `mobj_t` Functionally identical to `P_SPMAngle`, except that the missile's angle will always be `source`'s angle and the player's vertical aiming angle will always be used. This returns the Object spawned by the function.
`P_MobjFlip(mobj_t mobj)` int Returns -1 if the object is flipped (i.e., `MFE_VERTICALFLIP` is set in the Object's extra Object flags) or 1 if it is not.
`P_GetMobjGravity(mobj_t mobj)` fixed_t Returns the amount of gravity to be applied to the Object.
`P_WeaponOrPanel(int type)` boolean Returns true if the given Object type is any of the weapon ammo/panel types.
`P_FlashPal(player_t player, int type, int duration)` nil Sets the type and duration of the player's palette. This is used in the game to flash the screen in events such as when the player is teleported, or when an Armageddon Shield explodes – see PLAYPAL for the palette numbers available in the default `PLAYPAL` lump.
`P_GetClosestAxis(mobj_t source)` `mobj_t` Returns the closest Axis Object (of type `MT_AXIS`) to `source`.
`P_SpawnParaloop(fixed_t x, fixed_t y, fixed_t z, fixed_t radius, int number, int type, angle_t rotangle, [int state, [boolean spawncenter?]])` nil Spawns a loop of Objects at the given coordinates `x`, `y`, and `z`. `radius` determines the radius of the loop, `number` determines how many Objects are in the loop, `type` determines the type of the Objects spawned, `state` is the starting state of the Objects (defaults to `S_NULL` if not set, which means the state will not be changed), and `rotangle` sets the vertical rotation of the loop. If `spawncenter` is true, the Objects will all start at the center and move outwards, otherwise they will start at a distance of 4/5×`radius` from the center and move inwards. By default, `spawncenter` is `false`.

In SRB2, this function is called when the player uses the paraloop move while flying on a NiGHTS 2D track. It is also called by the action `A_RingExplode` to create an explosion effect. In both cases, the function is called multiple times in order to form a paraloop "ball". Specifically, this is done by calling the function 16 times with the same values, except that `rotangle` is set to different multiples of `ANGLE_22h` each time.

Below is some example Lua code that recreates `A_RingExplode`'s explosion, using an Object `actor` as a spawn position:

```for i=0,15
P_SpawnParaloop(actor.x, actor.y, actor.z + actor.height, FixedMul(actor.info.painchance, actor.scale), 16, MT_NIGHTSSPARKLE, i*ANGLE_22h, S_NULL, true)
end
```

Notes:

• For all Objects spawned by this function, `mobj.fuse` is set to `(FixedDiv(radius,5*(FRACUNIT/4))>>(FRACBITS+2)) + 1`, and `mobj.tics` to `mobj.fuse - 7`. The minimum values it can set for them are 2 and 1, respectively. These values are set to make sure that the Objects will all disappear eventually.
• The horizontal rotation cannot be controlled by this function.
`P_BossTargetPlayer(mobj_t actor, [boolean closest?])` boolean Used by bosses to search for players. Returns true if a player is targeted, false if not. If `closest` is true, the boss will target the closest player it can find, otherwise the boss will target the first player it finds.
`P_SupermanLook4Players(mobj_t actor)` boolean Similar to `P_LookForPlayers`, except `actor` can search anywhere in the map and even through walls.
`P_SetScale(mobj_t mobj, fixed_t scale)` nil Sets `mobj`'s scale to a new value. Editing `mobj.scale` does the same thing – however, calling `P_SetScale` will not affect `mobj.destscale`, unlike editing `mobj.scale` directly.
`P_InsideANonSolidFFloor(mobj_t mobj, ffloor_t rover)` boolean Returns true if the given FOF exists and is non-solid, and `mobj` is inside it.
`P_CheckDeathPitCollide(mobj_t mobj)` boolean Returns true if `mobj` is touching a death pit floor/ceiling.
`P_CheckSolidLava(ffloor_t rover)` boolean Returns true if the FOF `rover` is a solid lava block.
`P_CanRunOnWater(player_t player, ffloor_t rover)` boolean Returns true if the FOF `rover` is a water block and `player` is able to run on top of it. This requires the player to be at running speed, but other criteria include whether they have the swimming or running on water abilities, or if they're currently super.
`P_MaceRotate(mobj_t center, int baserot, int baseprevrot)` nil TODO
`P_CreateFloorSpriteSlope(mobj_t mobj)` nil Creates `pslope_t` userdata into `mobj` that allows it to render as a sloped floor sprite. It can then be accessed and manipulated in `mobj.floorspriteslope`.
`P_RemoveFloorSpriteSlope(mobj_t mobj)` nil Wipes the `mobj.floorspriteslope` field from `mobj`, effectively ceasing its rendering as a sloped floor sprite. Recommended to use when a sloped floor sprite is no longer needed, since they can increase memory usage.
`P_RailThinker(mobj_t mobj)` boolean Used by the Rail Ring. Instantly moves `mobj` if it has a type of momentum, returns `true` if the movement has failed or `mobj` was removed by movement (like death pit, missile hits wall, etc.).
`P_XYMovement(mobj_t mobj)` nil Moves `mobj` through the X/Y coordinate if it has momentum.
`P_RingXYMovement(mobj_t mobj)` nil Used by rings. Moves `mobj` through the X/Y coordinate if it has momentum but it will always slides to the walls if it collides with one.
`P_SceneryXYMovement(mobj_t mobj)` nil Used by scenery objects. Moves `mobj` through the X/Y coordinate if it has momentum but it will always slides to the walls if it collides with one and it does not have friction on the air or with the flag `MF_NOCLIPHEIGHT`.
`P_ZMovement(mobj_t mobj)` boolean Moves `mobj` through the Z coordinate if it has momentum, returns `false` if `mobj` was killed/exploded/removed, `true` otherwise.
`P_RingZMovement(mobj_t mobj)` nil Used by rings. Moves `mobj` through the Z coordinate if it has momentum. It has special functionallity to avoid getting clipped through FOFs
`P_SceneryZMovement(mobj_t mobj)` boolean Used by scenery objects. Moves `mobj` through the Z coordinate if it has momentum, returns `false` if `mobj` was killed/exploded/removed, `true` otherwise. It has special functionallity to avoid getting clipped through FOFs, checking for gravity, collide with death pits, and ajusting with the floors/ceilling
`P_PlayerZMovement(mobj_t mobj)` nil Used by players. Moves `mobj` through the Z coordinate if it has momentum. It has special functionallity to avoid getting clipped through FOFs, checking for gravity, play animations, have slope physics, and some NiGHTs logic.

### P_Polyobj

Function Return value(s) Description
`polyobjects.GetForNum(polyobj_t polyobject, INT32 id)` `polyobj_t` Retrieves a polyobject by its numeric ID. Returns `nil` if no such polyobject exists.

### P_Slopes

Function Return value(s) Description
`P_GetZAt(pslope_t slope, fixed_t x, fixed_t y, [fixed_t z])` fixed_t Returns the corresponding Z position on the slope for the X/Y coordinates given. If `slope` is nil, returns `z` instead.
`P_ButteredSlope(mobj_t mobj)` nil Slides `mobj` on the slope it is standing on, if it exists.

### P_Spec

Function Return value(s) Description
`P_Thrust(mobj_t mobj, angle_t angle, fixed_t move)` nil Boosts `mobj`'s horizontal momentum by the value of `move` in the direction of `angle`. Note that this will apply momentum relatively; i.e., all existing momentum applied to the Object in any direction is retained – if `P_Thrust` is used every tic, this can result in the Object accelerating in the given direction. If the Object has `MF2_TWOD`, only momentum in the X direction is modified – momentum in the Y direction is unaffected. To replace all existing momentum instead of adding to it, see `P_InstaThrust`.
`P_SetMobjStateNF(mobj_t mobj, int statenum)` boolean `mobj`'s state is changed to the specified state number, but without running any actions. If `statenum` is `S_NULL`, the Object will be removed (does not work on players).

Note: This should not be confused with the normal method of applying new states, which would be using the code `mobj.state = statenum` (where `mobj` and `statenum` follow the same meanings as the arguments for `P_SetMobjStateNF`).

`P_DoSuperTransformation(player_t player, [boolean giverings?])` nil Changes `player` into its Super form. If `giverings?` is true, the player is given 50 rings when the function runs. Note that the player still needs all seven Chaos Emeralds as well as the SF_SUPER skin flag for this function to work.
`P_ExplodeMissile(mobj_t missile)` nil Death sequence for the `missile` Object. Halts `missile`'s momentum, alters its flags, plays its `DeathSound` and sets its state to `DeathState`. Does not do anything if the Object has `MF_NOCLIPTHING` set, as it is used as a dummy flag to indicate when a missile is already "dead".
`P_PlayerTouchingSectorSpecial(player_t player, int section, int specialnum)` `sector_t` Checks if `player` is touching a sector with the specified sector special from the specified section. If one is found, this will return the sector with the special. Also accounts for FOFs – if the found sector is an FOF, the FOF's control sector is returned.
`P_PlayerTouchingSectorSpecialFlag(player_t player, int flags)` `sector_t`
 To doDocument it
`P_FindLowestFloorSurrounding(sector_t sector)` fixed_t Looks for the sector surrounding the current one whose floor height is lower than the current sector's floor height. If it is found, the floor height is returned. Otherwise, returns itself.
`P_FindHighestFloorSurrounding(sector_t sector)` fixed_t Looks for the sector surrounding the current one whose floor height is higher than the current sector's floor height. If it is found, the floor height is returned. Otherwise, returns itself.
`P_FindLowestCeilingSurrounding(sector_t sector)` fixed_t Looks for the sector surrounding the current one whose ceiling height is lower than the current sector's ceiling height. If it is found, the ceiling height is returned. Otherwise, returns itself.
`P_FindHighestCeilingSurrounding(sector_t sector)` fixed_t Looks for the sector surrounding the current one whose ceiling height is higher than the current sector's ceiling height. If it is found, the ceiling height is returned. Otherwise, returns itself.
`P_FindNextHighestFloor(sector_t sector, [fixed_t currentheight])` fixed_t Looks for a sector whose floor height is higher than the current sector's floor height. If it is found, the floor height is returned. Otherwise, returns itself.
`P_FindNextLowestFloor(sector_t sector, [fixed_t currentheight])` fixed_t Looks for a sector whose floor height is lower than the current sector's floor height. If it is found, the floor height is returned. Otherwise, returns itself.
`P_FindSpecialLineFromTag(int special, int tag, [int start])` int Finds the first linedef number after `start` which has the specified linedef special and tag. `start` can be -1 to start from the first linedef onwards, or set to another linedef's number to carry on from perhaps the last linedef number found (`start` defaults to -1 if not set).
`P_SwitchWeather(int weathernum, [player_t player])` nil Switches weather in-game with `weathernum` (use the `PRECIP_` constants). If `player` is or not specified, the weather is applied globally for all players; otherwise, the weather is applied only for the specified player.
`P_LinedefExecute(int tag, [mobj_t actor, [sector_t caller]])` nil Executes a linedef executor. `tag` is the tag of the executor's trigger linedef. If set, `actor` is the Object that activated it, and `caller` is the triggering sector.
`P_SpawnLightningFlash(sector_t sector)` nil Spawns a lightning flash in `sector`. For this to work in FOFs, `sector` should be the control sector of the FOF to flash in.
`P_FadeLight(int tag, int destvalue, int speed, [boolean ticbased, [boolean force]])` nil Fades all tagged sectors' lighting to a new value set by `destvalue`. `speed` determines how quickly the sector's light fades to the new value.
 To dodocument `ticbased` and `force`
`P_ThingOnSpecial3DFloor(mobj_t mobj)` `sector_t` If `mobj` is on top of or inside an FOF with a sector special, this function returns the FOF's control sector; otherwise returns nil.

Note: This function has been deprecated since the introduction of 2.2.11, we recommend you use the P_MobjTouchingSectorSpecial or P_MobjTouchingSectorSpecialFlag instead.

`P_MobjTouchingSectorSpecial(mobj_t mobj, int section, int number)` `sector_t`
 To doDocument it
`P_MobjTouchingSectorSpecialFlag(mobj_t mobj, int flags)` `sector_t`
 To doDocument it
`P_IsFlagAtBase(int type)` boolean Returns true if the flag of the given type is at its corresponding CTF base. Should only be used with types `MT_BLUEFLAG` and `MT_REDFLAG`.
`P_SetupLevelSky(int skynum, [player_t player])` nil Sets the sky seen in-game to the value of `skynum`. If `player` is nil or not specified, the sky is applied globally for all players; otherwise, the sky is applied only for the specified player.
`P_SetSkyboxMobj([mobj_t mobj, [boolean/int centerpoint?, [player_t user]]])` nil Alternative versions:
• `P_SetSkyboxMobj(mobj_t mobj, boolean/int centerpoint?)`
• `P_SetSkyboxMobj(mobj_t mobj, player_t user)`
• `P_SetSkyboxMobj(mobj_t mobj, boolean/int centerpoint?, player_t user)`

Lua-exclusive: Sets which Object correponds to either the skybox's view point or center point (defaults to view point). `user` is the player to apply the new skybox view to, otherwise it applies to all players. If `mobj` is nil, the skybox is removed.

`P_StartQuake(fixed_t intensity, int time, [table{x, y, z} epicenter, [fixed_t radius]])` nil Lua-exclusive: Starts an earthquake camera effect. `intensity` determines the earthquake's strength, and `time` determines its duration. Currently, `epicenter` and `radius` are not supported by SRB2 itself, and will have no effect when specified.
`EV_CrumbleChain([sector_t sector,] ffloor_t rover)` nil Alternative version:
• `EV_CrumbleChain(ffloor_t rover)`

Shatters the FOF `rover`, making it vanish from the map and spawning debris at `sector`. If `sector` is not given, the debris will be spawned in all target sectors linked to the FOF's control sector.

`EV_StartCrumble(sector_t sector, ffloor_t rover, [boolean floating, [player_t player, [fixed_t origalpha, [boolean crumblereturn]]]])` boolean Crumbles the FOF `rover`, making the FOF belonging to `rover` fall from the map and respawning 10 seconds later at `sector` if `crumblereturn` is set to true, otherwise `rover` will not respawn. `player` is the player that made `rover` crumble, if player exists, and `origalpha` is the original alpha of `rover`.

### P_User

Function Return value(s) Description
`P_GetPlayerHeight(player_t player)` fixed_t Returns the player's normal height (default `48*FRACUNIT`, Fang's height is `60*FRACUNIT`). Automatically corrected to match the player's current scale.
`P_GetPlayerSpinHeight(player_t player)` fixed_t Returns the player's "spin" height (2/3 of the player's full height; normally `32*FRACUNIT`). Automatically corrected to match the player's current scale.
`P_GetPlayerControlDirection(player_t player)` int Returns a value depending on what is happening with the player's movement controls (forwards, backwards and strafing left/right) at the moment, compared to the current movement of the player itself:
• 0 – no controls pressed/no movement
• 1 – pressing in direction of movement (accelerating)
• 2 – pressing in opposite direction of movement (decelerating)
`P_AddPlayerScore(player_t player, int amount)` nil Adds `amount` to player's score. Also ensures that the score does not exceed `MAXSCORE` (999999990), and awards lives for every 50000 points (if not losing points). Handled somewhat differently for NiGHTS stages (both normal and Special Stages), modifying `player.marescore` instead of `player.score`.
`P_StealPlayerScore(player_t player, int amount)` nil Causes `player` to steal from everyone else's score in multiplayer.
`P_GetJumpFlags(player_t player)` int Checks whether `player`'s skin has `SF_NOJUMPDAMAGE` and returns the appropriate flags to set for their jump.
`P_PlayerInPain(player_t player)` boolean Returns true if `player` is in its pain state with `pw_flashing` set (and not sliding), false if not.
`P_DoPlayerPain(player_t player, [mobj_t source, [mobj_t inflictor]])` nil Throws back the player, setting the state to the player's pain state (does not spill rings/emeralds/flags nor remove health/shields). `source` is the Object the damage (or `inflictor`) came from, and `inflictor` (which is either `source` itself or a projectile from it) the Object that dealt the damage, `inflictor` in particular being used to determine the throw-back speed depending on the flags set. Setting the `source` and `inflictor` Objects is not required.
`P_ResetPlayer(player_t player)` nil Resets the player. This will halt anything the player is currently doing.
`P_PlayerCanDamage(player_t player, mobj_t mobj)` boolean Checks if `player` is capable of damaging `mobj` in their current state and returns true if so.
`P_IsObjectInGoop(mobj_t mobj)` boolean Is `mobj` inside goop? Returns true if yes, false if no. If the Object has `MF_NOGRAVITY` or is a spectator player, this will always return false.
`P_IsObjectOnGround(mobj_t mobj)` boolean Is `mobj` on the ground? Returns true if yes, false if no. The "ground" can be the Object's floorz or ceilingz depending on whether the Object is in reverse gravity or not. If the Object is currently within goop water, this will always return false.
`P_InSpaceSector(mobj_t mobj)` boolean Is `mobj` in a Space Countdown sector/FOF? Returns true if yes, false if no.
`P_InQuicksand(mobj_t mobj)` boolean Is `mobj` in a Quicksand FOF? Returns true if yes, false if no.
`P_InJumpFlipSector(mobj_t mobj)` boolean Is `mobj` in a Jump Flip sector? Returns true if yes, false if no.
`P_SetObjectMomZ(mobj_t mobj, fixed_t momz, [boolean relative?])` nil Sets `mobj`'s `momz` to the value given. If `relative` is true, this will be added to the Object's previous `momz`; otherwise, it will replace it. (Note: This also corrects for scaling and reverse gravity.)
`P_RestoreMusic(player_t player)` nil Restores the music to whatever it should be depending on whether `player` has any powerups or not.
`P_SpawnShieldOrb(player_t player)` nil Resets `player`'s shield orb appearance to the appropriate one for the player's current shield powers.
`P_SpawnGhostMobj(mobj_t mobj)` `mobj_t` Spawns a "ghost" of `mobj` (a 50% translucent clone of the Object that lasts only 8 tics normally before disappearing). Useful for creating afterimages of Objects such as players, such as with the Super Sneakers power-up or when a player is in Super form. Returns the ghost Object spawned. If a player Object the ghost was made after possesses a followitem, a ghost of that item's Object will additionally be spawned and assigned as the player ghost's tracer, and vice versa.
`P_GivePlayerRings(player_t player, int amount)` nil Adds `amount` to `player`'s ring count. Also corrects ring count if > 9999 or < 0. Also awards extra life bonuses for multiples of 100 rings up to the value of `maxXtraLife` in the `MainCfg` block (by default this is 2, which allows for extra life bonuses up to 200 rings).
`P_GivePlayerLives(player_t player, int amount)` nil Adds `amount` to `player`'s lives count. Also corrects lives count if > 99 or < 1.
`P_GiveCoopLives(player_t player, int amount, [boolean playsound])` nil Adds `amount` to the lives pool if the game is using shared lives. When not using shared lives, adds `amount` of lives to all individual players.
`P_ResetScore(player_t player)` nil Resets `player`'s `scoreadd` value to 0, ending any score chains in progress.
`P_DoJumpShield(player_t player)` nil If `player` has the shield power `SH_PROTECTELECTRIC`, this will activate the Lightning Shield's double jump. In any other case, `player` performs a Whirlwind Shield-style jump and switches to their falling animations.
`P_DoBubbleBounce(player_t player)` nil Landing handler for the Bubble Shield. Bounces `player` upwards.
`P_BlackOw(player_t player)` nil This is used by the Armageddon Shield to blow up enemies, flash the palettes of all players within the explosion radius (`1536*FRACUNIT`) and destroy the shield currently being held by `player`. Also plays the Armageddon explosion sound.
`P_ElementalFire(player_t player, [boolean cropcircle])` nil Spawns two Elemental Shield-style flames for both sides and behind `player`, but needs to be used repeatedly to spawn a true Elemental Shield fire trail. If `cropcircle` is true (default is `false`), this instead spawns flames in a circle pattern like that of the Elemental Shield's ground pound attack.
`P_DoPlayerFinish(player_t player)` nil Sets the flag `PF_FINISHED` on the `player`, causing the `player` to "finish" the level, while still allowing them to continue moving.

If in singleplayer, or if the console variable `exitmove` is not set, this will cause the player thinker to call `P_DoPlayerExit()`.

`P_DoPlayerExit(player_t player)` nil This is used to have `player` "complete" the level and become immobile; this will not immediately end the level itself, but prepares to end the level after a set amount of time.
`P_InstaThrust(mobj_t mobj, angle_t angle, fixed_t move)` nil Set an Object's horizontal momentum to the value of `move` in the direction of `angle`. Note that this will apply momentum absolutely; i.e., all existing momentum applied to the Object in any direction is lost. If the Object has `MF2_TWOD`, only momentum in the X-direction is modified – momentum in the Y-direction is unaffected. To add to existing momentum rather than completely replace it, see `P_Thrust`.
`P_ReturnThrustX(mobj_t mobj, angle_t angle, fixed_t move)` fixed_t Returns the X component of a set thrust value at a specified angle. `mobj` is unused.
`P_ReturnThrustY(mobj_t mobj, angle_t angle, fixed_t move)` fixed_t Returns the Y component of a set thrust value at a specified angle. `mobj` is unused.
`P_LookForEnemies(player_t player, [boolean nonenemies, [boolean bullet]])` `mobj_t` Returns a nearby Object that `player` can hit, if one is found. This is used by the `CA_HOMINGTHOK` and `CA2_GUNSLINGER` character abilities, as well as the Attraction Shield's homing attack ability.

By default, this only looks for shootable enemies or bosses (not including the Deton), they must be within `RING_DIST` (= 512 fracunits) from the player's position, and they cannot be more than 24 fracunits above the player's z position. If `nonenemies` is `true` (default is `false`), this function will also look for springs and monitors. If `bullet` is `true` (default is `false`), the function can look upwards but is limited to a looking span of 30 degrees up or down, the searching distance is doubled (= 1024 fracunits), and monitors and Detons are included in the search.

Note that Objects with the secondary flag `MF2_INVERTAIMABLE` may invert some of the effects of this function when found by it.

`P_NukeEnemies(mobj_t inflictor, mobj_t source, fixed_t radius)` nil Instantly defeats all enemies and damages bosses (as well as players in shooting gametypes) within a radius around the `inflictor` Object (the Object causing the damage). The `source` Object is where `inflictor` came from, if not the `inflictor` itself.
`P_HomingAttack(mobj_t source, mobj_t target)` boolean The `source` Object faces the `target` Object and moves towards it; needs to be repeatedly used to work properly. `source`'s movement speed depends on what `source` is – players will move at 2/3 of their `actionspd` value, the Deton will move at 17/20 of the enemy player's `normalspeed` value, otherwise all other Objects will use their Object type's `Speed` value (a `threshold` of 32000 for the source cuts this in half). Returns `true` if the homing attack was successful, returns `false` if not.
`P_SuperReady(player_t player)` boolean Returns true if the conditions are right for `player` to turn Super, false if not.
`P_DoJump(player_t player, [boolean soundandstate])` nil Makes the player jump. `player.mo.momz` is set to a particular value depending on the situation, and the `PF_JUMPED` flag is given to `player.pflags`. If `soundandstate` is set to true (the default value), `player.mo`'s state will be changed to the appropriate jump states and play the jump sound. If the player has `PF_JUMPSTASIS` in `player.pflags`, or `player.jumpfactor` is 0, this function will do nothing.
`P_SpawnThokMobj(player_t player)` nil Spawns the `player`'s `thokitem` defined in `S_SKIN` at `player`'s location. Defaults to `MT_THOK` if no object is defined.
`P_SpawnSpinMobj(player_t player, int type)` nil Spawns a spin trail Object for `player` at `player`'s location. `type` determines the type of the Object spawned.
`P_Telekinesis(player_t player, fixed_t thrust, fixed_t range)` nil Pushes away all enemies and players within a radius of `range` around `player` with the thrust value `thrust`. If `thrust` is negative, this will instead pull in enemies and players towards `player`.
`P_SwitchShield(player_t player, int shield)` nil Switches the current shield `player` has with `shieldtype`. This will also cause an unused Armageddon Shield to explode. For the list of possible shield types, see Shield types.
`P_PlayJingle(player_t player, int jingletype)` nil Calls `P_PlayJingleMusic` for the player `player` with the appropriate arguments as set by `jingletype`. `jingletype` should be one of the `JT_*` constants.
`P_PlayJingleMusic(player_t player, string musname, [int musflags, [boolean looping, [int jingletype]]])` nil Pushes the music `musname` to `player`'s music stack with the properties set by `musflags`, `looping`, and `jingletype`, and plays the music for that player. If not specified, `musflags` will be set to 0, `looping` will be set to true, and `jingletype` will be set to `JT_OTHER`.
 To doDocument the music stack (see `s_sound.c`) and musflags (see `doomstat.h`)
`P_SpawnSkidDust(player_t player, fixed_t radius, [int sound])` nil Spawns spindash dust randomly around `player` within a certain `radius`, and plays `sound`.
`P_Earthquake(mobj_t inflictor, mobj_t source, fixed_t radius)` nil Damages enemies within the given `radius`. Used for Super Knuckles' landing.
`P_PlayerFullbright(player_t player)` boolean Returns `true` only if `player` is fullbright. Used in NiGHTS mode.
`P_MovePlayer(player_t player)` nil
`P_PlayerCanEnterSpinGaps(player_t player)` boolean
`P_PlayerShouldUseSpinHeight(player_t player)` boolean

### R_Data

Function Return value(s) Description
`R_TextureNumForName(string name)` int Returns the texture number for the texture whose name is supplied in `name`. For a list of textures by number, see List of textures by number.
`R_CheckTextureNumForName(string name)` int If a texture with the name given by `name` exists, returns its texture number. Otherwise, returns -1.
`R_TextureNameForNum(int number)` string Returns the texture name for the texture whose number is supplied in `number`. For a list of textures by number, see List of textures by number.
`R_CheckTextureNameForNum(int number)` string If a texture with the number given by `number` exists, returns its texture name. Otherwise, returns "-".

### R_Draw

Function Return value(s) Description
`R_GetColorByName(string name)` int Returns the skin color number that is represented by `name`. If no color is found, returns `SKINCOLOR_NONE`.
`R_GetSuperColorByName(string name)` int Returns the super color number that is represented by `name`. If no color is found, returns `SKINCOLOR_NONE`.
`R_GetNameByColor(int color)` string Returns the name of the input color.

The function will raise an error if an out of bounds number is entered.

### R_Defs

Function Return value(s) Description
`R_PointToAngle(fixed_t x, fixed_t y)` angle_t Returns the angle between the camera's X and Y coordinates and `x` and `y`.

Note: This will not work consistently among multiple players. Use at your own risk.

`R_PointToAngle2(fixed_t x, fixed_t y, fixed_t dest_x, fixed_t dest_y)` angle_t Returns the angle created by the line from `x` and `y` to `dest_x` and `dest_y`.
`R_PointToDist(fixed_t x, fixed_t y)` fixed_t Returns the distance from the camera's X and Y coordinates to `x` and `y`.

Note: This will not work consistently among multiple players. Use at your own risk.

`R_PointToDist2(fixed_t x, fixed_t y, fixed_t dest_x, fixed_t dest_y)` fixed_t Returns the distance from `x` and `y` to `dest_x` and `dest_y`.
`R_PointInSubsector(fixed_t x, fixed_t y)` `subsector_t` Returns the subsector that the given point is located in. Never returns nil, even if outside of the map.
`R_PointInSubsectorOrNil(fixed_t x, fixed_t y)` `subsector_t` or nil Same as `R_PointInSubsector`, but returns nil if point is not in subsector.

### R_Things

Function Return value(s) Description
`R_Char2Frame(string char)` int Returns the text character's frame number.

Example: `R_Char2Frame("A")` will return 0.

`R_Frame2Char(int frame)` string, int Returns the frame number's text character as both a string and its ASCII value.

Example: `R_Frame2Char(0)` will return "A",65.

`R_SetPlayerSkin(player_t player, int/string skin)` nil Sets the player's skin. `skin` can be either a skin number or a skin name string.
`R_SkinUsable(player_t player, int/string skin)` boolean Checks if `skin` is legal to switch to and returns true if so. Accounts for factors such as map forcecharacter and multiplayer forceskin.

### S_Sound

For all of the functions below with an optional `player` parameter, this determines which player the function is run for (if only a certain player is meant to hear a sound or change in music, for example). If this is omitted or set to nil, the function is run for all players.

Function Return value(s) Description
`S_StartSound(mobj_t/sector_t origin, int soundnum, [player_t player])` nil Starts the given sound effect from `origin`, or plays the sound globally if `origin` is nil. If `origin` exists and has a skin applied, certain sounds may be replaced with custom sounds set for the skin. If in a Mario mode or Christmas NiGHTS level, certain sounds will automatically be swapped with different sounds for the given level type (these take priority over custom skin sounds).

If the third argument is set, the sound will only be played for that player. Otherwise, it will be heard by all players.

`S_StartSoundAtVolume(mobj_t/sector_t origin, int soundnum, UINT8 volume, [player_t player])` nil Starts the given sound effect at a specific volume from `origin`, or plays the sound globally if `origin` is nil. If `origin` exists and has a skin applied, certain sounds may be replaced with custom sounds set for the skin. Unlike `S_StartSound`, Mario mode and Christmas NiGHTS have no effect on the sound used.

Volume ranges from 0 to 255, inclusive.

`S_StopSound(mobj_t/sector_t origin)` nil Stops any sound that the given `origin` is playing.
`S_StopSoundByID(mobj_t/sector_t origin, int soundnum)` nil Stops the sound `soundnum` that `origin` may be playing.
`S_ChangeMusic(string musicname, [boolean looping?, [player_t player, [int mflags, [int position, [int prefadems, [int fadeinms]]]]])` nil Alternative version: `S_ChangeMusic(int musicslot, [boolean looping?, [player_t player, [int mflags, [int position, [int prefadems, [int fadeinms]]]]])`

Changes the music to the specified music name or slot number. The music will loop unless `looping?` is specified and is false.

`mflags` can be used to set flags for the music:

• If `0x4000` is added to the value, the music track will start from the beginning if you attempt to change the music to the same track, instead of having no effect.
• If `0x8000` is added to the value, the music track will be reset when the current level is reloaded.

If the music format supports multiple tracks, you can supply the track number as well – if the new music's name was given, the track number must be added to `mflags`; if a slot number was given, the track number must be stored in the upper 16 bits (i.e., `musicnum == slot number+(track number<<16)`). This also means that the value given for `mflags` will be ignored.

Other features:

• `position` determines the position in the music track to start playing from, measured as a time in milliseconds. If set to 0, the music track will be played from the beginning. Note: Has no effect with music formats supported by the Game Music Emu library.
• `prefadems` determines the time in milliseconds to fade out of the current music track before changing to the new track. If set to 0, no fade out effect will be used.
• `fadeinms` determines the time in milliseconds to fade into the new music track. If set to 0, no fade in effect will be used.

To set a time in seconds for `position`, `prefadems` or `fadeinms`, multiply the time in seconds by the constant `MUSICRATE`; e.g.: `2*MUSICRATE` for 2 seconds.

`S_SpeedMusic(fixed_t musicspeed, [player_t player])` nil Changes the speed of the music – the speed given must be a multiple of `FRACUNIT`, where `FRACUNIT` is the default music speed.

Note that this function only works with music formats supported by the Game Music Emu library. For other music formats, it has no effect.

`S_StopMusic([player_t player])` nil Stops all music from playing.
`S_SetInternalMusicVolume(int volume, [player_t player])` boolean Immediately sets the internal volume of the current music track, as a percentage of the user's configured game volume, where 0 is silent and 100 is full volume.

Returns true if the volume change was done for all players or the user's local player, returns false if not.

`S_StopFadingMusic([player_t player])` boolean Stops any current fade from running. The music will remain playing at the current internal volume.

Returns true if the fade was done for all players or the user's local player, returns false if not.

`S_FadeMusic(int target_volume, int ms, [player_t player])` boolean Alternative version: `S_FadeMusic(int target_volume, int ms, [int source_volume, [player_t player]])`

Fades the current music track from source volume to target volume, 0-100%. If `source_volume` is not specified, the source volume is the current internal volume. `ms` is the length of the fade, measured in milliseconds. To set a time in seconds, multiply the time in seconds by the constant `MUSICRATE`; e.g.: `2*MUSICRATE` for 2 seconds.

Returns true if the fade was done for all players or the user's local player, returns false if not.

`S_FadeOutStopMusic(int ms, [player_t player])` boolean Fades the current music track from current internal volume to 0%, then stop the music. `ms` is the length of the fade, measured in milliseconds. To set a time in seconds, multiply the time in seconds by the constant `MUSICRATE`; e.g.: `2*MUSICRATE` for 2 seconds.

Returns true if the fade was done for all players or the user's local player, returns false if not.

`S_OriginPlaying(mobj_t/sector_t origin)` boolean Returns true if a sound effect with `origin` as the origin is being played, false if not.

Example:

```if S_OriginPlaying(players[0].mo) -- is a sound being played from the player's mobj?
print("beep!") -- beep if yes
end
```

Note: This function only checks sounds being played for the local client, and thus isn't network safe. Use at your own risk.

`S_IdPlaying(int soundnum)` boolean Returns true if a sound effect with the given ID is being played, false if not.

Example:

```if S_IdPlaying(sfx_thok) -- is a thok sound being played at all?
print("beep!") -- beep if yes
end
```

Note: This function only checks sounds being played for the local client, and thus isn't network safe. Use at your own risk.

`S_SoundPlaying(mobj_t/sector_t origin, int soundnum)` boolean Returns true if a sound effect with the given ID and `origin` as the origin is being played, false if not.

Example:

```if S_SoundPlaying(players[0].mo, sfx_thok) -- is a thok sound being played from the player's mobj?
print("beep!") -- beep if yes
end
```

Note: This function only checks sounds being played for the local client, and thus isn't network safe. Use at your own risk.

`S_StartMusicCaption(string caption, tic_t lifespan, [player_t player])` nil If the user has sound captions enabled, this will display the caption `caption` for the duration specified by `lifespan` in a similar manner to the captions displayed for Super Sneakers and Invincibility. If `player` is specified, this will only be displayed for that player.
`S_GetMusicLength()` int Returns the length of the currently playing music, in milliseconds.

Note: This function only checks the music being played for the local client, and thus isn't network safe. Use at your own risk.

`S_GetMusicPosition()` int Returns the position of the currently playing music, in milliseconds.

Note: This function only checks the music being played for the local client, and thus isn't network safe. Use at your own risk.

`S_SetMusicPosition(int position)` boolean Sets the position of the currently playing music, in milliseconds. Returns false if no music is playing or a MIDI is currently playing (and therefore the position could not be set), and returns true otherwise. Note that this may still return true in some instances where the position could not be set.
 To doVerify this is accurate.
`S_MusicType`
 To doEverything :3
`S_MusicExists(string mname, [boolean checkmidi, [boolean checkdigi]])` boolean Returns whether music of name `mname` exists within any of the currently loaded files.

By default, this checks for both digital (`O_`) and MIDI (`D_`) versions of the music file, but the checks can be toggled with the arguments `checkdigi` and `checkmidi`, respectively.

`S_MusicPlaying([player_t player])` boolean or nil
`S_MusicPaused([player_t player])` boolean or nil
`S_MusicName([player_t player])` string or nil
`S_SetMusicLoopPoint(UINT32 looppoint, [player_t player])` boolean or nil
`S_GetMusicLoopPoint([player_t player])` UINT32 or nil
`S_PauseMusic([player_t player])` boolean or nil
`S_ResumeMusic([player_t player])` boolean or nil

## Iterator functions

None of these functions should be called directly, with the exception of `mobjs.iterate`. They should be used in a for loop, as such:

```for player in players.iterate
-- Handle player here
end
```

Note that the ending parentheses, `()`, are omitted in the above code – this does not apply to `mobjs.iterate`, however, for technical reasons.

Function Iterator type Description
`players.iterate()` `player_t` Iterates over all players currently playing in the map. Note that `player.mo` will return nil for spectating players.
`mobjs.iterate()` `mobj_t` Iterates over all Objects in the map that use `P_MobjThinker`. This excludes all precipitation (rain and snow).

Note that this iterator is extremely slow due to the massive amount of thinkers in a typical map, and should not be used repeatedly so as not to cause framerate drops.[confirm? – discuss]

`skins.iterate()` `skin_t` Iterates over all valid skins loaded in the game.
`mapthings.iterate()` `mapthing_t` Iterates over all map Things in the map. Remember that not all Objects will necessarily have a respective map Thing, and not all map Things will necessarily have a respective Object.
`sectors.iterate()` `sector_t` Iterates over all sectors in the map.
`subsectors.iterate()` `subsector_t` Iterates over all subsectors in the map.
`lines.iterate()` `line_t` Iterates over all linedefs in the map.
`sides.iterate()` `side_t` Iterates over all sidedefs in the map.
`vertexes.iterate()` `vertex_t` Iterates over all vertexes in the map.
`polyobjects.iterate()` `polyobj_t` Iterates over all PolyObjects in the map.

## Lua framework

These are the functions included with the standard Lua libraries included with SRB2 (Basic, Coroutine, String and Table).

### Base Lua functions

Function Return value(s) Description
`assert(* v, [string errormsg])` any or nil If `v` is nil or false, an error message is printed; otherwise, this function returns all arguments given. `errormsg` is the message to use when the assertion fails; if not given, the default message used is "assertion failed!".
`collectgarbage([string opt, [int arg]])` `"step"`: boolean
all others: int
This function is a generic interface to the garbage collector. It performs different functions depending on its first argument, `opt`:
• `"collect"`: Performs a full garbage collection cycle. This is the default option.
• `"stop"`: Stops the garbage collector.
• `"restart"`: Restarts the garbage collector.
• `"count"`: Returns the total memory in use by Lua (in kilobytes).
• `"step"`: Performs a garbage collection step. The step size is controlled by `arg` (larger values mean more steps). Returns true if the step finished a collection cycle.
• `"setpause"`: Sets `arg` as the new value for the pause of the garbage collector. Returns the previous value for the pause.
• `"setstepmul"`: Sets `arg` as the new value for the step multiplier of the garbage collector. Returns the previous value for the step multiplier.
`error(string message, [int level])` nil Terminates the last protected function called and returns `message` as an error message.

Usually, `error` adds some information about where the error occurred at the beginning of the message. The `level` argument specifies how to get the error position. With level 1 (the default), the error position is where the `error` function was called. With level 2, the error position is where the function that called `error` was called, and so on. If `level` is set to 0, no information about the error position is added to the message.

`dofile(string file)` (return values) This loads the lua script `file` from the `Lua/` folder in the last loaded add-on, which must be a PK3. For instance, to load the file `Lua/script.lua`, use `dofile("script.lua")`. It is highly recommended this only be used in `init.lua` as the add-on is loading, though it can technically be used at any time.
`gcinfo()` int Returns Kb of dynamic memory in use.

This function is deprecated in Lua 5.1. Use collectgarbage ("count") instead.

`getfenv([function/int f])` (environment) Returns the current environment in use by the function.
`getmetatable(object obj)` (metatable) If `obj` does not have a metatable, returns nil. Otherwise, if `obj`'s metatable has a `__metatable` field, returns the associated value. Otherwise, returns the metatable of `obj`.
`ipairs(table{} t)` function, table, int This function is to be used in a for loop to iterate through all entries in an array-like table, such as in the code shown below:
```for k, v in ipairs(t)
--contents
end
```

`k` and `v` are the key and value for each entry in table `t`.

The iteration starts from key 1 (not 0) and iterates in numeric order.

This function only iterates through the array part of the table. The array part is made of all the entries which keys are integer numbers in the range [1; n], where n is the first key that precedes a nil entry (or, if there are no "holes", the last entry). Entries with any other key (strings, booleans, userdata, negative numbers, etc) are merely skipped.

Technical comment: this function actually returns three values: an iterator function, the table `t`, and 0. When used in a for loop, however, this detail is irrelevant to most purposes.

`next(table{} t, [int index])` (index), (value)
`pairs(table{} t)` function, table, nil This function is to be used in a for loop to iterate through all entries in a table, such as in the code shown below:
```for k, v in pairs(t)
--contents
end
```

`k` and `v` are the key and value for each entry in table `t`.

Unlike `ipairs`, every entry will be iterated through, in an undefined order.

Technical comment: this function actually returns three values: the `next` function, the table `t`, and nil. When used in a for loop, however, this detail is irrelevant to most purposes.

Note: This function iterates in an arbitrary order, NOT the order in which elements were added. It is VERY likely to iterate through a completely different order for mid-joiners, and thus isn't network safe. Use at your own risk.

`pcall(function fn, [* arg, [...]])` boolean, (return values or error message) Calls function `fn` with the given arguments in protected mode. The first value returned is the status code, which is `true` if the call succeeded without errors, and `false` if an error occurred.

If the call succeeded, all return values of the function call are also returned after the status code. If the call produced an error, the status code is followed by the error message instead.

`rawequal(* v1, * v2)` boolean Checks whether `v1` is equal to `v2`, without invoking any metamethod.
`rawget(table{} t, * index)` any Gets the real value of `t[index]`, without invoking any metamethod.
`rawset(table{} t, * index, * value)` table Sets the real value of `t[index]` to `value`, without invoking any metamethod. This function returns `t`.
`select(* index, ...)` arguments or int If `index` is a number, returns all arguments after argument number `index`. Otherwise, `index` must be the string `"#"`, and `select` returns the total number of extra arguments it received.
`setfenv(function/int f, table{} table)` function Sets the environment to be used by the given function.
`setmetatable(table{} t, table{} metatable)` table Sets the metatable for the given table. If `metatable` is nil, removes the metatable of the given table. If the original metatable has a `__metatable` field, raises an error.

This function returns `t`.

`tonumber(* e, [int base])` int or nil Returns the given variable as a number, if possible. Returns nil if the variable cannot be converted to a number.

Example: `tonumber("10")` will return 10.

`tostring(* e)` string Returns the given argument as a string.

Example: `tostring(10)` will return `"10"`.

`type(* v)` string Returns the type of `v` as a string.

Possible strings that may be returned by this function:

• `"no value"`
• `"nil"`
• `"boolean"`
• `"userdata"`
• `"number"`
• `"string"`
• `"table"`
• `"function"`
• `"thread"`
• `"proto"`
• `"upval"`

To find out if a given value is a specific type of userdata, see `userdataType`.

`unpack(table{} list, [int start, [int end]])` (table elements) Returns the elements from the given table.
`xpcall(function call, function(boolean status) errortrap)` boolean, (return values or error message) Calls function `f` in protected mode, using `errortrap` as the error handler. The first value returned is the status code, which is `true` if the call succeeded without errors, and `false` if an error occurred.

If the call succeeded, all return values of the function call are also returned after the status code. If the call produced an error, the status code is followed by the return value of `errortrap`.

### Coroutine library

Function Return value(s) Description
`coroutine.create(function fn)` thread Creates and returns a new coroutine that runs the function specified. To run the coroutine, use `coroutine.resume`.
`coroutine.resume(thread co, [* val, [...]])` boolean, (return values from `coroutine.yield`) Begins or resumes execution of the coroutine specified. If the coroutine has not yet been started, passes the remaining arguments to the coroutine's function (i.e.: they become the arguments to the function). If the coroutine has yielded, the remaining arguments are passed as the results from the yield (i.e.: they become the return values of `coroutine.yield`). If the function errors, returns false and the error message; otherwise, returns true plus the variables returned or passed to `coroutine.yield`.
`coroutine.running()` thread or nil Returns the running coroutine, or nil when called by the main thread.
`coroutine.status(thread co)` string Returns the status of coroutine `co`, as a string:
• `"running"`, if the coroutine is running (i.e., it called `status`)
• `"suspended"`, if the coroutine is suspended in a call to `yield`, or if it has not started running yet
• `"normal"`, if the coroutine is active but not running (i.e., it has resumed another coroutine)
• `"dead"`, if the coroutine has finished its body function, or if it has stopped with an error
`coroutine.wrap(function fn)` function Creates and returns a wrapper for a coroutine that runs the function specified. Calling the coroutine in the format `corout(args)` is equivalent to calling `coroutine.resume(corout, args)` on a coroutine created using `coroutine.create`, except that it will not return the initial true value, instead propagating any errors that the coroutine throws.
`coroutine.yield([...])` (return values from `coroutine.resume`) Temporarily suspends execution of the coroutine. Cannot be used while running a C function, a metamethod, or an iterator loop. The next time the coroutine is resumed, it will resume execution from the point of this function call. Arguments passed to this function will be returned by the `coroutine.resume` call that restarted the coroutine, and this function itself will return any extra arguments from the `coroutine.resume` call.

### String library

Function Return value(s) Description
`string.byte(string s, [int start, [int end]])` int × (`end` - `start` + 1) Alternative syntax: `s:byte([int start, [int end]])`

Returns the numerical values of the characters in string `s` between `start` and `end`. `start` and `end` default to 1 and the length of the string, respectively.

`string.char([int charid, [...]])` string Converts the given character codes into a string consisting of the respective characters (reverse of `string.byte`).
`string.find(string s, string pattern, [int start, [boolean plain?]])` int, int, (captures) Alternative syntax: `s:find(string pattern, [int start, [boolean plain?]])`

Looks for the first match of `pattern` in the string `s`. If it finds a match, returns the positions in `s` where this occurrence starts and ends; otherwise, returns nil.

`string.format(string formatstr, [...])` string Returns a formatted version of its variable number of arguments following the description given in its first argument (which must be a string).
`string.gmatch(string s, string pattern)` function Alternative syntax: `s:gmatch(string pattern)`
`string.gsub(string s, string pattern, int/string/table/function replace, [int n])` string Alternative syntax: `s:gsub(string pattern, int/string/table/function replace, [int n])`

Returns a copy of `s` in which all (or the first `n`, if given) occurrences of the pattern `pattern` have been replaced by a replacement string specified by `repl`. Also returns the total number of matches that occurred.

`string.len(string s)` int Alternative syntax: `s:len()`

Returns the length of the string `s`.

Example: `string.len("Hello")` will return 5.

`string.lower(string s)` string Alternative syntax: `s:lower()`

Converts string `s` to lowercase characters.

Example: `string.lower("HELLO")` will return `"hello"`.

`string.match(string s, string pattern, [int n])` (captures) or string Alternative syntax: `s:match(string pattern, [int n])`
`string.rep(string s, int n)` string Alternative syntax: `s:rep(int n)`

Repeats string `s` `n` times.

Example: `string.rep("Hello ", 5)` will return `"Hello Hello Hello Hello Hello "`.

`string.reverse(string s)` string Alternative syntax: `s:reverse()`

Reverses string `s`.

Example: `string.reverse("Hello")` will return `"olleH"`.

`string.sub(string s, int start, [int end])` string Alternative syntax: `s:sub(int start, [int end])`

Returns the substring of string `s` that starts at `start` and ends at `end`. If `end` is not supplied, it defaults to the end of `s`.

`string.upper(string s)` string Alternative syntax: `s:upper()`

Converts string `s` to uppercase characters.

Example: `string.upper("hello")` will return `"HELLO"`.

### Table library

Note: Most of these functions are not designed for tables with non-integer keys.

Function Return value(s) Description
`table.concat(table{} t, [string sep, [int start, [int end]]])` string Returns a string containing the elements of table `t` between the positions `start` and `end` concatenated together. `sep` is used as a separator between the elements (defaults to the empty string). `start` and `end` default to 1 and the length of the table, respectively.
`table.insert(table{} t, [int key], * element)` nil Inserts `element` at position `key` in table `t`. If `key` is not given, `element` is inserted at the end of table `t`.
`table.maxn(table{} t)` int Returns the largest positive numerical index of the given table, or zero if the table has no positive numerical indices.
`table.remove(table{} t, [int key])` any Removes from table `t` the element at position `key`, and returns the value of the removed element. All elements posterior to the removed element are then shifted down one position. If `key` is not given, removes the last element of table `t`.
`table.sort(table{} t, [function(* element_a,* element_b) comp])` nil Sorts the elements of table `t`, in-place, from `t[1]` to `t[n]`, where n is the length of the table `t`. If `comp` is given, then it must be a function that receives two table elements, and returns true when the first is less than the second. If `comp` is not given, then the standard Lua operator `<` is used instead.

### I/O library

Some functions have been removed or tweaked for usage in SRB2.

For safety reasons, Lua scripts are subject to some restrictions:

• Accessed files must be located within the `luafiles/` folder in the SRB2 root directory. All file paths used are relative to this folder, so `io.openlocal("client/MyModConfig.cfg", "w")` will open `PathToYourSRB2Folder/luafiles/client/MyModConfig.cfg`.
• If a CLIENT (not the host) needs to access a file LOCALLY, that file must be located within `luafiles/client/` or its subfolders. This limit only exists for clients, the host can access anything inside `luafiles/`
• Accessed files must have one of the following extensions (if the name contains multiple extensions, only the last one is checked):
• `.bmp`
• `.cfg`
• `.csv`
• `.dat`
• `.png`
• `.sav2`
• `.txt`
• Writing to a file must not cause it to be larger than 1 megabyte. There is no restriction for reading.

Trying to bypass one of these restrictions will raise an error.

Function Return value(s) Description
`io.open(string filename, [string mode], function callback)` nil * Callback function format: `function(file file, string filename)`

This is the function used for reading from a file owned by the host. It is netsafe.

If called within a netgame, it (automatically) sends the file to all clients and executes `callback` once everyone has downloaded it, so that the game will not desynchronise.

This function does not return a value, but if the file does not exist, `file` will be `nil` inside the callback, so you can still check for file not found errors.

Once the callback function returns or ends, the file handle is closed automatically (no need to call `io.close`).

This function is non-blocking (asynchronous), which means that even in a netgame, the game will not "pause" while all players are downloading the file. Instead, the script will continue to run as normal, except the callback will not be called immediately, but will instead wait for an undetermined amount of time (bandwidth, network latency, etc.) before finally calling the callback. Keep this in mind when setting variables with values found in the file, as those variables will not be updated until an indeterminate amount of time in the future.

`io.openlocal(string filename, [string mode])` `file*` or nil, string or nil This function opens a file, in the mode specified in the string mode. It returns a new file handle, or, in case of errors, `nil` plus an error message.

The mode string can be any of the following:

• "r": read mode (prefer `io.open` in most scenarios);
• "w": write mode;
• "a": append mode;
• "r+": update mode, all previous data is preserved;
• "w+": update mode, all previous data is erased;
• "a+": append update mode, previous data is preserved, writing is only allowed at the end of file.

The mode string can also have a 'b' at the end, which is needed to open the file in binary (non-text) mode.

Note: This function is run locally, and thus isn't network safe. It is primarily intended to be used for writing to a file. For reading from a file, it is HIGHLY recommended that you use `io.open` instead, unless you actually need to access data locally, such as a list of passwords. Use at your own risk.

`io.close(file file)` boolean or (nil, string, and int) or (nil, string) Closes the file handle `file`. Equivalent to `file:close()`

If the call was successful, returns true — otherwise, returns nil, an error message, and an error code. If an attempt is made to close one of the standard files `stdin`, `stdout`, or `stderr`, this function will return nil and an error message, but no error code.

Calling `io.close` with no arguments will attempt to close the standard file `stdout`, resulting in an error as described above.

`io.tmpfile()` `file*` Returns a handle for a temporary file. This file is opened in update mode and it is automatically removed when the program ends.
`io.type(* obj)` string or nil Checks whether `obj` is a valid file handle.

Returns the string `"file"` if `obj` is an open file handle, `"closed file"` if `obj` is a closed file handle, or `nil` if `obj` is not a file handle.

### OS library

Some functions have been removed for usage in SRB2.

Function Return value(s) Description
`os.clock()` int Returns the time in seconds to the nearest millisecond since SRB2 was running.
`os.difftime(int a, int b)` int Returns the number from time `a` to time `b`, in other words, `a` - `b`.
`os.date(string format, int time)` string or table Returns the date and time as a string or table.

The first argument accepts the `format`. Default is "%c".

• "%a". abbreviated weekday name (e.g., Wed);
• "%A". full weekday name (e.g., Wednesday);
• "%b". abbreviated month name (e.g., Sep);
• "%B". full month name (e.g., September);
• "%c". date and time (e.g., 09/16/98 23:48:10);
• "%d". day of the month (e.g., 16) [01-31];
• "%H". hour, using a 24-hour clock (e.g., 23) [00-23];
• "%I". hour, using a 12-hour clock (e.g., 11) [01-12];
• "%M". minute (e.g., 48) [00-59];
• "%m". month (e.g., 09) [01-12];
• "%p". either "am" or "pm" (pm);
• "%S". second (e.g., 10) [00-61];
• "%w". weekday (e.g., 3) [0-6 = Sunday-Saturday];
• "%x". date (e.g., 09/16/98);
• "%X". time (e.g., 23:48:10);
• "%Y". full year (e.g., 1998);
• "%y". two-digit year (e.g., 98) [00-99];
• "%%". the character `%´.
• "*t". returns the table;
• "!*t". returns the table (GMT).

If the `format` is "*t", returns the table:

• year (a full year)
• month (1 - 12)
• day (1-31)
• hour (00-23)
• min (00-59)
• sec (00-59)
• wday (day of the week, Sunday is 1)
• yday (day of the year)
• isdst (a boolean, true if daylight saving)

The second argument accepts the time in seconds. If `time` is not given, the function will return the current time.

`os.time(table t)` int Returns the time (the number of seconds elapsed since 00:00:00:00 on January 1, 1970).

If no argument is specified, returns the current time. The argument is a table that must have keys year, month, and day. It can have keys hour, min, sec, and isdst(daytime flag).

 Lua [view] Language features Syntax • Metatables SRB2 data Actions • Constants • Functions • Global variables • Hooks • Userdata structures SRB2Kart data Kart Userdata structures • Kart Functions • Kart Hooks • Kart Global Variables and Constants Tutorials Freeslots and Object resources • Custom player ability