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

ShuffleBoy

Известный
Друг
753
425
не могу найти функцию для того что бы получить скин игрока хелп
getCharModel(ped ped)

А как теперь сделать что бы был диалог а в нем еще один диалог а потом текст. Дайте пример позя, я только по примерам могу понять или тут исправте буду благодарен
Lua:
function dtest()
   sampShowDialog(102, "{4682B4}[Goska DRP]: {ffffff}Гос.Новости", string.format("{4682B4}1. {FFFFFF}Начало [Гос.Новости]\n{4682B4}2. {FFFFFF}Напоминание [Гос.Новости]\n{4682B4}3. {FFFFFF}Конец [Гос.Новости]"), "Выбрать","Закрыть", 2)
   lua_thread.create(function() -- Создаем новый поток
       repeat
       wait(0)
       result, button, list, input = sampHasDialogRespond(102)
       until result
       if button == 1 then
           if list == 0 then
               sampShowDialog(103, "{FFFF00}Начало [Гос.Новости]", string.format("{4682B4}1. {FFFFFF}Администрация Президента\n{4682B4}2. {FFFFFF}Мэрия г.Лос-Сантос"), "Выбрать","Закрыть", 2)
               repeat
               wait(0)
               result, button, list, input = sampHasDialogRespond(103)
               until result1
               if button == 1 then
                   if list == 0 then
                   sampSendChat("/n Вещаю..")
               end
           elseif list == 1 then
               sampShowDialog(104, "{FFFF00}Напоминание [Гос.Новости]", string.format("{4682B4}1. {FFFFFF}Администрация Президента\n{4682B4}2. {FFFFFF}Мэрия г.Лос-Сантос"), "Выбрать","Закрыть", 2)
           elseif list == 2 then
               sampShowDialog(105, "{FFFF00}Конец [Гос.Новости]", string.format("{4682B4}1. {FFFFFF}Администрация Президента\n{4682B4}2. {FFFFFF}Мэрия г.Лос-Сантос"), "Выбрать","Закрыть", 2)
           end
       end
   end)
end
По тому же прицнипу
 

штейн

Известный
Проверенный
1,003
688
Lua:
function sampev.onServerMessage(color, text)
    data = LIP.load('moonloader\\config\\hitman.ini')
    if text:find('Деньги перечислены на ваш банковский счёт.') then
    if data.options.screenshot == 1 and data.options.messages == 1 then
            screenshot()
            sampAddChatMessage("[ {800000}HitMan {ffffff}]: Контракт выполнен! {800000}Hitman Help {ffffff}автоматически сделает скриншот.", -1)
            zakaz = false
    else
        if data.options.messages == 1 then
            sampAddChatMessage("[ {800000}HitMan {ffffff}]: Контракт выполнен! {800000}Hitman Help {ffffff}мог автоматически сделать скриншот.", -1)
            zakaz = false
        end
        if data.options.messages == 1 then
            return false
        end
    end
end

    if text:find('.+контракт%s+(.*)%[%d+%].+%s+сумма%s+(%d+)$%s+') then
    nick, money = text:match('.+контракт%s+(.*)%[%d+%].+%s+сумма%s+(%d+)$%s+')
        local thisid = sampGetPlayerIdByNickname(nick)
        if nick ~= nil and money ~= nil and thisid ~= nil then
        if zakaz ~= true then
        local nick = nick:gsub('_', ' ')
        id = thisid
            if data.options.messages == 1 then
            zakaz = true
            sampAddChatMessage('[ {800000}HitMan {ffffff}]: Новый контракт: {800000}'..nick..'{ffffff}, на сумму в {800000}'..money..'$', -1)
            sampAddChatMessage("[ {800000}HitMan {ffffff}]: Поступил новый контракт! Чтобы попросить выдачу Вам контракта нажмите {800000}P{ffffff}.", -1) end
        if data.options.messages == 1 then
            return false
        end
    end
end

    if text:find('Ваша цель покинула сервер.') then
        if data.options.messages == 1 then
            sampAddChatMessage("[ {800000}HitMan {ffffff}]: Моя цель покинула сервер, я должен сообщить об этом в /f.", -1)
            sampSendChat("/f Цель покинула пределы Штата.")
            zakaz = false end
        if data.options.messages == 1 then
            return false
            end
        end
    end
