Text
Texts with values#
displayText and print take a template literal, or texts joined with +, with the
program's numbers in it, name(p) and color(p):
program(() => {
let wave = 3;
displayText(`${color(P2)}${name(P2)}\x01 has ${minerals(P2)} ore — wave ${wave + 1}`);
print(`Wave ${wave}`, { to: AllPlayers, position: "center" });
});
name(p) is the player's name and color(p) the colour code of their colour, both filled
in by the game; the ordinary colour codes work as ever. displayText shows the text to
the current player. print(text, { to, position }) shows it to someone else (a player,
AllPlayers or a force), or, with position: "center", on the line in the middle of the
screen where the game's own messages appear. A boolean in a text is true or false. A
program's texts never take a string of the map you edit: the build gives them strings of
their own.
A text is a value#
string is a type of a program as number is. A variable holds one, a function takes and
returns one, a record has one as a field, and there is no length to declare.
program(() => {
let wave = 3, left = 12, shown = "";
let title = wave > 10 ? "Late game" : "Early game"; // texts written in the script
let line = `Wave ${wave}: ${left} left`; // a text made in the game
line += "!";
if (line != shown) { print(line); shown = line; }
setMissionObjectives(`${title} - ${line}`);
});
The editor keeps a text one of two ways and says which at the end of its line. A variable
that only ever receives texts written in the script ("Boss", titles[level] out of a
list the script has) holds the number of a string, and costs what a number does. A text
that is made (a template with values in it, a + b, a method's result) keeps its
characters in the pool the growing arrays share, and holds up to 1 023 bytes. Past that it
is cut off, and the game says so once in red.
Texts take +, +=, templates, the comparisons, if (s) (not empty), switch (s),
length, s[i], at(), charAt(), charCodeAt(), codePointAt(), slice(),
substring(), indexOf(), includes(), startsWith(), endsWith(), padStart(),
padEnd(), repeat(), concat(), trim(), trimStart(), trimEnd(), toUpperCase()
and toLowerCase() (A to Z only), replace() and replaceAll() of a text, split() at
a text, parseInt(), isNaN(), String(n), n.toString() and for (const ch of s).
program(() => {
let wave = 3;
const line = ` Wave ${wave}: zerglings, hydras `;
const parts = line.trim().split(": ");
print(parts[1].toUpperCase().replaceAll(", ", " + ")); // ZERGLINGS + HYDRAS
print(`${parseInt("12 ore") + wave} ${line.includes("hydra")} ${"A".charCodeAt(0)}`); // 15 true 65
});
Characters#
A character counts as one, as JavaScript counts it, so "저글링".length is 3 and "저글링"[1]
is 글. The one difference is a character past U+FFFF, such as an emoji: a program counts
one where JavaScript counts two, and the game draws a dark square in its place. s[i] and
slice() walk the text from its start, so over a long text, for (const ch of s) is
quicker. That loop runs within the frame and cannot sleep. A loop over the places can,
which is how a text is typed out one character at a time:
program(() => {
let wave = 3;
let line = `Wave ${wave} is here`;
let typed = "";
for (let i = 0; i < line.length; i++) { typed += line[i]; print(typed); sleep(frames(2)); }
});
The game's font is proportional and a colour code has no width, so padStart does not
line columns up.
Texts outside the chat area#
The objectives, a leaderboard's label, a transmission's line and a unit type's name
(stats(units.TerranMarine).name = …) take a made text, up to 255 bytes. The game shows
the text as it was when the action ran, so when the text changes, run the action again. In
a program of every player, each player sees their own. Any other action's text, such as
setNextScenario or a sound's path, has to be written in the script.
Lines of JSX#
In a .tsx file, <line>…</line> is a line of text that may hold the program's values,
<bar value={hp} max={100} width={10} /> is a bar of squares, and <cell color={c} /> is
a square of one of the game's text colours. print takes a line, and
ui.lines(player, () => …) keeps the lines in a player's text area and draws them again
when the values in them change. The trigscript/ui library
builds panels, meters, menus and dialogs from them.
program(async () => {
let hp = 0;
ui.lines(P1, () => (
<line>
Base <bar value={hp} max={100} width={10} /> {hp}
</line>
));
while (hp < 100) {
hp += 25;
await sleep(seconds(1));
}
print(<line>Wave {hp / 25}</line>);
});