Ver código fonte

Fixed stoopid screen bug

Tig 9 meses atrás
pai
commit
a632c238e9

+ 1 - 16
Terminal.Gui/Application/Application.Screen.cs

@@ -3,28 +3,13 @@ namespace Terminal.Gui;
 
 public static partial class Application // Screen related stuff
 {
-    private static Size _screenSize = new (2048, 2048);
-
-    /// <summary>
-    ///     INTERNAL API for Unit Tests. Only works if there's no driver.
-    /// </summary>
-    /// <param name="size"></param>
-    internal static void SetScreenSize (Size size)
-    {
-        if (Driver is { })
-        {
-            throw new InvalidOperationException ("Cannot set the screen size when the ConsoleDriver is already initialized.");
-        }
-        _screenSize = size;
-    }
-
     /// <summary>
     ///     Gets the size of the screen. This is the size of the screen as reported by the <see cref="ConsoleDriver"/>.
     /// </summary>
     /// <remarks>
     ///     If the <see cref="ConsoleDriver"/> has not been initialized, this will return a default size of 2048x2048; useful for unit tests.
     /// </remarks>
-    public static Rectangle Screen => Driver?.Screen ?? new (new (0, 0), _screenSize);
+    public static Rectangle Screen => Driver?.Screen ?? new (new (0, 0), new (2048, 2048));
 
     /// <summary>Invoked when the terminal's size changed. The new size of the terminal is provided.</summary>
     /// <remarks>

+ 2 - 1
Terminal.Gui/View/Adornment/Adornment.cs

@@ -62,7 +62,8 @@ public class Adornment : View
             if (current != _thickness)
             {
                 Parent?.SetAdornmentFrames ();
-                Parent?.SetLayoutNeeded ();
+                SetLayoutNeeded ();
+                //Parent?.SetLayoutNeeded ();
 
                 OnThicknessChanged ();
             }

+ 22 - 45
Terminal.Gui/View/View.Layout.cs

@@ -167,7 +167,7 @@ public partial class View // Layout APIs
 
     #region Frame
 
-    private Rectangle _frame;
+    private Rectangle? _frame;
 
     /// <summary>Gets or sets the absolute location and dimension of the view.</summary>
     /// <value>
@@ -199,7 +199,7 @@ public partial class View // Layout APIs
             {
                 //Debug.WriteLine("Frame_get with _layoutNeeded");
             }
-            return _frame;
+            return _frame ?? Rectangle.Empty;
         }
         set
         {
@@ -207,10 +207,10 @@ public partial class View // Layout APIs
             if (SetFrame (value with { Width = Math.Max (value.Width, 0), Height = Math.Max (value.Height, 0) }))
             {
                 // If Frame gets set, set all Pos/Dim to Absolute values.
-                _x = _frame.X;
-                _y = _frame.Y;
-                _width = _frame.Width;
-                _height = _frame.Height;
+                _x = _frame!.Value.X;
+                _y = _frame!.Value.Y;
+                _width = _frame!.Value.Width;
+                _height = _frame!.Value.Height;
 
                 // Implicit layout is ok here because we are setting the Frame directly.
                 Layout ();
@@ -308,6 +308,18 @@ public partial class View // Layout APIs
         return frame;
     }
 
+    // helper for X, Y, Width, Height setters to ensure consistency
+    private void PosDimSet ()
+    {
+        SetLayoutNeeded ();
+
+        if (_x is PosAbsolute && _y is PosAbsolute && _width is DimAbsolute && _height is DimAbsolute)
+        {
+            // Implicit layout is ok here because all Pos/Dim are Absolute values.
+            Layout ();
+        }
+    }
+
     private Pos _x = Pos.Absolute (0);
 
     /// <summary>Gets or sets the X position for the view (the column).</summary>
@@ -346,22 +358,10 @@ public partial class View // Layout APIs
 
             _x = value ?? throw new ArgumentNullException (nameof (value), @$"{nameof (X)} cannot be null");
 
-            SetLayoutNeeded ();
-
-            if (IsAbsoluteLayout ())
-            {
-                // Implicit layout is ok here because all Pos/Dim are Absolute values.
-                Layout ();
-                SetLayoutNeeded ();
-            }
+            PosDimSet ();
         }
     }
 
-    private bool IsAbsoluteLayout ()
-    {
-        return _x is PosAbsolute && _y is PosAbsolute && _width is DimAbsolute && _height is DimAbsolute;
-    }
-
     private Pos _y = Pos.Absolute (0);
 
 
