Releases / v0.95.0
v0.95.0 Room For A Friend
2026-09-18 Engine Latest
The multiplayer tutorial ends with a friend actually playing; the 🌐 panel and a build's F1 menu take a Floptle Cloud code as typed; a joiner's avatar has its body from its first tick; a script that hosts while it is already in a session is told so; and the reference says the two things every action game needs to know. Plus, in the editor, a click into the viewport takes the keyboard off whatever field you were typing in.
The tutorial's friend gets to play
Make it multiplayer, step 11, used to end with the friend spectating: the
platformer has one Player, and it is the host's. The step now gives the
friend a body — duplicate Player as Player2, the second slot — makes each
machine's camera follow the player it steers, catches both players in the
respawn, and puts the host call behind a key so the friend's copy of the same
script does not host a lobby of its own before it can join yours. It ends when
their capsule moves on your screen and yours on theirs. The join line is the
one the engine accepts: net.join("cloud://" .. code). The 🎓 Learn tab and
the page agree.
A cloud code works from the panel
The 🌐 panel's relay field reads cloud now. Join by code sends a
six-character Floptle Cloud code as typed — the first letter names the region,
so the code is the whole address — and Host — get a lobby code hosts on
Floptle Cloud with the project's game key. A host:port in the field is your
own floptle-relay, with its five-letter codes, exactly as before. A build's
F1 menu is the same panel and behaves the same way. A code whose first letter
names no region is refused with the sentence net.join prints.
Hosting while joined is refused
net.host{} on a machine that is already joined, joining or hosting is
refused with one Console line that says which session this is and that
net.leave() ends it. Before, the in-editor loopback host went ahead beside
the live session, and from then on that client predicted somebody else's
avatar while its own never ran — nothing named the cause. The same door
covers the 🌐 panel's host buttons. net.join with an address in no known
form now lists cloud:// alongside the other three.
A joiner's avatar has its body from its first tick
A rig spawned for a joiner while their client was still loading the scene ran
its controller once before its body existed: node.vel read nil on that
one tick, a red line on every friend's Console, in a script that was right
everywhere else. The body is registered before the avatar is bound now, and
node.vel documents the promise: a body's fields are there from the first
tick its scripts run.
The "no Predicted node is yours" line is a note rather than a warning when the
scene authors no slots — a game that spawns avatars spectates for one round
trip by design. It stays a warning when the slots exist and are taken, which
is the one-Player scene with a friend in it. And when the server's scene
binds you to a different node than the Welcome did, the Console says so.
What the reference now says
docs/scripting/networking.md:
cloud://in thenet.joinrow and the lobby-codes section, beside the self-hostedrelay://form, with the six-versus-five-character rule.net.spawnstates what it takes: a prefab by name, a prefab path or a scene path;x, y, zas three numbers;ownerfor an avatar. Thefloptle api net.spawnentry says the same.- What a Predicted node's owner sees. On the owning client a script has two
copies of its state — its locals are the prediction,
syncedis the server — and anything only the server does reaches the owner throughsyncedalone. The publish/view pattern is on the page, with which copy a HUD, an animator and a camera read.docs/multiplayer.md§3 carries the same section. - Effects, sounds and drawing stay where they were made.
spawnEffect,audio.playanddraw.*never cross the wire; the synced-counter pattern that drives them from state is shown once, with a hit as the example. Thefloptle apientries for both calls say so in a clause. - The lag-compensation example reads a named action, as the page's own rule
requires, and
getScript/getscriptare documented as one call. sync animatoris scoped: this node's Animation Controller only.floptle servehands the authored slots out from #1, so aserve+run --jointest of a peer-hosted layout gives the first client the host's avatar; §6d says how to test that layout.
docs/export-builds.md describes joining by a cloud code from the F1 menu.
A click into the viewport ends typing
Type a value into the Inspector, right-click into the Scene view to look around, and the fly keys you press next went into the Inspector field. Any mouse button pressed over the Scene view, the Game view or the bare window now takes the keyboard off the field — and commits the value you typed. A press on a panel is still the panel's.
Upgrading
The 🌐 panel's relay field defaults to cloud; type a host:port for your own
relay. A script that calls net.host unconditionally in start now gets a
refusal on a machine that has joined — host from a key or a setting on the one
machine that should, as the tutorial does. Everything else is words on a page.
Floptle Hub
Engine
The binaries are not signed yet. On macOS, right-click the app and pick Open the first time. On Windows, if SmartScreen appears, pick More info then Run anyway.