Raise online play to 16-player lobbies and 8-player games

Lobbies hold 16 players and the sandbox 16 fighters, games up to 8. The arena
gets spawns 5-8 (outer ledges and middle platforms) and the race start eight
places. The sandbox adds eight more spawns, each the open spot farthest from
the rest. Rival cards wrap into rows of four, the lobby's player list goes to
two tiny columns when crowded, and the server keeps frame packets to one
datagram. Formatted with clang-format.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
shweetandClaude Opus 5.5 committed 2026-11-08 02:33:20 -05:00
1 parent 56af1c357c
commit 6003175173
19 files changed
+247 -140

No files matched your search

+18 -9
View File
@@ -37,7 +37,8 @@ constexpr const char INPUTS_LABEL[] = "inputs";
constexpr size_t MESSAGE_MAX = 65536;
constexpr int CODE_TRIES = 100;
constexpr int FRAME_RING = 256;
constexpr int FRAMES_PER_PACKET = 30;
// Frames go out a packet of at most this many bytes at a time, so a lossy one fits one datagram and is never split.
constexpr size_t FRAME_BYTES_MAX = 1100;
constexpr int INPUT_REACH = 120;
constexpr int CHECKSUM_INTERVAL = 60;
constexpr int CATCH_UP_TICKS = 5;
@@ -66,9 +67,10 @@ struct Room
int tick = 0;
};
// Someone connected: their name, socket and WebRTC connection (with its reliable channel and lossy one), their lobby (empty until they make or join one), the room they play in
// (0 for none), the last tick of it they've confirmed, how early their controls last came, and the fighter they
// brought, kept while they're away in a game so they come back to the sandbox as they left.
// Someone connected: their name, socket and WebRTC connection (with its reliable channel and lossy one), their lobby
// (empty until they make or join one), the room they play in (0 for none), the last tick of it they've confirmed, how
// early their controls last came, and the fighter they brought, kept while they're away in a game so they come back to
// the sandbox as they left.
struct Member
{
Profile profile;
@@ -135,8 +137,7 @@ static void send(int id, const std::string& message, bool isBinary = false, bool
member.socket->send(message);
}
catch (const std::exception&)
{
}
{}
}
// Answers a member's WebRTC offer with a connection of the server's own, passing its description and candidates back
@@ -606,7 +607,7 @@ static void game_follow(int serial)
rooms.erase(serial);
}
// Sends everyone in a room the frames they haven't confirmed (up to a packet's worth), and every so often the state's
// Sends everyone in a room the frames they haven't confirmed (as many as fit a packet), and every so often the state's
// checksum.
static void frames_send(int serial)
{
@@ -616,7 +617,14 @@ static void frames_send(int serial)
if (member.room != serial)
continue;
int first = std::max(member.ack + 1, room.tick - FRAME_RING + 1);
int count = std::min(room.tick - first, FRAMES_PER_PACKET);
int count = 0;
for (size_t bytes = 0; first + count < room.tick; count++)
{
bytes +=
sizeof(Uint16) + sizeof(Uint8) + room.frames[(first + count) % FRAME_RING].count * sizeof(Controls);
if (bytes > FRAME_BYTES_MAX && count > 0)
break;
}
if (count <= 0)
continue;
PacketWriter packet;
@@ -633,7 +641,8 @@ static void frames_send(int serial)
if (room.tick % CHECKSUM_INTERVAL == 0)
for (auto& [id, member] : members)
if (member.room == serial)
send(id, PacketWriter().put(PACKET_CHECKSUM).put(serial).put(room.tick).put(room.sim.checksum_get()).bytes,
send(id,
PacketWriter().put(PACKET_CHECKSUM).put(serial).put(room.tick).put(room.sim.checksum_get()).bytes,
true);
}