Вопросы по 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
 
Последнее редактирование:

imring

Ride the Lightning
Всефорумный модератор
2,365
2,552
Мне нужно чтобы в игре можно было менять значение в инике, например в инике стоит key = 123, ты зашел в игру и написал /setkey 545, и значение key = поменялось на 545.
Lua:
sampRegisterChatCommand('setkey', function(n)
    if tonumber(n) then
        local test = inicfg.load(nil, --[[path]])
        while not test do test = inicfg.load(nil, --[[path]]) end
        test.key = tonumber(n)
        inicfg.save(test, --[[path]])
    end
end)
 

Azller Lollison

ещкере
Друг
1,349
2,314
Выставил путь.
Код:
[ML] (error) AutoSc: D:\Games\GTA SA\moonloader\test.lua:28: attempt to index global 'abs' (a nil value)
stack traceback:
    D:\Games\GTA SA\moonloader\test.lua: in function <D:\Games\GTA SA\moonloader\test.lua:27>
stack traceback:
    [C]: in function 'create'
    D:\Games\GTA SA\moonloader\test.lua:27: in function <D:\Games\GTA SA\moonloader\test.lua:25>
кинь фулл код
 

Azller Lollison

ещкере
Друг
1,349
2,314
Вот код:
Lua:
require "lib.moonloader"
local sampev = require 'lib.samp.events'
local inicfg = require 'inicfg'

if not doesFileExist('moonloader\\config\\abs.ini') then
    if not doesDirectoryExist('moonloader\\config') then
        createDirectory('moonloader\\config')
    end
local    ini = {
        settings = {
            key     = 0x77,
            line     = 14,
        }
    }
    inicfg.save(ini, 'abs')
end
local ini = inicfg.load(nil, 'abs')

function main()
    if not isSampfuncsLoaded() or not isSampLoaded() then return end
    while not isSampAvailable() do wait(100) end
sampRegisterChatCommand('setkey', function(n)
    if tonumber(n) then
        local test = inicfg.load(nil, abs.ini)
        while not test do test = inicfg.load(nil, abs.ini) end
        test.key = tonumber(n)
        inicfg.save(test, abs.ini)
    end
end)
    while true do
        wait(0)
        if isKeyDown(VK_MENU) and isKeyJustPressed(VK_R) then
                    sampSendChat('test')
                    wait(300)
                    setVirtualKeyDown(ini.settings.key, true)
                    setVirtualKeyDown(ini.settings.key, false)
                    wait(300)
                    sampSendChat('test')
        end
    end
end

Вот ошибка:
Код:
[ML] (error) alol.lua: D:\Games\GTA SA\moonloader\alol.lua:24: attempt to index global 'abs' (a nil value)
stack traceback:
    D:\Games\GTA SA\moonloader\alol.lua:24: in function <D:\Games\GTA SA\moonloader\alol.lua:22>
[ML] (error) alol.lua: Script died due to an error. (0B6E104C)
Ты пытаешься засунуть переменную abs.ini вместо путя. Чтобы указать именно путь, его надо отправить строкой.

замени abs.ini на "abs.ini"
 

Azller Lollison

ещкере
Друг
1,349
2,314
А
Вот код:
Lua:
require "lib.moonloader"
local sampev = require 'lib.samp.events'
local inicfg = require 'inicfg'

if not doesFileExist('moonloader\\config\\abs.ini') then
    if not doesDirectoryExist('moonloader\\config') then
        createDirectory('moonloader\\config')
    end
local    ini = {
        settings = {
            key     = 0x77,
            line     = 14,
        }
    }
    inicfg.save(ini, 'abs')
end
local ini = inicfg.load(nil, 'abs')

function main()
    if not isSampfuncsLoaded() or not isSampLoaded() then return end
    while not isSampAvailable() do wait(100) end
