258 Commits
Author SHA1 Message Date
AyeZeeBB 8452f8871f Polls: answer with the number keys
A dedicated server's poll could only be answered by clicking a row on its card
or by typing /1, /2... in chat.

While a poll is running, the top-row number keys 1 to 6 give that answer (as
many keys as the poll has answers). They are read only while a poll is open,
so they stay the game's own the rest of the time, and not while the menu, the
console or the chat box has the keyboard, as with the Yes and No keys.

On the card each row's number is now a white keycap, blue for the player's own
answer, and the hint reads "Press 1 to N on the keyboard, or click an answer."
Clicking and /1, /2... still work.

Not covered: the numpad (the bind system does not read it), controller
buttons, and rebinding; these keys are fixed.
v2.0.2
2026-10-09 16:12:12 -05:00
zeex64 b2b434e622 Merge pull request #143 from moelrobi/claude/loving-goodall-98qb8j
Server votes: custom votes, polls, more vote settings and announcements
2026-10-09 16:06:15 -05:00
Robin MöllerandClaude Opus 5.5 c996fbda13 Server votes: custom votes, polls, more vote settings and announcements
Builds on the 2.0.0 vote card. Protocol 46: a server's vote can now be a
poll, and the roster carries who may start polls, the owner's own votes
and the current announcement.

Custom votes (votes.custom): the server owner defines /vote <name> [choice]
in ReSkateServer.json. When one passes, the server runs its command as the
console; {map} is the current map and {arg} the player's choice, which must
be one of the vote's "choices", so players never put free text into a
command. They show in /help, /vote list and the "/" menu.

Polls: /poll <question> | <answer> | ... with 2 to 6 answers. A poll runs
nothing. Players answer by clicking a row on the vote card or with /1, /2...;
the card shows each answer's count, then the result for a few seconds.
votes.polls says who may start one (off, admins, everyone), poll_seconds how
long it runs, and /poll end ends it early (its starter or an admin).

More vote settings: each vote may have its own seconds, cooldown_seconds and
min_players; starter_votes_yes says whether starting a vote counts as a yes.
The "votes" admin command sets all of them.

Announcements: "announce <text>" posts a chat line and shows a card at the
top of every player's screen. The new "announcements" section holds messages
the server posts in turn every interval_minutes while players are on;
"card": false keeps them to chat. Managed with the "announcements" command.

Older configs gain the new settings with their defaults on first start.
Server/README.txt documents them.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01WbSRfNf5T9wX4XMMQ5kwia
2026-10-09 21:01:40 +00:00
AyeZeeBB 43834aed92 Merge branch 'main' of https://github.com/Dingo-Shenanigans/ReSkate 2026-10-09 16:00:05 -05:00
AyeZeeBB e533dadccb Server: shed stale poses when behind, and send each pass on several threads
A full server (about 120 players) slowed down at random until everyone lagged:
one pass a second, each taking over six seconds, 115% busy, and whole poses
going out by the thousand.

Why it stuck. After any stall the next pass had everything that arrived
meanwhile to pass on, to every player, so it took longer still. By then the
poses each update would have built on had gone stale, so poses went out whole,
ten times the size and more work again. Each pass carried the whole of the
last one's arrivals and the server never caught up.

Shedding. A pass normally reads one or two poses from each player. When more
than three of one player's are waiting, only the newest is passed on. Contact
effects are held to two packets a player a pass. Each pass then has a bounded
amount to do whatever the backlog, so the server catches up; players see the
others at a lower rate for a moment. The log says when it happens (at most
every 30 s) and `net` has a "shed while behind" count.

Threads. Building each player's update of everyone else was 80% of a pass. It
reads the other players and writes only that player's own state, so it is now
done for several players at once (worker_pool.h); the server's own counts and
the marks on whole poses are added up afterwards, and sends into the transport
are made one at a time. New setting network.threads: 0 (default) is one thread
for each processor but one, up to 8; 1 is the single thread as before. The
server says how many it uses when it starts.

