1
0
Fork 0
mirror of https://github.com/OpenMW/openmw.git synced 2025-01-31 10:15:34 +00:00
openmw/files/data/scripts/omw/input/actionbindings.lua

181 lines
5.9 KiB
Lua

local core = require('openmw.core')
local input = require('openmw.input')
local util = require('openmw.util')
local async = require('openmw.async')
local storage = require('openmw.storage')
local ui = require('openmw.ui')
local I = require('openmw.interfaces')
local actionPressHandlers = {}
local function onActionPress(id, handler)
actionPressHandlers[id] = actionPressHandlers[id] or {}
table.insert(actionPressHandlers[id], handler)
end
local function bindHold(key, actionId)
input.bindAction(key, async:callback(function()
return input.isActionPressed(actionId)
end), {})
end
local function bindMovement(key, actionId, axisId, direction)
input.bindAction(key, async:callback(function()
local actionActive = input.isActionPressed(actionId)
local axisActive = input.getAxisValue(axisId) * direction > 0
return (actionActive or axisActive) and 1 or 0
end), {})
end
local function bindTrigger(key, actionid)
onActionPress(actionid, function()
input.activateTrigger(key)
end)
end
bindTrigger('AlwaysRun', input.ACTION.AlwaysRun)
bindTrigger('ToggleSneak', input.ACTION.Sneak)
bindTrigger('ToggleWeapon', input.ACTION.ToggleWeapon)
bindTrigger('ToggleSpell', input.ACTION.ToggleSpell)
bindTrigger('Jump', input.ACTION.Jump)
bindTrigger('AutoMove', input.ACTION.AutoMove)
bindTrigger('Inventory', input.ACTION.Inventory)
bindTrigger('Journal', input.ACTION.Journal)
bindTrigger('QuickKeysMenu', input.ACTION.QuickKeysMenu)
bindHold('TogglePOV', input.ACTION.TogglePOV)
bindHold('Sneak', input.ACTION.Sneak)
bindHold('Run', input.ACTION.Run)
input.bindAction('Run', async:callback(function(_, value)
local controllerInput = util.vector2(
input.getAxisValue(input.CONTROLLER_AXIS.MoveForwardBackward),
input.getAxisValue(input.CONTROLLER_AXIS.MoveLeftRight)
):length2()
return value or controllerInput > 0.25
end), {})
input.bindAction('Use', async:callback(function()
-- The value "0.6" shouldn't exceed the triggering threshold in BindingsManager::actionValueChanged.
-- TODO: Move more logic from BindingsManager to Lua and consider to make this threshold configurable.
return input.isActionPressed(input.ACTION.Use) or input.getAxisValue(input.CONTROLLER_AXIS.TriggerRight) >= 0.6
end), {})
bindMovement('MoveBackward', input.ACTION.MoveBackward, input.CONTROLLER_AXIS.MoveForwardBackward, 1)
bindMovement('MoveForward', input.ACTION.MoveForward, input.CONTROLLER_AXIS.MoveForwardBackward, -1)
bindMovement('MoveRight', input.ACTION.MoveRight, input.CONTROLLER_AXIS.MoveLeftRight, 1)
bindMovement('MoveLeft', input.ACTION.MoveLeft, input.CONTROLLER_AXIS.MoveLeftRight, -1)
do
local zoomInOut = 0
onActionPress(input.ACTION.ZoomIn, function()
zoomInOut = zoomInOut + 1
end)
onActionPress(input.ACTION.ZoomOut, function()
zoomInOut = zoomInOut - 1
end)
input.bindAction('Zoom3rdPerson', async:callback(function(dt, _, togglePOV)
local Zoom3rdPerson = zoomInOut * 10
if togglePOV then
local triggerLeft = input.getAxisValue(input.CONTROLLER_AXIS.TriggerLeft)
local triggerRight = input.getAxisValue(input.CONTROLLER_AXIS.TriggerRight)
local controllerZoom = (triggerRight - triggerLeft) * 100 * dt
Zoom3rdPerson = Zoom3rdPerson + controllerZoom
end
zoomInOut = 0
return Zoom3rdPerson
end), { 'TogglePOV' })
end
local bindingSection = storage.playerSection('OMWInputBindings')
local keyboardPresses = {}
local keybordHolds = {}
local boundActions = {}
local function bindAction(action)
if boundActions[action] then return end
boundActions[action] = true
input.bindAction(action, async:callback(function()
if keybordHolds[action] then
for _, binding in pairs(keybordHolds[action]) do
if input.isKeyPressed(binding.code) then return true end
end
end
return false
end), {})
end
local function registerBinding(binding, id)
if not input.actions[binding.key] and not input.triggers[binding.key] then
print(string.format('Skipping binding for unknown action or trigger: "%s"', binding.key))
return
end
if binding.type == 'keyboardPress' then
local bindings = keyboardPresses[binding.code] or {}
bindings[id] = binding
keyboardPresses[binding.code] = bindings
elseif binding.type == 'keyboardHold' then
local bindings = keybordHolds[binding.key] or {}
bindings[id] = binding
keybordHolds[binding.key] = bindings
bindAction(binding.key)
else
error('Unknown binding type "' .. binding.type .. '"')
end
end
function clearBinding(id)
for _, boundTriggers in pairs(keyboardPresses) do
boundTriggers[id] = nil
end
for _, boundKeys in pairs(keybordHolds) do
boundKeys[id] = nil
end
end
bindingSection:subscribe(async:callback(function(_, id)
if not id then return end
local binding = bindingSection:get(id)
clearBinding(id)
if binding ~= nil then
registerBinding(binding, id)
end
return id
end))
local initiated = false
local function init()
for id, binding in pairs(bindingSection:asTable()) do
registerBinding(binding, id)
end
end
return {
engineHandlers = {
onFrame = function()
if not initiated then
initiated = true
init()
end
end,
onInputAction = function(id)
if not actionPressHandlers[id] then
return
end
for _, handler in ipairs(actionPressHandlers[id]) do
handler()
end
end,
onKeyPress = function(e)
local bindings = keyboardPresses[e.code]
if bindings then
for _, binding in pairs(bindings) do
input.activateTrigger(binding.key)
end
end
end,
}
}