diff options
author | Jose Medrano <jose.medrano@microsoft.com> | 2019-06-10 13:46:18 +0300 |
---|---|---|
committer | GitHub <noreply@github.com> | 2019-06-10 13:46:18 +0300 |
commit | 910e7caebedd1d63503ee40afb853da5b55c1651 (patch) | |
tree | 4d53814efa3443b29041af6e6df651a7663c2d7f | |
parent | 4222db22b08da434b71dc9eba75073a0901763b2 (diff) | |
parent | dd86861ad3b6fdf1afaaf5c3d9b86789d2163801 (diff) |
Merge pull request #7841 from mono/splitview-harden-gdk-event-filter
Harden the MacSplitterWidget GDK event filter
-rw-r--r-- | main/src/core/MonoDevelop.Ide/MonoDevelop.Components.Docking/MacSplitterWidget.cs | 58 |
1 files changed, 52 insertions, 6 deletions
diff --git a/main/src/core/MonoDevelop.Ide/MonoDevelop.Components.Docking/MacSplitterWidget.cs b/main/src/core/MonoDevelop.Ide/MonoDevelop.Components.Docking/MacSplitterWidget.cs index 58349d1d23..7c11b62847 100644 --- a/main/src/core/MonoDevelop.Ide/MonoDevelop.Components.Docking/MacSplitterWidget.cs +++ b/main/src/core/MonoDevelop.Ide/MonoDevelop.Components.Docking/MacSplitterWidget.cs @@ -52,6 +52,7 @@ namespace MonoDevelop.Components.Docking public override void MouseEntered (NSEvent theEvent) { + lastEventTimestamp = theEvent.Timestamp; if (!dragging) { SetResizeCursor (); } @@ -61,6 +62,7 @@ namespace MonoDevelop.Components.Docking public override void MouseExited (NSEvent theEvent) { + lastEventTimestamp = theEvent.Timestamp; if (!dragging) { SetDefaultCursor (); } @@ -85,6 +87,7 @@ namespace MonoDevelop.Components.Docking public override void MouseMoved (NSEvent theEvent) { + lastEventTimestamp = theEvent.Timestamp; if (!dragging) { SetResizeCursor (); } @@ -95,7 +98,7 @@ namespace MonoDevelop.Components.Docking { if (dragging) { dragging = false; - AddRemoveFilter (false); + RemoveGdkEventFilter (); } } @@ -107,6 +110,7 @@ namespace MonoDevelop.Components.Docking public override void MouseDown (NSEvent theEvent) { + lastEventTimestamp = theEvent.Timestamp; dragging = true; var point = NSEvent.CurrentMouseLocation; @@ -120,7 +124,7 @@ namespace MonoDevelop.Components.Docking dragSize = obj.Allocation.Height; } - AddRemoveFilter (true); + AddGdkEventFilter (); } void SetDefaultCursor () @@ -133,6 +137,7 @@ namespace MonoDevelop.Components.Docking public override void MouseUp (NSEvent theEvent) { + lastEventTimestamp = theEvent.Timestamp; if (hover) { SetResizeCursor (); } else { @@ -144,6 +149,7 @@ namespace MonoDevelop.Components.Docking public override void MouseDragged (NSEvent theEvent) { + lastEventTimestamp = theEvent.Timestamp; SetResizeCursor (); var point = NSEvent.CurrentMouseLocation; @@ -165,15 +171,55 @@ namespace MonoDevelop.Components.Docking } } - void AddRemoveFilter (bool enable) + double lastEventTimestamp = Foundation.NSProcessInfo.ProcessInfo.SystemUptime; + bool enableGdkEventFiler; + bool gdkEventFilterInserted; + bool isDisposed; + + public override void RemoveFromSuperview () + { + RemoveGdkEventFilter (); + base.RemoveFromSuperview (); + } + + protected override void Dispose (bool disposing) { - if (enable) + isDisposed = true; + if (disposing) + RemoveGdkEventFilter (); + base.Dispose (disposing); + } + + void AddGdkEventFilter () + { + enableGdkEventFiler = true; + if (!gdkEventFilterInserted) { Gdk.Window.AddFilterForAll (Filter); - else + gdkEventFilterInserted = true; + } + } + + void RemoveGdkEventFilter () + { + enableGdkEventFiler = false; + if (gdkEventFilterInserted) { Gdk.Window.RemoveFilterForAll (Filter); + gdkEventFilterInserted = false; + } } - static Gdk.FilterReturn Filter (IntPtr xevent, Gdk.Event evnt) => Gdk.FilterReturn.Remove; + Gdk.FilterReturn Filter (IntPtr xevent, Gdk.Event evnt) + { + if (enableGdkEventFiler && !isDisposed && Window != null) { + // always recover GDK events after 2 seconds of inactivity, this makes sure + // that we don't lose GDK events forever if some other native view steals events + // which are required for the drag exit condition. + if (Foundation.NSProcessInfo.ProcessInfo.SystemUptime - lastEventTimestamp < 2.0) + return Gdk.FilterReturn.Remove; + } + RemoveGdkEventFilter (); + return Gdk.FilterReturn.Continue; + } } } |