sampRegisterChatCommand('setkey', function(n)
    if tonumber(n) then
        local test = inicfg.load(nil, abs.ini)
        while not test do test = inicfg.load(nil, abs.ini) end
        test.key = tonumber(n)
        inicfg.save(test, abs.ini)
    end
end)
    while true do
        wait(0)
        if isKeyDown(VK_MENU) and isKeyJustPressed(VK_R) then
                    sampSendChat('test')
                    wait(300)
                    setVirtualKeyDown(ini.settings.key, true)
                    setVirtualKeyDown(ini.settings.key, false)
                    wait(300)
                    sampSendChat('test')
        end
    end
end

Вот ошибка:
Код:
[ML] (error) alol.lua: D:\Games\GTA SA\moonloader\alol.lua:24: attempt to index global 'abs' (a nil value)
stack traceback:
    D:\Games\GTA SA\moonloader\alol.lua:24: in function <D:\Games\GTA SA\moonloader\alol.lua:22>
[ML] (error) alol.lua: Script died due to an error. (0B6E104C)
А вообще у тебя треш в коде.
Попробуй это:
Lua:
require "lib.moonloader"
local sampev = require 'lib.samp.events'
local inicfg = require 'inicfg'

if not doesFileExist('moonloader\\config\\abs.ini') then
    if not doesDirectoryExist('moonloader\\config') then
        createDirectory('moonloader\\config')
    end
local    ini = {
        settings = {
            key     = 0x77,
            line     = 14,
        }
    }
    inicfg.save(ini)
end

function main()
    if not isSampfuncsLoaded() or not isSampLoaded() then return end
    while not isSampAvailable() do wait(100) end
sampRegisterChatCommand('setkey', function(n)
    if tonumber(n) then
        local ini = inicfg.load(nil, "abs.ini")
        while not test do ini = inicfg.load(nil, "abs.ini") end
        ini.settings.key = tonumber(n)
        inicfg.save(ini)
    end
end)
    while true do
        wait(0)
        if isKeyDown(VK_MENU) and isKeyJustPressed(VK_R) then
                    sampSendChat('test')
                    wait(300)
                    setVirtualKeyDown(ini.settings.key, true)
                    setVirtualKeyDown(ini.settings.key, false)
                    wait(300)
                    sampSendChat('test')
        end
    end
end
 

Azller Lollison

ещкере
Друг
1,349
2,314
Поменял код на твой, после /setkey значение ГТА намертво виснет.
Lua:
require "lib.moonloader"
local sampev = require 'lib.samp.events'
local inicfg = require 'inicfg'

if not doesFileExist('moonloader\\config\\abs.ini') then
    if not doesDirectoryExist('moonloader\\config') then
        createDirectory('moonloader\\config')
    end
local    ini = {
        settings = {
            key     = 0x77,
            line     = 14,
        }
    }
end

function main()
    repeat wait(0) until isSampAvailable()
sampRegisterChatCommand('setkey', function(n)
    if tonumber(n) then
        local ini = inicfg.load(nil, "abs.ini")
        ini.settings.key = tonumber(n)
        inicfg.save(ini)
    end
end)
    while true do
        wait(0)
        if isKeyDown(VK_MENU) and isKeyJustPressed(VK_R) then
                    sampSendChat('test')
                    wait(300)
                    setVirtualKeyDown(ini.settings.key, true)
                    setVirtualKeyDown(ini.settings.key, false)
                    wait(300)
                    sampSendChat('test')
        end
    end
end
 

Patrickkk

Участник
162
19
Lua:
require "lib.moonloader"
local sampev = require 'lib.samp.events'
local inicfg = require 'inicfg'

if not doesFileExist('moonloader\\config\\abs.ini') then
    if not doesDirectoryExist('moonloader\\config') then
        createDirectory('moonloader\\config')
    end
local    ini = {
        settings = {
            key     = 0x77,
            line     = 14,
        }
    }
end

function main()
    repeat wait(0) until isSampAvailable()