Load test. Server/Test/server_load_tests.cpp drives the host with simulated
players over a transport that is not Steam's (built with the multiplayer tests
on Windows, not run by ctest). With 120 players at 20 TPS and 27 MB/s out, the
loop's share of one core went from about 50% on one thread to 26% on four and
22% on eight, and every player was sent byte for byte the same on 1, 2, 4 and
8 threads. A simulated 3 s stall shed about 7,000 poses, took one 169 ms pass
to recover and lost nobody.

The test's transport has none of Steam's send cost, so a real server's loop
sits higher than these figures. Receiving, choosing who is sent which pose and
the sends themselves still run on one thread.
2026-10-09 16:00:02 -05:00
zeex64 a4daa1993d Merge pull request #142 from Jean-LucTch/main
TEST (launcher): add DepotDownloader output regression tests and improve progress parsing
2026-10-09 15:50:23 -05:00
AyeZeeBB 0f38a9fdeb faster mod merging 2026-10-09 15:42:23 -05:00
AyeZeeBB 869c70849e Log why another player's outfit could not be shown
Another player's skater starts as a copy of this player's own and their outfit
is put on after. An outfit that is refused leaves them as that copy: a player
reported everyone on a server looking like their own character.

Nothing was written when that happened. The reason only showed as the
"Cosmetics:" line in the multiplayer menu's player details, so a report had
nothing to go on. A refused outfit now logs a warning with the reason, three
times per reason and then every 200th: "a player's outfit could not be shown,
so they look like you (N so far): ...". Waiting for a player's actors, the
ordinary start of every player, is not logged.

The cause of the report is not known yet. The likeliest is a mod on that
player's side that changes the skater's customization layout, which makes
every other player's outfit fail the layout check.
2026-10-09 14:54:21 -05:00
AyeZeeBB 464e189d61 Guard the game's level unload against an entry with no asset
Leaving a level could crash the game: an access violation in Skate.exe at
+0x3f5fc52, on one of its worker threads, with no ReSkate code on the stack.
Three reports from one PC show the same crash at the same address (two on
2.0.0, one on 1.1.8), each about half a second after leaving Skate3Improved on
a server of 81 to 101 players.

While a level unloads, a job walks each unloading object's table of 0x30-byte
entries and reads a number at +0xc8 of the asset each entry points to. An entry
whose asset never resolved holds null there, and the game reads it unchecked.

The loop is rewritten in place at startup so such an entry is skipped. The
2-byte nop before the loop makes room for a jz straight after the pointer is
masked, the two moves it displaced follow it, and the loop's jump back is
retargeted to the new start. Everything from the read on stays where it was;
nothing else in the function jumps into the rewritten bytes.

The patch is applied only when the game's 50 bytes are exactly what it was
written for. Otherwise the game runs as shipped and the log says why; startup
goes on either way. The log shows "Level unload crash guard: ready" when it is
in.

