fix: support native touch input on Wayland
mpv 0.40 on Wayland doesn't update mouse-pos during touch drags. Add touch-pos property observer for reliable gesture tracking and document the --native-touch=yes requirement.
This commit is contained in:
@@ -9,6 +9,10 @@
|
|||||||
* Configurable gesture zones, pixels-per-step sensitivity, per-control step sizes, and optional inverted direction.
|
* Configurable gesture zones, pixels-per-step sensitivity, per-control step sizes, and optional inverted direction.
|
||||||
* Shows OSD feedback after each adjustment.
|
* Shows OSD feedback after each adjustment.
|
||||||
|
|
||||||
|
Requirements:
|
||||||
|
* mpv 0.39+ recommended for native touch support.
|
||||||
|
* On Wayland, run mpv with `--native-touch=yes` for reliable touch tracking.
|
||||||
|
|
||||||
Configuration:
|
Configuration:
|
||||||
Edit the `config` table below to tune zone widths, step sizes, and OSD duration; script-opts files are ignored.
|
Edit the `config` table below to tune zone widths, step sizes, and OSD duration; script-opts files are ignored.
|
||||||
]]
|
]]
|
||||||
@@ -293,6 +297,9 @@ local function apply_steps(kind, steps)
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
local poll_timer = nil
|
||||||
|
local update_gesture
|
||||||
|
|
||||||
local function reset_state()
|
local function reset_state()
|
||||||
if state.active and config.log_debug then
|
if state.active and config.log_debug then
|
||||||
dbg(string.format("end gesture zone=%s accum=%.2f", tostring(state.zone), state.accum))
|
dbg(string.format("end gesture zone=%s accum=%.2f", tostring(state.zone), state.accum))
|
||||||
@@ -305,6 +312,24 @@ local function reset_state()
|
|||||||
state.last_y = 0
|
state.last_y = 0
|
||||||
state.start_x = 0
|
state.start_x = 0
|
||||||
state.start_y = 0
|
state.start_y = 0
|
||||||
|
if poll_timer then
|
||||||
|
poll_timer:kill()
|
||||||
|
poll_timer = nil
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
local function poll_position()
|
||||||
|
local pos = mp.get_property_native("mouse-pos")
|
||||||
|
if pos and pos.x and pos.y then
|
||||||
|
update_gesture(nil, pos)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
local function start_poll_timer()
|
||||||
|
if poll_timer then
|
||||||
|
poll_timer:kill()
|
||||||
|
end
|
||||||
|
poll_timer = mp.add_periodic_timer(0.016, poll_position)
|
||||||
end
|
end
|
||||||
|
|
||||||
local function begin_gesture_tracking(pos)
|
local function begin_gesture_tracking(pos)
|
||||||
@@ -319,6 +344,7 @@ local function begin_gesture_tracking(pos)
|
|||||||
state.cached_volume_pct = nil
|
state.cached_volume_pct = nil
|
||||||
state.cached_brightness_pct = nil
|
state.cached_brightness_pct = nil
|
||||||
dbg(string.format("begin tracking at (%.0f,%.0f)", pos.x, pos.y))
|
dbg(string.format("begin tracking at (%.0f,%.0f)", pos.x, pos.y))
|
||||||
|
start_poll_timer()
|
||||||
end
|
end
|
||||||
|
|
||||||
local function lock_axis(axis, zone)
|
local function lock_axis(axis, zone)
|
||||||
@@ -328,7 +354,7 @@ local function lock_axis(axis, zone)
|
|||||||
dbg(string.format("locked axis=%s zone=%s", axis, tostring(zone)))
|
dbg(string.format("locked axis=%s zone=%s", axis, tostring(zone)))
|
||||||
end
|
end
|
||||||
|
|
||||||
local function update_gesture(_, pos)
|
update_gesture = function(_, pos)
|
||||||
if not pos or not pos.x or not pos.y then
|
if not pos or not pos.x or not pos.y then
|
||||||
return
|
return
|
||||||
end
|
end
|
||||||
@@ -477,6 +503,27 @@ end
|
|||||||
|
|
||||||
mp.add_forced_key_binding("mouse_btn0", "touch-gestures", handle_touch, { complex = true })
|
mp.add_forced_key_binding("mouse_btn0", "touch-gestures", handle_touch, { complex = true })
|
||||||
mp.observe_property("mouse-pos", "native", update_gesture)
|
mp.observe_property("mouse-pos", "native", update_gesture)
|
||||||
|
mp.observe_property("touch-pos", "native", function(_, touch)
|
||||||
|
if touch and #touch > 0 then
|
||||||
|
local pos = { x = touch[1].x, y = touch[1].y }
|
||||||
|
if not state.active then
|
||||||
|
if not in_excluded_zone(pos) then
|
||||||
|
begin_gesture_tracking(pos)
|
||||||
|
end
|
||||||
|
else
|
||||||
|
update_gesture(nil, pos)
|
||||||
|
end
|
||||||
|
else
|
||||||
|
if state.active then
|
||||||
|
if not state.axis then
|
||||||
|
forwarding_click = true
|
||||||
|
mp.commandv("keypress", "mouse_btn0")
|
||||||
|
forwarding_click = false
|
||||||
|
end
|
||||||
|
reset_state()
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end)
|
||||||
|
|
||||||
mp.register_event("shutdown", function()
|
mp.register_event("shutdown", function()
|
||||||
reset_state()
|
reset_state()
|
||||||
|
|||||||
Reference in New Issue
Block a user