PurrNet
  • 🐈Introduction
    • ‼️Unique to PurrNet
    • 💲Pricing
    • 💻Compatibility
    • 📚Addon library
    • 🗺️Roadmap
    • 🏎️Performance
      • RPC Benchmarks
      • Network Transform benchmarks
    • 🥰Support PurrNet
  • 🏁Getting Started
    • Installation
    • Minimal Setup
    • Converting to PurrNet
      • Converting from Mirror
      • Converting from FishNet
  • 📚Simple Guides
    • Easy Multiplayer Physics (input Sync)
  • 🖥️Systems and modules
    • Network Manager
      • Network Rules
      • Network Prefabs
      • Network Visibility
        • Distance condition
      • Authentication
    • Transports
      • Composite Transport
      • UDP Transport
      • Web Transport
      • Local Transport
      • Steam Transport
      • Purr Transport
      • Simulating latency
    • Network Identity
      • Ownership
      • Spawning & Despawning
      • NetworkBehaviour
      • Don't destroy on load
    • Network Modules
      • Common Pitfalls
      • Sync Types
        • SyncVar
        • SyncList
        • SyncArray
        • SyncQueue
        • SyncDictionary
        • SyncEvent
        • SyncHashset
        • SyncTimer
        • SyncInput
    • Remote Procedure Calls
      • Generic RPC
      • Static RPC
      • Awaitable RPC
      • Direct Local Execution of RPCs
    • Broadcasts
    • Scene Management
    • Client Side Prediction
      • Overview
      • Predicted Identities
      • Predicted Hierarchy
      • Best Practices
      • Input Handling
      • State Handling
    • Instance Handler
    • Collider Rollback
    • BitPacker
      • Networking custom classes, structs & types
  • Plug n' play components
    • Network Transform
    • Network Animator
    • Network Ownership Toggle
    • Network Reflection
    • Network State Machine
  • 🎮Full game guides
    • 🔫First Person Shooter
    • 🪓Survival Game
  • ✊Community Guides
    • Chat system with broadcasts
  • 🧩Addons
    • Lobby System
  • 🤓Terminology
    • Early Access
    • Channels
    • Client Auth/Everyone (Unsafe)
    • Host
    • Server Auth (Safe)
    • PlayerID
  • 💡Integrations
    • Dissonance
    • Cozy Weather
Powered by GitBook
On this page
  • Introduction
  • Creating the ChatMessage struct:
  • Sending a ChatMessage to the Server
  • Receiving a ChatMessage on the Server, and sending it to all Clients
  • Receiving a ChatMessage on the Client
  • Wrap Up
  1. Community Guides

Chat system with broadcasts

Broadcast and chat

PreviousCommunity GuidesNextAddons

Last updated 5 months ago

Introduction

Broadcasting in PurrNet is useful, as it allows us to do some basic network functionality without needing a on our object. For things that are trivial, such as game chat, we don't necessarily need all the functionality of a .

The idea is as follows:

  1. Create a ChatMessage struct to store data such as a name and message.

  2. Send a ChatMessage with our desired name and message to the Server.

  3. Receive ChatMessage on the Server, then broadcast the ChatMessage to all Clients.

  4. Receive ChatMessage on the Clients, then print the ChatMessage out.

Creating the ChatMessage struct:

To get our chat message to the Server, we need to first create a struct to hold our data. As previously mentioned, this struct will hold a name, and a message. This struct will need to implement the interface, which will automatically handle the reading and writing of the data to the network. If this is not your style, take a look at the and interfaces.

The final struct is as follows:

public struct ChatMessage : IPackedAuto
{
    public string name;
    public string message;
}

Sending a ChatMessage to the Server

For our Clients to be able to send a message to the Server, we first need to hook into the Subscribe event from the NetworkManager

void NetworkManager.Subscribe<ChatMessage>(PlayerBroadcastDelegate<ChatMessage> callback, bool asServer)

The easiest way to do this, is create a script that inherits from PurrMonoBehaviour, as this gives us access to two very useful events:

public abstract void Subscribe(NetworkManager manager, bool asServer);
public abstract void Unsubscribe(NetworkManager manager, bool asServer);

For our case, let's create a ChatManager script, that inherits from PurrMonoBehaviour and subscribe to our chat events, as well as Creating an OnChatMessage function to pass in as our callback:

public class ChatManager : PurrMonoBehaviour
{
    // Subscribe to ChatMessage events as either the Server, Client, or both
    public override void Subscribe(NetworkManager manager, bool asServer)
    {
        manager.Subscribe<ChatMessage>(OnChatMessage, asServer);
    }

    // Unsubscribe to ChatMessage events as either the Server, Client, or both
    public override void Unsubscribe(NetworkManager manager, bool asServer)
    {
        manager.Unsubscribe<ChatMessage>(OnChatMessage, asServer);
    }

    // Called when a ChatMessage broadcast is sent from either the Server or a Client
    private void OnChatMessage(PlayerID player, ChatMessage data, bool asServer)
    {
        // TODO: Make this work
    }
}

Now that we've subscribed to the events required, we can actually send a ChatMessage to the Server! You can do this however you'd like, for testing, something like this will be more than sufficient for our needs:

void Update()
{
    if (Keyboard.current.enterKey.wasPressedThisFrame)
    {
        ChatMessage message = new ChatMessage
        {
            name = InstanceHandler.NetworkManager.localPlayer.ToString(),
            message = "Hello World!"
        };

        InstanceHandler.NetworkManager.SendToServer<ChatMessage>(message);
    }
}

Receiving a ChatMessage on the Server, and sending it to all Clients

Now that we are sending messages from the Client, let's update our OnChatMessage function to handle receiving a ChatMessage broadcast on the Server. As mentioned, if we are the Server receiving the broadcast, we want to relay this information and broadcast it back to all of our Clients, and we can do it very simply with NetworkManager.SendToAll<ChatMessage>(ChatMessage):

// Called when a ChatMessage broadcast is sent from either the Server or a Client
private void OnChatMessage(PlayerID player, ChatMessage data, bool asServer)
{
    if (asServer)   // The broadcast was sent to the Server from a Client
    {
        // Send the broadcast down to the Clients
        InstanceHandler.NetworkManager.SendToAll<ChatMessage>(data);
    }
}

Receiving a ChatMessage on the Client

Now that we are receiving messages from the Server, we can use our same OnChatMessage function to handle the data from the Server. For now, let's just debug the message:

// Called when a ChatMessage broadcast is sent from either the Server or a Client
private void OnChatMessage(PlayerID player, ChatMessage data, bool asServer)
{
    if (asServer)   // The broadcast was sent to the Server from a Client
    {
        // Send the broadcast down to the Clients
        InstanceHandler.NetworkManager.SendToAll<ChatMessage>(data);
    }
    else    // The broadcast was sent to the Clients from the Server
    {
        Debug.Log($"Received {data.message} from {data.name}!");
    }
}

Wrap Up

With what we have, our final script should look like such:

public struct ChatMessage : IPackedAuto
{
    public string name;
    public string message;
}

public class ChatManager : PurrMonoBehaviour
{
    void Update()
    {
        if (Keyboard.current.enterKey.wasPressedThisFrame)
        {
            ChatMessage message = new ChatMessage
            {
                name = InstanceHandler.NetworkManager.localPlayer.ToString(),
                message = "Hello World!"
            };

            InstanceHandler.NetworkManager.SendToServer<ChatMessage>(message);
        }
    }

    // Subscribe to ChatMessage events as either the Server, Client, or both
    public override void Subscribe(NetworkManager manager, bool asServer)
    {
        manager.Subscribe<ChatMessage>(OnChatMessage, asServer);
    }

    // Unsubscribe to ChatMessage events as either the Server, Client, or both
    public override void Unsubscribe(NetworkManager manager, bool asServer)
    {
        manager.Unsubscribe<ChatMessage>(OnChatMessage, asServer);
    }

    // Called when a ChatMessage broadcast is sent from either the Server or a Client
    private void OnChatMessage(PlayerID player, ChatMessage data, bool asServer)
    {
        if (asServer)   // The broadcast was sent to the Server from a Client
        {
            // Send the broadcast down to the Clients
            InstanceHandler.NetworkManager.SendToAll<ChatMessage>(data);
        }
        else    // The broadcast was sent to the Clients from the Server
        {
            Debug.Log($"Received {data.message} from {data.name}!");
        }
    }
}
✊
Network Behaviour
Network Behaviour
IPackedAuto
IPacked
IPackedSimple