sampRegisterChatCommand('setkey', function(n)
    if tonumber(n) then
        local ini = inicfg.load(nil, "abs.ini")
        ini.settings.key = tonumber(n)
        inicfg.save(ini)
    end
end)
    while true do
        wait(0)
        if isKeyDown(VK_MENU) and isKeyJustPressed(VK_R) then
                    sampSendChat('test')
                    wait(300)
                    setVirtualKeyDown(ini.settings.key, true)
                    setVirtualKeyDown(ini.settings.key, false)
                    wait(300)
                    sampSendChat('test')
        end
    end
end
Всё так же намертво виснет
 

Patrickkk

Участник
162
19
[14:23:17.578002] (system) alol.lua: Script terminated. (01A820C4)

[14:23:17.601004] (system) Loading script 'D:\Games\GTA SA\moonloader\alol.lua'...
[14:23:17.601004] (debug) New script: 0B6BD0DC
[14:23:17.632005] (system) alol.lua: Loaded successfully.
 

Azller Lollison

ещкере
Друг
1,349
2,314
[14:23:17.578002] (system) alol.lua: Script terminated. (01A820C4)

[14:23:17.601004] (system) Loading script 'D:\Games\GTA SA\moonloader\alol.lua'...
[14:23:17.601004] (debug) New script: 0B6BD0DC
[14:23:17.632005] (system) alol.lua: Loaded successfully.
Создай в конфиге файл alol.lua.ini и перенеси туда все что было в старом.
Через игру мне лень тестить)
Lua:
require "lib.moonloader"
local sampev = require 'lib.samp.events'
local inicfg = require 'inicfg'

    if not doesDirectoryExist('moonloader\\config') then
        createDirectory('moonloader\\config')
    end
local    ini = {
        settings = {
            key     = 0x77,
            line     = 14,
        }
    }

function main()
    repeat wait(0) until isSampAvailable()
    sampRegisterChatCommand('setkey', sooqa)
    while true do
        wait(0)
        if isKeyDown(VK_MENU) and isKeyJustPressed(VK_R) then
                    sampSendChat('test')
                    wait(300)
                    setVirtualKeyDown(ini.settings.key, true)
                    setVirtualKeyDown(ini.settings.key, false)
                    wait(300)
                    sampSendChat('test')
        end
    end
end

function sooqa(var)
    if tonumber(var) then
        ini = inicfg.load(nil, "alol.lua.ini")
        if ini == nil then
            sampAddChatMessage("ебучий ини не найден", -1)
        else
            ini.settings.key = var
            sampAddChatMessage("ебучая переменная сохранена в ебучий ини", -1)
            inicfg.save(ini)
        end
    end
end
 

Patrickkk

Участник
162
19
Создай в конфиге файл alol.lua.ini и перенеси туда все что было в старом.
Через игру мне лень тестить)
Lua:
require "lib.moonloader"
local sampev = require 'lib.samp.events'
local inicfg = require 'inicfg'

    if not doesDirectoryExist('moonloader\\config') then
        createDirectory('moonloader\\config')
    end
local    ini = {
        settings = {
            key     = 0x77,
            line     = 14,
        }
    }

function main()
    repeat wait(0) until isSampAvailable()
    sampRegisterChatCommand('setkey', sooqa)
    while true do
        wait(0)
        if isKeyDown(VK_MENU) and isKeyJustPressed(VK_R) then
                    sampSendChat('test')
                    wait(300)
                    setVirtualKeyDown(ini.settings.key, true)
                    setVirtualKeyDown(ini.settings.key, false)
                    wait(300)
                    sampSendChat('test')
        end
    end
end

function sooqa(var)
    if tonumber(var) then
        ini = inicfg.load(nil, "alol.lua.ini")
        if ini == nil then
            sampAddChatMessage("ебучий ини не найден", -1)
        else
            ini.settings.key = var
            sampAddChatMessage("ебучая переменная сохранена в ебучий ини", -1)
            inicfg.save(ini)
        end
    end
end
виснет дальше(