docs

the complete reference for the script language. for a guided start, open the editor: it loads a sample game that uses everything on this page.

the shape of a script

A game is one plain-text file with two regions: declarations at the top (what exists), then passages (what happens). The first passage is where the game begins. Lines starting with # are comments.

@title My Game
@author Me

skill nerve "Nerve" #8fb3a8 = 2
char jekyll "Dr. Jekyll" #f0c987

== start
jekyll: "Ready?"
* "Ready." -> begin

== begin
-> END

declarations

These only work above the first passage. Declaration lines may carry a trailing # comment.

@title / @author

Shown on the play page header and used for the share link preview.

@title Two Wings Good
@author Alaska Hoffman, Fable

@start

Begin at a specific passage instead of the first one defined.

@start cockpit

@points

Shows a build screen before play: the player distributes this many extra points on top of your declared skill values, and can also pull a skill below its starting value (down to zero) to spend those points elsewhere. max caps any one skill at creation. Skill descriptions appear here. Restarting returns to this screen. Without this line, play begins immediately.

@points 4 max 6

@wardrobe

Whether players may freely equip and unequip items. The default is locked: players can see their gear but only change it when your script allows it (see the ~ wardrobe effect). open leaves it free for the whole game.

@wardrobe open

@reveal

Line pacing on the play page. click (the default) reveals one line per tap, space, or enter. paced reveals lines on a timer, and a tap skips ahead. off shows each new passage at once. The editor preview is always instant.

@reveal paced

@fail

A fail rule: whenever an effect changes state and this condition is true, the run fails. The player sees your message and returns to the last checkpoint (see ~ save), or restarts if there is none. You can declare several rules. A choice can also fail directly with the FAIL target.

@fail resolve <= 0 "The sand is soft as snow, and warm."

@bg / @accent / @font

Restyle the player for your game. @bg takes a six-digit hex color; panel, border, and dim-text shades are derived from it, and light backgrounds get dark text automatically. @accent recolors the highlights. @font is one of book (the default), mono, serif, sans, humanist.

@bg #10141d
@accent #c8a96a
@font serif

skill

A skill is three things at once: a number the player can grow, a voice that can speak lines, and the thing dice checks roll against. The trailing number is its starting value (2 if omitted); the color is used wherever the skill appears. An optional quoted blurb at the end is shown on the character screen (and as a sidebar tooltip), so players know what they're choosing.

skill sangfroid "Sang-Froid" #8fb3a8 = 2
skill sangfroid "Sang-Froid" #8fb3a8 = 2 "Cold blood. The discipline to do the slow thing while the world goes fast."

char

A character who can speak. The first word is the short id you type in dialogue lines; the quoted name is what readers see. Declaring a you character is a common way to give the protagonist spoken lines.

char marchand "Marchand" #f0c987
char jekyll "Dr. Jekyll" #b8c4cc
char you "You" #e0d6c3

item

What an item modifies decides which of three kinds it is:

  • Equipment — a skill modifier (sangfroid+1). The player equips it from the wardrobe, and the modifier applies to every roll and total while it is worn. With no slot it stacks freely; a slot caps how many of a kind can be worn (see below).
  • Consumable — a stat modifier (water+1). It sits under ITEMS with its effect shown, and the reader can click it any time to apply the change and spend one.
  • Key itemno modifier. A plain thing you carry: nothing to wear or click, but has(item) still gates on it (a chart, a letter, a key).

An item is one kind, not a mix: equipment or a consumable, never both. All three stack and can be given in quantity (~ give water 3); has(item) reads as the count.

item jacket "Flying Jacket" sangfroid+1 hands-1   # equipment (a skill)
item cup "Cup of Water" water+1                  # consumable (a stat)
item chart "Soaked Chart"                        # key item (no modifier)

slot

A slot is a kind of equipment, and it caps how many of that kind can be worn at once, so gear forces a choice instead of stacking. Declare a slot with an id, an optional display name, and an optional limit. Then put items in it by using the slot's name as the keyword, exactly like item but slotted.