@@ -400,15 +400,7 @@ public partial class View // Layout APIs
             }
 
             _y = value ?? throw new ArgumentNullException (nameof (value), @$"{nameof (Y)} cannot be null");
-
-            SetLayoutNeeded ();
-
-            if (IsAbsoluteLayout ())
-            {
-                // Implicit layout is ok here because all Pos/Dim are Absolute values.
-                Layout ();
-                SetLayoutNeeded ();
-            }
+            PosDimSet ();
         }
     }
 
@@ -459,14 +451,7 @@ public partial class View // Layout APIs
             // Reset TextFormatter - Will be recalculated in SetTextFormatterSize
             TextFormatter.ConstrainToHeight = null;
 
-            SetLayoutNeeded ();
-
-            if (IsAbsoluteLayout ())
-            {
-                // Implicit layout is ok here because all Pos/Dim are Absolute values.
-                Layout ();
-                SetLayoutNeeded ();
-            }
+            PosDimSet ();
         }
     }
 
@@ -517,15 +502,7 @@ public partial class View // Layout APIs
 
             // Reset TextFormatter - Will be recalculated in SetTextFormatterSize
             TextFormatter.ConstrainToWidth = null;
-
-            SetLayoutNeeded ();
-
-            if (IsAbsoluteLayout ())
-            {
-                // Implicit layout is ok here because all Pos/Dim are Absolute values.
-                Layout ();
-                SetLayoutNeeded ();
-            }
+            PosDimSet ();
         }
     }
 

+ 23 - 14
UnitTests/View/Draw/NeedsDisplayTests.cs

@@ -1,8 +1,4 @@
 #nullable enable
-using System.Text;
-using Microsoft.VisualStudio.TestPlatform.Utilities;
-using Xunit.Abstractions;
-
 namespace Terminal.Gui.ViewTests;
 
 [Trait ("Category", "Output")]
@@ -116,7 +112,7 @@ public class NeedsDisplayTests ()
     }
 
     [Fact]
-    public void NeedsDisplay_False_After_SetRelativeLayout ()
+    public void NeedsDisplay_False_After_SetRelativeLayout_Absolute_Dims ()
     {
         var view = new View { Width = 2, Height = 2 };
         Assert.True (view.NeedsDisplay);
@@ -131,16 +127,22 @@ public class NeedsDisplayTests ()
         Assert.False (view.NeedsDisplay);
 
         view.SetLayoutNeeded ();
+
         // SRL won't change anything since the view is Absolute
         view.SetRelativeLayout (Application.Screen.Size);
         Assert.True (view.NeedsDisplay);
 
         view.NeedsDisplay = false;
+
         // SRL won't change anything since the view is Absolute. However, Layout has not been called
         view.SetRelativeLayout (new (10, 10));
         Assert.True (view.NeedsDisplay);
+    }
 
-        view = new View { Width = Dim.Percent (50), Height = Dim.Percent (50) };
+    [Fact]
+    public void NeedsDisplay_False_After_SetRelativeLayout_Relative_Dims ()
+    {
+        var view = new View { Width = Dim.Percent (50), Height = Dim.Percent (50) };
         View superView = new ()
         {
             Id = "superView",
@@ -164,18 +166,25 @@ public class NeedsDisplayTests ()
         superView.SetRelativeLayout (Application.Screen.Size);
         Assert.True (view.NeedsDisplay);
         Assert.True (superView.NeedsDisplay);
+    }
 
-        superView.NeedsDisplay = false;
-        superView.SetRelativeLayout (new (10, 10));
+
+    [Fact]
+    public void NeedsDisplay_False_After_SetRelativeLayout_10x10 ()
+    {
+        View superView = new ()
+        {
+            Id = "superView",
+            Width = Dim.Fill (),
+            Height = Dim.Fill ()
+        };
         Assert.True (superView.NeedsDisplay);
-        Assert.True (view.NeedsDisplay);
 
         superView.Layout ();
 
-        view.SetRelativeLayout (new (11, 11));
+        superView.NeedsDisplay = false;
+        superView.SetRelativeLayout (new (10, 10));
         Assert.True (superView.NeedsDisplay);
-        Assert.True (view.NeedsDisplay);
-
     }
 
     [Fact]
@@ -258,7 +267,7 @@ public class NeedsDisplayTests ()
         view.Frame = new (3, 3, 6, 6); // Grow right/bottom 1
         Assert.Equal (new (3, 3, 6, 6), view.Frame);
         Assert.Equal (new (0, 0, 6, 6), view.Viewport);
-        Assert.Equal (new (0, 0, 6, 6), view._needsDisplayRect); 
+        Assert.Equal (new (0, 0, 6, 6), view._needsDisplayRect);
 
         view.Frame = new (3, 3, 5, 5); // Shrink right/bottom 1
         Assert.Equal (new (3, 3, 5, 5), view.Frame);
@@ -278,7 +287,7 @@ public class NeedsDisplayTests ()
         view.Frame = new (3, 3, 6, 6); // Grow right/bottom 1
         Assert.Equal (new (3, 3, 6, 6), view.Frame);
         Assert.Equal (new (1, 1, 6, 6), view.Viewport);
-        Assert.Equal (new (1, 1, 6, 6), view._needsDisplayRect); 
+        Assert.Equal (new (1, 1, 6, 6), view._needsDisplayRect);
 
         view.Frame = new (3, 3, 5, 5);
         Assert.Equal (new (3, 3, 5, 5), view.Frame);

+ 2 - 1
UnitTests/View/Layout/Dim.AutoTests.cs

@@ -994,9 +994,10 @@ public partial class DimAutoTests (ITestOutputHelper output)
     }
 
     [Fact]
