diff --git a/src/Avalonia.Windowing/Avalonia.Windowing.csproj b/src/Avalonia.Windowing/Avalonia.Windowing.csproj index 8581ac578a..b255c857cd 100644 --- a/src/Avalonia.Windowing/Avalonia.Windowing.csproj +++ b/src/Avalonia.Windowing/Avalonia.Windowing.csproj @@ -11,6 +11,11 @@ + + + + + netstandard2.0 diff --git a/src/Avalonia.Windowing/Bindings/EventNotifier.cs b/src/Avalonia.Windowing/Bindings/EventNotifier.cs new file mode 100644 index 0000000000..aabaa843e5 --- /dev/null +++ b/src/Avalonia.Windowing/Bindings/EventNotifier.cs @@ -0,0 +1,17 @@ +using System; +using System.Runtime.InteropServices; + +namespace Avalonia.Windowing.Bindings +{ + public delegate void MouseEventCallback(IntPtr windowId, MouseEvent mouseEvent); + public delegate void ResizeEventCallback(IntPtr windowId, ResizeEvent resizeEvent); + public delegate void AwakenedEventCallback(); + + [StructLayout(LayoutKind.Sequential)] + public struct EventNotifier + { + public MouseEventCallback OnMouseEvent; + public AwakenedEventCallback OnAwakened; + public ResizeEventCallback OnResized; + } +} diff --git a/src/Avalonia.Windowing/Bindings/Events.cs b/src/Avalonia.Windowing/Bindings/Events.cs new file mode 100644 index 0000000000..29ba28c7ae --- /dev/null +++ b/src/Avalonia.Windowing/Bindings/Events.cs @@ -0,0 +1,32 @@ +using System; +using System.Runtime.InteropServices; + +namespace Avalonia.Windowing.Bindings +{ + public enum MouseEventType : int + { + LeaveWindow, + LeftButtonDown, + LeftButtonUp, + RightButtonDown, + RightButtonUp, + MiddleButtonDown, + MiddleButtonUp, + Move, + Wheel, + NonClientLeftButtonDown + } + + [StructLayout(LayoutKind.Sequential)] + public struct MouseEvent + { + public MouseEventType EventType { get; set; } + public LogicalPosition Position { get; set; } + } + + [StructLayout(LayoutKind.Sequential)] + public struct ResizeEvent + { + public LogicalSize Size { get; set; } + } +} diff --git a/src/Avalonia.Windowing/Bindings/EventsLoop.cs b/src/Avalonia.Windowing/Bindings/EventsLoop.cs index 652c72c980..d11015abd1 100644 --- a/src/Avalonia.Windowing/Bindings/EventsLoop.cs +++ b/src/Avalonia.Windowing/Bindings/EventsLoop.cs @@ -3,51 +3,6 @@ using System.Runtime.InteropServices; namespace Avalonia.Windowing.Bindings { - public enum MouseEventType : int - { - LeaveWindow, - LeftButtonDown, - LeftButtonUp, - RightButtonDown, - RightButtonUp, - MiddleButtonDown, - MiddleButtonUp, - Move, - Wheel, - NonClientLeftButtonDown - } - - [StructLayout(LayoutKind.Sequential)] - public struct MouseEvent - { - public MouseEventType EventType { get; set; } - public LogicalPosition Position { get; set; } - } - - [StructLayout(LayoutKind.Sequential)] - public struct ResizeEvent - { - public LogicalSize Size { get; set; } - } - - [StructLayout(LayoutKind.Sequential)] - public struct LogicalPosition - { - public double X { get; set; } - public double Y { get; set; } - } - - [StructLayout(LayoutKind.Sequential)] - public struct LogicalSize - { - public double Width { get; set; } - public double Height { get; set; } - } - - public delegate void MouseEventCallback(IntPtr windowId, MouseEvent mouseEvent); - public delegate void ResizeEventCallback(IntPtr windowId, ResizeEvent mouseEvent); - public delegate void AwakenedEventCallback(); - public class EventsLoop : IDisposable { [DllImport("winit_wrapper")] @@ -60,43 +15,58 @@ namespace Avalonia.Windowing.Bindings private static extern void winit_events_loop_run ( IntPtr handle, - MouseEventCallback callback, - AwakenedEventCallback awakenedEventCallback, - ResizeEventCallback resizeEventCallback + EventNotifier notifier + ); + + [UnmanagedFunctionPointer(CallingConvention.Cdecl)] + public delegate void TimerDel(); + + [DllImport("winit_wrapper")] + private static extern void winit_events_loop_timer + ( + TimerDel del2 ); public IntPtr Handle { get; private set; } private readonly EventsLoopProxy _eventsLoopProxy; + private readonly EventNotifier _notifier; - public event MouseEventCallback MouseEvent; - public event AwakenedEventCallback Awakened; - public event ResizeEventCallback Resized; + public event MouseEventCallback OnMouseEvent; + public event AwakenedEventCallback OnAwakened; + public event ResizeEventCallback OnResized; public EventsLoop() { Handle = winit_events_loop_new(out var elpHandle); - _eventsLoopProxy = new EventsLoopProxy(elpHandle); + _eventsLoopProxy = new EventsLoopProxy(elpHandle); + _notifier = new EventNotifier() + { + OnMouseEvent = (IntPtr windowId, MouseEvent mouseEvent) => OnMouseEvent?.Invoke(windowId, mouseEvent), + OnResized = (IntPtr windowId, ResizeEvent resizeEvent) => OnResized?.Invoke(windowId, resizeEvent), + OnAwakened = () => OnAwakened?.Invoke() + }; } public void Run() { - // We need a delegate callback here to support talking back to the C# code. - // Send an event type enum and then unsafely construct the event winit_events_loop_run( - Handle, - (windowId, mouseEvent) => { - MouseEvent?.Invoke(windowId, mouseEvent); - }, - () => - { - Awakened?.Invoke(); - }, - (windowId, ResizeEvent) => { - Resized?.Invoke(windowId, ResizeEvent); - } + Handle, + _notifier ); } + static TimerDel del = new TimerDel(() => + { + Console.WriteLine("WRK"); + }); + + public void RunTimer() + { + winit_events_loop_timer( + del); + + } + public void Wakeup() { _eventsLoopProxy.Wakeup(); @@ -108,6 +78,11 @@ namespace Avalonia.Windowing.Bindings winit_events_loop_destroy(Handle); } + public void GetAvailableMonitors() + { + // TODO + } + private class EventsLoopProxy : IDisposable { [DllImport("winit_wrapper")] diff --git a/src/Avalonia.Windowing/Bindings/EventsLoopProxy.cs b/src/Avalonia.Windowing/Bindings/EventsLoopProxy.cs new file mode 100644 index 0000000000..60aa663ab5 --- /dev/null +++ b/src/Avalonia.Windowing/Bindings/EventsLoopProxy.cs @@ -0,0 +1,10 @@ +using System; +namespace Avalonia.Windowing.Bindings +{ + public class EventsLoopProxy + { + public EventsLoopProxy() + { + } + } +} diff --git a/src/Avalonia.Windowing/Bindings/GlWindow.cs b/src/Avalonia.Windowing/Bindings/GlWindow.cs index 077bb62179..864cf76dcf 100644 --- a/src/Avalonia.Windowing/Bindings/GlWindow.cs +++ b/src/Avalonia.Windowing/Bindings/GlWindow.cs @@ -34,6 +34,12 @@ namespace Avalonia.Windowing.Bindings [DllImport("winit_wrapper")] private static extern void winit_gl_window_show(IntPtr handle); + [DllImport("winit_wrapper")] + private static extern void winit_gl_window_hide(IntPtr handle); + + [DllImport("winit_wrapper")] + private static extern void winit_gl_window_set_decorations(IntPtr handle, int visible); + [DllImport("winit_wrapper")] private static extern IntPtr winit_gl_window_get_proc_addr(IntPtr handle, string symbol); @@ -45,9 +51,12 @@ namespace Avalonia.Windowing.Bindings private IntPtr _handle; public IntPtr Id => winit_gl_window_get_id(_handle); + public EventsLoop EventsLoop { get; } + public GlWindowWrapper(EventsLoop eventsLoop) { - _handle = winit_gl_window_new(eventsLoop.Handle); + EventsLoop = eventsLoop; + _handle = winit_gl_window_new(EventsLoop.Handle); } public void Dispose() @@ -100,5 +109,15 @@ namespace Avalonia.Windowing.Bindings { winit_gl_window_resize_context(_handle, width, height); } + + public void ToggleDecorations(bool visible) + { + winit_gl_window_set_decorations(_handle, visible ? 1 : 0); + } + + public void Hide() + { + winit_gl_window_hide(_handle); + } } } diff --git a/src/Avalonia.Windowing/Bindings/IWindowWrapper.cs b/src/Avalonia.Windowing/Bindings/IWindowWrapper.cs index 777e8937fe..76227cdf86 100644 --- a/src/Avalonia.Windowing/Bindings/IWindowWrapper.cs +++ b/src/Avalonia.Windowing/Bindings/IWindowWrapper.cs @@ -7,10 +7,17 @@ namespace Avalonia.Windowing.Bindings public interface IWindowWrapper : IDisposable { IntPtr Id { get; } + EventsLoop EventsLoop { get; } + void SetTitle(string title); void SetSize(double width, double height); + (double, double) GetSize(); (double, double) GetPosition(); + + void ToggleDecorations(bool visible); + void Show(); + void Hide(); } } diff --git a/src/Avalonia.Windowing/Bindings/Monitor.cs b/src/Avalonia.Windowing/Bindings/Monitor.cs new file mode 100644 index 0000000000..c4e01ee333 --- /dev/null +++ b/src/Avalonia.Windowing/Bindings/Monitor.cs @@ -0,0 +1,12 @@ +using System; +using System.Runtime.InteropServices; + +namespace Avalonia.Windowing.Bindings +{ + [StructLayout(LayoutKind.Sequential)] + public struct Monitor + { + public LogicalSize Size { get; set; } + public LogicalPosition Position { get; set; } + } +} diff --git a/src/Avalonia.Windowing/Bindings/Monitors.cs b/src/Avalonia.Windowing/Bindings/Monitors.cs index cb5aba6591..0bb0544306 100644 --- a/src/Avalonia.Windowing/Bindings/Monitors.cs +++ b/src/Avalonia.Windowing/Bindings/Monitors.cs @@ -3,9 +3,15 @@ using Avalonia.Platform; namespace Avalonia.Windowing.Bindings { + public class Monitors : IScreenImpl { public int ScreenCount => 1; public Screen[] AllScreens => new Screen[] { new Screen(Rect.Empty, Rect.Empty, true) }; + + public Monitors() + { + + } } } diff --git a/src/Avalonia.Windowing/Bindings/Units.cs b/src/Avalonia.Windowing/Bindings/Units.cs new file mode 100644 index 0000000000..dcad04a828 --- /dev/null +++ b/src/Avalonia.Windowing/Bindings/Units.cs @@ -0,0 +1,19 @@ +using System; +using System.Runtime.InteropServices; + +namespace Avalonia.Windowing.Bindings +{ + [StructLayout(LayoutKind.Sequential)] + public struct LogicalPosition + { + public double X { get; set; } + public double Y { get; set; } + } + + [StructLayout(LayoutKind.Sequential)] + public struct LogicalSize + { + public double Width { get; set; } + public double Height { get; set; } + } +} diff --git a/src/Avalonia.Windowing/Bindings/Window.cs b/src/Avalonia.Windowing/Bindings/Window.cs deleted file mode 100644 index 43a19f83cb..0000000000 --- a/src/Avalonia.Windowing/Bindings/Window.cs +++ /dev/null @@ -1,53 +0,0 @@ -using System; -using System.Runtime.InteropServices; - -namespace Avalonia.Windowing.Bindings -{ - public class WindowWrapper : IWindowWrapper - { - [DllImport("winit_wrapper")] - private static extern IntPtr winit_window_new(IntPtr eventsLoopHandle); - - [DllImport("winit_wrapper")] - private static extern IntPtr winit_window_destroy(IntPtr handle); - - private IntPtr _handle; - - public IntPtr Id => IntPtr.Zero; - - public WindowWrapper(EventsLoop eventsLoop) - { - _handle = winit_window_new(eventsLoop.Handle); - } - - public void Dispose() - { - winit_window_destroy(_handle); - } - - public void SetTitle(string title) - { - - } - - public void SetSize(double width, double height) - { - throw new NotImplementedException(); - } - - public (double, double) GetSize() - { - return (0, 0); - } - - public (double, double) GetPosition() - { - return (0, 0); - } - - public void Show() - { - - } - } -} diff --git a/src/Avalonia.Windowing/WIndowingPlatform.cs b/src/Avalonia.Windowing/WIndowingPlatform.cs index efbe0a9151..b2baea9374 100644 --- a/src/Avalonia.Windowing/WIndowingPlatform.cs +++ b/src/Avalonia.Windowing/WIndowingPlatform.cs @@ -41,9 +41,9 @@ namespace Avalonia.Windowing public WindowingPlatform() { _eventsLoop = new EventsLoop(); - _eventsLoop.MouseEvent += _eventsLoop_MouseEvent; - _eventsLoop.Awakened += _eventsLoop_Awakened; - _eventsLoop.Resized += _eventsLoop_Resized; + _eventsLoop.OnMouseEvent += _eventsLoop_MouseEvent; + _eventsLoop.OnAwakened += _eventsLoop_Awakened; + _eventsLoop.OnResized += _eventsLoop_Resized; _windows = new Dictionary(); } @@ -129,6 +129,7 @@ namespace Avalonia.Windowing public IDisposable StartTimer(DispatcherPriority priority, TimeSpan interval, Action tick) { + _eventsLoop.RunTimer(); return Disposable.Create(() => { }); } } diff --git a/src/Avalonia.Windowing/WindowImpl.cs b/src/Avalonia.Windowing/WindowImpl.cs index 1a3a5a7d5a..d48ebdaae4 100644 --- a/src/Avalonia.Windowing/WindowImpl.cs +++ b/src/Avalonia.Windowing/WindowImpl.cs @@ -23,16 +23,16 @@ namespace Avalonia.Windowing public WindowState WindowState { get; set; } public Action WindowStateChanged { get; set; } public Func Closing { get; set; } - public Point Position + public Point Position { - get + get { var (x, y) = _windowWrapper.GetPosition(); return new Point(x, y); - } - set + } + set { - var x = value; + var x = value; } } @@ -46,8 +46,9 @@ namespace Avalonia.Windowing public IScreenImpl Screen => new Monitors(); - public Size ClientSize { - get + public Size ClientSize + { + get { var (width, height) = _windowWrapper.GetSize(); return new Size(width, height); @@ -94,6 +95,7 @@ namespace Avalonia.Windowing public void Hide() { + _windowWrapper.Hide(); } public void Invalidate(Rect rect) @@ -110,14 +112,14 @@ namespace Avalonia.Windowing public Point PointToScreen(Point point) { var position = Position; - return new Point(point.X - position.X, point.Y - position.Y);; + return new Point(point.X - position.X, point.Y - position.Y); ; } public void Resize(Size clientSize) { if (clientSize == ClientSize) return; - + // This is where we size the window accordingly.. _windowWrapper.SetSize(clientSize.Width, clientSize.Height); //Resized(clientSize); @@ -140,6 +142,7 @@ namespace Avalonia.Windowing public void SetSystemDecorations(bool enabled) { + _windowWrapper.ToggleDecorations(enabled); } public void SetTitle(string title) @@ -165,22 +168,22 @@ namespace Avalonia.Windowing { } - public void OnMouseEvent(MouseEvent evt) + public void OnMouseEvent(MouseEvent evt) { Dispatcher.UIThread.RunJobs(DispatcherPriority.Input); - if(evt.EventType == MouseEventType.Move) + if (evt.EventType == MouseEventType.Move) { _lastPosition = evt.Position; } - Input(new RawMouseEventArgs(MouseDevice, (uint)Environment.TickCount, _inputRoot, (RawMouseEventType)evt.EventType, new Point(_lastPosition.X, _lastPosition.Y), InputModifiers.None)); + Input(new RawMouseEventArgs(MouseDevice, (uint)Environment.TickCount, _inputRoot, (RawMouseEventType)evt.EventType, new Point(_lastPosition.X, _lastPosition.Y), InputModifiers.None)); } - public void OnResizeEvent(ResizeEvent evt) + public void OnResizeEvent(ResizeEvent evt) { Resized?.Invoke(ClientSize); Paint?.Invoke(new Rect(ClientSize)); } } -} +} \ No newline at end of file