The limit defaults to 1: a slot that holds one thing, where equipping a second item swaps the first out. Set a higher limit with = N for a budget; once it is full, the next item you equip pushes out the one you put on longest ago. Slots may be declared above or below the items that use them, and each appears under EQUIPMENT in the sidebar with a worn/limit tally.

slot hat                  # one hat at a time (limit defaults to 1)
slot charm "Charms" = 3   # a budget: wear any three

hat   fedora "Felt Fedora" logic+1 esprit-1
charm ring   "Brass Ring"  physique+1

currency

One per game: the player's money. It sits at the foot of the sidebar and shows as a float (340.00) so it reads as cash whatever you name it, and it powers the [pay]/[earn] choice tags and ~ pay/~ earn effects. It behaves as a normal variable in conditions. For non-money resources like water, ammo, or morale, use a stat instead.

currency franc "Francs" = 0

var / stat

Both declare a named value: a number, true/false, or a "string". A stat appears in the player's STATUS panel; a var is hidden bookkeeping. Give a numeric stat max N and the panel draws it as a row of filled/empty pips, a gauge the player sweats toward zero; the value then clamps at that cap (the floor stays open, so an @fail on <= 0 still fires).

stat resolve = 3 max 5   # a 5-pip gauge, capped at 5
stat morale = 2          # a plain number
var knows_drift = false

inside a passage

== name

Starts a passage. Names are single words (letters, digits, underscores). :: also works, for Twine muscle memory.

== night_walk

narration

Any plain line is narration. If a narration line would be mistaken for another kind of line (it starts with a bracket, or a word followed by a colon), start it with | to force it.

The desert at night is black sand under black sky.
| Warning: the well is dry.

dialogue

A declared character or skill id, a colon, and the line. Skills speak in their color with a bold name; using an undeclared name is a compile error (it is usually a typo).

marchand: "I'm not dead. That's the main thing."
sangfroid: Say it plainly and do not say it again.

? passive checks

An interjection that appears only if the skill's current total (including equipment) meets the number. No dice: passives are deterministic, and each fires at most once per run.

? senses 7: Petrol, but faint, and fading. She didn't burn.

-> jumps

Go straight to another passage. END finishes the game; FAIL triggers the fail state. With a line gate in front, a jump becomes conditional, which is how one passage can quietly route to different scenes.

-> dawn
[has(chart)] -> shortcut

line gates: [condition] and [once]

Any non-choice line (narration, dialogue, effects, jumps) can carry gates in front. A condition gate skips the line when false. [once] runs the line at most once per game, however often the passage repeats. This is how one passage varies with state instead of being cloned.

[once] Silence, enormous and sudden.
[knows_drift] reckoning: You are lower than the dial says.
[resolve < 2] ~ set shaky = true

choices

basics

Choices start with * and end with a target. All choices in a passage are offered together after its lines. Choices the player has picked before are shown in red; they stay selectable unless marked [once].

* Wait for dawn -> dawn
* Walk out now, into the dark -> night_walk

bracket gates

Brackets before the text modify the choice, and they combine freely: any number of conditions (all must hold), plus at most one check and one cost, plus [once]. A hidden condition hides the choice entirely; a spent [once] stays visible but locked.

* [has(chart)] Follow the chart's legible corner -> walk_end
* [once] Go through the wreck, pocket by pocket -> salvage
* [once] [mae_trusts] [pay 10] Buy her silence -> quiet

skill checks: [white] and [red]

A check rolls dice when chosen and needs two targets: success, then failure, separated by |. The tag on the choice shows the skill, difficulty, and live success odds. white checks can be retried after the skill itself improves; red checks get one attempt ever, and the whole choice is outlined in red as a warning.

* [white reckoning 10] Run the numbers again -> drift_yes | drift_no
* [red hands 12] Fly her into the ground like a landing -> wreck | wreck_hurt

costs: [pay] and [earn]

A pay choice shows its price, greys out when the player can't afford it, and charges on selection. [earn] is the reverse. A cost and a check can share a choice; the cost applies on the attempt, then the dice decide.

* [pay 20] Slip the guard a few notes -> through
* [pay 5] [white sense 9] Ante up and read the table -> win | lose