+    [SetupFakeDriver]
     public void DimAutoStyle_Content_Pos_AnchorEnd_Locates_Correctly ()
     {
-        Application.SetScreenSize (new Size (10, 10));
+        (((FakeDriver)Application.Driver)!).SetBufferSize(10,10);
 
         DimAutoTestView view = new (Auto (DimAutoStyle.Content), Auto (DimAutoStyle.Content));
 

+ 159 - 2
UnitTests/View/Layout/FrameTests.cs

@@ -22,14 +22,171 @@ public class FrameTests (ITestOutputHelper output)
     {
         Rectangle frame = new (1, 2, 3, 4);
         View view = new ();
+        Assert.False (view.NeedsLayout);
         Assert.Equal (Rectangle.Empty, view.Frame);
 
-        view.BeginInit ();
-        view.EndInit ();
         view.Frame = frame;
         Assert.Equal (frame, view.Frame);
+        Assert.False (view.NeedsLayout);
+
+        Assert.Equal(view.X, frame.X);
+        Assert.Equal (view.Y, frame.Y);
+        Assert.Equal (view.Width, frame.Width);
+        Assert.Equal (view.Height, frame.Height);
+    }
+
+    [Fact]
+    public void Frame_Initializer_Sets ()
+    {
+        Rectangle frame = new (1, 2, 3, 4);
+        View view = new ()
+        {
+            Frame = frame,
+        };
+
+        Assert.Equal (frame, view.Frame);
+        Assert.False (view.NeedsLayout);
+        Assert.Equal (frame.Size, view.Viewport.Size);
+
+
+        Assert.Equal (view.X, frame.X);
+        Assert.Equal (view.Y, frame.Y);
+        Assert.Equal (view.Width, frame.Width);
+        Assert.Equal (view.Height, frame.Height);
+    }
+
+
+    [Fact]
+    public void Frame_Empty_Initializer_Sets ()
+    {
+        Rectangle frame = new (1, 2, 3, 4);
+        View view = new ()
+        {
+            Frame = frame,
+        };
+
+        Assert.Equal (frame, view.Frame);
+        Assert.False (view.NeedsLayout);
+        Assert.Equal (frame.Size, view.Viewport.Size);
+
+        Assert.Equal (view.X, frame.X);
+        Assert.Equal (view.Y, frame.Y);
+        Assert.Equal (view.Width, frame.Width);
+        Assert.Equal (view.Height, frame.Height);
+
+        view.Frame = Rectangle.Empty;
+        Assert.Equal (Rectangle.Empty, view.Frame);
+        Assert.False (view.NeedsLayout);
+        Assert.Equal (Rectangle.Empty.Size, view.Viewport.Size);
+
+        Assert.Equal (view.X, Rectangle.Empty.X);
+        Assert.Equal (view.Y, Rectangle.Empty.Y);
+        Assert.Equal (view.Width, Rectangle.Empty.Width);
+        Assert.Equal (view.Height, Rectangle.Empty.Height);
+
+        view.Width = Dim.Fill ();
+        view.Height = Dim.Fill ();
+        Assert.True (view.NeedsLayout);
+        view.Layout ();
+        Assert.False (view.NeedsLayout);
+        Assert.Equal (Application.Screen, view.Frame);
+
+        view.Frame = Rectangle.Empty;
+        Assert.Equal (Rectangle.Empty, view.Frame);
+        Assert.False (view.NeedsLayout);
+        Assert.Equal (Rectangle.Empty.Size, view.Viewport.Size);
+
+        Assert.Equal (view.X, Rectangle.Empty.X);
+        Assert.Equal (view.Y, Rectangle.Empty.Y);
+        Assert.Equal (view.Width, Rectangle.Empty.Width);
+        Assert.Equal (view.Height, Rectangle.Empty.Height);
+
     }
 
+
+    [Fact]
+    public void Frame_Empty_Initializer_Overrides_Base ()
+    {
+        // Prove TestView is correct
+        FrameTestView view = new ();
+        Assert.True (view.NeedsLayout);
+
+        view.Layout ();
+        Assert.Equal (new Rectangle(10, 20, 30, 40), view.Frame);
+        Assert.Equal (10, view.X.GetAnchor(0));
+        Assert.Equal (20, view.Y.GetAnchor(0));
+        Assert.Equal (30, view.Width!.GetAnchor(0));
+        Assert.Equal (40, view.Height!.GetAnchor(0));
+        Assert.Equal (new Rectangle (0, 0, 30, 40), view.Viewport);
+
+        // Set Frame via init
+        Rectangle frame = new (1, 2, 3, 4);
+        view = new ()
+        {
+            Frame = frame,
+        };
+        Assert.Equal (frame, view.Frame);
+        Assert.False (view.NeedsLayout);
+        Assert.Equal (frame.Size, view.Viewport.Size);
+
+        Assert.Equal (view.X, frame.X);
+        Assert.Equal (view.Y, frame.Y);
+        Assert.Equal (view.Width, frame.Width);
+        Assert.Equal (view.Height, frame.Height);
+
+        // Set Frame via init to empty
+        frame = Rectangle.Empty;
+        view = new ()
+        {
+            Frame = frame,
+        };
+        Assert.Equal (frame, view.Frame);
+        Assert.False (view.NeedsLayout);
+        Assert.Equal (frame.Size, view.Viewport.Size);
+
+        Assert.Equal (view.X, frame.X);
+        Assert.Equal (view.Y, frame.Y);
+        Assert.Equal (view.Width, frame.Width);
+        Assert.Equal (view.Height, frame.Height);
+
+        // Set back to original state
+        view.X = Pos.Func (() => 10);
+        view.Y = Pos.Func (() => 20);
+        view.Width = Dim.Func (() => 30);
+        view.Height = Dim.Func (() => 40);
+        Assert.True (view.NeedsLayout);
+
+        view.Layout ();
+        Assert.Equal (new Rectangle (10, 20, 30, 40), view.Frame);
+        Assert.Equal (10, view.X.GetAnchor (0));
+        Assert.Equal (20, view.Y.GetAnchor (0));
+        Assert.Equal (30, view.Width!.GetAnchor (0));
+        Assert.Equal (40, view.Height!.GetAnchor (0));
+        Assert.Equal (new Rectangle (0, 0, 30, 40), view.Viewport);
+
+        view.Frame = frame;
+        Assert.Equal (frame, view.Frame);
+        Assert.False (view.NeedsLayout);
+        Assert.Equal (frame.Size, view.Viewport.Size);
+
+        Assert.Equal (view.X, frame.X);
+        Assert.Equal (view.Y, frame.Y);
+        Assert.Equal (view.Width, frame.Width);
+        Assert.Equal (view.Height, frame.Height);
+    }
+
+    private class FrameTestView : View
+    {
+        public FrameTestView ()
+        {
+            X = Pos.Func (() => 10);
+            Y = Pos.Func (() => 20);
+            Width = Dim.Func (() => 30);
+            Height = Dim.Func (() => 40);
+        }
+    }
+
+
     // Moved this test from AbsoluteLayoutTests
     // TODO: Refactor as Theory
     [Fact]

+ 0 - 2
UnitTests/Views/WindowTests.cs

@@ -154,8 +154,6 @@ public class WindowTests
         Assert.Equal ("title", windowWithFrameRectEmpty.Title);
         Assert.True (windowWithFrameRectEmpty.CanFocus);
         Assert.False (windowWithFrameRectEmpty.HasFocus);
-        Assert.Equal (Rectangle.Empty, windowWithFrameRectEmpty.Viewport);
-        Assert.Equal (Rectangle.Empty, windowWithFrameRectEmpty.Frame);
         Assert.Null (windowWithFrameRectEmpty.Focused);
         Assert.NotNull (windowWithFrameRectEmpty.ColorScheme);
         Assert.Equal (0, windowWithFrameRectEmpty.X);