RedM documentation

Murphy's Barber

Reference

Murphy Barber - Developer API


This documentation covers all the events available for developers who want to integrate murphy_barber with external scripts, character creators, or other resources.


Table of Contents


Client Events

murphy_barber:loadbarberoverlay

Loads the current player's hairstyle and overlays from the database and applies them to the player ped. Use this event when a player spawns or selects their character.

Usage:

lua
TriggerEvent("murphy_barber:loadbarberoverlay")

Description:

  • Resets global hairstyle caches to ensure a clean state
  • Fetches hairstyle data from the database for the current player
  • Applies hairstyles and makeup overlays to the player ped
  • This is the recommended event for loading hairstyles at player spawn

Example:

lua
-- In your spawn handler
Wait(500) -- Wait for ped to be ready
TriggerEvent("murphy_barber:loadbarberoverlay")

murphy_barber:loadbarberoverlayOnCharacter

Loads hairstyle and overlays for a specific character onto a specific ped. This is designed for character selection screens where you need to preview multiple characters without affecting the player's current cached data.

Parameters:

Parameter Type Description
charid string/int The character identifier from your database
ped number The ped handle to apply the hairstyle to

Usage:

lua
TriggerEvent("murphy_barber:loadbarberoverlayOnCharacter", charid, ped)

Description:

  • Uses isolated local caches to prevent polluting the global player cache
  • Safe to use on preview peds in character selection
  • Waits for the ped to be valid and fully loaded before applying
  • Perfect for character selection menus showing multiple characters

Example:

lua
-- When creating a preview ped for character selection
local previewPed = CreatePed(...)
local characterId = "char_12345"
-- Wait for ped model to load
while not DoesEntityExist(previewPed) do
Wait(100)
end
-- Load the character's hairstyle onto the preview ped
TriggerEvent("murphy_barber:loadbarberoverlayOnCharacter", characterId, previewPed)

murphy_barber:clotheitem

Applies hairstyle components to a ped. This event handles the actual application of hair, beard, and other hairstyle elements.

Parameters:

Parameter Type Description
hairstyleComponents table Table containing hairstyle data (model, texture per category)
outfitid string/int The outfit/preset ID
overlay boolean If true, keeps existing overlays; if false, removes and reloads overlays
target number (optional) Ped handle. Defaults to PlayerPedId()
charid string/int (optional) Character ID for database queries
isLoadOnly boolean (optional) If true, skips saving to database
isCharselectPreview boolean (optional) If true, uses isolated caches (for preview peds)

Usage:

lua
TriggerEvent("murphy_barber:clotheitem", hairstyleComponents, outfitid, overlay, target, charid, isLoadOnly, isCharselectPreview)

Example:

lua
-- Apply hairstyle to current player (and save to database)
local hairstyle = {
hair = { model = 5, texture = 0 },
beard = { model = 3, texture = 0 }
}
TriggerEvent("murphy_barber:clotheitem", hairstyle, "1234567", false)
-- Apply hairstyle to preview ped (no database save)
TriggerEvent("murphy_barber:clotheitem", hairstyle, "1234567", true, previewPed, nil, true, true)

murphy_barber:makeupitem

Toggles makeup overlay from a preset onto the player ped.

Parameters:

Parameter Type Description
outfitid string/int The preset ID to load makeup from

Usage:

lua
TriggerEvent("murphy_barber:makeupitem", outfitid)

Description:

  • If the same outfitid is triggered twice, it will toggle off the makeup
  • Only works if the player ped has a valid head component

Server Events

murphy_barber:updatehairstyle

Updates the hairstyle data in the database for the current player.

Parameters:

Parameter Type Description
hairstyle table The hairstyle components table
overlays table The overlay data table
outfitid string/int The outfit/preset ID

Usage:

lua
TriggerServerEvent("murphy_barber:updatehairstyle", hairstyleCache, overlay_all_layers, outfitid)

Note: This event is typically called automatically by the client when making changes. You shouldn't need to call this directly unless implementing custom logic.


Integration Examples

Loading Hairstyle at Character Spawn

lua
-- In your spawn handler after the player ped is created
Citizen.CreateThread(function()
-- Wait for player ped to be ready
while not DoesEntityExist(PlayerPedId()) or IsEntityDead(PlayerPedId()) do
Wait(100)
end
Wait(500) -- Additional wait for ped components
-- Load the player's saved hairstyle
TriggerEvent("murphy_barber:loadbarberoverlay")
end)

Loading Hairstyle on Character Selection Preview

lua
-- When creating character preview peds
local function LoadCharacterPreview(charid, ped)
-- Wait for ped to be fully loaded
while not DoesEntityExist(ped) do
Wait(100)
end
Wait(200)
-- Load hairstyle without affecting player's global cache
TriggerEvent("murphy_barber:loadbarberoverlayOnCharacter", charid, ped)
end
-- Usage
local previewPed = CreatePed(pedModel, x, y, z, heading, false, false)
LoadCharacterPreview("ABC123", previewPed)

