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

deleted-user-139653

Гость
 

MLycoris

На вид оружие массового семяизвержения
Проверенный
1,993
2,186
могу такой пример дать, не знаю насколько он правильный, но вроде рабоает
Следи, чтоб на 31 строке false был
Lua:
local imgui = require 'mimgui'
local faicons = require('fAwesome6')

local WinState = imgui.new.bool(true)

imgui.OnFrame(function() return WinState[0] end, function()
    imgui.SetNextWindowPos(imgui.ImVec2(500,500), imgui.Cond.Always, imgui.ImVec2(0.5, 0.5))
    imgui.SetNextWindowSize(imgui.ImVec2(500,500), imgui.Cond.Always)
    imgui.Begin('##Window', WinState)
    imgui.PushFont(one)
    imgui.Text(faicons('user')..'Test 1')
    imgui.Button(faicons('user')..'Test 1')
    imgui.PopFont()
    imgui.Separator()
    imgui.PushFont(two)
    imgui.Button(faicons('user')..'Test 2')
    imgui.Text(faicons('user')..'Test 2')
    imgui.PopFont()
    imgui.End()
end)

function main()
    sampRegisterChatCommand('testt', function()
        WinState[0] = not WinState[0]
    end) wait(-1)
end

imgui.OnInitialize(function()
    imgui.GetIO().IniFilename = nil
    local config = imgui.ImFontConfig()
    config.MergeMode = false
    config.PixelSnapH = true
    local iconRanges = imgui.new.ImWchar[3](faicons.min_range, faicons.max_range, 0)
    one = imgui.GetIO().Fonts:AddFontFromMemoryCompressedBase85TTF(faicons.get_font_data_base85('solid'), 12, config, iconRanges) -- solid - тип иконок, так же есть thin, regular, light и duotone
    two = imgui.GetIO().Fonts:AddFontFromMemoryCompressedBase85TTF(faicons.get_font_data_base85('solid'), 24, config, iconRanges) -- solid - тип иконок, так же есть thin, regular, light и duotone
end)

1690107628126.png
 
  • Влюблен
Реакции: Julimba

Julimba

Участник
108
10
WSiUU.png

иконка с fawesome6 вообще пропадает
 

MLycoris

На вид оружие массового семяизвержения
Проверенный
1,993
2,186
Как проверить, открыт ли диалог? А если диалог открыт, сразу нажать ENTER?
Lua:
    while true do wait(0)
        if mainIni.config.parcela then
            setGameKeyState(11, 255)
setGameKeyState(15, 255)
            wait(10)
   sampSendDialogResponse(sampGetCurrentDialogId(), 1, 0, nil)
            wait(0)
        end
    end
end
Я хочу сделать галочку здесь для открытия диалога.
Lua:
if sampIsDialogActive() then -- если самп диалог открыт, то выполняется след код
    sampCloseCurrentDialogWithButton(1) -- 1 left button, 0 right button
end
 

tsunamiqq

Участник
433
17
Как сделать кнопку в диалоговом окне, у меня есть onShowDialog и return, в return'e мне нужно сделать кнопку
Lua:
hook.onShowDialog(id, style, title, b1, b2, text)

        return {id, style, title, b1, b2, text.. "  \n- 123: {00FF00}$"..tostring(statbizWeek).."\n-123:{00FF00}$"..tostring(statbizDay).."\n- 123: {00FF00}$"..tostring(sum).."\n- {FF0000}Обновить список(Это должно быть кнопкой)"}
актуал
 

ChаtGPT

Активный
371
93
Есть вот такая функция, она красит и центрирует текст по колонке, однако очень криво центрирует русский текст. Как решить проблему?
Mimgui

Код:
function imgui.CenterTextColoredRGB(text)
    --imgui.SetCursorPosX(imgui.GetWindowSize().x / 2 - imgui.CalcTextSize(text).x / 2) -- Центрирование текста по окну
    imgui.SetCursorPosX( ( imgui.GetColumnOffset() + ( imgui.GetColumnWidth() / 2 ) ) - imgui.CalcTextSize( text ).x / 2 ) -- Центрирование текста по колонке
    imgui.TextColoredRGB(text)
