OnPlayerMarkersSend
OnPlayerMarkersSend is called on the server right before the map marker list for a single player is sent to their client, letting plugins add, edit or strip markers before the RPC is dispatched.
void OnPlayerMarkersSend(BasePlayer player, ProtoBuf.MapNoteList mapNoteList)Parameters
| Parameter | Type | Description |
|---|---|---|
player | BasePlayer | The BasePlayer whose client is about to receive the marker list. This is the connection that BasePlayer.SendMarkersToClient is building the payload for, so it is always a connected player. |
mapNoteList | ProtoBuf.MapNoteList | The ProtoBuf.MapNoteList that will be serialized into the Client_ReceiveMarkers RPC. You can add entries to `mapNoteList.notes`, edit or remove existing ones, or clear the list before it is sent. |
Return value
The return value is ignored: SendMarkersToClient continues and sends the (possibly modified) list to the client regardless of what your hook returns. Return nothing and edit mapNoteList.notes in place to change the payload.
How it works
The hook fires inside BasePlayer.SendMarkersToClient, after the game has built the ProtoBuf.MapNoteList from that player's personal map notes and the world points of interest, and immediately before the Client_ReceiveMarkers RPC is sent to that one client. Because the call site is per-player, it runs whenever the server pushes markers to a player: on connect, on respawn, and whenever the marker state is refreshed for them.
player is the recipient. mapNoteList carries notes, a list of ProtoBuf.MapNote entries (each with type, x, y, and usually noteType/note fields). Mutating that list changes what this single player sees; entries you add appear only on their map and vanish on their next refresh if you do not re-add them.
The hook has one signature only. Declaring player as a more specific subtype is possible (every argument must be an instance of the declared type), but markers are only sent to real players, so there is rarely a reason to narrow it. The list is cleared by the game after the RPC, so do not keep a reference to it.
Example plugin: Show teammate positions as markers for each player
using System;
using System.Collections.Generic;
using Newtonsoft.Json;
using Oxide.Core;
using ProtoBuf;
using UnityEngine;
namespace Oxide.Plugins
{
[Info("Team Marker Broadcast", "RustPluginGenerator", "1.0.0")]
[Description("Adds a map marker for every teammate when the server sends map markers to a player")]
public class TeamMarkerBroadcast : RustPlugin
{
private const string PermUse = "teammarkerbroadcast.use";
private PluginConfig config;
private class PluginConfig
{
[JsonProperty("Enable team markers")]
public bool Enabled { get; set; } = true;
[JsonProperty("Marker note type")]
public int NoteType { get; set; } = 7;
[JsonProperty("Ignore players without permission")]
public bool RequirePermission { get; set; } = false;
}
protected override void LoadDefaultConfig() => config = new PluginConfig();
protected override void LoadConfig()
{
base.LoadConfig();
try
{
config = Config.ReadObject<PluginConfig>();
if (config == null) throw new System.Exception();
}
catch
{
PrintWarning("Configuration file is invalid, using defaults");
LoadDefaultConfig();
}
SaveConfig();
}
protected override void SaveConfig() => Config.WriteObject(config);
private void Init()
{
permission.RegisterPermission(PermUse, this);
}
private void OnPlayerMarkersSend(BasePlayer player, MapNoteList mapNoteList)
{
if (player == null || mapNoteList == null || mapNoteList.notes == null) return;
if (!config.Enabled) return;
if (config.RequirePermission && !permission.UserHasPermission(player.UserIDString, PermUse)) return;
if (player.currentTeam == 0UL) return;
RelationshipManager.PlayerTeam team = RelationshipManager.ServerInstance.FindTeam(player.currentTeam);
if (team == null || team.members == null) return;
foreach (ulong memberId in team.members)
{
if (memberId == player.userID.Get()) continue;
BasePlayer member = BasePlayer.FindByID(memberId);
if (member == null || !member.IsConnected || member.IsDead()) continue;
if (member.IsSleeping()) continue;
Vector3 pos = member.transform.position;
mapNoteList.notes.Add(new ProtoBuf.MapNote
{
noteType = config.NoteType,
label = member.displayName,
worldPosition = pos
});
}
}
}
}The plugin does not track team membership itself: inside OnPlayerMarkersSend it reads player.currentTeam, looks up the team via RelationshipManager.ServerInstance.FindTeam and skips when the player has no team. For each member that is alive, connected, not sleeping and not the sender, it appends a ProtoBuf.MapNote positioned at that member's transform.position, using the configured Marker note type value. Because the hook fires every time markers are pushed, the added entries stay roughly in sync with member movement without a timer.
Common use cases
Team member markers
Inject synthetic markers for teammates before the list leaves the server, giving squads live positional awareness on the map without a custom CUI overlay.
Hide world POIs or death markers
Iterate
mapNoteList.notesand remove entries of a certain type so specific players never see points of interest, death markers or other stale notes.Admin-only annotations
For players with a permission, append markers for events such as incoming airdrops, hackable crates or raid targets so staff can navigate quickly.
Pitfalls
The list is short-lived
The game calls
mapNoteList.notes.Clear()right after the RPC, so any reference you keep is emptied. Always add entries during the hook call and never store the list itself.Markers are not persisted
Entries you append exist only in this one payload. They disappear on the next refresh unless you re-add them, which is fine because the hook runs again on that refresh.
Keep the work cheap
The hook can fire for every connected player during marker refreshes. Avoid heavy iteration over
BaseNetworkable.serverEntitiesper call and keep team lookups cached where practical.
Build a plugin with OnPlayerMarkersSend
Describe what should happen and get a compiled plugin that uses this hook.
Edit the prompt on the next screen. 2 free plugins a month, no card.
Last updated Oct 26, 2026. Found a mistake? Email support@rustplugingenerator.com.
Build a plugin with OnPlayerMarkersSend
Generate