Исходник Perfect Binder или как стать гуру imgui hotkey

Статус
В этой теме нельзя размещать новые ответы.

AnWu

Известный
Автор темы
Всефорумный модератор
4,777
5,400
Привет задроты, хочу показать вам свою очень сырую разработку, но т.к. доводить до ума её капец как долго - хочу выложить как пример сейчас.

Показываю один раз и с минимум информации:
upload_2018-6-21_19-18-56.png


Всё рабочее что на скрине, тем кому это нужно - придется попотеть чтобы всё понять, но если понять - потеть больше не придется.

Код:
Lua:
script_name("Perfect Binder | Lua")
script_author("DonHomka")
script_description("ImGui Binder on lua")

local imgui = require 'imgui'
local vkeys = require 'vkeys'
local rkeys = require 'rkeys'
local encoding = require 'encoding'
local hk = require 'lib.imcustom.hotkey'
local wm = require 'lib.windows.message'
local gk = require 'game.keys'

encoding.default = 'CP1251'
u8 = encoding.UTF8
hk._SETTINGS.noKeysMessage = u8("Нет")

local file = getWorkingDirectory() .. "\\config\\binds.bind"
local tEditData = {
   id = -1,
   inputActive = false
}
local bMainWindow = imgui.ImBool(false)
local sInputEdit = imgui.ImBuffer(128)
local bIsEnterEdit = imgui.ImBool(false)

local tBindList = {}
if doesFileExist(file) then
   local f = io.open(file, "r")
   if f then
      tBindList = decodeJson(f:read("a*"))
      f:close()
   end
else
   tBindList = {
      [1] = {
         text = "/r [Взвод №1]: ",
         v = {vkeys.VK_3}
      },
      [2] = {
         text = "/rb ",
         v = {vkeys.VK_4}
      },
      [3] = {
         text = "/time[enter]",
         v = {vkeys.VK_MENU, vkeys.VK_6}
      },
      [4] = {
         text = "/clist 30[enter]",
         v = {vkeys.VK_MENU, vkeys.VK_2}
      },
      [5] = {
         text = "/clist 7[enter]",
         v = {vkeys.VK_F2}
      },
      [6] = {
         text = "/clist ",
         v = {vkeys.VK_MENU, vkeys.VK_4}
      },
      [7] = {
         text = "/lock[enter]",
         v = {vkeys.VK_1}
      },
      [8] = {
         text = "/members[enter]",
         v = {vkeys.VK_MENU, vkeys.VK_3}
      }
   }
end

function main()
if not isSampLoaded() then
return
end
while not isSampAvailable() do
wait(0)
end

sampRegisterChatCommand("bind", function ()
bMainWindow.v = not bMainWindow.v
   end)
   rkeys.registerHotKey({vkeys.VK_F1}, true, function ()
      bMainWindow.v = not bMainWindow.v
   end)

   for k, v in pairs(tBindList) do
      rkeys.registerHotKey(v.v, true, onHotKey)
   end

while true do
wait(0)
      imgui.Process = bMainWindow.v
end
end