end

переставил все энды по несколько раз, не понимаю где именно я ошибся
 

ШPEK

Известный
1,474
525
как создать диалог 2 id с 3 строками, если нажать на любую из них будет sampAddChatMessage("222", 00FFFF)
 

штейн

Известный
Проверенный
1,003
688
как создать диалог 2 id с 3 строками, если нажать на любую из них будет sampAddChatMessage("222", 00FFFF)
Lua:
    if isKeyJustPressed(VK_L) and not sampIsChatInputActive() and not sampIsDialogActive() and not isPauseMenuActive() then
        sampShowDialog(801, ("xuina"), nazvanie, "{ffffff}Далее", "Закрыть", 2)
        end
        local re, bu, li, inp = sampHasDialogRespond(801)
        if re == true and bu == 1 then
            if li == 0 then sampAddChatMessage("222", 00FFFF) end
            if li == 1 then sampAddChatMessage("222", 00FFFF) end
            if li == 2 then sampAddChatMessage("222", 00FFFF) end
        end

   nazvanie = [[
1
2
3]]
 

ШPEK

Известный
1,474
525
Lua:
    if isKeyJustPressed(VK_L) and not sampIsChatInputActive() and not sampIsDialogActive() and not isPauseMenuActive() then
        sampShowDialog(801, ("xuina"), nazvanie, "{ffffff}Далее", "Закрыть", 2)
        end
        local re, bu, li, inp = sampHasDialogRespond(801)
        if re == true and bu == 1 then
            if li == 0 then sampAddChatMessage("222", 00FFFF) end
            if li == 1 then sampAddChatMessage("222", 00FFFF) end
            if li == 2 then sampAddChatMessage("222", 00FFFF) end
        end

   nazvanie = [[
1
2
3]]
Надо чтобы строки были
upload_2018-4-21_18-40-18.png
 

BND / PLP

Новичок
84
4
скрипт - тупо маркеры на игроков и их удаление
Lua:
local m = {}

function main()
  if not isSampfuncsLoaded() or not isSampLoaded() then return end
  while not isSampAvailable() do wait(100) end
  sampRegisterChatCommand("mark", mark)
  sampRegisterChatCommand("clmark", clmark)
  while true do
        wait(0)
    end
end

