Chat and commands
Send messages and add your own chat commands.
Messages
mp.chat.send(player, "Only you see this")
mp.chat.broadcast("Everyone sees this")Both appear as server messages in the chat. Normal chat between players needs no code - the server passes it on by itself. To read it, use the playerChat event.
Messages in a player's name
mp.chat.sendAs sends a message with a player's name in front - exactly like their own chat message - but only to the players you choose. That is all you need for private messages or team chat:
mp.commands.add("msg", "<id> <text> - a private message", (player, [id, ...words]) => {
const target = mp.players.get(Number(id))
if (!target) return mp.chat.send(player, "No player with this id")
mp.chat.sendAs(player, [target, player], `(private) ${words.join(" ")}`)
})
// company chat: everyone in the same company
mp.commands.add("c", "<text> - company chat", (player, words) => {
if (!player.company) return mp.chat.send(player, "You have no company")
const team = mp.players.all().filter((p) => p.company?.id === player.company?.id)
mp.chat.sendAs(player, team, `[${player.company.name}] ${words.join(" ")}`)
})playerChat and mp.chat.onMessage do not see these messages - they come from your gamemode, not from the player.
Filtering and changing chat
mp.chat.onMessage takes the chat over: every normal message goes to your handler first.
const muted = new Set<number>()
mp.chat.onMessage((player, text) => {
if (muted.has(player.id)) return false // dropped
return text.replace(/idiot/gi, "***") // sent like this
// returning nothing sends it unchanged
})Only one gamemode can take the chat over. playerChat still fires for every message.
Commands
Players type commands in the chat with a leading /. Add your own with mp.commands.add(name, help, run):
mp.commands.add("repair", "repairs truck, trailer and cargo", (player) => {
mp.players.repair(player)
mp.chat.send(player, "All repaired.")
})- name: without the
/; letters, digits,_and-. Players can type it in any case. - help: a short text for help lists and the hints in the chat (below). Write the arguments first, then
-and what the command does:"<amount> - sets your bank balance". An empty text hides the command from both - useful for aliases. - run(player, args):
argsare the words after the command. - options (optional):
{ role: "moderator" }- only players with that role or admins may use it.
Arguments
// /money 25000
mp.commands.add("money", "<amount> - sets your bank balance", (player, [value]) => {
const amount = Number(value)
if (!value || !(amount >= 0)) return mp.chat.send(player, "Usage: /money <amount>")
mp.players.setMoney(player, amount)
})
// /say hello everyone -> args = ["hello", "everyone"]
mp.commands.add("say", "<text> - a message to everyone", (player, args) => {
mp.chat.broadcast(`${player.name} says: ${args.join(" ")}`)
})Hints in the chat
While a player types a command, the chat shows hints above its input, made from your help texts:
/and the start of a name: the matching commands with their arguments and description. Tab completes the first one.- After the name and a space: that command's arguments stay in view, the one being typed is highlighted -
<amount>while typing/money 25.
Arguments are the parts in <...> (needed) and [...] (optional) before the -. A player only sees the commands they may use: those with a role only with that role or as an admin.
Aliases
Register the same function under a second name without help text:
const repair = (player: OpenRoadMP.Player) => mp.players.repair(player)
mp.commands.add("repair", "repairs your truck", repair)
mp.commands.add("fix", "", repair)A help command
mp.commands.all() returns the commands of all gamemodes on the server, with name, help and gamemode:
mp.commands.add("help", "shows all commands", (player) => {
for (const c of mp.commands.all()) {
if (c.help) mp.chat.send(player, `/${c.name} - ${c.help}`)
}
})Rules for commands
- A command belongs to the gamemode that registers it first. If another gamemode registers the same name later, the server keeps the first one and logs a warning.
- Commands nobody registered are answered by the server ("unknown command").
- Every command also fires the
playerCommandevent in all gamemodes - handy for logging, but do not use it to implement commands. - Commands are not shown to other players.