This guide explains how to set up your Unity project to work with HypeDuel, including both server and client versions.
To integrate HypeDuel into your Unity game, you need to create two separate builds/scenes:
- Server Version – Responsible for recording and pushing gameplay data.
- Client Version – Responsible for playing back the recorded data.
HypeDuelServerManagerHypeDuelRecorder
- Server Port:
3000 - Recorder: reference to your HypeDuelRecorder
- Max Upload Step Count:
200 - Overwrite Auth Token:
fc0d08ce-38c7-4980-a5e6-23deacb30528 - Overwrite Match Id: [Leave empty]
- Target Framerate: 120
- Hyper Sim:
false
-
Transform Tracking:
Add all theTransformobjects you want to track.- Transform: The transform to track
- Interpolate: Whether to smooth out movement on the client (CLIENT ONLY)
- Interpolation Strength: How much to interpolate, 0 being no interpolation, larger value = more smoothing (CLIENT ONLY)
- Id: an integer id for this transform that will need to be matched on the client.
- Prefab Id: Leave empty/0
-
Tracked Prefabs: Needed to spawn synced prefabs at runtime with
HypeDuelRecorder.SpawnPrefabById -
Unique IDs:
Assign a unique ID to each tracked transform.
These IDs must be replicated exactly in the client version. -
Push State:
Use thePushStateChangemethod on recorder to push your game state (e.g., scores, timer, and custom data).
HypeDuelClientHypeDuelRecorder(configured the same as the server)
- Add the same transforms and IDs as in the server version to ensure correct data playback.
- Receive State Changes:
Use theOnStateChangeevent to listen for and react to incoming game state updates.
- Use
npx ws-echo -i 3000 -o 3001 --ow recording.txtin your assets folder to begin recording a match - Run the server scene, recording should begin.
- Once done, you can use
npx ws-echo -i 3001 -o 3000 --ir recording.txt --loopto begin playback - Launch the client scene while playback is running to test
The PushStateChange method on the recorder, takes state updates for the game. The default state class is defined as follows:
[Serializable]
public class FrameState
{
[JsonProperty("scores")]
public Dictionary<string, float> scores;
[JsonProperty("announcedEvents")]
public List<string> announcedEvents;
[JsonProperty("time")]
public float? time;
}To add your own variables and properties you can extend the class.
[Serializable]
public class MyState : FrameState
{
public int foo;
public float x;
}When requiring use of Vectors or Quaternions you need to use their serializeable versions SerializableVector3 and SerializableQuaternion.
The scores property is required to decide the winner of the game.
To push state:
void Update()
{
MyState state = new MyState();
state.scores = new Dictionary<string, float>() { { "teamA", 2 }, { "teamB", 2} };
state.foo = 2;
HypeDuelServerManager.Instance.recorder.PushStateChange(state);
}To read state on client, recommended is to add one listener in the awake of your game manager:
void Awake()
{
HypeDuelClient.Instance.OnStateChange += (newState) =>
{
MyState state = newState.ToObject<MyState>();
Debug.Log("Team a has score " + state.scores["teamA"]);
};
}- Ensure both server and client recorders have identical transform setups.
- Handle all gameplay logic and UI updates using the
OnStateChangecallback on the client. - Build with state in mind. Server writes/creates state and pushes it every frame, Client listens for state changes and recreates the scene.