瀏覽代碼

Fixed Menu: Was not dealing with Border correctly

Tig Kindel 1 年之前
父節點
當前提交
3d30b06212

+ 1 - 1
Terminal.Gui/View/Layout/ViewLayout.cs

@@ -561,7 +561,7 @@ public partial class View
 
     // CONCURRENCY: This method is not thread-safe.
     // Undefined behavior and likely program crashes are exposed by unsynchronized access to InternalSubviews.
-    public static View? FindDeepestView (View? start, int x, int y, bool findAdornments = false)
+    public static View? FindDeepestView (View? start, int x, int y, bool findAdornments = true)
     {
         if (start is null || !start.Visible)
         {

+ 20 - 32
Terminal.Gui/Views/Menu/Menu.cs

@@ -719,35 +719,24 @@ internal sealed class Menu : View
             return;
         }
 
-        Point locationOffset = _host.GetScreenOffsetFromCurrent ();
-
-        if (SuperView is { } && SuperView != Application.Current)
+        if (!Visible)
         {
-            locationOffset.X += SuperView.Border.Thickness.Left;
-            locationOffset.Y += SuperView.Border.Thickness.Top;
+            throw new InvalidOperationException ("This shouldn't running on a invisible menu!");
         }
 
-        View view = FindDeepestView (this, a.MouseEvent.X + locationOffset.X, a.MouseEvent.Y + locationOffset.Y);
-
-        if (view == this)
+        Point boundsPoint = ScreenToBounds (a.MouseEvent.X, a.MouseEvent.Y);
+        var me = new MouseEvent
         {
-            if (!Visible)
-            {
-                throw new InvalidOperationException ("This shouldn't running on a invisible menu!");
-            }
+            X = boundsPoint.X,
+            Y = boundsPoint.Y,
+            Flags = a.MouseEvent.Flags,
+            ScreenPosition = new (a.MouseEvent.X, a.MouseEvent.Y),
+            View = this
+        };
 
-            var screen = view.FrameToScreen ();
-            var nme = new MouseEvent {
-                X = a.MouseEvent.X - screen.X,
-                Y = a.MouseEvent.Y - screen.Y,
-                Flags = a.MouseEvent.Flags,
-                View = view
-            };
-
-            if (OnMouseEvent (nme) || a.MouseEvent.Flags == MouseFlags.Button1Pressed || a.MouseEvent.Flags == MouseFlags.Button1Released)
-            {
-                a.MouseEvent.Handled = true;
-            }
+        if (OnMouseEvent (me) || a.MouseEvent.Flags == MouseFlags.Button1Pressed || a.MouseEvent.Flags == MouseFlags.Button1Released)
+        {
+            a.MouseEvent.Handled = true;
         }
     }
 
@@ -1192,23 +1181,22 @@ internal sealed class Menu : View
 
         _host._handled = false;
         bool disabled;