Integration with Custom Character Creator

For developers integrating murphy_barber with their own character creator, here's how murphy_creator does it:

1. Required Variables

You need to track hairstyle and overlay data during character creation:

lua
-- Hairstyle cache - stores current hairstyle selections
hairstyleCache = {}
-- Overlay cache - stores makeup/overlay data
overlay_all_layers = {}
-- Base overlay template (copy from murphy_barber/shared/config.lua)
baseoverlay = {
{ name = "eyeliners", opacity = 1.0, var = 0, tx_color_type = 0, tx_normal = 0, palette = 0, tx_unk = 0, palette_color_primary = 0, palette_color_secondary = 0, palette_color_tertiary = 0, visibility = 0, tx_opacity = 1.0, tx_id = 1 },
{ name = "lipsticks", opacity = 1.0, var = 0, tx_color_type = 0, tx_normal = 0, palette = 0, tx_unk = 0, palette_color_primary = 0, palette_color_secondary = 0, palette_color_tertiary = 0, visibility = 0, tx_opacity = 1.0, tx_id = 1 },
-- ... more overlay categories
}

2. Initialize Hairstyle Cache

When entering character creation, initialize the hairstyle cache for all categories:

lua
-- MURPHY_ASSETS is defined in murphy_barber/shared/murphy_assets.lua
-- You need to share this file or include it in your creator
function InitializeHairstyleCache(gender)
hairstyleCache = {}
for category, data in pairs(MURPHY_ASSETS[gender]) do
hairstyleCache[category] = {
model = 0,
texture = 0
}
end
overlay_all_layers = deepcopy(baseoverlay)
end

3. Build Barber Menu Categories

Build the menu data structure for your NUI:

lua
local menucategories = {
male = {
categories = { "barber", "lifestyle", "makeup" },
barber = {
"hairstabble", "hair", "hair_bonnet", "beardstabble", "beard",
"beards_complete", "beards_chin", "beards_chops", "beards_mustache"
},
makeup = {
"eyeliners", "lipsticks", "shadows", "paintedmasks", "blush", "blush2", "foundation",
},
lifestyle = {
"eyebrows", "scars", "scars2", "scars3", "acne", "ageing", "complex",
"disc", "freckles", "grime", "moles", "spots"
},
},
female = {
categories = { "barber", "lifestyle", "makeup" },
barber = {
"hair", "hair_bonnet", "beard", "beards_complete", "beards_chin",
"beards_chops", "beards_mustache"
},
makeup = {
"eyeliners", "lipsticks", "shadows", "paintedmasks", "blush", "blush2", "foundation",
},
lifestyle = {
"eyebrows", "scars", "scars2", "scars3", "acne", "ageing", "complex",
"disc", "freckles", "grime", "moles", "spots"
},
}
}
function OpenBarberMenu(ped, gender)
local showoverlay = GetHead(ped) ~= 0
local categories = {}
local items = {}
-- Build categories
for _, k in ipairs(menucategories[gender].categories) do
if k == "makeup" or k == "lifestyle" then
if showoverlay then
table.insert(categories, { id = k, name = k })
end
else
table.insert(categories, { id = k, name = k })
end
end
-- Build items
for key, value in pairs(menucategories[gender]) do
for index, cat in pairs(value) do
if MURPHY_ASSETS[gender][cat] and next(MURPHY_ASSETS[gender][cat]) ~= nil then
if tostring(key) ~= "categories" then
table.insert(items, {
id = cat,
name = cat,
category = key,
totalAmount = #MURPHY_ASSETS[gender][cat],
value = hairstyleCache[cat] and hairstyleCache[cat].model or 0,
})
end
end
end
end
-- Send to your NUI
SendNUIMessage({
type = "openBarberMenu",
categories = categories,
items = items
})
end

4. Apply Hairstyle During Preview

When the player changes a hairstyle in the creator menu:

lua
function ApplyHairstyle(ped, gender, category, modelIndex, textureIndex)
-- Update cache
hairstyleCache[category] = {
model = modelIndex,
texture = textureIndex
}
-- Get drawable data from MURPHY_ASSETS
if modelIndex > 0 and MURPHY_ASSETS[gender][category][modelIndex] then
local assetData = MURPHY_ASSETS[gender][category][modelIndex]
if assetData.drawable then
-- Hair with palette tints
local variant = assetData.variants[textureIndex] or assetData.variants[1]
local albedo = variant.albedo
local normal = variant.normal
local material = variant.material
local palette = variant.palette
-- Apply using natives (see murphy_barber/client/function.lua for UpdateCustomhairstyle)
UpdateCustomhairstyle(ped, assetData.drawable, albedo, normal, material, palette, 0, 0, 0)
else
-- Component-based hair/beard
local hash = assetData[textureIndex] and assetData[textureIndex].hash or assetData[1].hash
NativeSetPedComponentEnabled(ped, hash, false, true, true)
end
NativeUpdatePedVariation(ped)
end
end