Not known: which asset is unresolved (the map's, or something another player
had equipped), and why it only happens some of the time. The reports hold
stacks only.
2026-10-09 14:49:33 -05:00
Jean-Luc T. d2e17db9cb Merge branch 'Dingo-Shenanigans:main' into main 2026-10-09 18:36:10 +02:00
Jean-Luc T. 9865de12df Ignore local CMake user presets
Add `CMakeUserPresets.json` to `.gitignore` so machine-specific CMake presets stay untracked.
2026-10-09 18:34:39 +02:00
AyeZeeBB 4d77b859bc Start under Proton again; vote card on the right in the notices' look; Hall of Meat note
Linux and Steam Deck. 2.0.0 did not start under Proton: the launcher said
"ReSkate could not attach to Skate". The block on EA's online services hooks
five of Windows' name lookups and took any failure as fatal, and Wine's ws2_32
has no GetAddrInfoExA. Only getaddrinfo, the one Skate.exe resolves names
through, is required now. The other four are extra cover for anything else in
the process: one that is missing or cannot be hooked is left as it is, with a
line in the log. A function the system does not have cannot be called, so
nothing is left unblocked. On Windows all five are hooked as before.
Vote card. It sat on top of chat and looked like neither the menu nor the
notices. It is now on the middle of the screen's right edge, whatever chat is
doing, as a flat dark tile with a strip of colour down its left: blue while
running, green passed, red failed, grey cancelled. The question is in the
heading font, the bar is under it with the tally below, and Yes and No are
menu tiles with their binds on white keycaps. The server's line that starts a
vote says "the card at the right of your screen".
Hall of Meat. Its row in the Insert overlay now says when No Bail (or noclip,
which includes it) is stopping the bails it scores. The tab it is on,
MOVEMENT, is now GAMEPLAY, and the card FLIGHT & BAILS.
v2.0.1
2026-10-09 11:26:10 -05:00
Jean-Luc T. e031571e1a Validate DepotDownloader progress output
Reject malformed, non-finite, and out-of-range progress values while preserving them as ordinary messages. Add parser regression tests for progress and QR-code output, and register them with CMake.
2026-10-09 18:14:35 +02:00
AyeZeeBB f02a39a3f0 Hall of Meat toggle in the overlay; objects placed in a burst are deleted, not held
Overlay. Hall of Meat could only be switched from the game's own menu and the
console. The Insert overlay's skater page now has a "Hall of Meat" switch on
the Movement card, under No Bail. It runs the same "hallofmeat 0|1" command, so
both menus agree and the choice is saved with the profile. It is greyed out
when Hall of Meat did not start.

Server. A player who is not an admin and places more than twice the object
limit plus 100 in a minute (a modified game animating objects by respawning
them) had their objects held as they were for a minute. They are now deleted
for everyone, and nothing that player places is shared for the next minute:
without that their game would upload them again at once. The log names the
player once with their SteamID and how many objects went, and they are told in
chat. After the minute only what they place anew is shared.

The server cannot delete the objects in that one player's own game, so they
still see them there; nobody else does.
v2.0.0
2026-10-09 10:30:31 -05:00
zeex64 b158887f06 Merge pull request #137 from Krischan-Klug/main
Add Hall of Meat: the bones a bail hurt and its Meat score
2026-10-09 10:24:36 -05:00
AyeZeeBB b3b067a356 The creator tag reads "Content Creator"
The badge a content creator gets before their name, in chat, on their nametag
and on their own tag in the menu, said "Creator". It now says
"Content Creator". Tests and comments that quoted the old text follow.
2026-10-09 10:04:49 -05:00
AyeZeeBB ccfd05e0df Dedicated servers: everything goes through the server; object burst hold; names for bans by ID 2026-10-09 09:59:45 -05:00
Krischan-KlugandClaude Opus 5.5 c7d2ca3601 Add Hall of Meat: the bones a bail hurt and its Meat score
As in skate. 3: when the local skater bails, the bones it hurt show over
the world through the body, yellow where a hit bruised one and red where
one broke it, with the bail's Meat card in the bottom left corner in the
place of skate.'s own HUD there: its time, hits (head hits double,
vehicles half again), broken bones, road rash, airtime, fall, top speed
and rotations, each scoring, and the map's best. A bone breaking pulses
the screen's edges red and, in single player, slows the game down a
moment. Off until switched on, as in skate.: in skate.'s menu (Custom
Stuff > Player) or with `hallofmeat 0|1`, saved with the profile.

Everything it draws is skate.'s own, read from the installed game: its
skeleton mesh (the Dem Bones costume) posed with the renderer's own
skinning matrices, its scoring icons, the THRASHER wordmark and its UI
brush strokes. Nothing is shipped.

How it works: No Bail already hooks the skeleton response, which runs
once a physics step right after the body contacts; it now hands that step
on, with the local skater it follows, but only while Hall of Meat is on.
Each step reads what every ragdoll body hit and how hard, and whether the
skater is a ragdoll; the bail runs on the game's own clock so slow motion
measures what the body did. The feature's own hooks, on the renderer's
skinned draw packets and main view and on the UI model's write, are
prepared at startup and switched on only with the feature, and off again
once the HUD corner and the game's speed are given back: switched off, the
game never calls them and the physics step pays nothing. The skeleton mesh
is read the first time it is on; only the images are read at startup,
since the overlay builds its atlas once. The renderer's picture of the
skater is read only while a bail shows. The menu's switch reads the
overlay model like the others. Every address is in the build table with a
fingerprint checked before use. Extension/HallOfMeat/README.md describes
the parts; its tests build with DINGOSDK_BUILD_HALL_OF_MEAT_TESTS.

