Контекстное меню ox_lib: registerContext, inputDialog и alertDialog
Построение меню в FiveM с ox_lib: lib.registerContext и lib.showContext с подменю и значками, плюс lib.inputDialog и lib.alertDialog, и исправление 'lib' равного nil.
Вы вызываете lib.registerContext и консоль говорит:
attempt to index a nil value (global 'lib')Или код меню запускается и ничего не открывается. Эта статья охватывает инструменты меню ox_lib: контекстное меню, диалог ввода и диалог оповещения, с строкой манифеста, которая делает lib существующим.
Загрузите ox_lib в ваш манифест
lib — это глобальное значение, которое ox_lib добавляет в ваш ресурс через файл инициализации. Без него каждый вызов lib. не работает с ошибкой выше. В fxmanifest.lua:
fx_version 'cerulean'
game 'gta5'
lua54 'yes'
shared_script '@ox_lib/init.lua'
client_scripts { 'client/*.lua' }
server_scripts { 'server/*.lua' }Затем запустите ox_lib перед вашим скриптом в server.cfg:
ensure ox_lib
ensure my_scriptЕсли файл вообще не найден, смотрите @ox_lib/init.lua not found.
Контекстное меню
Контекстное меню — это список щёлкаемых опций. Вы регистрируете его один раз под id, затем показываете его, когда он вам нужен. Оба вызова — на стороне клиента:
lib.registerContext({
id = 'my_script_main',
title = 'Garage',
options = {
{
title = 'Take out a vehicle',
description = 'Choose from your parked vehicles',
icon = 'car',
onSelect = function()
print('take out')
end,
},
{
title = 'Store vehicle',
description = 'Park the vehicle you are in',
icon = 'warehouse',
onSelect = function()
print('store')
end,
},
{
title = 'Impound',
description = 'Not available',
icon = 'lock',
disabled = true,
},
},
})
lib.showContext('my_script_main')Опции, которые вы будете использовать чаще всего:
| Поле | Что оно делает |
|---|---|
title |
Основной текст опции. |
description |
Вторая строка текста под названием. |
icon |
Имя значка Font Awesome, например car. Вы также можете передать полный класс, такой как fa-solid fa-car. |
onSelect |
Функция, которая запускается при нажатии опции. |
menu |
Id другого контекстного меню для открытия (подменю). |
arrow |
Показывает стрелку справа, намёк на то, что это что-то открывает. |
disabled |
Затемняет опцию, чтобы её нельзя было щёлкнуть. |
Существуют другие поля, такие как event, serverEvent, args, metadata и progress. Проверьте документацию ox_lib для вашей версии.
Подменю
Чтобы открыть подменю, дайте опцию menu с id следующего контекстного меню. Дайте второму контекстному меню menu, указывающий на первый, и оно получит кнопку 'назад':
lib.registerContext({
id = 'my_script_main',
title = 'Garage',
options = {
{
title = 'My vehicles',
icon = 'car',
arrow = true,
menu = 'my_script_vehicles',
},
},
})
lib.registerContext({
id = 'my_script_vehicles',
title = 'My vehicles',
menu = 'my_script_main',
options = {
{
title = 'Sultan',
description = 'Plate ABC 123',
onSelect = function()
print('selected Sultan')
end,
},
},
})
lib.showContext('my_script_main')Совет: таблица опций строится при регистрации меню. Для списка, который изменяется, такого как транспортные средства игрока, постройте таблицу и вызовите
lib.registerContextещё раз прямо передlib.showContext. Регистрация того же id снова заменяет старое меню.
lib.hideContext() закрывает меню из кода.
Попросите ввод с inputDialog
lib.inputDialog открывает форму и ждёт, пока игрок подтвердит или отменит. Это возвращает таблицу со значениями в порядке строк, или nil, если игрок отменил:
local input = lib.inputDialog('New shop', {
{ type = 'input', label = 'Shop name', required = true },
{ type = 'number', label = 'Price', default = 100, min = 0 },
{ type = 'checkbox', label = 'Open to everyone' },
})
if not input then return end
local name, price, open = input[1], input[2], input[3]
print(name, price, open)Другие типы строк включают select, slider и textarea. select принимает список опций:
local input = lib.inputDialog('Pick a colour', {
{
type = 'select',
label = 'Colour',
options = {
{ value = 'red', label = 'Red' },
{ value = 'blue', label = 'Blue' },
},
},
})
if input then print(input[1]) endПотому что вызов ждёт, запустите его в потоке или в обработчике, которому разрешено ждать, такой как функция onSelect. Никогда не проверяйте только на клиенте. Когда значение идёт на сервер, проверьте его там также.
Подтвердите с alertDialog
lib.alertDialog — это окно да/нет. Это возвращает 'confirm' или 'cancel':
local alert = lib.alertDialog({
header = 'Delete the shop?',
content = 'This cannot be undone.',
centered = true,
cancel = true,
})
if alert == 'confirm' then
print('deleting')
endБез cancel = true есть только кнопка OK.
Используйте его из цели или команды
Меню обычно открывается чем-то другим. С ox_target вызовите lib.showContext в onSelect (смотрите ox_target: как добавлять цели). С командой вызовите её в обработчике:
RegisterCommand('garage', function()
lib.showContext('my_script_main')
end, false)Зарегистрируйте контекстные меню сначала, в начале файла клиента или при запуске скрипта, так чтобы id существовал, когда команда запускается.
Контрольный список
| Симптом | Решение |
|---|---|
attempt to index a nil value (global 'lib') |
Добавьте shared_script '@ox_lib/init.lua' и запустите ox_lib первым |
lib.showContext открывает ничего |
Зарегистрируйте id с lib.registerContext перед его показом |
| Подменю не имеет кнопки 'назад' | Установите menu в подменю на id родителя |
| Меню показывает устаревшие данные | Зарегистрируйте её снова с новыми опциями перед lib.showContext |
inputDialog возвращает nil |
Игрок отменил: проверьте на nil |
| Значок не появляется | Используйте допустимое имя Font Awesome, или полный класс как fa-solid fa-car |
Короткие ответы
Почему lib равен nil в моём скрипте?
Ваш манифест не загружает файл инициализации ox_lib. Добавьте shared_script '@ox_lib/init.lua' и убедитесь, что ox_lib запускается перед вашим ресурсом.
Как сделать подменю?
Зарегистрируйте второе контекстное меню со своим id, затем дайте опцию в первом меню menu = 'second_id'. Установите menu = 'first_id' на втором, так оно получит кнопку 'назад'.
Как я прочитаю, что написал игрок?
lib.inputDialog возвращает таблицу с одним значением за строку в порядке, или nil, если игрок отменил. Всегда проверяйте на nil.
Скрипты без этой проблемы
Item Creator V2Создавайте используемые предметы с анимациями, пропами, эффектами и не только — без кода.Смотреть скрипт →
Shop CreatorМагазин меньше чем за минуту — владельцы, сотрудники, сейфы и ограбления в комплекте.Смотреть скрипт →
Quest CreatorВизуальный редактор квестов и диалогов с NPC — узел за узлом прямо в игре.Смотреть скрипт →