浏览代码

Basic support for absolute pointing libinput devices

Nikita Tsukanov 6 年之前
父节点
当前提交
567defb825

+ 45 - 0
src/Linux/Avalonia.LinuxFramebuffer/Input/LibInput/LibInputBackend.cs

@@ -15,6 +15,8 @@ namespace Avalonia.LinuxFramebuffer.Input.LibInput
         private IInputRoot _inputRoot;
         private IInputRoot _inputRoot;
         private readonly Queue<Action> _inputThreadActions = new Queue<Action>();
         private readonly Queue<Action> _inputThreadActions = new Queue<Action>();
         private TouchDevice _touch = new TouchDevice();
         private TouchDevice _touch = new TouchDevice();
+        private MouseDevice _mouse = new MouseDevice();
+        private Point _mousePosition;
         
         
         private readonly Queue<RawInputEventArgs> _inputQueue = new Queue<RawInputEventArgs>();
         private readonly Queue<RawInputEventArgs> _inputQueue = new Queue<RawInputEventArgs>();
         private Action<RawInputEventArgs> _onInput;
         private Action<RawInputEventArgs> _onInput;
@@ -50,6 +52,10 @@ namespace Avalonia.LinuxFramebuffer.Input.LibInput
                     if (type >= LibInputEventType.LIBINPUT_EVENT_TOUCH_DOWN &&
                     if (type >= LibInputEventType.LIBINPUT_EVENT_TOUCH_DOWN &&
                         type <= LibInputEventType.LIBINPUT_EVENT_TOUCH_CANCEL)
                         type <= LibInputEventType.LIBINPUT_EVENT_TOUCH_CANCEL)
                         HandleTouch(ev, type);
                         HandleTouch(ev, type);
+
+                    if (type >= LibInputEventType.LIBINPUT_EVENT_POINTER_MOTION
+                        && type <= LibInputEventType.LIBINPUT_EVENT_POINTER_AXIS)
+                        HandlePointer(ev, type);
                     
                     
                     libinput_event_destroy(ev);
                     libinput_event_destroy(ev);
                     libinput_dispatch(ctx);
                     libinput_dispatch(ctx);
@@ -123,6 +129,45 @@ namespace Avalonia.LinuxFramebuffer.Input.LibInput
             }
             }
         }
         }
 
 
+        private void HandlePointer(IntPtr ev, LibInputEventType type)
+        {
+            //TODO: support input modifiers
+            var pev = libinput_event_get_pointer_event(ev);
+            var info = _screen.ScaledSize;
+            var ts = libinput_event_pointer_get_time_usec(pev) / 1000;
+            if (type == LibInputEventType.LIBINPUT_EVENT_POINTER_MOTION_ABSOLUTE)
+            {
+                _mousePosition = new Point(libinput_event_pointer_get_absolute_x_transformed(pev, (int)info.Width),
+                    libinput_event_pointer_get_absolute_y_transformed(pev, (int)info.Height));
+                ScheduleInput(new RawPointerEventArgs(_mouse, ts, _inputRoot, RawPointerEventType.Move, _mousePosition,
+                    InputModifiers.None));
+            }
+            else if (type == LibInputEventType.LIBINPUT_EVENT_POINTER_BUTTON)
+            {
+                var button = (EvKey)libinput_event_pointer_get_button(pev);
+                var buttonState = libinput_event_pointer_get_button_state(pev);
+
+
+                var evnt = button == EvKey.BTN_LEFT ?
+                    (buttonState == 1 ? RawPointerEventType.LeftButtonDown : RawPointerEventType.LeftButtonUp) :
+                    button == EvKey.BTN_MIDDLE ?
+                        (buttonState == 1 ? RawPointerEventType.MiddleButtonDown : RawPointerEventType.MiddleButtonUp) :
+                        button == EvKey.BTN_RIGHT ?
+                            (buttonState == 1 ?
+                                RawPointerEventType.RightButtonDown :
+                                RawPointerEventType.RightButtonUp) :
+                            (RawPointerEventType)(-1);
+                if (evnt == (RawPointerEventType)(-1))
+                    return;
+                        
+
+                ScheduleInput(
+                    new RawPointerEventArgs(_mouse, ts, _inputRoot, evnt, _mousePosition, InputModifiers.None));
+            }
+            
+        }
+            
+        
 
 
         public void Initialize(IScreenInfoProvider screen, Action<RawInputEventArgs> onInput)
         public void Initialize(IScreenInfoProvider screen, Action<RawInputEventArgs> onInput)
         {
         {

+ 19 - 2
src/Linux/Avalonia.LinuxFramebuffer/Input/LibInput/LibInputNativeUnsafeMethods.cs

@@ -116,7 +116,24 @@ namespace Avalonia.LinuxFramebuffer.Input.LibInput
         
         
         [DllImport(LibInput)]
         [DllImport(LibInput)]
         public extern static double libinput_event_touch_get_y_transformed(IntPtr ev, int height);
         public extern static double libinput_event_touch_get_y_transformed(IntPtr ev, int height);
-
-
+        
+        [DllImport(LibInput)]
+        public extern static IntPtr libinput_event_get_pointer_event(IntPtr ev);
+        
+        
+        [DllImport(LibInput)]
+        public extern static ulong libinput_event_pointer_get_time_usec(IntPtr ev);
+        
+        [DllImport(LibInput)]
+        public extern static double libinput_event_pointer_get_absolute_x_transformed(IntPtr ev, int width);
+        
+        [DllImport(LibInput)]
+        public extern static double libinput_event_pointer_get_absolute_y_transformed(IntPtr ev, int height);
+        
+        [DllImport(LibInput)]
+        public extern static int libinput_event_pointer_get_button(IntPtr ev);
+        
+        [DllImport(LibInput)]
+        public extern static int libinput_event_pointer_get_button_state(IntPtr ev);
     }
     }
 }
 }