HyperScript
Docs

← All of the Docs The basics

Variables

Guide and examples

There are two kinds of variable, told apart by the first character of the name.

KindWritten asLifetimeExample
Global{name}Saved, and shared by every script{event_active}
Local{_name}One run of one trigger; never saved{_tempDamage}
set {event_active} to true
set {_tempDamage} to 4.5
set {%player%.coins} to 100
delete {%player%.coins}
  • Values are numbers, text, the booleans true and false, items, durations, locations, or a list of any of those. See Value types.
  • {name} is global: one saved value that any script can read and change.
  • {_name} is local: a name that begins with an underscore. It exists for one run of the command, event handler or function it appears in, starts unset every time, and nothing else can see it, not even another trigger in the same file.
  • A local may be written without its braces, as plain _name. It is the same variable either way, and a script may use both. The braces are how these pages write it, because every other variable has them too; scripts written the shorter way keep working as they are.
  • A local can be a small table: {_data.name} and {_data.kills} are named values inside the local {_data}. The whole table can be handed to a function, returned from one, and looped over with for each {_key}, {_value} in {_data}:. Like any local it is never saved.
  • Names are case-insensitive and may use letters, digits, _, - and ..
  • A global name that starts with a player belongs to that player. {%player%.coins} is the coins of the player of this trigger, {%arg.1%.coins} the coins of whoever was named in the command, and {%loop-player%.coins} the coins of each player in a loop all players. Everybody has their own value, it is stored with their account so it survives a name change, and it can be read and changed while they are offline.
  • A player is anyone online or anyone who has played on the server before. If the first part of a name is not a player, the variable is an ordinary global under the name as written. So for a table that is *not* about players, start the name with a fixed word: {warp.%arg.1%} rather than {%arg.1%.warp}.
  • Reading {%player%.<name>} when there is no player (a console command, a timer) gives unset; writing it is a runtime error.
  • {player.coins}, without the percent signs, is one global shared by everyone. The word player in a variable name is just part of the name; it is %player% that stands for the player.
  • A colon works like a dot in a variable's name, for those who prefer it: {%player%:role} is the same variable as {%player%.role}, and {stats::kills} the same as {stats.kills}.
  • Tables in lists. A local table can be put in a list and saved, which is how to keep records of several things each: set {_home.name} to "base", set {_home.spot} to player's location, append _home to {%player%.homes}. Looping gives each one back as a table: for each {_home} in {%player%.homes}: then {_home.name} and {_home.spot}. The list holds its own copy, so the local can be changed and used again for the next one.
  • Shared variables. With storage.shared-variables on, a variable whose name starts with shared. is the same on every server that uses the database; see The database.
  • Variables for a time. set {%player%.boost} to 2 for 10 minutes sets it and unsets it again by itself when the time is up. The time keeps counting while the server is off, and a variable whose time ran out then is gone when the server starts. Setting it for another time starts the time anew; setting it without for changes the value but not when it ends. This is for saved variables; a local one ends with its trigger anyway.
  • Temporary variables. A variable whose name starts with temp. is never saved. {temp.round} lasts until the server stops, and a player's own, {%player%.temp.combat}, is forgotten the moment they leave. Use them for things that should not outlive a session, such as "is in a fight" or "has a menu open", and there is nothing to tidy up when a player joins.
  • Unset variables count as 0 in math, as nothing when joined to text with +, and as false in conditions, so counters need no setup: add 1 to {%player%.joins} works the first time. Test for it explicitly with is set / is not set.
  • A variable may have any name that is not already a built-in placeholder. {%player%.coins} and {event.start_time} are fine; {player.name} is refused, because player.name is built in. The same name after %player%. is allowed: {%player%.name} is simply a per-player variable.
  • To put a variable in a string, wrap it in percent signs: "%{%player%.coins}%" and "%{_reward}%".
  • A value between percent signs may have a name in quotes of its own: "Mined: %quest progress "miner"%", "You have %plural({_n}, "home")%.". So inside text, %{...}% is a variable and %...% without braces is a placeholder.
  • A value written out works between percent signs too, as long as it is several words or a call: "You have %size of {_list}% items", "That is %round({_n})% coins". Something that does not read as a value is shown as it was written, so "50% off, 20% more" stays what it is. Text in quotes cannot stand inside it; put that in a local variable first.