-        int meY = me.Y - (Border is null ? 0 : Border.Thickness.Top);
 
         if (me.Flags == MouseFlags.Button1Clicked)
         {
             disabled = false;
 
-            if (meY < 0)
+            if (me.Y < 0)
             {
                 return true;
             }
 
-            if (meY >= _barItems.Children.Length)
+            if (me.Y >= _barItems.Children.Length)
             {
                 return true;
             }
 
-            MenuItem item = _barItems.Children [meY];
+            MenuItem item = _barItems.Children [me.Y];
 
             if (item is null || !item.IsEnabled ())
             {
@@ -1220,7 +1208,7 @@ internal sealed class Menu : View
                 return true;
             }
 
-            _currentChild = meY;
+            _currentChild = me.Y;
             RunSelected ();
 
             return true;
@@ -1238,12 +1226,12 @@ internal sealed class Menu : View
         {
             disabled = false;
 
-            if (meY < 0 || meY >= _barItems.Children.Length)
+            if (me.Y < 0 || me.Y >= _barItems.Children.Length)
             {
                 return true;
             }
 
-            MenuItem item = _barItems.Children [meY];
+            MenuItem item = _barItems.Children [me.Y];
 
             if (item is null)
             {
@@ -1257,7 +1245,7 @@ internal sealed class Menu : View
 
             if (!disabled)
             {
-                _currentChild = meY;
+                _currentChild = me.Y;
             }
 
             if (_host.UseSubMenusSingleFrame || !CheckSubMenu ())

+ 2 - 2
UnitTests/View/FindDeepestViewTests.cs

@@ -217,10 +217,10 @@ public class FindDeepestViewTests (ITestOutputHelper output)
     [InlineData (10, 10, false)]
     [InlineData (7, 8, false)]
     [InlineData (6, 7, false)]
+    [InlineData (1, 2, false)]
+    [InlineData (5, 6, false)]
 
-    [InlineData (1, 2, true)]
     [InlineData (2, 3, true)]
-    [InlineData (5, 6, true)]
     [InlineData (2, 3, true)]
     public void Returns_Correct_If_SubView_Has_Adornments (int testX, int testY, bool expectedSubViewFound)
     {

+ 11 - 33
UnitTests/View/NavigationTests.cs

@@ -857,7 +857,7 @@ public class NavigationTests
         Assert.Equal (0, col);
         Assert.Equal (0, row);
         var found = View.FindDeepestView (top, 0, 0);
-        Assert.Equal (top, found);
+        Assert.Equal (top.Border, found);
  
         Assert.Equal (0, found.Frame.X);
         Assert.Equal (0, found.Frame.Y);
@@ -915,33 +915,28 @@ public class NavigationTests
         Assert.Equal (0, col);
         Assert.Equal (0, row);
         found = View.FindDeepestView (top, 0, 0);
-        Assert.Equal (top, found);
-        //Assert.Equal (0, found.FrameToScreen ().X);
-        //Assert.Equal (0, found.FrameToScreen ().Y);
+        Assert.Equal (top.Border, found);
+
         Assert.Equal (new Point (-1, -1), view.ScreenToFrame (3, 2));
         view.BoundsToScreen (0, 0, out col, out row);
         Assert.Equal (4, col);
         Assert.Equal (3, row);
         found = View.FindDeepestView (top, 4, 3);
         Assert.Equal (view, found);
-        //Assert.Equal (0, found.FrameToScreen ().X);
-        //Assert.Equal (0, found.FrameToScreen ().Y);
+        
         Assert.Equal (new Point (9, -1), view.ScreenToFrame (13, 2));
         view.BoundsToScreen (10, 0, out col, out row);
         Assert.Equal (14, col);
         Assert.Equal (3, row);
         found = View.FindDeepestView (top, 14, 3);
         Assert.Equal (top, found);
-        //Assert.Equal (14, found.FrameToScreen ().X);
-        //Assert.Equal (3, found.FrameToScreen ().Y);
+        
         Assert.Equal (new Point (10, 0), view.ScreenToFrame (14, 3));
         view.BoundsToScreen (11, 1, out col, out row);
         Assert.Equal (15, col);
         Assert.Equal (4, row);
         found = View.FindDeepestView (top, 15, 4);
         Assert.Equal (top, found);
-        //Assert.Equal (15, found.FrameToScreen ().X);
-        //Assert.Equal (4, found.FrameToScreen ().Y);
     }
 
     [Fact]
@@ -1017,30 +1012,25 @@ public class NavigationTests
         Assert.Equal (0, row);
         var found = View.FindDeepestView (top, -4, -3);
         Assert.Null (found);
-        //Assert.Equal (0, found.FrameToScreen ().X);
-        //Assert.Equal (0, found.FrameToScreen ().Y);
         Assert.Equal (Point.Empty, top.ScreenToFrame (3, 2));
+
         top.BoundsToScreen (0, 0, out col, out row);
         Assert.Equal (4, col);
         Assert.Equal (3, row);
-        Assert.Equal (top, View.FindDeepestView (top, 3, 2));
-        //Assert.Equal (0, found.FrameToScreen ().X);
-        //Assert.Equal (0, found.FrameToScreen ().Y);
+        Assert.Equal (top.Border, View.FindDeepestView (top, 3, 2));
         Assert.Equal (new Point (10, 0), top.ScreenToFrame (13, 2));
+
         top.BoundsToScreen (10, 0, out col, out row);
         Assert.Equal (14, col);
         Assert.Equal (3, row);
-        Assert.Equal (top, View.FindDeepestView (top, 13, 2));
-        //Assert.Equal (10, found.FrameToScreen ().X);
-        //Assert.Equal (0, found.FrameToScreen ().Y);
+        Assert.Equal (top.Border, View.FindDeepestView (top, 13, 2));
+
         Assert.Equal (new Point (11, 1), top.ScreenToFrame (14, 3));
         top.BoundsToScreen (11, 1, out col, out row);
         Assert.Equal (15, col);
         Assert.Equal (4, row);
         Assert.Equal (top, View.FindDeepestView (top, 14, 3));
-        //Assert.Equal (11, found.FrameToScreen ().X);
-        //Assert.Equal (1, found.FrameToScreen ().Y);
-
+        
         // view
         Assert.Equal (new Point (-7, -5), view.ScreenToFrame (0, 0));
         view.Margin.BoundsToScreen (-6, -4, out col, out row);
@@ -1056,43 +1046,31 @@ public class NavigationTests
         Assert.Equal (1, col);
         Assert.Equal (1, row);
         Assert.Null (View.FindDeepestView (top, 1, 1));
-        //Assert.Equal (0, found.FrameToScreen ().X);
-        //Assert.Equal (0, found.FrameToScreen ().Y);
         Assert.Equal (new Point (-4, -3), view.ScreenToFrame (3, 2));
         view.BoundsToScreen (-3, -2, out col, out row);
         Assert.Equal (4, col);
         Assert.Equal (3, row);
         Assert.Equal (top, View.FindDeepestView (top, 4, 3));
-        //Assert.Equal (1, found.FrameToScreen ().X);
-        //Assert.Equal (1, found.FrameToScreen ().Y);
         Assert.Equal (new Point (-1, -1), view.ScreenToFrame (6, 4));
         view.BoundsToScreen (0, 0, out col, out row);
         Assert.Equal (7, col);
         Assert.Equal (5, row);
         Assert.Equal (view, View.FindDeepestView (top, 7, 5));
-        //Assert.Equal (0, found.FrameToScreen ().X);
-        //Assert.Equal (0, found.FrameToScreen ().Y);
         Assert.Equal (new Point (6, -1), view.ScreenToFrame (13, 4));
         view.BoundsToScreen (7, 0, out col, out row);
         Assert.Equal (14, col);
         Assert.Equal (5, row);
         Assert.Equal (view, View.FindDeepestView (top, 14, 5));
-        //Assert.Equal (7, found.FrameToScreen ().X);
-        //Assert.Equal (0, found.FrameToScreen ().Y);
         Assert.Equal (new Point (7, -2), view.ScreenToFrame (14, 3));
         view.BoundsToScreen (8, -1, out col, out row);
         Assert.Equal (15, col);
         Assert.Equal (4, row);
         Assert.Equal (top, View.FindDeepestView (top, 15, 4));
-        //Assert.Equal (12, found.FrameToScreen ().X);
-        //Assert.Equal (2, found.FrameToScreen ().Y);
         Assert.Equal (new Point (16, -2), view.ScreenToFrame (23, 3));
         view.BoundsToScreen (17, -1, out col, out row);
         Assert.Equal (24, col);
         Assert.Equal (4, row);
         Assert.Null (View.FindDeepestView (top, 24, 4));
-        //Assert.Equal (0, found.FrameToScreen ().X);
-        //Assert.Equal (0, found.FrameToScreen ().Y);
     }
 
     [Fact]

+ 5 - 5
UnitTests/Views/ContextMenuTests.cs

@@ -643,7 +643,7 @@ public class ContextMenuTests
         Assert.True (
                      top.Subviews [0]
                         .OnMouseEvent (
-                                     new MouseEvent { X = 0, Y = 4, Flags = MouseFlags.ReportMousePosition, View = top.Subviews [0] }
+                                     new MouseEvent { X = 0, Y = 3, Flags = MouseFlags.ReportMousePosition, View = top.Subviews [0] }
                                     )
                     );
         Application.Refresh ();
@@ -691,7 +691,7 @@ public class ContextMenuTests
         Assert.True (
                      top.Subviews [0]
                         .OnMouseEvent (
-                                     new MouseEvent { X = 30, Y = 4, Flags = MouseFlags.ReportMousePosition, View = top.Subviews [0] }
+                                     new MouseEvent { X = 30, Y = 3, Flags = MouseFlags.ReportMousePosition, View = top.Subviews [0] }
                                     )
                     );
         Application.Refresh ();
@@ -738,7 +738,7 @@ public class ContextMenuTests
         Assert.True (
                      top.Subviews [0]
                         .OnMouseEvent (
-                                     new MouseEvent { X = 30, Y = 4, Flags = MouseFlags.ReportMousePosition, View = top.Subviews [0] }
+                                     new MouseEvent { X = 30, Y = 3, Flags = MouseFlags.ReportMousePosition, View = top.Subviews [0] }
                                     )
                     );
         Application.Refresh ();
@@ -782,7 +782,7 @@ public class ContextMenuTests
         Assert.True (
                      top.Subviews [0]
                         .OnMouseEvent (
-                                     new MouseEvent { X = 30, Y = 4, Flags = MouseFlags.ReportMousePosition, View = top.Subviews [0] }
+                                     new MouseEvent { X = 30, Y = 3, Flags = MouseFlags.ReportMousePosition, View = top.Subviews [0] }
                                     )
                     );
         Application.Refresh ();
@@ -826,7 +826,7 @@ public class ContextMenuTests
         Assert.True (
                      top.Subviews [0]
                         .OnMouseEvent (
-                                     new MouseEvent { X = 30, Y = 4, Flags = MouseFlags.ReportMousePosition, View = top.Subviews [0] }
+                                     new MouseEvent { X = 30, Y = 3, Flags = MouseFlags.ReportMousePosition, View = top.Subviews [0] }
                                     )
                     );
         Application.Refresh ();

+ 13 - 13
UnitTests/Views/MenuBarTests.cs

@@ -44,7 +44,7 @@ public class MenuBarTests
 
         Assert.True (
                      menu._openMenu.OnMouseEvent (
-                                                new MouseEvent { X = 0, Y = 1, Flags = MouseFlags.Button1Clicked, View = menu._openMenu }
+                                                new MouseEvent { X = 0, Y = 0, Flags = MouseFlags.Button1Clicked, View = menu._openMenu }
                                                )
                     );
         Application.MainLoop.RunIteration ();
@@ -76,7 +76,7 @@ public class MenuBarTests
 
         Assert.True (
                      menu._openMenu.OnMouseEvent (
-                                                new MouseEvent { X = 0, Y = 1, Flags = MouseFlags.Button1Clicked, View = menu._openMenu }
+                                                new MouseEvent { X = 0, Y = 0, Flags = MouseFlags.Button1Clicked, View = menu._openMenu }
                                                )
                     );
         Application.MainLoop.RunIteration ();
@@ -94,7 +94,7 @@ public class MenuBarTests
 
         Assert.True (
                      menu._openMenu.OnMouseEvent (
-                                                new MouseEvent { X = 0, Y = 1, Flags = MouseFlags.Button1Clicked, View = menu._openMenu }
+                                                new MouseEvent { X = 0, Y = 0, Flags = MouseFlags.Button1Clicked, View = menu._openMenu }
                                                )
                     );
         Application.MainLoop.RunIteration ();
@@ -549,7 +549,7 @@ public class MenuBarTests
                                                       _output
                                                      );
 
-        for (var i = 1; i < items.Count; i++)
+        for (var i = 0; i < items.Count; i++)
         {
             menu.OpenMenu ();
 
@@ -2190,7 +2190,7 @@ wo
 
         Assert.True (
                      mCurrent.OnMouseEvent (
-                                          new MouseEvent { X = 1, Y = 2, Flags = MouseFlags.ReportMousePosition, View = mCurrent }
+                                          new MouseEvent { X = 1, Y = 1, Flags = MouseFlags.ReportMousePosition, View = mCurrent }
                                          )
                     );
         Assert.True (menu.IsMenuOpen);
@@ -2199,7 +2199,7 @@ wo
 
         Assert.True (
                      mCurrent.OnMouseEvent (
-                                          new MouseEvent { X = 1, Y = 3, Flags = MouseFlags.ReportMousePosition, View = mCurrent }
+                                          new MouseEvent { X = 1, Y = 2, Flags = MouseFlags.ReportMousePosition, View = mCurrent }
                                          )
                     );
         Assert.True (menu.IsMenuOpen);
@@ -2385,7 +2385,7 @@ Edit
         // Click on Paste
         Assert.True (
                      mCurrent.OnMouseEvent (
-                                          new MouseEvent { X = 10, Y = 3, Flags = MouseFlags.ReportMousePosition, View = mCurrent }
+                                          new MouseEvent { X = 10, Y = 2, Flags = MouseFlags.ReportMousePosition, View = mCurrent }
                                          )
                     );
         Assert.True (menu.IsMenuOpen);
@@ -2418,12 +2418,12 @@ Edit
             if (i == 2)
             {
                 Assert.Equal ("_Edit", miCurrent.Parent.Title);
-                Assert.Equal ("C_ut", miCurrent.Title);
+                Assert.Equal ("_Paste", miCurrent.Title);
             }
             else if (i == 1)
             {
                 Assert.Equal ("_Edit", miCurrent.Parent.Title);
-                Assert.Equal ("_Copy", miCurrent.Title);
+                Assert.Equal ("C_ut", miCurrent.Title);
             }
             else if (i == 0)
             {
@@ -2965,7 +2965,7 @@ Edit
                       menu.OnMouseEvent (
                                        new MouseEvent
                                        {
-                                           X = 1, Y = 3, Flags = MouseFlags.ReportMousePosition, View = Application.Top.Subviews [1]
+                                           X = 1, Y = 2, Flags = MouseFlags.ReportMousePosition, View = Application.Top.Subviews [1]
                                        }
                                       )
                      );
@@ -2988,7 +2988,7 @@ Edit
                       menu.OnMouseEvent (
                                        new MouseEvent
                                        {
-                                           X = 1, Y = 2, Flags = MouseFlags.ReportMousePosition, View = Application.Top.Subviews [1]
+                                           X = 1, Y = 1, Flags = MouseFlags.ReportMousePosition, View = Application.Top.Subviews [1]
                                        }
                                       )
                      );
@@ -3270,7 +3270,7 @@ Edit
 
         Assert.False (
                       menu.OnMouseEvent (
-                                       new MouseEvent { X = 1, Y = 3, Flags = MouseFlags.Button1Clicked, View = Application.Top.Subviews [1] }
+                                       new MouseEvent { X = 1, Y = 2, Flags = MouseFlags.Button1Clicked, View = Application.Top.Subviews [1] }
                                       )
                      );
         Application.Top.Draw ();
@@ -3290,7 +3290,7 @@ Edit
 
         Assert.False (
                       menu.OnMouseEvent (
-                                       new MouseEvent { X = 1, Y = 2, Flags = MouseFlags.Button1Clicked, View = Application.Top.Subviews [2] }
+                                       new MouseEvent { X = 1, Y = 1, Flags = MouseFlags.Button1Clicked, View = Application.Top.Subviews [2] }
                                       )
                      );
         Application.Top.Draw ();