function apply_custom_style()
   local style = imgui.GetStyle()
   local colors = style.Colors
   local clr = imgui.Col
   local ImVec4 = imgui.ImVec4
   style.WindowRounding = 1.5
   style.WindowTitleAlign = imgui.ImVec2(0.5, 0.5)
   style.ChildWindowRounding = 1.5
   style.FrameRounding = 1.0
   style.ItemSpacing = imgui.ImVec2(5.0, 4.0)
   style.ScrollbarSize = 13.0
   style.ScrollbarRounding = 0
   style.GrabMinSize = 8.0
   style.GrabRounding = 1.0
   -- style.Alpha =
   style.WindowPadding = imgui.ImVec2(4.0, 4.0)
   -- style.WindowMinSize =
   style.FramePadding = imgui.ImVec2(2.5, 3.5)
   -- style.ItemInnerSpacing =
   -- style.TouchExtraPadding =
   -- style.IndentSpacing =
   -- style.ColumnsMinSpacing = ?
   style.ButtonTextAlign = imgui.ImVec2(0.02, 0.4)
   -- style.DisplayWindowPadding =
   -- style.DisplaySafeAreaPadding =
   -- style.AntiAliasedLines =
   -- style.AntiAliasedShapes =
   -- style.CurveTessellationTol =
   colors[clr.Text] = ImVec4(1.00, 1.00, 1.00, 1.00)
   colors[clr.TextDisabled] = ImVec4(0.50, 0.50, 0.50, 1.00)
   colors[clr.WindowBg] = imgui.ImColor(0, 0, 0, 227):GetVec4()
   colors[clr.ChildWindowBg] = ImVec4(1.00, 1.00, 1.00, 0.00)
   colors[clr.PopupBg] = ImVec4(0.08, 0.08, 0.08, 0.94)
   colors[clr.ComboBg] = colors[clr.PopupBg]
   colors[clr.Border] = imgui.ImColor(40, 142, 110, 90):GetVec4()
   colors[clr.BorderShadow] = ImVec4(0.00, 0.00, 0.00, 0.00)
   colors[clr.FrameBg] = imgui.ImColor(40, 142, 110, 113):GetVec4()
   colors[clr.FrameBgHovered] = imgui.ImColor(40, 142, 110, 164):GetVec4()
   colors[clr.FrameBgActive] = imgui.ImColor(40, 142, 110, 255):GetVec4()
   colors[clr.TitleBg] = imgui.ImColor(40, 142, 110, 236):GetVec4()
   colors[clr.TitleBgActive] = imgui.ImColor(40, 142, 110, 236):GetVec4()
   colors[clr.TitleBgCollapsed] = ImVec4(0.05, 0.05, 0.05, 0.79)
   colors[clr.MenuBarBg] = ImVec4(0.14, 0.14, 0.14, 1.00)
   colors[clr.ScrollbarBg] = ImVec4(0.02, 0.02, 0.02, 0.53)
   colors[clr.ScrollbarGrab] = imgui.ImColor(40, 142, 110, 236):GetVec4()
   colors[clr.ScrollbarGrabHovered] = ImVec4(0.41, 0.41, 0.41, 1.00)
   colors[clr.ScrollbarGrabActive] = ImVec4(0.51, 0.51, 0.51, 1.00)
   colors[clr.CheckMark] = ImVec4(1.00, 1.00, 1.00, 1.00)
   colors[clr.SliderGrab] = ImVec4(0.28, 0.28, 0.28, 1.00)
   colors[clr.SliderGrabActive] = ImVec4(0.35, 0.35, 0.35, 1.00)
   colors[clr.Button] = imgui.ImColor(40, 142, 110, 255):GetVec4()
   colors[clr.ButtonHovered] = imgui.ImColor(35, 121, 93, 174):GetVec4()
   colors[clr.ButtonActive] = imgui.ImColor(44, 154, 119, 255):GetVec4()
   colors[clr.Header] = imgui.ImColor(40, 142, 110, 255):GetVec4()
   colors[clr.HeaderHovered] = ImVec4(0.34, 0.34, 0.35, 0.89)
   colors[clr.HeaderActive] = ImVec4(0.12, 0.12, 0.12, 0.94)
   colors[clr.Separator] = colors[clr.Border]
   colors[clr.SeparatorHovered] = ImVec4(0.26, 0.59, 0.98, 0.78)
   colors[clr.SeparatorActive] = ImVec4(0.26, 0.59, 0.98, 1.00)
   colors[clr.ResizeGrip] = imgui.ImColor(40, 142, 110, 255):GetVec4()
   colors[clr.ResizeGripHovered] = imgui.ImColor(35, 121, 93, 174):GetVec4()
   colors[clr.ResizeGripActive] = imgui.ImColor(44, 154, 119, 255):GetVec4()
   colors[clr.CloseButton] = ImVec4(0.41, 0.41, 0.41, 0.50)
   colors[clr.CloseButtonHovered] = ImVec4(0.98, 0.39, 0.36, 1.00)
   colors[clr.CloseButtonActive] = ImVec4(0.98, 0.39, 0.36, 1.00)
   colors[clr.PlotLines] = ImVec4(0.61, 0.61, 0.61, 1.00)
   colors[clr.PlotLinesHovered] = ImVec4(1.00, 0.43, 0.35, 1.00)
   colors[clr.PlotHistogram] = ImVec4(0.90, 0.70, 0.00, 1.00)
   colors[clr.PlotHistogramHovered] = ImVec4(1.00, 0.60, 0.00, 1.00)
   colors[clr.TextSelectedBg] = ImVec4(0.26, 0.59, 0.98, 0.35)
   colors[clr.ModalWindowDarkening] = ImVec4(0.10, 0.10, 0.10, 0.35)