function mark(param)
    local id = tonumber(param)
    local exist, handle = sampGetCharHandleBySampPlayerId(id)
    if exist and doesCharExist(handle) then
        if not isCharInCar(handle, car) then
            local marker = addBlipForChar(handle)
            changeBlipColour(marker, 0xFF0000FF)
            setBlipAlwaysDisplayOnZoomedRadar(marker, -1)
            m[#m+1] = marker
        else result, car = sampGetCarHandleBySampVehicleId(carid)
            result1 = doesBlipExist(marker)
            local marker = addBlipForCar(car)
            changeBlipColour(marker, 0xFF0000FF)
            setBlipAlwaysDisplayOnZoomedRadar(marker, -1)
            m[#m+1] = marker
        end
    end
end

function clmark()
    for id = 0, 1000 do
        local marker = m[#m]
        removeBlip(marker)
        m[#m] = nil
    end
end
можете сделать так что бы возвращались маркеры на игроков если те выходят из стрима и снова заходят обратно

мне объясняли как это сделать, но я не понял
 
Последнее редактирование:

ШPEK

Известный
1,474
525
Lua:
require 'lib.moonloader'
local events = require "lib.samp.events"

function main()
while true do
wait(0)
if isKeyJustPressed(VK_5) then
local x, y, z = getCharCoordinates(playerPed)
sampAddChatMessage(x, -1)
end
if x >= 338.00000000000 and <= 342.00000000000 then
sampAddChatMessage("ввв")
end
end
end
Что тут не верно? Ожидалось чтобы при вставании на координату x - писало ввв
 
Последнее редактирование модератором:

BND / PLP

Новичок
84
4
Lua:
require 'lib.moonloader' 
local events = require "lib.samp.events"
function main()
    if not isSampfuncsLoaded() or not isSampLoaded() then return end
    while not isSampAvailable() do wait(100) end
    while true do
        wait(0)
        if isKeyJustPressed(VK_5) then
            local x, y, z = getCharCoordinates(playerPed)
            sampAddChatMessage(""..x, -1)
        end
        if x >= 338.00000000000 and x <= 342.00000000000 then
            sampAddChatMessage("ввв", -1)
        end
    end
end
исправил ошибки в твоем коде

ты встаешь не на координату х, а на диапозон в котором она может быть
 
Последнее редактирование модератором:

RTD

Потужно
Модератор
399
470
Lua:
require 'lib.moonloader'
local events = require "lib.samp.events"

function main()
while true do
wait(0)
if isKeyJustPressed(VK_5) then
local x, y, z = getCharCoordinates(playerPed)
sampAddChatMessage(x, -1)
end
if x >= 338.00000000000 and <= 342.00000000000 then
sampAddChatMessage("ввв")
end
end
end
Что тут не верно? Ожидалось чтобы при вставании на координату x - писало ввв
Ты объявляешь x координату локальной. Опять же читай основы, если бы прочитал, то знал, что она работает только в условии if IsKeyJust....
Делаешь условие либо в if isKeyJust... (после sampAddChatMessage(x, -1)), либо объявляй x коорду глобальной
 

Jason2222

Известный
180
3
Помогите, пожалуйста. Запускается все, но после закрытия окна курсор вообще не пропадает. Другие ошибки есть в коде?
Код:
require "lib.moonloader"
require "lib.sampfuncs"
samp = require 'samp.events'

local imgui = require 'imgui'

local main_window_state = imgui.ImBool(false)
function imgui.OnDrawFrame()
  if main_window_state.v then
    imgui.SetNextWindowSize(imgui.ImVec2(150, 200), imgui.Cond.FirstUseEver) 
    imgui.Begin('My window', main_window_state)
    imgui.Text('Hello world')
    if imgui.Button('Press me') then
      printStringNow('Button pressed!', 1000)
    end
    imgui.End()
  end
end

function start()
        main_window_state.v = not main_window_state.v
    imgui.Process = main_window_state.v
  end

function main()
while not isSampAvailable() do wait(0) end
    while sampGetCurrentServerName() == 'SA-MP' do wait(0) end
sampAddChatMessage('Helper: Скрипт загружен.', 0xFFFFFF)
sampRegisterChatCommand('drugs', start)
end
 
1,417
1,032
Помогите, пожалуйста. Запускается все, но после закрытия окна курсор вообще не пропадает. Другие ошибки есть в коде?
Код:
require "lib.moonloader"
require "lib.sampfuncs"
samp = require 'samp.events'

local imgui = require 'imgui'

local main_window_state = imgui.ImBool(false)
function imgui.OnDrawFrame()
  if main_window_state.v then
    imgui.SetNextWindowSize(imgui.ImVec2(150, 200), imgui.Cond.FirstUseEver)
    imgui.Begin('My window', main_window_state)
    imgui.Text('Hello world')
    if imgui.Button('Press me') then
      printStringNow('Button pressed!', 1000)
    end
    imgui.End()
  end
end

function start()
        main_window_state.v = not main_window_state.v
    imgui.Process = main_window_state.v
  end

function main()
while not isSampAvailable() do wait(0) end
    while sampGetCurrentServerName() == 'SA-MP' do wait(0) end
sampAddChatMessage('Helper: Скрипт загружен.', 0xFFFFFF)
sampRegisterChatCommand('drugs', start)
end
Lua:
require "lib.moonloader"
require "lib.sampfuncs"
samp = require 'samp.events'

local imgui = require 'imgui'

local main_window_state = imgui.ImBool(false)
function imgui.OnDrawFrame()
  if main_window_state.v then
    imgui.SetNextWindowSize(imgui.ImVec2(150, 200), imgui.Cond.FirstUseEver)
    imgui.Begin('My window', main_window_state)
    imgui.Text('Hello world')
    if imgui.Button('Press me') then
      printStringNow('Button pressed!', 1000)
    end
    imgui.End()
  end
end

function main()
    while not isSampAvailable() do wait(0) end
        while sampGetCurrentServerName() == 'SA-MP' do wait(0) end
    sampAddChatMessage('Helper: Скрипт загружен.', 0xFFFFFF)
    sampRegisterChatCommand('drugs', start)
    while true do wait(0)
        imgui.Process = main_window_state.v
    end
end

function start()
    main_window_state.v = not main_window_state.v
end
 
  • Нравится
Реакции: Jason2222