Configuration
Configuration
BUPA Chat's configuration is split across shared/config/*.lua. All of these files are in escrow_ignore, so they stay editable after purchase. This page walks the general, display, emoji, emote and message settings. Categories and Discord have their own pages.
General — general.lua
Keys, sounds, defaults and the mask system.
config.chatKey = "T" -- key to open the chat input
config.chatVisibilityKey = "" -- key to cycle visibility mode ("" = unbound)
config.clearCommand = { "clear", "temizle" } -- commands that clear chat history
config.closeOnOutsideClick = true -- click outside closes the input
config.typingSound = true -- keyboard sound while typing
config.allowNoSlashCommands = true -- run commands without a leading slash
config.uiUpdateRate = 24 -- ms update rate for head indicators
config.defaultAddTag = true -- first arg becomes a tag when no tags given
config.showPrintsOnChat = false -- mirror server prints into chat
config.discordTagCacheTime = 60 * 60 -- Discord role cache (seconds)
config.defaultChatCategory = "command" -- tab focused on openJoin / quit messages follow the standard convars:
config.showJoinMessages = GetConvarInt('chat_showJoins', 1) == 0
config.showQuitMessages = GetConvarInt('chat_showQuits', 1) == 0Admin chat name source
The admin category can show a different name source than character name:
config.adminChatName = {
mode = "discord", -- "character" | "steam" | "discord"
discord = {
botToken = "", -- required for "discord" mode
guildId = "",
cacheTime = 600, -- nick cache seconds
fallback = "steam", -- used when a nick can't be resolved
},
}Mask-aware names — config.noneMask
config.noneMask lists mask drawables (by ped model, collection and index) that should not hide a player's name in chat. When active, a masked player's name is shown as Unknown unless the category sets showWearingMask = true, or the worn mask is in this allow-list.
Display — display.lua
Private messages — config.pm
config.pm = {
active = true,
command = { "pm", "dm" }, -- send a private message
webhookKey = "chatMessage", -- Discord log key
maxLength = 300,
sender = { --[[ tags/color/name/id/job/discordTag/hour for the sender copy ]] },
receiver = { --[[ same shape for the receiver copy ]] },
}Sender and receiver each have independent styling (tags, color, showPlayerName, showPlayerId, showPlayerJob, discordTag, showHour).
Head text & player ID display
config.headTextMaxStack = 4 -- max head texts stacked on one player
config.playerIdDisplay = {
active = false, -- show IDs above heads while chat is open
showOwn = true, -- include your own ID
dist = 5.0, -- max display distance (m)
template = "[{serverId}] {discordId}", -- {serverId}{name}{steamId}{discordId}{fivemId}
headText = { bone = 31086, offset = vector3(0.3, 0.0, 0.0), maxRenderDist = 30.0 },
cssStyle = { color = "#fff", fontSize = "1.8vh", fontWeight = "600" },
}The template supports the placeholders {serverId}, {name}, {steamId}, {discordId}, {fivemId}, \n line breaks and inline HTML/CSS.
Emojis — emojis.lua
The emoji picker is fully data-driven. Each category is { tab = "<icon emoji>", label = "<HEADER>", list = { ... } } and each emoji is { emoji, name, code }.
config.emojis = {
{
tab = "😀", label = "SMILEYS",
list = {
{ emoji = "😀", name = "Grinning", code = ":grinning:" },
{ emoji = "😂", name = "Joy", code = ":joy:" },
-- ...
},
},
-- GESTURES (👍), SYMBOLS (❤️), OBJECTS (🚗)
}Ships with four groups — Smileys, Gestures, Symbols and Objects. Add, remove or reorder freely; code is the searchable shortcode shown under the preview.
Emotes — emotes.lua
Typing indicator — config.chatOpenEmote
Animated dots above a player's head while they type:
config.chatOpenEmote = {
active = true,
texts = { { text = "•", time = 500 }, { text = "••", time = 500 }, { text = "•••", time = 500 } },
cssStyle = { color = "#fff", fontSize = "1.6vh" },
dist = 8.0, -- how far others can see it (m)
}
config.emoteOneAtATime = true -- one active instance of each emote command per playerEmote commands — config.emoteCommands
Ships with /me, /do, /dice (/zar) and /rps (/tkm). Each emote can play an animation, render head text, and optionally mirror to chat:
{
command = "me",
desc = "EMOTE_ME_COMMAND_DESC",
webhookKey = "emoteCommand", -- Discord log (optional)
dist = 8.0,
time = 10000, -- head text duration (ms)
template = "{text}", -- {text} {playerName} {playerCensoredName}
cssStyle = { color = "#b6a8ff", fontStyle = "italic" },
sendToChat = { active = true, tags = { { tag = "ME" } }, color = { 182, 168, 255 } },
}Additional fields: anim (dict, clip, flag, duration), headText (bone/offset/scale), params (custom typed args with help keys) and msgCb(args) for computed output (used by /dice and /rps).
Messages — messages.lua
Auto broadcasts, welcome messages and txAdmin event styling — all off by default.
config.autoMessages = {
active = false,
messages = {
{ interval = 3600000, tags = { { tag = "Auto Message" } }, color = { 88, 166, 255 },
args = { "Test message for auto message (1)" } },
},
}
config.welcomeMessages = {
active = false,
messages = { { tags = { { tag = "Welcome" } }, color = { 255, 255, 255 },
args = { "Welcome to the BUPA Test server!" } } },
}
config.txAdmin = {
announcement = { active = true, tagBgColor = { 255, 190, 60 } },
scheduledRestart = { active = true, tagBgColor = { 255, 105, 97 } },
directMessage = { active = true, tagBgColor = { 100, 180, 255 } },
}- autoMessages — periodic broadcasts, each with its own
interval(ms), tags, color and text. - welcomeMessages — one or more lines shown to a player when they load in.
- txAdmin — styles for txAdmin announcements, scheduled restarts and direct messages surfaced in chat.