end

function imgui.TextColoredRGB(text)
    local style = imgui.GetStyle()
    local colors = style.Colors
    local col = imgui.Col
 
    local designText = function(text__)
        local pos = imgui.GetCursorPos()
        if sampGetChatDisplayMode() == 2 then
            for i = 1, 1 --[[Степень тени]] do
                imgui.SetCursorPos(imgui.ImVec2(pos.x + i, pos.y))
                imgui.TextColored(imgui.ImVec4(0, 0, 0, 1), text__) -- shadow
                imgui.SetCursorPos(imgui.ImVec2(pos.x - i, pos.y))
                imgui.TextColored(imgui.ImVec4(0, 0, 0, 1), text__) -- shadow
                imgui.SetCursorPos(imgui.ImVec2(pos.x, pos.y + i))
                imgui.TextColored(imgui.ImVec4(0, 0, 0, 1), text__) -- shadow
                imgui.SetCursorPos(imgui.ImVec2(pos.x, pos.y - i))
                imgui.TextColored(imgui.ImVec4(0, 0, 0, 1), text__) -- shadow
            end
        end
        imgui.SetCursorPos(pos)
    end
 
 
 
    local text = text:gsub('{(%x%x%x%x%x%x)}', '{%1FF}')

    local color = colors[col.Text]
    local start = 1
    local a, b = text:find('{........}', start)
 
    while a do
        local t = text:sub(start, a - 1)
        if #t > 0 then
            designText(t)
            imgui.TextColored(color, t)
            imgui.SameLine(nil, 0)
        end

        local clr = text:sub(a + 1, b - 1)
        if clr:upper() == 'STANDART' then color = colors[col.Text]
        else
            clr = tonumber(clr, 16)
            if clr then
                local r = bit.band(bit.rshift(clr, 24), 0xFF)
                local g = bit.band(bit.rshift(clr, 16), 0xFF)
                local b = bit.band(bit.rshift(clr, 8), 0xFF)
                local a = bit.band(clr, 0xFF)
                color = imgui.ImVec4(r / 255, g / 255, b / 255, a / 255)
            end
        end

        start = b + 1
        a, b = text:find('{........}', start)
    end
    imgui.NewLine()
    if #text >= start then
        imgui.SameLine(nil, 0)
        designText(text:sub(start))
        imgui.TextColored(color, text:sub(start))
    end
end

Код взят из mimgui chat
Актуально))
не понимаю в каком смысле "играться с кодировкой"
Функция криво центрирует текст на любом языке в колонке если текст имеет цвет
 
Последнее редактирование:
D

deleted-user-139653

Гость
возможно ли нажать клавишу ALT в АФК не выходя из афк на определенное время, игрок находиться в афк через эту функцию
Lua:
function sampev.onSendPlayerSync(data)
    return false
end
Пробовал через эти функции setGameKeyState и setVirtualKeyDown, но на отрез не хочет нажимать кнопку
Также пробовал ставить script_properties('work-in-pause'), не помогает.
Может знает кто?) Буду благодарен.
 

whyega52

Гений, миллионер, плейбой, долбаеб
Модератор
2,782
2,609
возможно ли нажать клавишу ALT в АФК не выходя из афк на определенное время, игрок находиться в афк через эту функцию
Lua:
function sampev.onSendPlayerSync(data)
    return false
end
Пробовал через эти функции setGameKeyState и setVirtualKeyDown, но на отрез не хочет нажимать кнопку
Также пробовал ставить script_properties('work-in-pause'), не помогает.
Может знает кто?) Буду благодарен.
Нет, кнопка отправляется через плеер синхру
 
  • Грустно
Реакции: deleted-user-139653

Andrinall

Известный
702
518
Актуально))
не понимаю в каком смысле "играться с кодировкой"
Функция криво центрирует текст на любом языке в колонке если текст имеет цвет
Пробни так, скорее всего криво центрует из-за "цветовых тегов" в тексте, которые он тоже считает за символы
Lua:
function imgui.CenterTextColoredRGB(text)
    --imgui.SetCursorPosX(imgui.GetWindowSize().x / 2 - imgui.CalcTextSize(text).x / 2) -- Центрирование текста по окну
    imgui.SetCursorPosX( ( imgui.GetColumnOffset() + ( imgui.GetColumnWidth() / 2 ) ) - imgui.CalcTextSize( text:gsub("{%x+}", "") ).x / 2 ) -- Центрирование текста по колонке
    imgui.TextColoredRGB(text)