The slow motion changes SimulationTime's rate, frame cap and time scale as
a session override and steps the local skater along, since skate. sets a
skater's step only when it builds its core. It runs the same at every
break, but never faster than the game ran: with the trainer's game speed
below 1 it only takes the part that is slower still. Afterwards it writes
back what it found, each setting only while it still holds what the slow
motion wrote, so the trainer's speed comes back as it was; a setting
changed from elsewhere meanwhile is left as it is and ends that slow
motion. named_setting_value reads a setting's value for it.

Tuned in play: a bruise from 7 m/s and a break from 12 m/s along the
contact normal (raised twice: a hard fall on flat ground broke bones), a
break worth ten of the lightest hits (a heavy bail's hits and breaks
outweighed the rest of the card) and a fall half of skate. 3's rate.

Fix: the overlay now draws in the back buffer's pixels, not the window's,
so it lines up on displays Windows scales (1920x1080 borderless on 4K).

The skater's render hooks, its skeleton and its body maps were first
found by gBGYo's ReSkate fork (github.com/gBGYo/ReSkate).

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-09 15:29:38 +02:00
AyeZeeBB b229062400 Skater effects on other players: costume and board trails, and contact sparks and dust
Other players' skaters and skateboards showed none of the game's skater
effects: not the trail or fire a costume or deck comes with, and not the
sparks, dust and puffs of a skater touching the world.

Costume and skateboard effects. The game gives another player's skater and
skateboard the right effect sets by itself, but builds them before their
outfit is on, so nothing showed. They are now built again half a second after
the outfit is applied. An always-on effect that a skater's item puts on the
skateboard's wheel joints (the Ghost Skater trail) follows the skater's own
copy of those joints, which only this player's skater keeps up to date: for
other players it is taken out of the skater's sets and built on their
skateboard, which has the same joints.

Contact effects. They come from a skater touching the world, which only
happens in that player's own game. Each game now captures its skater's
contacts (position, velocity, surface normal, surface material) and sends up
to three a tick in a new unreliable packet, PacketKind::effects. Other games
play each through the game's own function, so the effect is still chosen from
the surface and the speed. A contact is shown as late as that player's poses
are, only within 30 m of their skater, and only for a material the level's
table has: the game reads that table without a bound.

Server. A dedicated server relays effects packets to players within 150 m of
the sender, at most one packet a tick from each player. New setting
players.sync_effects (default true), console and admin command
"effects on|off". Off: the server relays none, and the roster tells games
neither to send their contacts nor to build other players' costume and
skateboard effects. Player-hosted lobbies relay through the host and always
share them.

The roster carries one more byte for the setting. Still protocol 45, which
has not been released.

New console command "mp effects": what has been captured and played, and why
the last contact was refused if one was.
2026-10-09 00:10:11 -05:00
AyeZeeBB 574860da72 Binds for first person, the HUD, voice chat, time of day, No Bail, challenges, nametags and dots
Binds for first person, the HUD, voice chat, time of day, No Bail, challenges, nametags and dots

Eight more actions can be put on a keyboard key, a chord or a controller
combo, in the binds list beside the others. None is bound until the player
binds it.

- First person, Hide HUD, Voice chat on / off, Next time of day, No Bail,
  Show / hide challenges, Player nametags, Player dots.
- Each bind runs the console switch for it, so it follows the same rules as
  typing it: No Bail still answers to a server that has it off, and the time
  of day goes to the server for an admin where the server sets it.
- They are one table (action_binds): a bind is its name in the profile, the
  name "bind <name>" takes, its label and its command.
- "bind firstperson|hidehud|voicechat|tod|nobail|challenges|nametags|
  nametagdots <n>" sets one from the console; 0 clears it.
- They are not read while the menu, the console or the chat box is open.

