--[[
-- Controller
"select",
"alt_select",
"exit",
"back",
"nav_up",
"nav_down",
"nav_left",
"nav_right",
"joy_up",
"joy_down",
"joy_left",
"joy_right",
"alt_joy_up",
"alt_joy_down",
"alt_joy_left",
"alt_joy_right",
"scroll_up",
"scroll_down",
"scroll_left",
"scroll_right",
"dpad_up",
"dpad_down",
"dpad_left",
"dpad_right",
"all_unassigned",
-- Game specific
"map", // SR4: Bring up the HUB menu
"pause", // SR4: Pause menu
-- Gamepad
"gamepad_a",
"gamepad_b",
"gamepad_x",
"gamepad_y",
"key_up",
"key_down",
"key_left",
"key_right",
"any_key",
"scancode",
-- Mouse Inputs
"mouse_click",
"mouse_right_click",
"mouse_middle_click",
"mouse_down",
"mouse_move",
"mouse_move_always",
"mouse_drag",
"mouse_drag_release",
"mouse_scroll",
]]--
-- Object to simplify turning on/off input event subscriptions
Vdo_input_tracker = {}
VDO_INPUT_TRACKER_DELAY_SECONDS = 0.6 -- Base time in seconds to delay before sending next inpt event
VDO_INPUT_TRACKER_ACCELERATION_FACTOR = 1.2 -- How quickly input velocity compounds over time when holding the input button
VDO_INPUT_TRACKER_MAX_ACCELERATION = 10 -- Maximum accleration. The smallest delay time will be VDO_INPUT_TRACKER_DELAY_SECONDS * VDO_INPUT_TRACKER_MAX_ACCELERATION.
VDO_INPUT_SLIDER_ACCEL_REPEAT = 0.4
VDO_INPUT_SLIDER_ACCEL_FACTOR = 30
VDO_INPUT_SLIDER_ACCEL_LIMIT = 1000
-- Creates a new vdo input event tracker
--
function Vdo_input_tracker:new()
local obj = {
input_infos = {},
}
setmetatable(obj, self)
self.__index = self
self.highspeed_on = -1
return obj
end
-- Adds an input event to use (Note that it doesn't actually subscribe the input)
-- is_raw is optional
--
function Vdo_input_tracker:add_input(event_name, func_name, priority, is_raw, scancode, lock_on_release)
-- Make a new entry after any current entries
local index = #self.input_infos + 1
self.input_infos[index] = {}
local info = self.input_infos[index]
info.event_name = event_name
info.func_name = func_name
info.priority = priority
info.is_raw = is_raw or false
if lock_on_release == nil then
lock_on_release = true
end
info.lock_on_release = lock_on_release
if game_get_platform() == "PC" then
info.scancode = scancode or -1
end
end
-- Adds a mouse input event to use (Note that it doesn't actually subscribe the input)
--
function Vdo_input_tracker:add_mouse_input(event_name, func_name, priority, target_handle)
-- Make a new entry after any current entries
local index = #self.input_infos + 1
self.input_infos[index] = {}
local info = self.input_infos[index]
info.event_name = event_name
info.func_name = func_name
info.priority = priority
info.target_handle = target_handle
info.is_raw = false
info.is_mouse = true
end
--[[ ---------------------------------------------------------------------
-- Function - remove_input_by_object_handle
-- Description - Removes a specific mouse input event and unsubscribes to it if necessary
-- Parameters -
-- event_name - The name of the mouse input to remove
-- target_handle - The target handle of the input to remove
-- Returns - nil
]]-- ---------------------------------------------------------------------
function Vdo_input_tracker:remove_input_by_object_handle(event_name, target_handle)
-- Cycle through all inputs
for i, info in pairs(self.input_infos) do
-- Find an input that matches the specified name
if( info.event_name == event_name )then
-- Find an input that matches the specified handle
if( info.target_handle == target_handle )then
if( info.handle ~= nil ) then
if( info.is_raw )then -- Unsubcribe if it is raw
vint_unsubscribe_to_raw_input(info.handle)
elseif( info.is_mouse )then -- Unsubscribe if it is mouse
vint_unsubscribe_to_mouse_input(info.handle)
else -- Unsubcribe if it is anything else
vint_unsubscribe_to_input_event(info.handle)
end
end
-- Clear that part of the table
self.input_infos[i] = nil
return
end
end
end
end
-- Removes an input event and unsubscribes to it if necessary
--
function Vdo_input_tracker:remove_input(event_name)
for i, info in pairs(self.input_infos) do
if info.event_name == event_name then
if info.handle ~= nil then
if info.is_raw then
vint_unsubscribe_to_raw_input(info.handle)
elseif info.is_mouse then
vint_unsubscribe_to_mouse_input(info.handle)
else
vint_unsubscribe_to_input_event(info.handle)
end
end
self.input_infos[i] = nil
return
end
end
end
-- Removes all of the input events and unsubscribes to them if necessary
--
function Vdo_input_tracker:remove_all(dont_force_mouse_move)
for i, info in pairs(self.input_infos) do
if info.handle ~= nil then
if info.is_raw then
vint_unsubscribe_to_raw_input(info.handle)
elseif info.is_mouse then
vint_unsubscribe_to_mouse_input(info.handle)
if dont_force_mouse_move ~= true and game_is_active_input_gamepad() == false then
--vint_force_mouse_move_event()
end
else
vint_unsubscribe_to_input_event(info.handle)
end
end
self.input_infos[i] = nil
end
end
-- Subscribes/unsubscribes all added input events
--
function Vdo_input_tracker:subscribe(enable, dont_force_mouse_move)
self.is_subscribed = enable
local mouse_move_event_changed = false
-- Just in case, always unsubscribe any existing input_infos (should be empty if we properly unsubscribed before subscribing)
for i, info in pairs(self.input_infos) do
if info.handle ~= nil then
if info.is_raw then
vint_unsubscribe_to_raw_input(info.handle)
elseif info.is_mouse then
vint_unsubscribe_to_mouse_input(info.handle)
mouse_move_event_changed = true
else
vint_unsubscribe_to_input_event(info.handle)
end
info.handle = nil
end
end
if enable then
for i, info in pairs(self.input_infos) do
if info.is_raw then
info.handle = vint_subscribe_to_raw_input(info.event_name, info.func_name, info.priority)
elseif info.is_mouse then
info.handle = vint_subscribe_to_mouse_input(info.event_name, info.func_name, info.priority, info.target_handle)
mouse_move_event_changed = true
else
local scancode = info.scancode or -1
info.handle = vint_subscribe_to_input_event(info.event_name, info.func_name, info.priority, scancode, info.lock_on_release)
if info.handle ~= nil then
self:set_input_accelleration(info.handle, info.event_name)
end
end
end
end
if mouse_move_event_changed and dont_force_mouse_move ~= true and game_is_active_input_gamepad() == false then
--vint_force_mouse_move_event()
end
end
-------------------------------------------------------------------------------
-- Sets the input accelleration per input, depends whether or not the highspeed flag has been set or not for the entire vdo. (JMH 5/17/2011)
-- NOTE: This should be generalized per input subscription and handled directly on each item type in a megalist...
--
function Vdo_input_tracker:set_input_accelleration(handle, event_name)
local delay = VDO_INPUT_TRACKER_DELAY_SECONDS
local factor_acc = VDO_INPUT_TRACKER_ACCELERATION_FACTOR
local max_acc = VDO_INPUT_TRACKER_MAX_ACCELERATION
if self.highspeed_on == true then
if event_name == "nav_left" or event_name == "nav_right" then
delay = VDO_INPUT_SLIDER_ACCEL_REPEAT
factor_acc = VDO_INPUT_SLIDER_ACCEL_FACTOR
max_acc = VDO_INPUT_SLIDER_ACCEL_LIMIT
end
end
vint_set_input_params(handle, delay, factor_acc, max_acc, false, true)
end
-------------------------------------------------------------------------------
-- Toggles highspeed for left and right inputs. (JMH 5/17/2011)
-- Note: This needs to be a more generalized solution, and input_tracker should
-- be embedded into VDO's with specific callback functions.
--
function Vdo_input_tracker:highspeed_left_right(highspeed_on)
if self.highspeed_on ~= highspeed_on then
self.highspeed_on = highspeed_on
for i, info in pairs(self.input_infos) do
if info.handle ~= nil then
self:set_input_accelleration(info.handle, info.event_name)
end
end
end
end