end
 

ChаtGPT

Активный
371
93
Пробни так, скорее всего криво центрует из-за "цветовых тегов" в тексте, которые он тоже считает за символы
Lua:
function imgui.CenterTextColoredRGB(text)
    --imgui.SetCursorPosX(imgui.GetWindowSize().x / 2 - imgui.CalcTextSize(text).x / 2) -- Центрирование текста по окну
    imgui.SetCursorPosX( ( imgui.GetColumnOffset() + ( imgui.GetColumnWidth() / 2 ) ) - imgui.CalcTextSize( text:gsub("{%x+}", "") ).x / 2 ) -- Центрирование текста по колонке
    imgui.TextColoredRGB(text)
end
Спасибо, проблема решена)

Почему при вызове функции в sampev.onSetPlayerColor, цвет игрока изменяется? Функция вызывается только тогда, когда цвет игрока изменяется. При подключении к серверу, до момента регистрации/авторизации, у игрока уже стоит какой-то цвет, фиолетовый, синий, серый и какой-либо ещё. Мне же нужно вызывать функцию проверки в этой функции, при изменении цвета игрока, но цвет просто замораживается, если принтом вывести цвет, он будет такой, какой нужно.

Код:
function sampev.onSetPlayerColor(playerID, color)
    
    local result, id = sampGetPlayerIdByCharHandle(PLAYER_PED)
    if id == playerID then
        check()
        PlayerColor = color
  
        if PlayerColor then -- Проверка что бы не крашнул скрипт, если PlayerColor будет пуста
            playerHEXcolor = bit.tohex(bit.rshift(PlayerColor, 8), 6) --PlayerColor - записывается цвет игрока
            --print(p_color)
        end
    end
end
function checkFaction() --Вызывая функцию узнаём название группировки в которой игрок
    checkFaction1 = true -- скрываем сообщения
    checkFaction2 = true -- Скрываем диалоговое окно и записываем название группировки

    sampSendChat('/faction_info')
end

function sampev.onShowDialog(did, style, title, b1, b2, text)
    if checkFaction2 == true then
        checkFaction1 = false
        checkFaction2 = false
        if did == 32766 then
            --local group text:match('Введите {......}5 {......}символов'
            local cleanedText = text:gsub('{%x+}', '') -- удаление символов цвета
            groupName = cleanedText:match("Группировка:%s*([^%c]+)")
            return false
        end 
    end
end

function sampev.onServerMessage(color, text) --{......} .-любой символ (любой цвет текста)
    if checkFaction1 == true then
        if text:find('Вы не состоите в группировке') then
            --sampAddChatMessage('1',-1)
            groupName = 'Одиночка'
            --print('return false: ','Вы не состоите в группировке', text)
            checkFaction1 = false
            return false
        end
        if text:find('Список участников группировки в сети:') then
            --sampAddChatMessage('2',-1)
            --print('return false: ','Список участников группировки в сети:', text)
            --checkFaction1 = false
            return false
        
        elseif text:find('%[(.+)%](.+)') then
            --sampAddChatMessage('3',-1)
            --print('return false: ','%[(.+)%](.+)', text)
            checkFaction1 = false
            return false
        end
    end
end
 
Последнее редактирование:

NotFound

Участник
77
23
Приведите пример кода с imgui drag and drop. Можно ли это реализовать с imgui.InputTex и тд?
42392543-8140fc1e-8153-11e8-8f15-6c4da5521508.gif
 

chapo

чопа сребдс // @moujeek
Модератор
8,868
11,575
Приведите пример кода с imgui drag and drop. Можно ли это реализовать с imgui.InputTex и тд?
42392543-8140fc1e-8153-11e8-8f15-6c4da5521508.gif
 
  • Нравится
Реакции: NotFound