Метаданные элементов ox_inventory: AddItem, Search, SetMetadata и уникальные элементы

Используйте метаданные в ox_inventory: добавляйте элементы с данными, ищите и читайте слоты, обновляйте с помощью SetMetadata, показывайте пользовательскую метку и описание, и создавайте уникальные элементы, такие как ID и ключи.

Элемент в ox_inventory — это имя и количество. Когда два элемента с одним именем нужно отличать, такие как ключ от машины для одного номера и ключ для другого, вы используете метаданные: таблица, хранящаяся с элементом. Эта статья показывает, как добавить элемент с метаданными, найти его снова, прочитать и обновить, отобразить и построить уникальные элементы, такие как ID и ключи.

Добавьте элемент с метаданными

Четвёртый аргумент AddItem — это таблица метаданных:

lua
exports.ox_inventory:AddItem(source, 'car_key', 1, {
    plate = 'ABC 123',
    label = 'Key ABC 123',
    description = 'Opens the car with plate ABC 123.',
})

Сигнатура — AddItem(inventory, item, count, metadata). inventory — это идентификатор игрока для инвентаря игрока. Любой ключ, который вы добавляете, хранится со слотом, и вы можете прочитать его позже. Держите метаданные маленькими и состоящими из простых данных: строк, чисел, логических значений и простых таблиц.

Совет: элемент должен существовать в data/items.lua, например car_key. Смотрите добавление элементов в ox_inventory.

Покажите это игроку

Несколько ключей метаданных изменяют то, что показывает инвентарь:

Ключ Эффект
label Заменяет имя элемента в инвентаре
description Заменяет описание элемента
image Заменяет значок, используя имя изображения в web/images
lua
exports.ox_inventory:AddItem(source, 'id_card', 1, {
    label = 'ID card: Jane Doe',
    description = 'Born 1994-05-12',
    image = 'id_card',
})

Всё остальное, что вы помещаете в таблицу, хранится, но не показывается, если только определение элемента это не отображает. Используйте уникальный label, когда вам нужно, чтобы игроки отличали элементы с первого взгляда.

Ищите элементы

Search находит элементы в инвентаре. С 'count' это возвращает количество, с 'slots' это возвращает слоты:

lua
local count = exports.ox_inventory:Search(source, 'count', 'car_key')

local slots = exports.ox_inventory:Search(source, 'slots', 'car_key')
for _, slot in pairs(slots) do
    print(slot.slot, slot.metadata and slot.metadata.plate)
end

Вы также можете фильтровать по метаданным. Передайте таблицу как четвёртый аргумент:

lua
local keys = exports.ox_inventory:Search(source, 'slots', 'car_key', { plate = 'ABC 123' })
if #keys > 0 then
    -- the player has the key for that plate
end

Это стандартный способ проверить владение: сделайте это на сервере, с данными, которым вы доверяете, никогда с сообщением от клиента.

Прочитайте один слот

Если вы знаете номер слота, GetSlot возвращает данные этого слота:

lua
local slot = exports.ox_inventory:GetSlot(source, 5)
if slot and slot.name == 'car_key' then
    print(slot.metadata.plate)
end

Когда вы знаете только элемент, используйте GetSlotWithItem:

lua
local slot = exports.ox_inventory:GetSlotWithItem(source, 'car_key', { plate = 'ABC 123' })

Оба возвращают nil, когда ничто не совпадает, поэтому проверьте результат перед чтением slot.metadata. Слот также имеет slot.count и slot.weight.

Обновите метаданные с помощью SetMetadata

Чтобы изменить существующий слот, например отметить ключ как скопированный, или уменьшить оставшиеся заряды на элементе, используйте SetMetadata:

lua
local slot = exports.ox_inventory:GetSlotWithItem(source, 'battery')
if slot then
    local metadata = slot.metadata or {}
    metadata.charge = (metadata.charge or 100) - 10
    exports.ox_inventory:SetMetadata(source, slot.slot, metadata)
