PK Battle
TikTok-style live PK battles between hosts with real-time scoring and split-screen views
Overview
PK Battle enables live competitive interactions between two or more hosts. Hosts are placed in a shared battle room where viewers can watch both streams side-by-side and send scores (gifts, votes, likes) that update in real time. State is managed entirely via room metadata and data channels — no Redis required.
N-Host Support
Support 2 or more hosts in a single battle
Real-time Scoring
Scores update instantly via data channel
Custom Duration
Configurable battle length from 10s to 1 hour
Auto Winner
Winner determined automatically at battle end
Battle Lifecycle
Each PK battle progresses through a series of states:
Quick Start
Get a PK battle running in minutes
Create a PK Battle
1import { useBaxCloud } from '@baxcloud/react';
2
3const client = useBaxCloud();
4
5const battle = await client.createPKBattle({
6 duration: 300, // 5 minutes
7 creatorIdentity: 'host-a',
8 creatorName: 'Streamer A',
9});
10console.log(battle.id); // battle IDInvite another host
1await client.inviteToPK(battle.id, {
2 inviteeIdentity: 'host-b',
3 inviteeName: 'Streamer B',
4});Host B accepts the invite
1const { state, token, serverUrl } = await client.joinPK(battle.id, {
2 identity: 'host-b',
3 name: 'Streamer B',
4});
5// Use token + serverUrl to join the PK battle roomStart the battle
1await client.startPKBattle(battle.id, 3); // 3-second countdownSend scores during battle
1await client.sendPKScore(battle.id, {
2 hostIdentity: 'host-a',
3 value: 100,
4 type: 'gift',
5});End the battle
1const result = await client.endPKBattle(battle.id);
2console.log(result.winner); // identity of the winnerReact UI Components
Pre-built split-screen battle view and hook
PKBattleView Component
Drop-in split-screen component that displays hosts side-by-side with live scores, countdown overlay, and result screen. Fully customizable via render props.
1import { PKBattleView } from '@baxcloud/react';
2
3function MyBattlePage({ battleId }: { battleId: string }) {
4 return (
5 <PKBattleView
6 battleId={battleId}
7 layout="horizontal"
8 pollInterval={1000}
9 onPKEvent={(event, data) => {
10 console.log('PK event:', event, data);
11 }}
12 onStateChange={(state) => {
13 console.log('Battle state:', state.status);
14 }}
15 style={{ width: '100%', height: 400 }}
16 />
17 );
18}usePKBattle Hook
Full-featured hook for building custom PK battle UIs with state management, countdown timer, event listener, and all battle actions.
1import { usePKBattle } from '@baxcloud/react';
2
3function CustomBattleUI({ battleId }: { battleId: string }) {
4 const {
5 state,
6 countdown,
7 loading,
8 error,
9 lastEvent,
10 sendScore,
11 end,
12 refresh,
13 } = usePKBattle({ battleId, pollInterval: 1000 });
14
15 if (loading) return <div>Loading...</div>;
16 if (!state) return <div>No battle</div>;
17
18 return (
19 <div>
20 <h2>Status: {state.status}</h2>
21 {countdown > 0 && <h1>{countdown}</h1>}
22 {state.hosts.map((host) => (
23 <div key={host.identity}>
24 {host.name}: {host.score}
25 <button onClick={() => sendScore({
26 hostIdentity: host.identity,
27 value: 1,
28 })}>
29 +1
30 </button>
31 </div>
32 ))}
33 {state.winner && <p>Winner: {state.winner}</p>}
34 </div>
35 );
36}API Reference
| Method | Description | Endpoint |
|---|---|---|
| createPKBattle() | Create a new PK battle with duration and creator | POST /v1/pk/create |
| inviteToPK() | Invite another host to the battle | POST /v1/pk/:id/invite |
| joinPK() | Accept and join a PK battle (returns token) | POST /v1/pk/:id/join |
| declinePK() | Decline a PK battle invitation | POST /v1/pk/:id/decline |
| startPKBattle() | Start the battle with optional countdown | POST /v1/pk/:id/start |
| sendPKScore() | Send a score/gift/vote to a host | POST /v1/pk/:id/score |
| endPKBattle() | End the battle and determine winner | POST /v1/pk/:id/end |
| getPKBattle() | Get current battle state | GET /v1/pk/:id |
| listPKBattles() | List all active battles | GET /v1/pk |
| getPKViewerToken() | Get a viewer token for the PK room | POST /v1/pk/:id/viewer-token |
| updatePKSettings() | Update duration or metadata | PUT /v1/pk/:id/settings |
Webhook Events
Subscribe to PK battle events in your webhook settings
| Event | Description |
|---|---|
| pk.started | PK battle began (after countdown) |
| pk.score_update | A host's score changed during the battle |
| pk.ended | PK battle finished with final scores and winner |
| pk.cancelled | PK battle was cancelled or declined before starting |
Real-time Data Channel Events
Events broadcast via sendData for instant updates
These events are sent to all participants in the PK battle room via the data channel. Use onPKEvent() in client SDKs or the usePKBattle hook in React to listen for them.
| Event | When |
|---|---|
| pk.invited | A host was invited |
| pk.accepted | A host accepted the invite |
| pk.declined | A host declined |
| pk.countdown | Countdown started |
| pk.started | Battle began |
| pk.score_update | Score changed |
| pk.ended | Battle ended |
| pk.cancelled | Battle cancelled |
| pk.host_joined | A host joined the room |
| pk.host_left | A host left the room |
| pk.settings_updated | Battle settings changed |
pk.ended) to store final results in your own database.