HOTKEY_MANAGER_USEONSELF = 1 HOTKEY_MANAGER_USEONTARGET = 2 HOTKEY_MANAGER_USEWITH = 3 HotkeyColors = { text = '#888888', textAutoSend = '#FFFFFF', itemUse = '#8888FF', itemUseSelf = '#00FF00', itemUseTarget = '#FF0000', itemUseWith = '#CC0000', } hotkeysManagerLoaded = false hotkeysWindow = nil hotkeysButton = nil currentHotkeysList = nil hotkeyLabelSelectedOnList = nil currentItemPreview = nil itemWidget = nil addHotkeyButton = nil removeHotkeyButton = nil hotkeyText = nil hotKeyTextLabel = nil sendAutomatically = nil selectObjectButton = nil clearObjectButton = nil useOnSelf = nil useOnTarget = nil useWith = nil hotkeyList = {} -- public functions function init() hotkeysWindow = g_ui.displayUI('hotkeys_manager.otui') local hotkeyListPanel = hotkeysWindow:getChildById('currentHotkeys') hotkeysWindow:setVisible(false) hotkeysButton = TopMenu.addLeftGameButton('hotkeysButton', tr('Hotkeys') .. ' (Ctrl+K)', '/game_hotkeys/icon.png', toggle) g_keyboard.bindKeyDown('Ctrl+K', toggle) g_keyboard.bindKeyPress('Down', function() hotkeyListPanel:focusNextChild(KeyboardFocusReason) end, hotkeysWindow) g_keyboard.bindKeyPress('Up', function() hotkeyListPanel:focusPreviousChild(KeyboardFocusReason) end, hotkeysWindow) currentHotkeysList = hotkeysWindow:getChildById('currentHotkeys') currentItemPreview = hotkeysWindow:getChildById('itemPreview') addHotkeyButton = hotkeysWindow:getChildById('addHotkeyButton') removeHotkeyButton = hotkeysWindow:getChildById('removeHotkeyButton') hotkeyText = hotkeysWindow:getChildById('hotkeyText') hotKeyTextLabel = hotkeysWindow:getChildById('hotKeyTextLabel') sendAutomatically = hotkeysWindow:getChildById('sendAutomatically') selectObjectButton = hotkeysWindow:getChildById('selectObjectButton') clearObjectButton = hotkeysWindow:getChildById('clearObjectButton') useOnSelf = hotkeysWindow:getChildById('useOnSelf') useOnTarget = hotkeysWindow:getChildById('useOnTarget') useWith = hotkeysWindow:getChildById('useWith') itemWidget = g_ui.createWidget('UIItem') itemWidget:setVirtual(true) itemWidget:setVisible(false) itemWidget:setFocusable(false) connect(g_game, { onGameEnd = hide }) connect(currentHotkeysList, { onChildFocusChange = function (self, focusedChild) checkSelectedHotkey(focusedChild) end } ) hotkeysManagerLoaded = true load() end function terminate() hotkeysManagerLoaded = false disconnect(g_game, { onGameEnd = hide }) g_keyboard.unbindKeyDown('Ctrl+K') save() for keyCombo,v in pairs(hotkeyList) do g_keyboard.unbindKeyPress(keyCombo) end hotkeyList = {} itemWidget:destroy() hotkeysWindow:destroy() hotkeysButton:destroy() end function load() local hotkeySettings = g_settings.getNode('HotkeysManager') local hasCombos = false if hotkeySettings ~= nil then for i, v in pairs(hotkeySettings) do addKeyCombo(nil, v.keyCombo, v) hasCombos = true end end -- add default F keys combos if not hasCombos then for i=1,12 do addKeyCombo(nil, 'F' .. i) end end end function save() local hotkeySettings = {} for i=1, currentHotkeysList:getChildCount() do local child = currentHotkeysList:getChildByIndex(i) table.insert(hotkeySettings, {keyCombo = child.keyCombo, autoSend = child.autoSend, itemId = child.itemId, useType = child.useType, value = child.value}) end g_settings.setNode('HotkeysManager', hotkeySettings) end function toggle() if hotkeysWindow:isVisible() then hide() else show() end end function show() if g_game.isOnline() then hotkeysWindow:grabKeyboard() hotkeysWindow:show() hotkeysWindow:raise() end end function hide() hotkeysWindow:ungrabKeyboard() hotkeysWindow:hide() end -- private functions function onChooseItemMouseRelease(self, mousePosition, mouseButton) local item = nil if mouseButton == MouseLeftButton then local clickedWidget = modules.game_interface.getRootPanel():recursiveGetChildByPos(mousePosition, false) if clickedWidget then if clickedWidget:getClassName() == 'UIMap' then local tile = clickedWidget:getTile(mousePosition) if tile then local thing = tile:getTopMoveThing() if thing and thing:isItem() then item = thing end end elseif clickedWidget:getClassName() == 'UIItem' and not clickedWidget:isVirtual() then item = clickedWidget:getItem() end end end if item then currentItemPreview:setItemId(item:getId()) hotkeyLabelSelectedOnList.itemId = item:getId() changeUseType(HOTKEY_MANAGER_USEONSELF) checkSelectedHotkey(hotkeyLabelSelectedOnList) show() end g_mouse.restoreCursor() self:ungrabMouse() self:destroy() end function startChooseItem() local mouseGrabberWidget = g_ui.createWidget('UIWidget') mouseGrabberWidget:setVisible(false) mouseGrabberWidget:setFocusable(false) connect(mouseGrabberWidget, { onMouseRelease = onChooseItemMouseRelease }) mouseGrabberWidget:grabMouse() g_mouse.setTargetCursor() hide() end function clearObject() hotkeyLabelSelectedOnList.itemId = nil currentItemPreview:clearItem() changeUseType(HOTKEY_MANAGER_USEONSELF) setSendAutomatically(false) hotkeyLabelSelectedOnList:setText(hotkeyLabelSelectedOnList.keyCombo .. ': ') checkSelectedHotkey(hotkeyLabelSelectedOnList) end function addHotkey() local widget messageBox = g_ui.createWidget('MainWindow', rootWidget) messageBox:grabKeyboard() messageBox:setId('assignWindow') messageBox:setText(tr('Button Assign')) messageBox:setWidth(420) messageBox:setHeight(140) messageBox:setDraggable(false) widget = g_ui.createWidget('Label', messageBox) widget:setText(tr('Please, press the key you wish to add onto your hotkeys manager')) widget:resizeToText() widget:addAnchor(AnchorHorizontalCenter, 'parent', AnchorHorizontalCenter) widget:addAnchor(AnchorTop, 'parent', AnchorTop) widget = g_ui.createWidget('Label', messageBox) widget:setId('comboPreview') widget:setText(tr('Current hotkey to add: %s', 'none')) widget.keyCombo = '' widget:resizeToText() widget:addAnchor(AnchorHorizontalCenter, 'parent', AnchorHorizontalCenter) widget:addAnchor(AnchorTop, 'prev', AnchorBottom) widget:setMarginTop(20) widget = g_ui.createWidget('Button', messageBox) widget:setId('cancelButton') widget:setText(tr('Cancel')) widget:setWidth(64) widget:addAnchor(AnchorBottom, 'parent', AnchorBottom) widget:addAnchor(AnchorRight, 'parent', AnchorRight) widget.onClick = function (self) messageBox = nil self:getParent():destroy() end widget = g_ui.createWidget('Button', messageBox) widget:setId('addButton') widget:setText(tr('Add')) widget:setWidth(64) widget:disable() widget:addAnchor(AnchorBottom, 'cancelButton', AnchorBottom) widget:addAnchor(AnchorRight, 'cancelButton', AnchorLeft) widget:setMarginRight(10) widget.onClick = function (self) messageBox = nil addKeyCombo(self:getParent(), self:getParent():getChildById('comboPreview').keyCombo) end connect(messageBox, { onKeyDown = hotkeyCapture }, true) end function addKeyCombo(messageBox, keyCombo, keySettings) local label = nil if currentHotkeysList:getChildById(keyCombo) == nil then local label = g_ui.createWidget('HotkeyListLabel', currentHotkeysList) label:setId(keyCombo) label:setColor(HotkeyColors.text) label:setText(keyCombo..': ') if keySettings then hotkeyLabelSelectedOnList = label label.keyCombo = keyCombo setSendAutomatically(keySettings.autoSend) label.itemId = keySettings.itemId currentItemPreview:setItemId(keySettings.itemId) changeUseType(tonumber(keySettings.useType)) label.value = keySettings.value else label.keyCombo = keyCombo label.autoSend = false label.itemId = nil label.useType = HOTKEY_MANAGER_USEONSELF label.value = '' end checkSelectedHotkey(label) hotkeyList[keyCombo] = label g_keyboard.bindKeyPress(keyCombo, function () call(keyCombo) end, nil, 350) end if messageBox then messageBox:destroy() messageBox = nil end end function call(keyCombo) if g_game.isOnline() then local hotKey = hotkeyList[keyCombo] if hotKey ~= nil and hotKey.itemId == nil and hotKey.value ~= '' then if hotKey.autoSend then g_game.talk(hotKey.value) else modules.game_console.setTextEditText(hotKey.value) end elseif hotKey.itemId ~= nil then if hotKey.useType == HOTKEY_MANAGER_USEONSELF then g_game.useInventoryItemWith(hotKey.itemId, g_game.getLocalPlayer()) elseif hotKey.useType == HOTKEY_MANAGER_USEONTARGET then local attackingCreature = g_game.getAttackingCreature() if attackingCreature then g_game.useInventoryItemWith(hotKey.itemId, attackingCreature) end elseif hotKey.useType == HOTKEY_MANAGER_USEWITH then itemWidget:setItemId(hotKey.itemId) modules.game_interface.startUseWith(itemWidget:getItem()) end end end end function checkSelectedHotkey(focused) if not focused then return end if hotkeysManagerLoaded then hotkeyLabelSelectedOnList = focused if hotkeyLabelSelectedOnList ~= nil then removeHotkeyButton:enable() if hotkeyLabelSelectedOnList.itemId == nil then hotkeyText:enable() hotkeyText:focus() hotKeyTextLabel:enable() hotkeyText:setText(hotkeyLabelSelectedOnList.value) if hotkeyLabelSelectedOnList.value ~= '' then sendAutomatically:setChecked(hotkeyLabelSelectedOnList.autoSend) sendAutomatically:enable() else sendAutomatically:disable() end selectObjectButton:enable() clearObjectButton:disable() currentItemPreview:setItemId(0) else hotkeyText:clearText() hotkeyText:disable() hotKeyTextLabel:disable() sendAutomatically:disable() selectObjectButton:disable() clearObjectButton:enable() currentItemPreview:setItemId(hotkeyLabelSelectedOnList.itemId) end changeUseType(hotkeyLabelSelectedOnList.useType) else hotkeyText:clearText() removeHotkeyButton:disable() hotkeyText:disable() sendAutomatically:disable() sendAutomatically:setChecked(false) currentItemPreview:setItemId(0) selectObjectButton:disable() clearObjectButton:disable() useOnSelf:disable() useOnTarget:disable() useWith:disable() useOnSelf:setChecked(false) useOnTarget:setChecked(false) useWith:setChecked(false) end end end function changeUseType(useType, checked) if checked == nil or checked then hotkeyLabelSelectedOnList.useType = useType if hotkeyLabelSelectedOnList.itemId ~= nil and currentItemPreview:getItem():isMultiUse() then useOnSelf:enable() useOnTarget:enable() useWith:enable() if useType == HOTKEY_MANAGER_USEONSELF then hotkeyLabelSelectedOnList:setText(tr('%s: (use object on yourself)', hotkeyLabelSelectedOnList.keyCombo)) hotkeyLabelSelectedOnList:setColor(HotkeyColors.itemUseSelf) useOnSelf:setChecked(true) useOnTarget:setChecked(false) useWith:setChecked(false) elseif useType == HOTKEY_MANAGER_USEONTARGET then hotkeyLabelSelectedOnList:setText(tr('%s: (use object on target)', hotkeyLabelSelectedOnList.keyCombo)) hotkeyLabelSelectedOnList:setColor(HotkeyColors.itemUseTarget) useOnSelf:setChecked(false) useOnTarget:setChecked(true) useWith:setChecked(false) elseif useType == HOTKEY_MANAGER_USEWITH then hotkeyLabelSelectedOnList:setText(tr('%s: (use object with crosshair)', hotkeyLabelSelectedOnList.keyCombo)) hotkeyLabelSelectedOnList:setColor(HotkeyColors.itemUseWith) useOnSelf:setChecked(false) useOnTarget:setChecked(false) useWith:setChecked(true) end elseif hotkeyLabelSelectedOnList.itemId ~= nil and not currentItemPreview:getItem():isMultiUse() then useOnSelf:disable() useOnTarget:disable() useWith:disable() hotkeyLabelSelectedOnList:setText(tr('%s: (use object)', hotkeyLabelSelectedOnList.keyCombo)) hotkeyLabelSelectedOnList:setColor(HotkeyColors.itemUse) useOnSelf:setChecked(false) useOnTarget:setChecked(false) useWith:setChecked(false) else useOnSelf:disable() useOnTarget:disable() useWith:disable() useOnSelf:setChecked(false) useOnTarget:setChecked(false) useWith:setChecked(false) end end end function removeHotkey() if hotkeyLabelSelectedOnList ~= nil then hotkeyList[hotkeyLabelSelectedOnList.keyCombo] = nil g_keyboard.unbindKeyPress(hotkeyLabelSelectedOnList.keyCombo) hotkeyLabelSelectedOnList:destroy() end end function onHotkeyTextChange(id, value) if hotkeyLabelSelectedOnList ~= nil and hotkeyLabelSelectedOnList.keyCombo ~= nil then hotkeyLabelSelectedOnList:setText(hotkeyLabelSelectedOnList.keyCombo .. ': ' .. value) hotkeyLabelSelectedOnList.value = value if value ~= '' then sendAutomatically:enable() else sendAutomatically:disable() sendAutomatically:setChecked(false) end end end function setSendAutomatically(value) hotkeyLabelSelectedOnList.autoSend = value if value then hotkeyLabelSelectedOnList:setColor(HotkeyColors.autoSend) else hotkeyLabelSelectedOnList:setColor(HotkeyColors.text) end end function hotkeyCapture(widget, keyCode, keyboardModifiers) local keyCombo = determineKeyComboDesc(keyCode, keyboardModifiers) local comboPreview = rootWidget:getChildById('assignWindow'):getChildById('comboPreview') comboPreview:setText(tr('Current hotkey to add: %s', keyCombo)) comboPreview.keyCombo = keyCombo comboPreview:resizeToText() rootWidget:getChildById('assignWindow'):getChildById('addButton'):enable() return true end