Console, which the binds use and anyone can type:
- Every on/off switch takes "toggle" ("nobail toggle", "hideui toggle").
- "firstperson 0|1", which was only in the menu.
- "tod next": the time of day after the current one.
- "mp voice-chat on|off|toggle": the player's own voice chat, leaving the
  rest of their voice settings; it says which way it went in their chat.
2026-10-08 22:39:05 -05:00
AyeZeeBB 46cf65df0a Server: remove players who have been away too long
Server: remove players who have been away too long

A dedicated server can remove players who are away from their game.

- "afk_kick_minutes" in the config's "players" section: 1 to 1440, or 0
  (the default) for never. "afk-kick <minutes>|off" from the console or an
  admin; a change is saved and applies at once.
- Away is doing nothing a player at their game does: not moving or turning,
  not speaking, not sending chat, and not placing, moving or removing an
  object.
- A minute before the limit the player is told in chat; at the limit they
  are removed with a message saying why and that they can join again. The
  log has an "[afk]" line.
- Admins are never removed for it. The time starts once a player's game has
  loaded the map, and starts over after a map change and when the setting is
  changed.
2026-10-08 22:25:17 -05:00
AyeZeeBB 9ab985e778 Server: object scaling can be turned off
Server: object scaling can be turned off

A dedicated server can stop players resizing the objects they place.

- "allow_object_scaling" in the config's "players" section (default true),
  and "object-scaling on|off" from the console or an admin. A change is
  saved and applies at once.
- Off: the server shares every player's objects at their own size, whatever
  that player's game sent. Admins can still resize theirs, as with the
  object limit.
- The roster tells each game. In the park editor of a player on such a
  server the SCALE mode is not offered, its Y shortcut does nothing, the
  scale box is disabled with a note saying why, and what is placed or edited
  is its own size.
- An object resized before the setting was turned off is its own size for
  everyone else straight away; its owner sees it resized until they edit it.
2026-10-08 22:21:00 -05:00
AyeZeeBB c8c6cf16f2 Launcher: mod overviews show the README, in a larger two-column layout
The overview that opens when a mod is clicked, on both MY MODS and GET MODS,
now shows the mod's README and has more room for it.

README:
- GET MODS fetches a package's README from Thunderstore the first time its
  overview opens (/api/experimental/package/<owner>/<name>/<version>/readme/)
  and keeps it while the launcher runs.
- MY MODS shows the mod's own README.md from its folder, or the package's
  from Thunderstore when the folder has none.
- The markdown is laid out as plain text: headings in bold, lists, rules and
  code blocks kept; links keep their text; images and HTML are dropped; a
  table row shows its cells side by side. A README is cut at 400 lines, with
  a note that the rest is on the mod's page, and one over 512 KB is not read.

Layout:
- The overview is up to 1080 x 740, from 680 x 560.
- The header has a larger icon with the name, the author and the short
  description beside it. An installed mod shows its Thunderstore icon.
- Under the buttons the README has the wide column and the facts (version,
  downloads, updated, size, categories, folder, maps and so on) have a panel
  of their own on the right.
2026-10-08 22:12:48 -05:00
AyeZeeBB 5967124f3a Vote card above chat with rebindable Yes and No; fix full servers breaking on extra slots
Votes on a dedicated server show as a card above chat instead of being
followed through chat lines.

- The card has what is voted on, the Yes and No counts, how many are needed,
  a bar of how far Yes has got, and the seconds left. When the vote ends it
  shows Passed, Failed or Cancelled for four seconds.
- Yes and No are two buttons, labelled with the player's binds. The answer
  given is highlighted and can be changed. They can be clicked whenever the
  cursor is free (chat, menu or console open).
- Two new binds, "Vote yes" and "Vote no", in the binds list: F1 and F2
  unless changed, to keys or controller combos like the others. They are
  read only while a vote is running, and not while typing.
- /yes and /no still work and show on the card. The player a kick vote is
  about sees the card and has no vote in it.
- Console: "mp vote yes|no", "bind voteyes <n>", "bind voteno <n>".

