Browse Source

Add macOS `SetCursorPos` implementation and integrate platform-specific handling

- Implement `SetCursorPos` using macOS native interop in `NativeMethods`.
- Update `WindowResizing` to handle `SetCursorPos` with macOS-specific logic.
- Replace placeholder method in `App.axaml.cs` with actual implementation.
Ruben 1 week ago
parent
commit
64e8bf485a

+ 1 - 2
src/PicView.Avalonia.MacOS/App.axaml.cs

@@ -90,7 +90,6 @@ public class App : Application, IPlatformSpecificService, IPlatformWindowService
                 }
             };
             Current.UrlsOpened -= handler;
-
         }
         catch (Exception)
         {
@@ -113,7 +112,7 @@ public class App : Application, IPlatformSpecificService, IPlatformWindowService
 
     public void SetCursorPos(int x, int y)
     {
-        // TODO: Implement SetCursorPos
+        NativeMethods.SetCursorPos(x, y);
     }
 
     public List<FileInfo> GetFiles(FileInfo fileInfo)

+ 16 - 3
src/PicView.Avalonia/WindowBehavior/WindowResizing.cs

@@ -1,4 +1,5 @@
-using Avalonia;
+using System.Runtime.InteropServices;
+using Avalonia;
 using Avalonia.Controls;
 using Avalonia.Media.Imaging;
 using Avalonia.Threading;
@@ -97,8 +98,20 @@ public static class WindowResizing
         var control = controlProvider();
         if (control is not null)
         {
-            var screenPoint = control.PointToScreen(offset);
-            vm.PlatformService?.SetCursorPos(screenPoint.X, screenPoint.Y);
+            if (RuntimeInformation.IsOSPlatform(OSPlatform.OSX))
+            {
+                Dispatcher.UIThread.Post(() =>
+                {
+                    var screenPoint = control.PointToScreen(offset);
+                    vm.PlatformService?.SetCursorPos(screenPoint.X, screenPoint.Y);
+                }, DispatcherPriority.Render);
+
+            }
+            else
+            {
+                var screenPoint = control.PointToScreen(offset);
+                vm.PlatformService?.SetCursorPos(screenPoint.X, screenPoint.Y);
+            }
         }
 
         setTrigger(false);

+ 41 - 0
src/PicView.Core.MacOS/NativeMethods.cs

@@ -0,0 +1,41 @@
+using System.Runtime.InteropServices;
+using PicView.Core.DebugTools;
+
+namespace PicView.Core.MacOS;
+
+public static partial class NativeMethods
+{
+    private const string CoreGraphicsLib = "/System/Library/Frameworks/CoreGraphics.framework/CoreGraphics";
+    
+    #region macOS Native Interop SetCursorPos
+    
+    [LibraryImport(CoreGraphicsLib, StringMarshalling = StringMarshalling.Utf16)]
+    private static partial int CGWarpMouseCursorPosition(CGPoint newCursorPosition);
+    
+    [StructLayout(LayoutKind.Sequential)]
+    private struct CGPoint
+    {
+        public double X;
+        public double Y;
+        
+        public CGPoint(double x, double y)
+        {
+            X = x;
+            Y = y;
+        }
+    }
+
+    public static int SetCursorPos(double x, double y)
+    {
+        var point = new CGPoint(x, y);
+        var result = CGWarpMouseCursorPosition(point);
+        
+        if (result != 0)
+        {
+            DebugHelper.LogDebug(nameof(NativeMethods), nameof(SetCursorPos), $"Failed to set cursor position: error code {result}");
+        }
+        return result;
+    }
+    
+    #endregion
+}