end

SetMetadata(inventory, slot, metadata) заменяет метаданные слота таблицей, которую вы даёте. Сначала скопируйте существующую таблицу, измените одно поле и отправьте всю таблицу обратно, иначе вы сотрёте другие ключи.

Уникальные элементы: ID, ключи, лицензии

Для уникального элемента вам нужны две вещи: элемент, который не складывается, и метаданные, которые его идентифицируют.

lua
-- data/items.lua
['id_card'] = {
    label = 'ID card',
    weight = 10,
    stack = false,
    close = true,
},
lua
-- server: give it at character creation
exports.ox_inventory:AddItem(source, 'id_card', 1, {
    firstname = 'Jane',
    lastname = 'Doe',
    dob = '1994-05-12',
    label = 'ID card: Jane Doe',
})

Элементы с разными метаданными не складываются, поэтому две ключи для двух машин всегда занимают два слота, и stack = false делает это явным для элементов, которые никогда не должны.

Чтобы прочитать данные при использовании элемента, зарегистрируйте серверный экспорт на элементе:

lua
-- data/items.lua
['id_card'] = {
    label = 'ID card',
    weight = 10,
    stack = false,
    server = { export = 'my_script.id_card' },
},
lua
-- my_script/server.lua
exports('id_card', function(event, item, inventory, slot, data)
    if event == 'usingItem' then
        local info = exports.ox_inventory:GetSlot(inventory.id, slot)
        if info and info.metadata then
            print(info.metadata.firstname, info.metadata.lastname)
        end
    end
end)

Аргумент event говорит вам фазу использования. Точные аргументы зависят от вашей версии ox_inventory, поэтому проверьте документацию для вашего выпуска, если экспорт не вызывается.

Вещи, которые нужно смотреть

  • Метаданные живут на слоте. Когда игрок бросает или торгует элементом, они движутся с ним, и это элемент, который доказывает право доступа к чему-либо.
  • Не помещайте секреты в метаданные. Игроки не видят неперечисленные ключи, но рассматривают их как данные, а не как защиту.
  • Много элементов с большими таблицами метаданных делает сохранение инвентаря медленнее. Сохраняйте ID и держите тяжёлые данные в собственной таблице базы данных.
  • Метаданные, установленные на клиенте, не доверяются. Всегда вызывайте AddItem и SetMetadata из кода сервера.

Контрольный список

Симптом Решение
Две ключи объединяются в один стек Они имеют идентичные метаданные; добавьте уникальное поле, такое как plate
Метка не изменяется Поместите label внутри таблицы метаданных, а не в items.lua
Search находит ничего Передайте правильное имя элемента и фильтр метаданных как таблицу
SetMetadata стёр другие поля Скопируйте существующие метаданные, измените один ключ, отправьте всю таблицу
slot.metadata равен nil Проверьте слот существует и читайте metadata только после проверки nil
Данные элемента отредактированы игроками Запустите AddItem и SetMetadata только на сервере

Короткие ответы

Что такое метаданные в ox_inventory?

Таблица дополнительных данных, хранящихся на одном слоте элемента. Это позволяет двум элементам с одним именем отличаться, например две ключи для разных машин, или удостоверение личности для разных людей.

Как мне показать пользовательский текст на элементе?

Установите label, description или image внутри метаданных при добавлении элемента. ox_inventory показывает их вместо текста элемента по умолчанию.

Складываются ли элементы с разными метаданными?

Нет. Два элемента складываются только когда их метаданные одинаковые, поэтому элементы с уникальными метаданными занимают слот каждый.

Скрипты без этой проблемы

Item Creator V2Создавайте используемые предметы с анимациями, пропами, эффектами и не только — без кода.Смотреть скрипт →Shop CreatorМагазин меньше чем за минуту — владельцы, сотрудники, сейфы и ограбления в комплекте.Смотреть скрипт →

Читайте также