end

apply_custom_style()
function imgui.OnDrawFrame()
   local iScreenWidth, iScreenHeight = getScreenResolution()
   local tLastKeys = {}

imgui.SetNextWindowPos(imgui.ImVec2(iScreenWidth / 2, iScreenHeight / 2), imgui.Cond.FirstUseEver, imgui.ImVec2(0.5, 0.5))
imgui.SetNextWindowSize(imgui.ImVec2(800, 500), imgui.Cond.FirstUseEver)

imgui.Begin(u8("Perfect Binder | Главное меню##main"), bMainWindow, imgui.WindowFlags.NoCollapse + imgui.WindowFlags.NoResize)
   imgui.BeginChild("##bindlist", imgui.ImVec2(795, 442))
   for k, v in ipairs(tBindList) do
      if hk.HotKey("##HK" .. k, v, tLastKeys, 100) then
         if not rkeys.isHotKeyDefined(v.v) then
            if rkeys.isHotKeyDefined(tLastKeys.v) then
               rkeys.unRegisterHotKey(tLastKeys.v)
            end
            rkeys.registerHotKey(v.v, true, onHotKey)
         end
      end
      imgui.SameLine()
      if tEditData.id ~= k then
         local sText = v.text:gsub("%[enter%]$", "")
         imgui.BeginChild("##cliclzone" .. k, imgui.ImVec2(500, 21))
         imgui.AlignTextToFramePadding()
         if sText:len() > 0 then
            imgui.Text(u8(sText))
         else
            imgui.TextDisabled(u8("Пустое сообщение ..."))
         end
         imgui.EndChild()
         if imgui.IsItemClicked() then
            sInputEdit.v = sText:len() > 0 and u8(sText) or ""
            bIsEnterEdit.v = string.match(v.text, "(.)%[enter%]$") ~= nil
            tEditData.id = k
            tEditData.inputActve = true
         end
      else
         imgui.PushAllowKeyboardFocus(false)
         imgui.PushItemWidth(500)
         local save = imgui.InputText("##Edit" .. k, sInputEdit, imgui.InputTextFlags.EnterReturnsTrue)
         imgui.PopItemWidth()
         imgui.PopAllowKeyboardFocus()
         imgui.SameLine()
         imgui.Checkbox(u8("Ввод") .. "##editCH" .. k, bIsEnterEdit)
         if save then
            tBindList[tEditData.id].text = u8:decode(sInputEdit.v) .. (bIsEnterEdit.v and "[enter]" or "")
            tEditData.id = -1
         end
         if tEditData.inputActve then
            tEditData.inputActve = false
            imgui.SetKeyboardFocusHere(-1)
         end
      end
   end
   imgui.EndChild()

   imgui.Separator()

   if imgui.Button(u8"Добавить клавишу") then
      tBindList[#tBindList + 1] = {text = "", v = {}}
   end

imgui.End()
end

function rkeys.onHotKey(id, keys)
   if sampIsChatInputActive() or sampIsDialogActive() or isSampfuncsConsoleActive() then
      return false
   end
end

function onHotKey(id, keys)
   local sKeys = tostring(table.concat(keys, " "))
   for k, v in pairs(tBindList) do
      if sKeys == tostring(table.concat(v.v, " ")) then
         if tostring(v.text):len() > 0 then
            local bIsEnter = string.match(v.text, "(.)%[enter%]$") ~= nil
            if bIsEnter then
               sampSendChat(v.text:gsub("%[enter%]$", ""))
            else
               sampSetChatInputText(v.text)
               sampSetChatInputEnabled(true)
            end
         end
      end
   end
end

function onScriptTerminate(scr)
   if scr == script.this then
      if doesFileExist(file) then
         os.remove(file)
      end
      local f = io.open(file, "w")
      if f then
         f:write(encodeJson(tBindList))
         f:close()
      end
   end
end

addEventHandler("onWindowMessage", function (msg, wparam, lparam)
   if msg == wm.WM_KEYDOWN or msg == wm.WM_SYSKEYDOWN then
      if tEditData.id > -1 then
         if wparam == vkeys.VK_ESCAPE then
            tEditData.id = -1
            consumeWindowMessage(true, true)
         elseif wparam == vkeys.VK_TAB then
            bIsEnterEdit.v = not bIsEnterEdit.v
            consumeWindowMessage(true, true)
         end
      end
   end
end)

А так же прикрепляю готовый файл.

Кстати этот биндер отправляет сообщения на обработку в чат, а значит команды /fpslimit, /q, /pagesize будут работать (проверял).

Установка файлом: переместить файл в папку moonloader

Окно: на F1

Удачки. Для работы нужны:
[Module] ImGui Custom [v 1.1.5](https://blast.hk/threads/22080/)
Исходник - Софт - [Module] RKeys / Работаем с клавишами [v 1.0.7](https://blast.hk/threads/22145/)

AHK сосет

ПС: Есть проблемы с самим модулем хоткеев, но это пока не могу решить. Проблемы не явны и очень редкие, не буду вдаваться в подробности
 

Вложения

  • perfect binder.lua
    9.2 KB · Просмотры: 945

Revalto

Известный
532
225
Цитирование: AHK сосёт.
Если ты не смог импортировать ImGUI на AHK, не значит, что AHK хуже LUA. Хотя ImGUI на LUA не ты импортировал. Когда есть готовый сурс, все возможно сделать :D
 

AnWu

Известный
Автор темы
Всефорумный модератор
4,777
5,400
Цитирование: AHK сосёт.
Если ты не смог импортировать ImGUI на AHK, не значит, что AHK хуже LUA. Хотя ImGUI на LUA не ты импортировал. Когда есть готовый сурс, все возможно сделать :D
Это не отменяет того факта что АХК сосет. Почему-то никто на ахк еще не имортнул sampProcessChat().
Ах да, еще ахк дико тупой и медленный.
Если сложить 2 + 2 получится что ахк сосет.
 

maestto

Известный
93
116
если сложить паскаль и немного изменения то получится ахк.
Это не отменяет того факта что АХК сосет. Почему-то никто на ахк еще не имортнул sampProcessChat().
Ах да, еще ахк дико тупой и медленный.
Если сложить 2 + 2 получится что ахк сосет.
Плюсую, но АХК лично для меня послужило неким началом, именно благодаря ему я узнал что такое логические операторы и тд. Думаю он был началом для многих. ЛУА конечно лучше, но не стоит критиковать и сравнивать с ним АХК.
 
  • Нравится
Реакции: 777qwerty777, AnWu и #Rin

Aniki

🐰
Администратор
1,229
1,564
и где ж ты был раньше, когда я писал привязку к клавишам на ммедитор?
4C-8GQIlZbM.jpg
 
  • Нравится
Реакции: Skelmer и AnWu

Revalto

Известный
532
225
Ну критиковать AHK, к тому что он не лучше работает на GTA:SA это бред. Ведь только глупые люди не знают, что AHK изначально не был предназначен для GTA:SA. Так что я не вижу смысла, критиковать здесь AHK в сторону говна...
 

#Rin

Известный
Всефорумный модератор
1,214
1,043
импортировать ImGUI на AHK
upload_2018-6-22_3-4-15.png



roflebalo.png


Это еще я большую часть выполнил на стороне C++.
А то у меня в архивах есть такие сложные хуетени, что там даже WndProc и хуки на Reset, Present выполняются в ахк.
upload_2018-6-22_3-9-32.png

3 часа ночи, делать было нечего, а уже че-то да получается :D
upload_2018-6-22_4-19-18.png
 
Последнее редактирование:

Frapsy

Известный
Проверенный
393
227
Не качал и не проверял, по этому спрошу: одну строку на кнопку забиндить можно или несколько?
 

AnWu

Известный
Автор темы
Всефорумный модератор
4,777
5,400
Не качал и не проверял, по этому спрошу: одну строку на кнопку забиндить можно или несколько?
этож пример. пока только одну.

комментаторам выше хочу сказать что уровень серьёзности у вас повышенный. для меня ахк тоже был началом пути и у меня даж свой биндер на ахк есть. сравнивать языки бесполезно, ибо ахк сосет)))
 

