diff --git a/Terminal.Gui/Application.cs b/Terminal.Gui/Application.cs
index 53cd14af6..b8cbb7f1f 100644
--- a/Terminal.Gui/Application.cs
+++ b/Terminal.Gui/Application.cs
@@ -318,7 +318,7 @@ public static partial class Application
private static void Driver_SizeChanged (object sender, SizeChangedEventArgs e) { OnSizeChanging (e); }
private static void Driver_KeyDown (object sender, Key e) { OnKeyDown (e); }
private static void Driver_KeyUp (object sender, Key e) { OnKeyUp (e); }
- private static void Driver_MouseEvent (object sender, MouseEventEventArgs e) { OnMouseEvent (e); }
+ private static void Driver_MouseEvent (object sender, MouseEvent e) { OnMouseEvent (e); }
/// Gets of list of types that are available.
///
@@ -1441,12 +1441,12 @@ public static partial class Application
///
/// The will contain the that contains the mouse coordinates.
///
- public static event EventHandler MouseEvent;
+ public static event EventHandler MouseEvent;
/// Called when a mouse event occurs. Raises the event.
/// This method can be used to simulate a mouse event, e.g. in unit tests.
/// The mouse event with coordinates relative to the screen.
- internal static void OnMouseEvent (MouseEventEventArgs a)
+ internal static void OnMouseEvent (MouseEvent mouseEvent)
{
if (IsMouseDisabled)
{
@@ -1454,16 +1454,16 @@ public static partial class Application
}
// TODO: In PR #3273, FindDeepestView will return adornments. Update logic below to fix adornment mouse handling
- var view = View.FindDeepestView (Current, a.MouseEvent.X, a.MouseEvent.Y);
+ var view = View.FindDeepestView (Current, mouseEvent.X, mouseEvent.Y);
if (view is { })
{
- a.MouseEvent.View = view;
+ mouseEvent.View = view;
}
- MouseEvent?.Invoke (null, new (a.MouseEvent));
+ MouseEvent?.Invoke (null, mouseEvent);
- if (a.MouseEvent.Handled)
+ if (mouseEvent.Handled)
{
return;
}
@@ -1472,25 +1472,25 @@ public static partial class Application
{
// If the mouse is grabbed, send the event to the view that grabbed it.
// The coordinates are relative to the Bounds of the view that grabbed the mouse.
- Point boundsLoc = MouseGrabView.ScreenToBounds (a.MouseEvent.X, a.MouseEvent.Y);
+ Point boundsLoc = MouseGrabView.ScreenToBounds (mouseEvent.X, mouseEvent.Y);
var viewRelativeMouseEvent = new MouseEvent
{
X = boundsLoc.X,
Y = boundsLoc.Y,
- Flags = a.MouseEvent.Flags,
- ScreenPosition = new (a.MouseEvent.X, a.MouseEvent.Y),
+ Flags = mouseEvent.Flags,
+ ScreenPosition = new (mouseEvent.X, mouseEvent.Y),
View = MouseGrabView
};
if (MouseGrabView.Bounds.Contains (viewRelativeMouseEvent.X, viewRelativeMouseEvent.Y) is false)
{
// The mouse has moved outside the bounds of the view that grabbed the mouse
- _mouseEnteredView?.OnMouseLeave (a.MouseEvent);
+ _mouseEnteredView?.OnMouseLeave (mouseEvent);
}
//System.Diagnostics.Debug.WriteLine ($"{nme.Flags};{nme.X};{nme.Y};{mouseGrabView}");
- if (MouseGrabView?.OnMouseEvent (viewRelativeMouseEvent) == true)
+ if (MouseGrabView?.NewMouseEvent (viewRelativeMouseEvent) == true)
{
return;
}
@@ -1511,13 +1511,13 @@ public static partial class Application
if ((view is null || view == OverlappedTop)
&& Current is { Modal: false }
&& OverlappedTop != null
- && a.MouseEvent.Flags != MouseFlags.ReportMousePosition
- && a.MouseEvent.Flags != 0)
+ && mouseEvent.Flags != MouseFlags.ReportMousePosition
+ && mouseEvent.Flags != 0)
{
// This occurs when there are multiple overlapped "tops"
// E.g. "Mdi" - in the Background Worker Scenario
- View? top = FindDeepestTop (Top, a.MouseEvent.X, a.MouseEvent.Y);
- view = View.FindDeepestView (top, a.MouseEvent.X, a.MouseEvent.Y);
+ View? top = FindDeepestTop (Top, mouseEvent.X, mouseEvent.Y);
+ view = View.FindDeepestView (top, mouseEvent.X, mouseEvent.Y);
if (view is { } && view != OverlappedTop && top != Current)
{
@@ -1535,27 +1535,27 @@ public static partial class Application
if (view is Adornment adornment)
{
- Point frameLoc = adornment.ScreenToFrame (a.MouseEvent.X, a.MouseEvent.Y);
+ Point frameLoc = adornment.ScreenToFrame (mouseEvent.X, mouseEvent.Y);
me = new ()
{
X = frameLoc.X,
Y = frameLoc.Y,
- Flags = a.MouseEvent.Flags,
- ScreenPosition = new (a.MouseEvent.X, a.MouseEvent.Y),
+ Flags = mouseEvent.Flags,
+ ScreenPosition = new (mouseEvent.X, mouseEvent.Y),
View = view
};
}
- else if (view.BoundsToScreen (view.Bounds).Contains (a.MouseEvent.X, a.MouseEvent.Y))
+ else if (view.BoundsToScreen (view.Bounds).Contains (mouseEvent.X, mouseEvent.Y))
{
- Point boundsPoint = view.ScreenToBounds (a.MouseEvent.X, a.MouseEvent.Y);
+ Point boundsPoint = view.ScreenToBounds (mouseEvent.X, mouseEvent.Y);
me = new ()
{
X = boundsPoint.X,
Y = boundsPoint.Y,
- Flags = a.MouseEvent.Flags,
- ScreenPosition = new (a.MouseEvent.X, a.MouseEvent.Y),
+ Flags = mouseEvent.Flags,
+ ScreenPosition = new (mouseEvent.X, mouseEvent.Y),
View = view
};
}
@@ -1577,7 +1577,7 @@ public static partial class Application
_mouseEnteredView = view;
}
- if (!view.WantMousePositionReports && a.MouseEvent.Flags == MouseFlags.ReportMousePosition)
+ if (!view.WantMousePositionReports && mouseEvent.Flags == MouseFlags.ReportMousePosition)
{
return;
}
@@ -1586,7 +1586,7 @@ public static partial class Application
//Debug.WriteLine ($"OnMouseEvent: ({a.MouseEvent.X},{a.MouseEvent.Y}) - {a.MouseEvent.Flags}");
- if (view.OnMouseEvent (me))
+ if (view.NewMouseEvent (me) == false)
{
// Should we bubble up the event, if it is not handled?
//return;
diff --git a/Terminal.Gui/ConsoleDrivers/ConsoleDriver.cs b/Terminal.Gui/ConsoleDrivers/ConsoleDriver.cs
index 2a80f3473..1974b6147 100644
--- a/Terminal.Gui/ConsoleDrivers/ConsoleDriver.cs
+++ b/Terminal.Gui/ConsoleDrivers/ConsoleDriver.cs
@@ -538,11 +538,11 @@ public abstract class ConsoleDriver
public void OnKeyUp (Key a) { KeyUp?.Invoke (this, a); }
/// Event fired when a mouse event occurs.
- public event EventHandler MouseEvent;
+ public event EventHandler MouseEvent;
/// Called when a mouse event occurs. Fires the event.
///
- public void OnMouseEvent (MouseEventEventArgs a) { MouseEvent?.Invoke (this, a); }
+ public void OnMouseEvent (MouseEvent a) { MouseEvent?.Invoke (this, a); }
/// Simulates a key press.
/// The key character.
diff --git a/Terminal.Gui/ConsoleDrivers/CursesDriver/CursesDriver.cs b/Terminal.Gui/ConsoleDrivers/CursesDriver/CursesDriver.cs
index 08457cc83..d372c52d4 100644
--- a/Terminal.Gui/ConsoleDrivers/CursesDriver/CursesDriver.cs
+++ b/Terminal.Gui/ConsoleDrivers/CursesDriver/CursesDriver.cs
@@ -812,7 +812,7 @@ internal class CursesDriver : ConsoleDriver
var me = new MouseEvent { Flags = mouseFlag, X = pos.X, Y = pos.Y };
Debug.WriteLine ($"CursesDriver: ({me.X},{me.Y}) - {me.Flags}");
- OnMouseEvent (new MouseEventEventArgs (me));
+ OnMouseEvent (me);
}
#region Color Handling
diff --git a/Terminal.Gui/ConsoleDrivers/NetDriver.cs b/Terminal.Gui/ConsoleDrivers/NetDriver.cs
index 0f4188be4..4a85804f2 100644
--- a/Terminal.Gui/ConsoleDrivers/NetDriver.cs
+++ b/Terminal.Gui/ConsoleDrivers/NetDriver.cs
@@ -1138,7 +1138,7 @@ internal class NetDriver : ConsoleDriver
case EventType.Mouse:
MouseEvent me = ToDriverMouse (inputEvent.MouseEvent);
Debug.WriteLine ($"NetDriver: ({me.X},{me.Y}) - {me.Flags}");
- OnMouseEvent (new MouseEventEventArgs (me));
+ OnMouseEvent (me);
break;
case EventType.WindowSize:
diff --git a/Terminal.Gui/ConsoleDrivers/WindowsDriver.cs b/Terminal.Gui/ConsoleDrivers/WindowsDriver.cs
index ac5dd75ff..e02234aa3 100644
--- a/Terminal.Gui/ConsoleDrivers/WindowsDriver.cs
+++ b/Terminal.Gui/ConsoleDrivers/WindowsDriver.cs
@@ -1396,18 +1396,16 @@ internal class WindowsDriver : ConsoleDriver
break;
}
- OnMouseEvent (new MouseEventEventArgs (me));
+ OnMouseEvent (me);
if (_processButtonClick)
{
- OnMouseEvent (
- new MouseEventEventArgs (
- new MouseEvent
- {
- X = me.X,
- Y = me.Y,
- Flags = ProcessButtonClick (inputEvent.MouseEvent)
- }));
+ OnMouseEvent (new ()
+ {
+ X = me.X,
+ Y = me.Y,
+ Flags = ProcessButtonClick (inputEvent.MouseEvent)
+ });
}
break;
@@ -1715,7 +1713,7 @@ internal class WindowsDriver : ConsoleDriver
{
// When a user presses-and-holds, start generating pressed events every `startDelay`
// After `iterationsUntilFast` iterations, speed them up to `fastDelay` ms
- const int startDelay = 50;
+ const int startDelay = 500;
const int iterationsUntilFast = 4;
const int fastDelay = 50;
@@ -1744,7 +1742,7 @@ internal class WindowsDriver : ConsoleDriver
//Debug.WriteLine($"ProcessContinuousButtonPressedAsync: {view}");
if (_isButtonPressed && (mouseFlag & MouseFlags.ReportMousePosition) == 0)
{
- Application.Invoke (() => OnMouseEvent (new MouseEventEventArgs (me)));
+ Application.Invoke (() => OnMouseEvent (me));
}
}
}
diff --git a/Terminal.Gui/View/Adornment/Border.cs b/Terminal.Gui/View/Adornment/Border.cs
index 5cf8cd808..8e32edde2 100644
--- a/Terminal.Gui/View/Adornment/Border.cs
+++ b/Terminal.Gui/View/Adornment/Border.cs
@@ -56,6 +56,9 @@ public class Border : Adornment
Parent = parent;
Application.GrabbingMouse += Application_GrabbingMouse;
Application.UnGrabbingMouse += Application_UnGrabbingMouse;
+
+ EnablingHighlight += Border_EnablingHighlight;
+ DisablingHighlight += Border_DisablingHighlight;
}
#if SUBVIEW_BASED_BORDER
@@ -187,6 +190,23 @@ public class Border : Adornment
#region Mouse Support
+ private LineStyle _savedHighlightLineStyle;
+
+ private void Border_EnablingHighlight (object sender, System.ComponentModel.CancelEventArgs e)
+ {
+ _savedHighlightLineStyle = Parent?.BorderStyle ?? LineStyle;
+ LineStyle = LineStyle.Heavy;
+ Parent?.SetNeedsDisplay ();
+ e.Cancel = true;
+ }
+
+ private void Border_DisablingHighlight (object sender, System.ComponentModel.CancelEventArgs e)
+ {
+ LineStyle = _savedHighlightLineStyle;
+ Parent?.SetNeedsDisplay ();
+ e.Cancel = true;
+ }
+
private Point? _dragPosition;
private Point _startGrabPoint;
@@ -222,6 +242,7 @@ public class Border : Adornment
_startGrabPoint = new (mouseEvent.X + Frame.X, mouseEvent.Y + Frame.Y);
_dragPosition = new (mouseEvent.X, mouseEvent.Y);
Application.GrabMouse (this);
+ EnableHighlight ();
}
return true;
@@ -265,6 +286,7 @@ public class Border : Adornment
{
_dragPosition = null;
Application.UngrabMouse ();
+ DisableHighlight();
return true;
}
diff --git a/Terminal.Gui/View/ViewAdornments.cs b/Terminal.Gui/View/ViewAdornments.cs
index 5cf036439..55445cef8 100644
--- a/Terminal.Gui/View/ViewAdornments.cs
+++ b/Terminal.Gui/View/ViewAdornments.cs
@@ -99,7 +99,10 @@ public partial class View
if (value != LineStyle.None)
{
- Border.Thickness = new (1);
+ if (Border.Thickness == Thickness.Empty)
+ {
+ Border.Thickness = new (1);
+ }
}
else
{
diff --git a/Terminal.Gui/View/ViewMouse.cs b/Terminal.Gui/View/ViewMouse.cs
index 689168e50..9f3dac4f2 100644
--- a/Terminal.Gui/View/ViewMouse.cs
+++ b/Terminal.Gui/View/ViewMouse.cs
@@ -1,4 +1,7 @@
-namespace Terminal.Gui;
+using System.ComponentModel;
+using System.Diagnostics;
+
+namespace Terminal.Gui;
public partial class View
{
@@ -77,18 +80,31 @@ public partial class View
/// Event fired when the mouse leaves the View's .
public event EventHandler MouseLeave;
- [CanBeNull]
- private ColorScheme _savedColorScheme;
-
- /// Called when a mouse event occurs within the view's .
+ ///
+ /// Processes a . This method is called by when a mouse
+ /// event occurs.
+ ///
///
///
- /// The coordinates are relative to .
+ /// A view must be both enabled and visible to receive mouse events.
+ ///
+ ///
+ /// This method calls to process the event. If the event is not handled, and one of the
+ /// mouse buttons was clicked, it calls to process the click.
+ ///
+ ///
+ /// If is , the view will be highlighted when the mouse is
+ /// pressed.
+ /// See and for more information.
+ ///
+ ///
+ /// If is , the event
+ /// will be invoked repeatedly while the button is pressed.
///
///
///
- /// , if the event was handled, otherwise.
- protected internal virtual bool OnMouseEvent (MouseEvent mouseEvent)
+ /// if the event was handled, otherwise.
+ public bool? NewMouseEvent (MouseEvent mouseEvent)
{
if (!Enabled)
{
@@ -101,23 +117,67 @@ public partial class View
return false;
}
- var args = new MouseEventEventArgs (mouseEvent);
+ if (OnMouseEvent (mouseEvent))
+ {
+ // Technically mouseEvent.Handled should already be true if implementers of OnMouseEvent
+ // follow the rules. But we'll update it just in case.
+ return mouseEvent.Handled = true;
+ }
- // Default behavior is to invoke Accept (via HotKey) on clicked.
- if (
- // !WantContinuousButtonPressed &&
- Application.MouseGrabView != this
+ if ((HighlightOnPress || WantContinuousButtonPressed) && Highlight (mouseEvent))
+ {
+ Debug.Assert (mouseEvent.Handled);
+
+ return mouseEvent.Handled;
+ }
+
+ if (mouseEvent.Flags.HasFlag (MouseFlags.Button1Clicked)
+ || mouseEvent.Flags.HasFlag (MouseFlags.Button2Clicked)
+ || mouseEvent.Flags.HasFlag (MouseFlags.Button3Clicked)
+ || mouseEvent.Flags.HasFlag (MouseFlags.Button4Clicked))
+ {
+ return OnMouseClick (new (mouseEvent));
+ }
+
+ return false;
+ }
+
+ ///
+ /// Highlight the view when the mouse is pressed.
+ ///
+ ///
+ ///
+ /// Set to to have the view highlighted when the mouse is
+ /// pressed.
+ ///
+ ///
+ /// Calls which fires the event.
+ ///
+ ///
+ /// Calls which fires the event.
+ ///
+ ///
+ ///
+ /// , if the event was handled, otherwise.
+ private bool Highlight (MouseEvent mouseEvent)
+ {
+ if (Application.MouseGrabView == this
&& (mouseEvent.Flags.HasFlag (MouseFlags.Button1Clicked)
|| mouseEvent.Flags.HasFlag (MouseFlags.Button2Clicked)
|| mouseEvent.Flags.HasFlag (MouseFlags.Button3Clicked)
|| mouseEvent.Flags.HasFlag (MouseFlags.Button4Clicked)))
- {
- return OnMouseClick (args);
- }
-
- if (!HighlightOnPress)
{
- return false;
+ // We're grabbed. Clicked event comes after the last Release. This is our signal to ungrab
+ Application.UngrabMouse ();
+ DisableHighlight ();
+
+ // If mouse is still in bounds, click
+ if (!WantContinuousButtonPressed && Bounds.Contains (mouseEvent.X, mouseEvent.Y))
+ {
+ return OnMouseClick (new (mouseEvent));
+ }
+
+ return mouseEvent.Handled = true;
}
if (mouseEvent.Flags.HasFlag (MouseFlags.Button1Pressed)
@@ -125,47 +185,34 @@ public partial class View
|| mouseEvent.Flags.HasFlag (MouseFlags.Button3Pressed)
|| mouseEvent.Flags.HasFlag (MouseFlags.Button4Pressed))
{
- // If WantContinuousButtonPressed is true, and this is not the first pressed event,
- // invoke Accept (via HotKey)
- if (WantContinuousButtonPressed && Application.MouseGrabView == this)
- {
- return OnMouseClick (args);
- }
-
- // The first time we get pressed event, grab the mouse and invert the colors
+ // The first time we get pressed event, grab the mouse and set focus
if (Application.MouseGrabView != this)
{
Application.GrabMouse (this);
- if (HighlightOnPress && ColorScheme is { })
- {
- _savedColorScheme = ColorScheme;
- if (CanFocus)
- {
- // TODO: Make the inverted color configurable
- var cs = new ColorScheme (ColorScheme)
- {
- Focus = new (ColorScheme.Normal.Foreground, ColorScheme.Focus.Background)
- };
- ColorScheme = cs;
- }
- else
- {
- var cs = new ColorScheme (ColorScheme)
- {
- Normal = new (ColorScheme.Focus.Background, ColorScheme.Normal.Foreground)
- };
- ColorScheme = cs;
- }
- }
-
if (CanFocus)
{
// Set the focus, but don't invoke Accept
SetFocus ();
}
}
- args.Handled = true;
+
+ if (Bounds.Contains (mouseEvent.X, mouseEvent.Y))
+ {
+ EnableHighlight ();
+ }
+ else
+ {
+ DisableHighlight ();
+ }
+
+ if (WantContinuousButtonPressed && Application.MouseGrabView == this)
+ {
+ // If this is not the first pressed event, click
+ return OnMouseClick (new (mouseEvent));
+ }
+
+ return mouseEvent.Handled = true;
}
if (mouseEvent.Flags.HasFlag (MouseFlags.Button1Released)
@@ -173,31 +220,128 @@ public partial class View
|| mouseEvent.Flags.HasFlag (MouseFlags.Button3Released)
|| mouseEvent.Flags.HasFlag (MouseFlags.Button4Released))
{
-
if (Application.MouseGrabView == this)
{
- // When the mouse is released, if WantContinuousButtonPressed is set, invoke Accept one last time.
- //if (WantContinuousButtonPressed)
- {
- OnMouseClick (args);
- }
-
- Application.UngrabMouse ();
-
- if (HighlightOnPress && _savedColorScheme is { })
- {
- ColorScheme = _savedColorScheme;
- _savedColorScheme = null;
- }
+ DisableHighlight ();
}
- args.Handled = true;
+
+ return mouseEvent.Handled = true;
}
- if (args.Handled != true)
+ return mouseEvent.Handled;
+ }
+
+ [CanBeNull]
+ private ColorScheme _savedHighlightColorScheme;
+
+ ///
+ /// Enables the highlight for the view. Called from OnMouseEvent.
+ ///
+ public void EnableHighlight ()
+ {
+ if (OnEnablingHighlight () == true)
{
- MouseEvent?.Invoke (this, args);
+ return;
}
+ if (_savedHighlightColorScheme is null && ColorScheme is { })
+ {
+ _savedHighlightColorScheme ??= ColorScheme;
+
+ if (CanFocus)
+ {
+ // TODO: Make the inverted color configurable
+ var cs = new ColorScheme (ColorScheme)
+ {
+ // For Buttons etc...
+ Focus = new (ColorScheme.Normal.Foreground, ColorScheme.Focus.Background),
+
+ // For Adornments
+ Normal = new (ColorScheme.Focus.Foreground, ColorScheme.Normal.Background)
+ };
+ ColorScheme = cs;
+ }
+ else
+ {
+ var cs = new ColorScheme (ColorScheme)
+ {
+ // For Buttons etc... that can't focus (like up/down).
+ Normal = new (ColorScheme.Focus.Background, ColorScheme.Normal.Foreground)
+ };
+ ColorScheme = cs;
+ }
+ }
+ }
+
+ ///
+ /// Fired when the view is highlighted. Set to
+ /// to implement a custom highlight scheme or prevent the view from being highlighted.
+ ///
+ public event EventHandler EnablingHighlight;
+
+ ///
+ /// Called when the view is to be highlighted.
+ ///
+ /// , if the event was handled, otherwise.
+ protected virtual bool? OnEnablingHighlight ()
+ {
+ CancelEventArgs args = new ();
+ EnablingHighlight?.Invoke (this, args);
+
+ return args.Cancel;
+ }
+
+ ///
+ /// Disables the highlight for the view. Called from OnMouseEvent.
+ ///
+ public void DisableHighlight ()
+ {
+ if (OnDisablingHighlight () == true)
+ {
+ return;
+ }
+
+ // Unhighlight
+ if (_savedHighlightColorScheme is { })
+ {
+ ColorScheme = _savedHighlightColorScheme;
+ _savedHighlightColorScheme = null;
+ }
+ }
+
+ ///
+ /// Fired when the view is no longer to be highlighted. Set to
+ ///
+ /// to implement a custom highlight scheme or prevent the view from being highlighted.
+ ///
+ public event EventHandler DisablingHighlight;
+
+ ///
+ /// Called when the view is no longer to be highlighted.
+ ///
+ /// , if the event was handled, otherwise.
+ protected virtual bool? OnDisablingHighlight ()
+ {
+ CancelEventArgs args = new ();
+ DisablingHighlight?.Invoke (this, args);
+
+ return args.Cancel;
+ }
+
+ /// Called when a mouse event occurs within the view's .
+ ///
+ ///
+ /// The coordinates are relative to .
+ ///
+ ///
+ ///
+ /// , if the event was handled, otherwise.
+ protected internal virtual bool OnMouseEvent (MouseEvent mouseEvent)
+ {
+ var args = new MouseEventEventArgs (mouseEvent);
+
+ MouseEvent?.Invoke (this, args);
+
return args.Handled;
}
diff --git a/Terminal.Gui/Views/ComboBox.cs b/Terminal.Gui/Views/ComboBox.cs
index 9d151f465..b3c719b5e 100644
--- a/Terminal.Gui/Views/ComboBox.cs
+++ b/Terminal.Gui/Views/ComboBox.cs
@@ -264,7 +264,7 @@ public class ComboBox : View
FocusSelectedItem ();
}
- return true;
+ return me.Handled = true;
}
if (me.Flags == MouseFlags.Button1Pressed)
@@ -274,7 +274,7 @@ public class ComboBox : View
_search.SetFocus ();
}
- return true;
+ return me.Handled = true;
}
return false;
diff --git a/Terminal.Gui/Views/Menu/Menu.cs b/Terminal.Gui/Views/Menu/Menu.cs
index d02791836..60f7c00bf 100644
--- a/Terminal.Gui/Views/Menu/Menu.cs
+++ b/Terminal.Gui/Views/Menu/Menu.cs
@@ -712,9 +712,9 @@ internal sealed class Menu : View
}
}
- private void Application_RootMouseEvent (object sender, MouseEventEventArgs a)
+ private void Application_RootMouseEvent (object sender, MouseEvent a)
{
- if (a.MouseEvent.View is { } and (MenuBar or not Menu))
+ if (a.View is { } and (MenuBar or not Menu))
{
return;
}
@@ -724,21 +724,21 @@ internal sealed class Menu : View
throw new InvalidOperationException ("This shouldn't running on a invisible menu!");
}
- View view = a.MouseEvent.View ?? this;
+ View view = a.View ?? this;
- Point boundsPoint = view.ScreenToBounds (a.MouseEvent.X, a.MouseEvent.Y);
+ Point boundsPoint = view.ScreenToBounds (a.X, a.Y);
var me = new MouseEvent
{
X = boundsPoint.X,
Y = boundsPoint.Y,
- Flags = a.MouseEvent.Flags,
- ScreenPosition = new (a.MouseEvent.X, a.MouseEvent.Y),
+ Flags = a.Flags,
+ ScreenPosition = new (a.X, a.Y),
View = view
};
- if (view.OnMouseEvent (me) || a.MouseEvent.Flags == MouseFlags.Button1Pressed || a.MouseEvent.Flags == MouseFlags.Button1Released)
+ if (view.NewMouseEvent (me) == true || a.Flags == MouseFlags.Button1Pressed || a.Flags == MouseFlags.Button1Released)
{
- a.MouseEvent.Handled = true;
+ a.Handled = true;
}
}
@@ -1189,12 +1189,12 @@ internal sealed class Menu : View
if (me.Y < 0)
{
- return true;
+ return me.Handled = true;
}
if (me.Y >= _barItems.Children.Length)
{
- return true;
+ return me.Handled = true;
}
MenuItem item = _barItems.Children [me.Y];
@@ -1206,13 +1206,13 @@ internal sealed class Menu : View
if (disabled)
{
- return true;
+ return me.Handled = true;
}
_currentChild = me.Y;
RunSelected ();
- return true;
+ return me.Handled = true;
}
if (me.Flags != MouseFlags.Button1Pressed
@@ -1229,14 +1229,14 @@ internal sealed class Menu : View
if (me.Y < 0 || me.Y >= _barItems.Children.Length)
{
- return true;
+ return me.Handled = true;
}
MenuItem item = _barItems.Children [me.Y];
if (item is null)
{
- return true;
+ return me.Handled = true;
}
if (item?.IsEnabled () != true)
@@ -1254,12 +1254,12 @@ internal sealed class Menu : View
SetNeedsDisplay ();
SetParentSetNeedsDisplay ();
- return true;
+ return me.Handled = true;
}
_host.OnMenuOpened ();
- return true;
+ return me.Handled = true;
}
}
diff --git a/Terminal.Gui/Views/Menu/MenuBar.cs b/Terminal.Gui/Views/Menu/MenuBar.cs
index e1c8189ac..07ff6912c 100644
--- a/Terminal.Gui/Views/Menu/MenuBar.cs
+++ b/Terminal.Gui/Views/Menu/MenuBar.cs
@@ -1715,7 +1715,7 @@ public class MenuBar : View
{
if (!CloseMenu (true, false))
{
- return true;
+ return me.Handled = true;
}
Activate (i);
@@ -1733,7 +1733,7 @@ public class MenuBar : View
}
}
- return true;
+ return me.Handled = true;
}
if (i == Menus.Length - 1 && me.Flags == MouseFlags.Button1Clicked)
@@ -1742,7 +1742,7 @@ public class MenuBar : View
{
CloseAllMenus ();
- return true;
+ return me.Handled = true;
}
}
@@ -1804,7 +1804,7 @@ public class MenuBar : View
nme = new () { X = me.X + current.Frame.X, Y = 0, Flags = me.Flags, View = v };
}
- v.OnMouseEvent (nme);
+ v.NewMouseEvent (nme);
return false;
}
diff --git a/Terminal.Gui/Views/ScrollBarView.cs b/Terminal.Gui/Views/ScrollBarView.cs
index 92fcbd505..e70f1e5c7 100644
--- a/Terminal.Gui/Views/ScrollBarView.cs
+++ b/Terminal.Gui/Views/ScrollBarView.cs
@@ -325,7 +325,7 @@ public class ScrollBarView : View
|| mouseEvent.Flags == MouseFlags.WheeledRight
|| mouseEvent.Flags == MouseFlags.WheeledLeft))
{
- return Host.OnMouseEvent (mouseEvent);
+ return Host.NewMouseEvent (mouseEvent) == true;
}
if (mouseEvent.Flags == MouseFlags.Button1Pressed && location == 0)
@@ -800,7 +800,7 @@ public class ScrollBarView : View
|| me.MouseEvent.Flags == MouseFlags.WheeledRight
|| me.MouseEvent.Flags == MouseFlags.WheeledLeft)
{
- OnMouseEvent (me.MouseEvent);
+ NewMouseEvent (me.MouseEvent);
}
else if (me.MouseEvent.Flags == MouseFlags.Button1Clicked)
{
diff --git a/Terminal.Gui/Views/ScrollView.cs b/Terminal.Gui/Views/ScrollView.cs
index 72ebcb355..f021932ab 100644
--- a/Terminal.Gui/Views/ScrollView.cs
+++ b/Terminal.Gui/Views/ScrollView.cs
@@ -434,11 +434,11 @@ public class ScrollView : View
}
else if (me.X == _vertical.Frame.X && ShowVerticalScrollIndicator)
{
- _vertical.OnMouseEvent (me);
+ _vertical.NewMouseEvent (me);
}
else if (me.Y == _horizontal.Frame.Y && ShowHorizontalScrollIndicator)
{
- _horizontal.OnMouseEvent (me);
+ _horizontal.NewMouseEvent (me);
}
else if (IsOverridden (me.View, "OnMouseEvent"))
{
diff --git a/Terminal.Gui/Views/TabView.cs b/Terminal.Gui/Views/TabView.cs
index 88689e2c5..8c7638a1d 100644
--- a/Terminal.Gui/Views/TabView.cs
+++ b/Terminal.Gui/Views/TabView.cs
@@ -533,7 +533,7 @@ public class TabView : View
return Style.ShowTopLine ? 3 : 2;
}
- private void Tab_MouseClick (object sender, MouseEventEventArgs e) { e.Handled = _tabsBar.OnMouseEvent (e.MouseEvent); }
+ private void Tab_MouseClick (object sender, MouseEventEventArgs e) { e.Handled = _tabsBar.NewMouseEvent (e.MouseEvent) == true; }
private void UnSetCurrentTabs ()
{
diff --git a/UICatalog/Scenarios/ASCIICustomButton.cs b/UICatalog/Scenarios/ASCIICustomButton.cs
index 729db9265..8051e08ea 100644
--- a/UICatalog/Scenarios/ASCIICustomButton.cs
+++ b/UICatalog/Scenarios/ASCIICustomButton.cs
@@ -134,7 +134,7 @@ public class ASCIICustomButtonTest : Scenario
}
public event Action PointerEnter;
- private void This_MouseClick (object sender, MouseEventEventArgs obj) { OnMouseEvent (obj.MouseEvent); }
+ private void This_MouseClick (object sender, MouseEventEventArgs obj) { NewMouseEvent (obj.MouseEvent); }
}
public class ScrollViewTestWindow : Window
diff --git a/UICatalog/Scenarios/Adornments.cs b/UICatalog/Scenarios/Adornments.cs
index 91c40f5a4..302eda623 100644
--- a/UICatalog/Scenarios/Adornments.cs
+++ b/UICatalog/Scenarios/Adornments.cs
@@ -85,7 +85,7 @@ public class Adornments : Scenario
view.X = 36;
view.Y = 0;
view.Width = Dim.Percent (60);
- view.Height = Dim.Percent (80);
+ view.Height = Dim.Percent (80);
editor.Initialized += (s, e) => { editor.ViewToEdit = view; };
diff --git a/UICatalog/Scenarios/BasicColors.cs b/UICatalog/Scenarios/BasicColors.cs
index faefc6441..9fc6fead5 100644
--- a/UICatalog/Scenarios/BasicColors.cs
+++ b/UICatalog/Scenarios/BasicColors.cs
@@ -85,10 +85,10 @@ public class BasicColors : Scenario
Application.MouseEvent += (s, e) =>
{
- if (e.MouseEvent.View != null)
+ if (e.View != null)
{
- Color fore = e.MouseEvent.View.GetNormalColor ().Foreground;
- Color back = e.MouseEvent.View.GetNormalColor ().Background;
+ Color fore = e.View.GetNormalColor ().Foreground;
+ Color back = e.View.GetNormalColor ().Background;
lblForeground.Text =
$"#{fore.R:X2}{fore.G:X2}{fore.B:X2} {fore.GetClosestNamedColor ()} ";
diff --git a/UICatalog/Scenarios/ContextMenus.cs b/UICatalog/Scenarios/ContextMenus.cs
index 35ac50c64..f1bb6c90d 100644
--- a/UICatalog/Scenarios/ContextMenus.cs
+++ b/UICatalog/Scenarios/ContextMenus.cs
@@ -74,7 +74,7 @@ public class ContextMenus : Scenario
Application.MouseEvent += ApplicationMouseEvent;
- void ApplicationMouseEvent (object sender, MouseEventEventArgs a) { mousePos = new Point (a.MouseEvent.X, a.MouseEvent.Y); }
+ void ApplicationMouseEvent (object sender, MouseEvent a) { mousePos = new Point (a.X, a.Y); }
Win.WantMousePositionReports = true;
diff --git a/UICatalog/Scenarios/Mouse.cs b/UICatalog/Scenarios/Mouse.cs
index 9e4096e4a..7291ba92c 100644
--- a/UICatalog/Scenarios/Mouse.cs
+++ b/UICatalog/Scenarios/Mouse.cs
@@ -58,10 +58,10 @@ public class Mouse : Scenario
win.Add (ml);
- CheckBox cbWantContinuousPresses = new CheckBox ()
+ CheckBox cbWantContinuousPresses = new ()
{
X = Pos.Right (filterSlider),
- Y = Pos.Bottom (ml) + 1,
+ Y = Pos.Bottom (ml),
Title = "_Want Continuous Button Pressed",
};
cbWantContinuousPresses.Toggled += (s, e) =>
@@ -70,11 +70,23 @@ public class Mouse : Scenario
};
win.Add (cbWantContinuousPresses);
+ CheckBox cbHighlightOnPress = new ()
+ {
+ X = Pos.Right (filterSlider),
+ Y = Pos.Bottom (cbWantContinuousPresses),
+ Title = "_Highlight on Press",
+ };
+ cbHighlightOnPress.Toggled += (s, e) =>
+ {
+ win.HighlightOnPress = !win.HighlightOnPress;
+ };
+
+ win.Add (cbHighlightOnPress);
var demo = new MouseDemo ()
{
X = Pos.Right (filterSlider),
- Y = Pos.Bottom (cbWantContinuousPresses) + 1,
+ Y = Pos.Bottom (cbHighlightOnPress),
Width = 20,
Height = 3,
Text = "Enter/Leave Demo",
@@ -105,17 +117,15 @@ public class Mouse : Scenario
Application.MouseEvent += (sender, a) =>
{
- var i = filterSlider.Options.FindIndex (o => o.Data == a.MouseEvent.Flags);
+ var i = filterSlider.Options.FindIndex (o => o.Data == a.Flags);
if (filterSlider.GetSetOptions().Contains(i))
{
- ml.Text = $"MouseEvent: ({a.MouseEvent.X},{a.MouseEvent.Y}) - {a.MouseEvent.Flags} {count}";
- appLogList.Add ($"({a.MouseEvent.X},{a.MouseEvent.Y}) - {a.MouseEvent.Flags} {count++}");
+ ml.Text = $"MouseEvent: ({a.X},{a.Y}) - {a.Flags} {count}";
+ appLogList.Add ($"({a.X},{a.Y}) - {a.Flags} {count++}");
appLog.MoveDown ();
- }
+ }
};
-
-
label = new Label ()
{
Text = "_Window Events:",
@@ -137,13 +147,19 @@ public class Mouse : Scenario
clearButton.Accept += (s, e) =>
{
appLogList.Clear ();
+ appLog.SetSource (appLogList);
winLogList.Clear ();
+ winLog.SetSource(winLogList);
};
win.MouseEvent += (sender, a) =>
{
- winLogList.Add ($"MouseEvent: ({a.MouseEvent.X},{a.MouseEvent.Y}) - {a.MouseEvent.Flags} {count++}");
- winLog.MoveDown ();
+ var i = filterSlider.Options.FindIndex (o => o.Data == a.MouseEvent.Flags);
+ if (filterSlider.GetSetOptions ().Contains (i))
+ {
+ winLogList.Add ($"MouseEvent: ({a.MouseEvent.X},{a.MouseEvent.Y}) - {a.MouseEvent.Flags} {count++}");
+ winLog.MoveDown ();
+ }
};
win.MouseClick += (sender, a) =>
{
diff --git a/UICatalog/Scenarios/Scrolling.cs b/UICatalog/Scenarios/Scrolling.cs
index 33c15e866..f9cf29376 100644
--- a/UICatalog/Scenarios/Scrolling.cs
+++ b/UICatalog/Scenarios/Scrolling.cs
@@ -251,7 +251,7 @@ public class Scrolling : Scenario
Text = "Mouse: "
};
Win.Add (mousePos);
- Application.MouseEvent += (sender, a) => { mousePos.Text = $"Mouse: ({a.MouseEvent.X},{a.MouseEvent.Y}) - {a.MouseEvent.Flags} {count++}"; };
+ Application.MouseEvent += (sender, a) => { mousePos.Text = $"Mouse: ({a.X},{a.Y}) - {a.Flags} {count++}"; };
var progress = new ProgressBar { X = Pos.Right (scrollView) + 1, Y = Pos.AnchorEnd (2), Width = 50 };
Win.Add (progress);
diff --git a/UICatalog/Scenarios/TrueColors.cs b/UICatalog/Scenarios/TrueColors.cs
index df8697106..7e8962617 100644
--- a/UICatalog/Scenarios/TrueColors.cs
+++ b/UICatalog/Scenarios/TrueColors.cs
@@ -76,9 +76,9 @@ public class TrueColors : Scenario
Application.MouseEvent += (s, e) =>
{
- if (e.MouseEvent.View != null)
+ if (e.View != null)
{
- Attribute normal = e.MouseEvent.View.GetNormalColor ();
+ Attribute normal = e.View.GetNormalColor ();
lblRed.Text = normal.Foreground.R.ToString ();
lblGreen.Text = normal.Foreground.G.ToString ();
lblBlue.Text = normal.Foreground.B.ToString ();
diff --git a/UnitTests/Application/ApplicationTests.cs b/UnitTests/Application/ApplicationTests.cs
index 2dbad7ccc..9569c99b7 100644
--- a/UnitTests/Application/ApplicationTests.cs
+++ b/UnitTests/Application/ApplicationTests.cs
@@ -41,9 +41,9 @@ public class ApplicationTests
{
Assert.Null (Application.Top);
Application.Begin (new ());
- Assert.Equal (new Rectangle (0, 0, 80, 25), Application.Top.Frame);
+ Assert.Equal (new (0, 0, 80, 25), Application.Top.Frame);
((FakeDriver)Application.Driver).SetBufferSize (5, 5);
- Assert.Equal (new Rectangle (0, 0, 5, 5), Application.Top.Frame);
+ Assert.Equal (new (0, 0, 5, 5), Application.Top.Frame);
}
[Fact]
@@ -62,10 +62,10 @@ public class ApplicationTests
Assert.Null (rs.Toplevel);
- var top = Application.Top;
+ Toplevel top = Application.Top;
#if DEBUG_IDISPOSABLE
- var exception = Record.Exception (() => Shutdown ());
+ Exception exception = Record.Exception (() => Shutdown ());
Assert.NotNull (exception);
Assert.False (top.WasDisposed);
top.Dispose ();
@@ -130,7 +130,7 @@ public class ApplicationTests
var driver = (ConsoleDriver)Activator.CreateInstance (driverType);
Application.Init (driverName: driverType.Name);
Assert.NotNull (Application.Driver);
- Assert.NotEqual(driver, Application.Driver);
+ Assert.NotEqual (driver, Application.Driver);
Assert.Equal (driverType, Application.Driver.GetType ());
Shutdown ();
}
@@ -212,7 +212,7 @@ public class ApplicationTests
Application._mainThreadId = 1;
//Application._topLevels = new List ();
- Application._mouseEnteredView = new View ();
+ Application._mouseEnteredView = new ();
//Application.SupportedCultures = new List ();
Application.Force16Colors = true;
@@ -225,7 +225,7 @@ public class ApplicationTests
//Application.OverlappedChildren = new List ();
//Application.OverlappedTop =
- Application._mouseEnteredView = new View ();
+ Application._mouseEnteredView = new ();
//Application.WantContinuousButtonPressedView = new View ();
@@ -464,6 +464,7 @@ public class ApplicationTests
Application.Run (t1);
Assert.Equal (t1, Application.Top);
+
// top wasn't run and so never was added to toplevel's stack
Assert.NotEqual (top, Application.Top);
#if DEBUG_IDISPOSABLE
@@ -511,7 +512,6 @@ public class ApplicationTests
#region RunTests
[Fact]
-
public void Run_T_After_InitWithDriver_with_TopLevel_Does_Not_Throws ()
{
// Setup Mock driver
@@ -533,7 +533,6 @@ public class ApplicationTests
}
[Fact]
-
public void Run_T_After_InitWithDriver_with_TopLevel_and_Driver_Does_Not_Throws ()
{
// Setup Mock driver
@@ -547,6 +546,7 @@ public class ApplicationTests
Assert.True (Application.Top is Window);
Application.Top.Dispose ();
+
// Run when already initialized or not with a Driver will not throw (because Dialog is derived from Toplevel)
Application.Run