effects

Effect lines start with ~ and change state as the passage plays. All accept line gates.

~ set

Assign any variable, stat, or skill from an expression. Silent: nothing is shown to the player.

~ set resolve = resolve - 1
~ set knows_drift = true

~ give / take / equip / unequip

Move items in and out of the player's possession. give and take announce themselves; equip also gives the item if needed and puts it on regardless of the wardrobe state. If the item is in a slot, equipping it obeys that slot's limit, swapping out the longest-worn piece when the slot is full.

Items stack: give/take may carry a count, the sidebar shows ×N, and has(item) stays true while any remain. That makes a consumable — a [has(water)] choice that does ~ take water plus whatever the item should do (refill a stat, say).

~ give water 3
~ take water        # removes one; "Item lost" only when the last is gone
~ equip jacket

~ pay / earn

Spend or gain currency, with a visible line. The amount can be an expression. Requires a declared currency.

~ earn 50
~ pay toll

~ points

Grant skill points. The player allocates them immediately on a +/− screen, anywhere they like, before play continues.

~ points 1

~ skill

An author-directed change to one specific skill, up or down, announced to the player. Raising a skill this way can reopen its failed white checks; this and ~ points are the two ways through that lock.

~ skill sangfroid -1

~ save

A checkpoint. Progress persists in the reader's browser; returning visitors get CONTINUE or START OVER, and fail states return here. There is no player-initiated saving: you decide where the mercy goes.

~ save

~ wardrobe

Open or close the player's ability to change equipment. Typical rhythm: open during safe scenes, close before commitments.

~ wardrobe open
~ wardrobe close

expressions

Conditions, ~ set, ~ pay/~ earn amounts, and curly interpolation all use the same small language:

Inside narration, dialogue, or choice text, {expression} is replaced with its value. Braces that don't parse are left alone.

* [water >= 2 and not has(chart)] Ration carefully -> morning
You fill your pockets: raisins, the thermos with its {water} cups.

how play works

dice

A check rolls 2d6 and adds the skill's total (base plus equipment). Meet or beat the difficulty to succeed. Double sixes always succeed; double ones always fail. The roll is shown itemized, and choices display their live odds.

Difficulty names, for flavor and calibration:

6 Trivial   8 Easy   10 Medium   12 Challenging
14 Formidable   16 Legendary   18 Heroic   20 Impossible

white checks, red checks, and the lock

A failed white check locks, marked failed, until that skill itself is upgraded past the value it failed at (via ~ points or ~ skill). Equipment improves rolls but cannot reopen a failed check: the mind that failed has to grow. A passed check disappears. A red check is once ever, whatever happens.

checkpoints and failure

When a @fail rule triggers or a choice hits FAIL, the run ends with your message and one button: return to the last ~ save, or start over if none was reached. Checkpoints live in the reader's browser, per game; republishing a game invalidates old checkpoints. Finishing a game clears its checkpoint.

reading flow

By default each tap reveals one line, and everything above the newest line dims so the reader's place is always the bright edge. Choices appear when the passage has fully arrived. Already-picked choices show in red.

reader settings

The settings button in the header lets readers adjust text size or switch to a two-color e-ink view, saved on their device for every game. These sit on top of your theme and never change your file, so the same story stays readable however someone needs to read it. (E-ink mode replaces color-coded meaning with text, so a red check still reads as one even with no color.)

publishing and exporting

PUBLISH puts your game at a bare link you can share; readers play in the browser with no account, and you can republish updates to the same link or unpublish it from the same browser you published from. EXPORT downloads a zip holding a self-contained playable index.html (it runs offline, forever, with no dependence on this site) plus your script as source.txt. IMPORT reads that zip, or any plain .txt, back into the editor. The zip is also exactly what itch.io's "HTML project" upload wants, if you'd like to host or sell your game there.

A published game is pinned to the engine version it was made under. When andstar updates, a game you already shared keeps the exact look and behavior it had at publish time, so new features never disturb your back catalog. Republishing moves it to the current engine (which is what you see in the editor).

What you publish stays yours. Stories are never used for AI training, sold, or mined for data.