Frapsy

Известный
Проверенный
393
227
этож пример. пока только одну.
Окей, спасибо :)
Плюсую, АХК предназначен для выполнения каких либо простеньких действий при работе с клавой, облегчить к примеру ввод шаблонных сообщений и подобного, но никак не для извращений с бедным ахк по типу SAMP UDF и как выше показали imgui ahk o_o
 

for (;;)

Участник
71
31
Посмотреть вложение 15194


Посмотреть вложение 15191

Это еще я большую часть выполнил на стороне C++.
А то у меня в архивах есть такие сложные хуетени, что там даже WndProc и хуки на Reset, Present выполняются в ахк.

3 часа ночи, делать было нечего, а уже че-то да получается :D
Посмотреть вложение 15197
И почему все пролистали молча данный революционный пост?
 

#Rin

Известный
Всефорумный модератор
1,214
1,043
И почему все пролистали молча данный революционный пост?
Популярность AHK for SAMP была высока до выхода MoonLoader'а.
Ведь lua удобнее клео и проще ахк, так как все функции сделаны и готовы к использованию FYP'ом и его командой.
И ImGui для луа выполнена в виде .dll.

Если нужны сурсы имгуя для ахк могу кинуть, но учти что там дохера чё нужно сделать, а если захочется рисовать имгуй в той же ГТА, нужно в длл написать хук на reset и present и CreateRemoteTheard по адресу который передается функцией SetRenderFunc. А в ахк инжектить длл в гта (это изи), путем не сложных математический операций вычислить адреса функций в чужом процессе, и вызвать эти функции по адресу тоже через удаленное создание потоков, но тут ещё нужно через writeProcessMemory записать все параметры необходимые функции, а перед этим нужно выделить память, а после нужно позаботиться по освобождению, иначе произойдет утечка памяти.
Но можно ничего не менять в ахк классе, если ахк будет тоже заинжекнута в процесс.
 

Ni4ellas

Известный
114
7
короче установил всё как надо но работать отказывается
 

Revalto

Известный
532
225
Окей, спасибо :)

Плюсую, АХК предназначен для выполнения каких либо простеньких действий при работе с клавой, облегчить к примеру ввод шаблонных сообщений и подобного, но никак не для извращений с бедным ахк по типу SAMP UDF и как выше показали imgui ahk o_o
Лол, тебе выше даже сказали, что LUA работает так же на либах как и AHK с SAMPUDF xD
 
Статус
В этой теме нельзя размещать новые ответы.