Вопросы по Lua скриптингу

Общая тема для вопросов по разработке скриптов на языке программирования Lua, в частности под MoonLoader.
  • Задавая вопрос, убедитесь, что его нет в списке частых вопросов и что на него ещё не отвечали (воспользуйтесь поиском).
  • Поищите ответ в теме посвященной разработке Lua скриптов в MoonLoader
  • Отвечая, убедитесь, что ваш ответ корректен.
  • Старайтесь как можно точнее выразить мысль, а если проблема связана с кодом, то обязательно прикрепите его к сообщению, используя блок [code=lua]здесь мог бы быть ваш код[/code].
  • Если вопрос связан с MoonLoader-ом первым делом желательно поискать решение на wiki.

Частые вопросы

—
Как научиться писать скрипты? С чего начать?
Информация - Гайд - Всё о Lua скриптинге для MoonLoader(https://blast.hk/threads/22707/)
— Как вывести текст на русском? Вместо русского текста у меня какие-то каракули.
Изменить кодировку файла скрипта на Windows-1251. В Atom: комбинация клавиш Ctrl+Shift+U, в Notepad++: меню Кодировки -> Кодировки -> Кириллица -> Windows-1251.
— Как получить транспорт, в котором сидит игрок?
Lua:
local veh = storeCarCharIsInNoSave(PLAYER_PED)
— Как получить свой id или id другого игрока?
Lua:
local _, id = sampGetPlayerIdByCharHandle(PLAYER_PED) -- получить свой ид
local _, id = sampGetPlayerIdByCharHandle(ped) -- получить ид другого игрока. ped - это хендл персонажа
— Как проверить, что строка содержит какой-то текст?
Lua:
if string.find(str, 'текст', 1, true) then
-- строка str содержит "текст"
end
— Как эмулировать нажатие игровой клавиши?
Lua:
local game_keys = require 'game.keys' -- где-нибудь в начале скрипта вне функции main

setGameKeyState(game_keys.player.FIREWEAPON, -1) -- будет сэмулировано нажатие клавиши атаки
Все иды клавиш находятся в файле moonloader/lib/game/keys.lua.
Подробнее о функции setGameKeyState здесь: lua - setgamekeystate | BlastHack — DEV_WIKI(https://www.blast.hk/wiki/lua:setgamekeystate)
— Как получить id другого игрока, в которого целюсь я?
Lua:
local valid, ped = getCharPlayerIsTargeting(PLAYER_HANDLE) -- получить хендл персонажа, в которого целится игрок
if valid and doesCharExist(ped) then -- если цель есть и персонаж существует
  local result, id = sampGetPlayerIdByCharHandle(ped) -- получить samp-ид игрока по хендлу персонажа
  if result then -- проверить, прошло ли получение ида успешно
    -- здесь любые действия с полученным идом игрока
  end
end
— Как зарегистрировать команду чата SAMP?
Lua:
-- До бесконечного цикла/задержки
sampRegisterChatCommand("mycommand", function (param)
     -- param будет содержать весь текст введенный после команды, чтобы разделить его на аргументы используйте string.match()
    sampAddChatMessage("MyCMD", -1)
end)
— Крашит игру при вызове sampSendChat. Как это исправить?
Это происходит из-за бага в SAMPFUNCS, когда производится попытка отправки пакета определенными функциями изнутри события исходящих RPC и пакетов. Исправления для этого бага нет, но есть способ не провоцировать его. Вызов sampSendChat изнутри обработчика исходящих RPC/пакетов нужно обернуть в скриптовый поток с нулевой задержкой:
Lua:
function onSendRpc(id)
  -- крашит:
  -- sampSendChat('Send RPC: ' .. id)

  -- норм:
  lua_thread.create(function()
    wait(0)
    sampSendChat('Send RPC: ' .. id)
  end)
end
 
Последнее редактирование:

everlight

Известный
289
57
Doesn't work only on pause or does not work at all?
Are you sure this is the event you need? Can you try with the onShowTextDraw event?
Lua:
INCOMING_RPCS[RPC.SHOWTEXTDRAW]               = {'onShowTextDraw',
  {textdrawId = 'uint16'},
  {textdraw = {
    {flags = 'uint8'},
    {letterWidth = 'float'},
    {letterHeight = 'float'},
    {letterColor = 'int32'},
    {lineWidth = 'float'},
    {lineHeight = 'float'},
    {boxColor = 'int32'},
    {shadow = 'uint8'},
    {outline = 'uint8'},
    {backgroundColor = 'int32'},
    {style = 'uint8'},
    {selectable = 'uint8'},
    {position = 'vector2d'},
    {modelId = 'uint16'},
    {rotation = 'vector3d'},
    {zoom = 'float'},
    {color1 = 'int16'},
    {color2 = 'int16'},
    {text = 'string16'}
  }}
}
fish bot works when im in game, every 4 seconds it writes /zvejoti (/fish)
but if im gonna alt+tab fish bot will stop working and not gonna type /zvejoti
 

Dmitriy Makarov

25.05.2021
Проверенный
2,511
1,139
fish bot works when im in game, every 4 seconds it writes /zvejoti (/fish)
but if im gonna alt+tab fish bot will stop working and not gonna type /zvejoti
Specifies that the script will continue executing while the game is paused (assuming the game is maximized and in the foreground).
Try with this.
 

joumey

Активный
194
43
У меня проект есть minergame, там должна быть огромная сума денег ( что бы улучшить игру и баланс после 2ккк с чем то не уходил в минус, ведь это стает концом игры), и вот мне нужно сохраять это в иникфг и использовать в имгуи
как пользоваться ffi.new и как сохранить его значение в файл и использовать в имгуи, если можно?
up
 

Luis_Mora

Участник
31
1
Привет. telegram
Есть такая штука как телеграм контрол самп. https://www.blast.hk/threads/62811
Интересует вопрос. Можно ли как то отлавливать сообщения НЕ от пользователей.
Т.е. меня интересует непосредственно отловить сообщение которое туда отправляет сам бот.
Я по определённой команде отправляю сообщение в канал в телеграме, от лица бота.
Если допустим человек в этом же канале пишет /send вывпвып, то всем у кого настроен данный скрипт, соответственно придёт в чат "вывпвып"
Мне нужно чтобы бот, при такой отправке, сам же смог отловить условно эту же команду. Т.е. посылаем в канал через команду /test сообщение /send sdfsdf от лица бота, и сам же бот его принимает и выполняет.
Может кто знает как это сделать можно.
 

Tak

Известный
180
70
Аризона лаунчер и onSetMapIcon
Если использовать библиотеку для обработки сетевых пакетов SAMP.Lua.
И пытаться получить TYPE (с помощью onSetMapIcon) иконок с карты на ArizonaRP (лаунчер), то будут несоответствующие типы указанным здесь: Сайт с иконками
(Как же всё-таки найти эти неизвестные иконки?)
Решение: лезем в hud.txd файл игры лаунчера и находим там иконки с 64 по 127 ID, это как раз те неизвестные иконки
Вот и всё =)

(спрашивал об этой проблеме здесь, но нашел решение позже сам)
сам спросил сам ответил
 
Последнее редактирование:

The Spark

frontend
Проверенный
800
842
Я так понимаю, у тебя что-то на подобии кликера, где баланс доходит до гигантских чисел. В таких играх никто не использует целые числа, а используют абстракции, например:

Числа 0-999 будем записывать в виде целого, без постфикса, числа 1000-999999 в виде "1-999K", 1000000-999999999 "1-999М" и тд. И того в конфиге сохраняется значение не более 10 тысяч. ("99.833М" - 99.833.000. От точности мы отказываемся по мере возрастания числа)
Проблему с конфигом решили, а как в коде обрабатывать?

В коде ты также должен приводить все операции с этим числом в упрощенный тип. Например:
Хотим прибавить 99.831М + 1К. Получаем 99.832М. Если нужно будет прибавить 500, то тут проблема, ведь точности нет. Скорее всего такие малые суммы уже прибавлять будет не нужно, а если и нужно, то веди отдельное число точности, к которому будут прибавляться маленькие числа.
При использовании 64 битных чисел, через ffi.new, или 1ULL через компиляцию luaJIT тебе придется пилить сложные математические преобразования, что точно не нужно
 
  • Нравится
Реакции: вайега52

sosnov

Известный
328
115
как сделать так чтоб плеер пед не падал с велика?
Lua:
SetCharCanBeKnockedOffBike(PLAYER_PED, false)
эта строка не работает,надо либо ее менять,либо другую ставить
 

вайега52

cache miss
Модератор
3,084
3,415
мне нужно вызвать у bs метод, который хранится в переменной, пробовал делать через ключ - крашит скрипт. Решил попробовать сделать это через load(), но она загружают в локальную область, как я понимаю, из-за чего она не видит bs. как можно реализовать вызов метода через строку?
Lua:
local bs = RakLuaBitStream.new()

bs[("write%s"):format(data[1])](data[2][0]) -- ошибка: received nil for 'self' argument (use ':' for accessing member functions, make sure member variables are preceeded by the actual object with '.' syntax)

load(("bs:write%s(data[2][0])"):format(data[1]))() -- 2 варик, не видит bs

как сделать так чтоб плеер пед не падал с велика?
Lua:
SetCharCanBeKnockedOffBike(PLAYER_PED, false)
эта строка не работает,надо либо ее менять,либо другую ставить
setCharCanBeKnockedOffBike(PLAYER_PED, false)
 

Leon_Trotsky

Участник
39
2
Что за ошибка может быть?

Код:
[ML] (error) AdminTools: C:\Users\marke\Desktop\Ìîÿ ñáîðêà\moonloader\ATools.lua:10798: attempt to call global 'update' (a boolean value)
stack traceback:
    C:\Users\marke\Desktop\Ìîÿ ñáîðêà\moonloader\ATools.lua:10798: in function <C:\Users\marke\Desktop\Ìîÿ ñáîðêà\moonloader\ATools.lua:10797>
[ML] (error) AdminTools: Script died due to an error. (16DBD5A4)

Первый раз функция отрабатывает нормально, во второй умирает скрипт

Lua:
    sampRegisterChatCommand("upd", function()
        update()
    end)

update:
function update()
    local fpath = os.getenv('TEMP') .. '\\Admin Tools.json' -- куда будет качаться наш файл для сравнения версии
    downloadUrlToFile('https://pastebin.com/raw/bgkgsSy5', fpath, function(id, status, p1, p2) -- ссылку на ваш гитхаб где есть строчки которые я ввёл в теме или любой другой сайт
      if status == dlstatus.STATUS_ENDDOWNLOADDATA then
      local f = io.open(fpath, 'r') -- открывает файл
      if f then
        local info = decodeJson(f:read('*a')) -- читает
        updatelink = info.updateurl
        if info and info.latest then
          version = tonumber(info.latest) -- переводит версию в число
        if version > tonumber(thisScript().version) then -- если версия больше чем версия установленная то...
            lua_thread.create(goupdate)
        else -- если меньше, то
            update = false
            lua_thread.create(nonupdate)
        end
        end
      end
    end
  end)
end
  --------------------------------------------[[UPDATE 2]]-------------------------------------------------
function goupdate()
    mod.addNotification('Начинаю загрузку обновления.\n{ffa500}Ожидайте', 5)
    wait(300)
    downloadUrlToFile(updatelink, thisScript().path, function(id3, status1, p13, p23) -- качает ваш файлик с latest version
    if status1 == dlstatus.STATUS_ENDDOWNLOADDATA then
        thisScript():reload()
    end
  end)
end

function nonupdate()
    sampAddChatMessage('{ffa500}Admin Tools {FFFFFF}| Версия скрипта актуальна', -1)
end