# Getting started

## Where scripts live

Open the Lynx menu, go to **Play → Lua**, and put a `.lua` file in the scripts folder shown at the top of the tab (under the app's documents directory in `Lynx/Scripts`). Press **Refresh**; the file name is the script name. See [Installing and using scripts](/using/using-scripts/).

## The top level is load

A script has no `on_load` function. Loading compiles the file and runs its top level once; that run **is** load. Set your widgets up and register your callbacks there.

```lua
-- This whole chunk runs once, at load.
local enabled = ui.new_checkbox("Lua", "Main", "Enabled")
client.log("hello, loaded")

-- register a callback for later frames
client.set_event_callback("paint", function()
  if ui.get(enabled) then
    renderer.text(15, 15, 235, 235, 235, 255, nil, 0, "on")
  end
end)
```

**Unload** closes the state (delivering `shutdown` first); **Reload** does both.

## Reading game state

The base globals read timing, the menu and the overlay. The game's own namespace reads the match. Everything the game hands you is a plain Lua table you read directly:

```lua
local t = pool.table()      -- 8 Ball Pool
for _, ball in ipairs(t.balls) do
  client.log(ball.number, ball.position.x, ball.position.y)
end
```

Which namespace you get depends on the build; `client.game()` returns the game key. See the game's page under **Games**.