튜토리얼 7 — 온라인 멀티플레이어
JumPHP는 릴레이 서버(WebSocket)로 플레이어를 연결해요. 데스크톱과 브라우저에서 같은 코드로 온라인 플레이가 돼요. Pong 게임이 완전한 예제예요(src/Scene/PlayScene.php).
로비
$this->scenes()->switchTo(LobbyScene::class, [
'next' => PlayScene::class, // 플레이어가 모이면 열 게임 장면
'nextParams' => ['mode' => 'online'],
'back' => TitleScene::class,
'players' => 2,
]);
로비는 방을 만들거나(공유할 4글자 코드), 방에 참가하거나, 상대를 찾아 줘요. 그런 다음 ['online' => true, 'net' => NetSession, 'host' => bool, 'peer' => int]와 함께 게임 장면을 열어요.
메시지
$net = $params['net'];
$net->removeAllListeners();
$net->on('message', fn (int $from, int $type, string $payload) => $this->receive($from, $type, $payload));
$net->on('peerLeave', fn (int $peer) => $this->scenes()->switchTo(TitleScene::class));
$net->send(self::MSG_STATE, pack('gg', $this->x, $this->y), reliable: false); // 자주 보내요: 유실될 수 있어요
$net->sendJson(self::MSG_EVENT, ['goal' => 1]); // 드물게 보내요: 반드시 도착해요
좋은 구조
- 호스트가 결정해요. 호스트가 게임을 시뮬레이션하고, 점수를 계산하고, 초당 약 20번 상태를 보내요.
- 나머지 플레이어는 초당 약 30번 자신의 입력을 보내요.
- 다른 플레이어의 오브젝트는 약간 지연시켜 부드럽게 그려요.
SnapshotBuffer를 사용해요 (push($this->engine->time(), $state)다음에sample($this->engine->time())).
릴레이 서버는 내 컴퓨터에서 bin/jumphp relay up으로 실행해요. 게임은 game.yaml의 net_url(또는 페이지 주소의 ?net=wss://…)로 사용할 서버를 알려 줘요.