Server:
- The roster carries the running vote (id, kind, tally, seconds left,
  starter, target, label) and the one just finished with how it ended.
- A chat line is no longer sent for each change of the tally; the lines for
  a vote starting and ending stay.

Fix: a dedicated server's roster may list more players than its limit.
The extra slots for reserved players and admins (33 of 32) made a roster the
protocol refused to encode, so with one in use the server logged
"Server error" every pass and stopped part-way through each one until
somebody left. Lobbies hosted by a player are still held to their size.
2026-10-08 21:54:45 -05:00
AyeZeeBBandClaude Opus 5.5 4f92ec0d22 Merge pull request #98 from Vebjorhk: keep the game off EA's online services
Without contrib/ea-watch.ps1, the script for recording what the game connects
to, and without the README line that pointed to it.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-08 21:37:42 -05:00
zeex64 5d1c7af6c0 Merge pull request #97 from xThrasherrr/fix/custom-maps-mod-loading
Make mod loading tolerate damaged mods and BOM manifests
2026-10-08 21:33:51 -05:00
zeex64 7cdd2eaede Merge pull request #132 from VexFlint/fix/mesh-tests-direct-join
Build the mesh tests again: their fake transport takes the direct address
2026-10-08 21:31:38 -05:00
AyeZeeBBandClaude Opus 5.5 254af5f303 Merge pull request #130 from ValveTextureFile: record the merge
The change itself went in with 29c4291, which was made as an ordinary commit
and so left the pull request's own commit out of main's history. This merge
adds it, with no change to any file.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-08 21:30:25 -05:00
AyeZeeBBandClaude Opus 5.5 29c42911ff Merge pull request #130: server admin commands in their own file; one update loop
Conflicts in Server/server_host.cpp: main changed the command code after this
branch moved it to Server/server_commands.cpp. The moved copy now has what
main added since: the "chat-color" command, "park random", and its line in
the help text.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-08 21:24:32 -05:00
zeex64 2c90fbec36 Merge pull request #43 from ComputerKWasTaken/codex/random-community-parks
Add random community park loading and launch randomization
2026-10-08 21:20:47 -05:00
zeex64 a243ece725 Merge pull request #33 from JusSkates/true-first-person
Keep the first-person view level and steady; optional third person on foot
2026-10-08 21:09:49 -05:00
zeex64 de90c302d7 Merge branch 'main' into true-first-person 2026-10-08 21:09:41 -05:00
zeex64 63ee53382a Merge pull request #63 from northdroplet/feat/gamepad-touchpad
Launcher: controller support and the Steam Deck trackpad as a mouse
2026-10-08 21:04:34 -05:00
AyeZeeBBandClaude Opus 5.5 a0b4d4c0aa Overlay: the PlayStation pad reader no longer needs the rest of the overlay to link
The reader's input-access counter was defined in input_capture.cpp. Built on
its own, as the launcher's controller support (#63) builds it, the reader
then failed to link with an unresolved overlay_input_access. The counter is
now defined beside the reader; the overlay uses the same one as before.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-08 21:02:12 -05:00
VexandClaude Opus 5.5 57c440507a Build the mesh tests again: their fake transport takes the direct address
38d86e1 gave SteamTransport::join a direct IP and port and added
take_direct_notes(), but the fake transport in mesh_tests.cpp kept the old
join and had no take_direct_notes, so the Windows test build failed. The
fake ignores the direct address and has no notes.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-08 22:53:11 -03:00
zeex64 30f000f90d Merge pull request #65 from Eplisium/trainer-map-waypoint
Trainer: teleport to the pause-map waypoint, onto the surface there
2026-10-08 20:52:22 -05:00
zeex64 f18b50913b Merge pull request #122 from Swagi-REDACTED/main
Added lots of new binds, allowed keys to be bound for controller back button support.
2026-10-08 20:49:59 -05:00
zeex64 4bfa71e94f Merge branch 'main' into main 2026-10-08 20:49:51 -05:00
zeex64 24762cf135 Merge pull request #100 from VexFlint/docs/linux-proton-client
Document running the game on Linux through Proton
2026-10-08 20:44:42 -05:00
zeex64 1ea7fc1d4a Merge pull request #101 from ComputerKWasTaken/codex/fix-fakie-forward-boost
Fix Forward Boost direction while riding Fakie
2026-10-08 20:44:11 -05:00
zeex64 b8942a16c7 Merge pull request #103 from wildesPepega/pterodactyl-egg
Add a Pterodactyl egg for the Linux dedicated server
2026-10-08 20:43:47 -05:00
AyeZeeBB 0b58163de5 Server: its chat lines in colours the owner chooses; protocol 45
Server: its chat lines in colours the owner chooses; protocol 45