5. Save Hairstyle at End of Character Creation

When the character creation is finalized, save the hairstyle data to the database:

lua
-- Client-side: Trigger server save
function SaveCharacterBarberData()
local gender = IsPedMale(PlayerPedId())
TriggerServerEvent("murphy_barber_creator:updatehairstyle", hairstyleCache, overlay_all_layers, 0)
end
-- Or use the callback system if available
Callback.triggerServer('murphy_creator:SavePreset', function(result, outfitid)
if result then
print("Barber data saved successfully")
end
end, hairstyleCache, overlay_all_layers, nil, 0, IsPedMale(PlayerPedId()))

Server-side handler (add to your server script):

lua
RegisterServerEvent("murphy_barber_creator:updatehairstyle", function(hairstyle, overlays, outfitid)
local source = source
local charid = GetCharIdentifier(source) -- Your framework's function
if not charid then
print("[Barber Creator] Error: No charid found")
return
end
local encodedHairstyle = json.encode(hairstyle)
local encodedOverlays = json.encode({})
local permanentOverlay = {}
-- Extract permanent overlays (makeup that persists)
for k, v in pairs(overlays) do
if v.visibility and v.visibility > 0 then
permanentOverlay[v.name] = v
end
end
local encodedPermanent = json.encode(permanentOverlay)
-- Check if entry exists
MySQL.query('SELECT * FROM murphy_barber WHERE `charid`=@charid', {
charid = charid
}, function(result)
if result[1] then
-- Update existing
MySQL.update("UPDATE murphy_barber SET hairstyle = @hairstyle, overlays = @overlays, permanentoverlay = @permanentoverlay, outfit_id = @outfit_id WHERE charid = @charid", {
hairstyle = encodedHairstyle,
overlays = encodedOverlays,
permanentoverlay = encodedPermanent,
outfit_id = outfitid or 0,
charid = charid
})
else
-- Insert new
MySQL.update("INSERT INTO murphy_barber (charid, hairstyle, overlays, permanentoverlay, outfit_id) VALUES (@charid, @hairstyle, @overlays, @permanentoverlay, @outfit_id)", {
charid = charid,
hairstyle = encodedHairstyle,
overlays = encodedOverlays,
permanentoverlay = encodedPermanent,
outfit_id = outfitid or 0
})
end
end)
end)

6. Load Hairstyle on Spawn

After character creation or when the player spawns:

lua
-- Just trigger the load event
TriggerEvent("murphy_barber:loadbarberoverlay")

Key Files to Reference

For full implementation details, refer to these files in murphy_creator:

File Purpose
client/function/barber.lua Hairstyle loading and application logic
client/NUI/NUIMessages.lua OpenBarberMenu() function
client/NUI/NUICallbacks.lua NUI callbacks for hairstyle changes
server/callbacks.lua murphy_creator:SavePreset callback
shared/murphy_assets.lua Hairstyle data (shared with murphy_barber)

Required Shared Files

Your creator needs access to these files from murphy_barber:

  1. murphy_assets.lua - Contains all hairstyle/overlay definitions
  2. config.lua - Contains baseoverlay template and configuration

You can either:

  • Copy these files to your creator
  • Or include murphy_barber's shared folder in your fxmanifest.lua

Database Tables

Murphy_barber uses the following tables:

murphy_barber

Stores the current hairstyle for each character.

Column Type Description
charid int/varchar Character identifier
hairstyle LONGTEXT JSON encoded hairstyle data
overlays LONGTEXT JSON encoded overlay data
permanentoverlay LONGTEXT JSON encoded permanent overlays
outfit_id int Current outfit ID

murphy_barber_preset

Stores saved presets/outfits.

Column Type Description
id int Auto-increment primary key
charid int/varchar Character identifier
outfit_id varchar(50) Unique preset ID
price float Preset price
name varchar(255) Preset name
hairstyle LONGTEXT JSON encoded hairstyle
overlays LONGTEXT JSON encoded overlays
gender LONGTEXT Character gender

Hairstyle Data Format

The hairstyle components table follows this structure:

lua
hairstyleCache = {
hair = { model = 5, texture = 0 },
beard = { model = 3, texture = 2 },
beards_chin = { model = 0, texture = 0 },
beards_chops = { model = 0, texture = 0 },
beards_mustache = { model = 0, texture = 0 },
beards_complete = { model = 0, texture = 0 },
hair_bonnet = { model = 0, texture = 0 },
-- ... other categories
}

Each category has:

  • model: The component index (0 = none/default)
  • texture: The texture variation

Available categories are defined in shared/murphy_assets.lua.


Last updated: September 9, 2026