A dedicated server's own lines in chat (its welcome, console messages and
answers) were made violet in #129. The owner can now pick the colours.

- "chat_color": the "Server" badge and name, as "#RRGGBB" (default
  "#8E5CFF", violet).
- "chat_text_color": the text of those lines (default "#D9C8FF", lavender).
- Both are in the config's "server" section; a value that is not a colour
  stops the server from starting and names the setting.
- Console: chat-color <#badge> [<#text>]. Saved, and sent to everyone on
  the server, so the next line uses it.
- With the defaults, chat looks as it did.

The colours travel in the roster, so this is protocol 45: servers and
games must both update. Lobbies hosted by a player are unchanged.
2026-10-08 20:42:51 -05:00
zeex64 e57bae499a Merge pull request #105 from lennyblk/main
Name the file and the reason when cannot open it for SHA-256 on Linux
2026-10-08 20:42:27 -05:00
zeex64 c434558a66 Merge pull request #111 from AlexanderPuglisi/fix/log-steam-offline-reason
Launcher: log why Steam counts as offline
2026-10-08 20:42:05 -05:00
zeex64 8d21a19b18 Merge pull request #131 from wilu222/board-wear-persist
Persist the board wear toggle across map changes and restarts
2026-10-08 20:38:39 -05:00
zeex64 8fe9964f73 Merge pull request #129 from moelrobi/claude/compassionate-heisenberg-ekazit
Chat: highlight server messages in violet
2026-10-08 20:34:48 -05:00
vtf fbb76133c9 server: admin commands in their own file; one update loop for both platforms. 2026-10-08 21:00:09 -04:00
wilu222 73e71a1be6 Keep the board wear toggle on across map changes and restarts 2026-10-08 20:54:47 -04:00
Robin MöllerandClaude Opus 5.5 bc21311ccf Chat: server lines stand out in violet
A dedicated server's own chat lines (its console, welcome message and
answers to this player) get a violet "Server" badge and name and
lavender text, in the open chat and the fading lines.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01MzTrhiZ2cNYyJgMHqTp1kf
2026-10-09 00:07:58 +00:00
AyeZeeBB f13995dfe8 Fix players freezing on dedicated servers; reserved slots are extra slots; bone scale limit 2
Fix players freezing on dedicated servers; reserved slots are extra slots; bone scale limit 2

Players stopping and jumping (1.1.6):
- The new sound messages begin with the same four bytes ("RMS1") as the
  pose updates games send each other over their direct links. The game
  took those pose updates for sound and discarded them, so a directly
  linked player moved only when a whole state arrived.
- Game: only messages from the dedicated server are read as its sound,
  pose or acknowledgement messages; anything from another player is
  decoded as what it is.
- Server: poses and sound go through the server to every player, whether
  or not two games have linked to each other. This fixes games still on
  1.1.6 without an update, at the cost of more outbound on small servers.

Reserved slots:
- "reserved_players_slots" no longer holds slots back. Anyone joins until
  max_players are on; the listed players and the admins can still join
  after that, each adding one slot beyond the limit (33/32 and so on).
- An admin who is also listed counts once, and the total never exceeds
  what a session can hold.
- The list holds up to 1024 players again. "reserved" in the console shows
  how many extra slots there are.

Server:
- "bone_scale_limit" is 2 by default. The game's own skater height is a
  bone scale, so 1 showed everyone at one height. A config that already
  has 1 written in it keeps it until changed.
v1.1.8
2026-10-08 17:12:41 -05:00