Remove some bogosity from widget mouse handling.

This commit is contained in:
Paul Chote
2011-01-05 23:01:17 +13:00
parent df460d7407
commit 5254deedcb
13 changed files with 63 additions and 50 deletions

View File

@@ -44,7 +44,7 @@ namespace OpenRA.Widgets
return base.LoseFocus(mi); return base.LoseFocus(mi);
} }
public override bool HandleInputInner(MouseInput mi) public override bool HandleMouseInput(MouseInput mi)
{ {
if (mi.Button != MouseButton.Left) if (mi.Button != MouseButton.Left)
return false; return false;
@@ -55,15 +55,27 @@ namespace OpenRA.Widgets
// Only fire the onMouseUp order if we successfully lost focus, and were pressed // Only fire the onMouseUp order if we successfully lost focus, and were pressed
if (Focused && mi.Event == MouseInputEvent.Up) if (Focused && mi.Event == MouseInputEvent.Up)
{ {
var wasPressed = Depressed; LoseFocus(mi);
return (LoseFocus(mi) && wasPressed); return OnMouseUp(mi);
} }
if (mi.Event == MouseInputEvent.Down) if (mi.Event == MouseInputEvent.Down)
Depressed = true; {
// OnMouseDown returns false if the button shouldn't be pressed
if (!OnMouseDown(mi))
Depressed = true;
else
LoseFocus(mi);
}
else if (mi.Event == MouseInputEvent.Move && Focused) else if (mi.Event == MouseInputEvent.Move && Focused)
{
Depressed = RenderBounds.Contains(mi.Location.X, mi.Location.Y); Depressed = RenderBounds.Contains(mi.Location.X, mi.Location.Y);
// All widgets should recieve MouseMove events
OnMouseMove(mi);
}
return Depressed; return Depressed;
} }
@@ -120,11 +132,9 @@ namespace OpenRA.Widgets
public static void ShowDropPanel(Widget w, Widget panel, IEnumerable<Widget> dismissAfter, Func<bool> onDismiss) public static void ShowDropPanel(Widget w, Widget panel, IEnumerable<Widget> dismissAfter, Func<bool> onDismiss)
{ {
// Mask to prevent any clicks from being sent to other widgets
var fullscreenMask = new ContainerWidget(); var fullscreenMask = new ContainerWidget();
// Don't use initializers - breaks on mono 2.6.7
fullscreenMask.Bounds = new Rectangle(0, 0, Game.viewport.Width, Game.viewport.Height); fullscreenMask.Bounds = new Rectangle(0, 0, Game.viewport.Width, Game.viewport.Height);
fullscreenMask.ClickThrough = false;
fullscreenMask.Visible = true;
Widget.RootWidget.AddChild(fullscreenMask); Widget.RootWidget.AddChild(fullscreenMask);
Action HideDropDown = () => Action HideDropDown = () =>
@@ -139,13 +149,12 @@ namespace OpenRA.Widgets
fullscreenMask.OnMouseDown = mi => fullscreenMask.OnMouseDown = mi =>
{ {
if (onDismiss()) HideDropDown(); if (onDismiss()) HideDropDown();
return false; return true;
}; };
fullscreenMask.OnMouseUp = mi => true;
var oldBounds = panel.Bounds; var oldBounds = panel.Bounds;
panel.Bounds = new Rectangle(w.RenderOrigin.X, w.RenderOrigin.Y + w.Bounds.Height, oldBounds.Width, oldBounds.Height); panel.Bounds = new Rectangle(w.RenderOrigin.X, w.RenderOrigin.Y + w.Bounds.Height, oldBounds.Width, oldBounds.Height);
panel.ClickThrough = false;
panel.Visible = true;
panel.OnMouseUp = mi => true; panel.OnMouseUp = mi => true;
foreach (var ww in dismissAfter) foreach (var ww in dismissAfter)
@@ -175,13 +184,10 @@ namespace OpenRA.Widgets
dismissAfter.Add(ww); dismissAfter.Add(ww);
ww.ClickThrough = false; ww.ClickThrough = false;
ww.IsVisible = () => true; ww.IsVisible = () => true;
ww.OnMouseMove = mi => ww.OnMouseMove = mi => items.Do(lw =>
{ {
items.Do(lw => lw.Background = null; ww.Background = "dialog2";
{ });
lw.Background = null; ww.Background = "dialog2";
}); return true;
};
dropDown.AddChild(ww); dropDown.AddChild(ww);
items.Add(ww); items.Add(ww);

View File

@@ -51,8 +51,6 @@ namespace OpenRA.Widgets
return composing ? false : base.LoseFocus(mi); return composing ? false : base.LoseFocus(mi);
} }
public override bool HandleInputInner(MouseInput mi) { return false; }
public override bool HandleKeyPressInner(KeyInput e) public override bool HandleKeyPressInner(KeyInput e)
{ {
if (e.Event == KeyInputEvent.Up) return false; if (e.Event == KeyInputEvent.Up) return false;

View File

@@ -41,9 +41,13 @@ namespace OpenRA.Widgets
new float2(rect.Left + 2, rect.Top + 2)); new float2(rect.Left + 2, rect.Top + 2));
} }
public override bool HandleInputInner(MouseInput mi) public override bool HandleMouseInput(MouseInput mi)
{ {
return mi.Button == MouseButton.Left; // Checkboxes require lmb
if (mi.Button != MouseButton.Left)
return false;
return base.HandleMouseInput(mi);
} }
public CheckboxWidget() : base() { } public CheckboxWidget() : base() { }

View File

@@ -33,8 +33,6 @@ namespace OpenRA.Widgets
} }
public override Widget Clone() { return new MapPreviewWidget(this); } public override Widget Clone() { return new MapPreviewWidget(this); }
public override bool HandleInputInner(MouseInput mi) { return true; }
public int2 ConvertToPreview(MapStub map, int2 point) public int2 ConvertToPreview(MapStub map, int2 point)
{ {
return new int2(MapRect.X + (int)(PreviewScale*(point.X - map.Bounds.Left)) , MapRect.Y + (int)(PreviewScale*(point.Y - map.Bounds.Top))); return new int2(MapRect.X + (int)(PreviewScale*(point.X - map.Bounds.Left)) , MapRect.Y + (int)(PreviewScale*(point.Y - map.Bounds.Top)));

View File

@@ -129,7 +129,8 @@ namespace OpenRA.Widgets
} }
int2 lastMouseLocation; int2 lastMouseLocation;
public override bool HandleInputInner(MouseInput mi) // TODO: ScrollPanelWidget doesn't support delegate methods for mouse input
public override bool HandleMouseInput(MouseInput mi)
{ {
if (mi.Button == MouseButton.WheelDown) if (mi.Button == MouseButton.WheelDown)
{ {

View File

@@ -63,7 +63,8 @@ namespace OpenRA.Widgets
Offset = ((newOffset - Little) / Spread).Clamp(0f, 1f); Offset = ((newOffset - Little) / Spread).Clamp(0f, 1f);
} }
public override bool HandleInputInner(MouseInput mi) // TODO: SliderWidget doesn't support delegate methods for mouse input
public override bool HandleMouseInput(MouseInput mi)
{ {
if (mi.Button != MouseButton.Left) if (mi.Button != MouseButton.Left)
return false; return false;

View File

@@ -42,13 +42,14 @@ namespace OpenRA.Widgets
return lose; return lose;
} }
public override bool HandleInputInner(MouseInput mi) // TODO: TextFieldWidgets don't support delegate methods for mouse input
public override bool HandleMouseInput(MouseInput mi)
{ {
if (mi.Event == MouseInputEvent.Move) if (mi.Event == MouseInputEvent.Move)
return false; return false;
// Lose focus if they click outside the box; return false so the next widget can grab this event // Lose focus if they click outside the box; return false so the next widget can grab this event
if (mi.Event == MouseInputEvent.Down && !RenderBounds.Contains(mi.Location.X, mi.Location.Y) && LoseFocus(mi)) if (mi.Event == MouseInputEvent.Down && !RenderBounds.Contains(mi.Location) && LoseFocus(mi))
return false; return false;
if (mi.Event == MouseInputEvent.Down && !TakeFocus(mi)) if (mi.Event == MouseInputEvent.Down && !TakeFocus(mi))

View File

@@ -34,7 +34,8 @@ namespace OpenRA.Widgets
protected ViewportScrollControllerWidget(ViewportScrollControllerWidget widget) : base(widget) {} protected ViewportScrollControllerWidget(ViewportScrollControllerWidget widget) : base(widget) {}
public override void DrawInner( WorldRenderer wr ) {} public override void DrawInner( WorldRenderer wr ) {}
public override bool HandleInputInner(MouseInput mi) // TODO: ViewportScrollController doesn't support delegate methods for mouse input
public override bool HandleMouseInput(MouseInput mi)
{ {
if (mi.Event == MouseInputEvent.Move && if (mi.Event == MouseInputEvent.Move &&
(mi.Button == MouseButton.Middle || mi.Button == (MouseButton.Left | MouseButton.Right))) (mi.Button == MouseButton.Middle || mi.Button == (MouseButton.Left | MouseButton.Right)))

View File

@@ -41,7 +41,7 @@ namespace OpenRA.Widgets
// Common Funcs that most widgets will want // Common Funcs that most widgets will want
public Func<MouseInput, bool> OnMouseDown = mi => false; public Func<MouseInput, bool> OnMouseDown = mi => false;
public Func<MouseInput, bool> OnMouseUp = mi => false; public Func<MouseInput, bool> OnMouseUp = mi => false;
public Func<MouseInput, bool> OnMouseMove = mi => false; public Action<MouseInput> OnMouseMove = mi => {};
public Func<KeyInput, bool> OnKeyPress = e => false; public Func<KeyInput, bool> OnKeyPress = e => false;
public Func<bool> IsVisible; public Func<bool> IsVisible;
@@ -222,22 +222,21 @@ namespace OpenRA.Widgets
if (child.HandleMouseInputOuter(mi)) if (child.HandleMouseInputOuter(mi))
return true; return true;
// Do any widgety behavior (button click etc) return HandleMouseInput(mi);
// Return false if it can't handle any user actions
if (!HandleInputInner(mi))
return false;
// Apply any special logic added by delegates; they return true if they caught the input
if (mi.Event == MouseInputEvent.Down && OnMouseDown(mi)) return true;
if (mi.Event == MouseInputEvent.Up && OnMouseUp(mi)) return true;
if (mi.Event == MouseInputEvent.Move && OnMouseMove(mi)) return true;
return true;
} }
// Hack: Don't eat mouse input that others want // Hack: Don't eat mouse input that others want
// TODO: Solve this properly // TODO: Solve this properly
public virtual bool HandleInputInner(MouseInput mi) { return !ClickThrough && mi.Button == MouseButton.Left && mi.Event != MouseInputEvent.Move; } public virtual bool HandleMouseInput(MouseInput mi)
{
// Apply any special logic added by delegates; they return true if they caught the input
if (mi.Event == MouseInputEvent.Down && OnMouseDown(mi)) return true;
if (mi.Event == MouseInputEvent.Up && OnMouseUp(mi)) return true;
if (mi.Event == MouseInputEvent.Move)
OnMouseMove(mi);
return false;
}
public virtual bool HandleKeyPressInner(KeyInput e) { return false; } public virtual bool HandleKeyPressInner(KeyInput e) { return false; }
public virtual bool HandleKeyPressOuter(KeyInput e) public virtual bool HandleKeyPressOuter(KeyInput e)

View File

@@ -47,7 +47,8 @@ namespace OpenRA.Widgets
float2 dragStart, dragEnd; float2 dragStart, dragEnd;
public override bool HandleInputInner(MouseInput mi) // TODO: WorldInteractionController doesn't support delegate methods for mouse input
public override bool HandleMouseInput(MouseInput mi)
{ {
var xy = Game.viewport.ViewToWorld(mi); var xy = Game.viewport.ViewToWorld(mi);
if (mi.Button == MouseButton.Left && mi.Event == MouseInputEvent.Down) if (mi.Button == MouseButton.Left && mi.Event == MouseInputEvent.Down)
@@ -75,6 +76,7 @@ namespace OpenRA.Widgets
if (mi.Button == MouseButton.Right && mi.Event == MouseInputEvent.Down) if (mi.Button == MouseButton.Right && mi.Event == MouseInputEvent.Down)
ApplyOrders(world, xy, mi); ApplyOrders(world, xy, mi);
return true; return true;
} }

View File

@@ -157,7 +157,8 @@ namespace OpenRA.Mods.RA.Widgets
return DoBuildingHotkey(Char.ToLowerInvariant(e.KeyChar), world); return DoBuildingHotkey(Char.ToLowerInvariant(e.KeyChar), world);
} }
public override bool HandleInputInner(MouseInput mi) // TODO: BuildPaletteWidget doesn't support delegate methods for mouse input
public override bool HandleMouseInput(MouseInput mi)
{ {
if (mi.Event != MouseInputEvent.Down) if (mi.Event != MouseInputEvent.Down)
return false; return false;

View File

@@ -84,7 +84,8 @@ namespace OpenRA.Mods.RA.Widgets
return CursorProvider.HasCursorSequence(cursor+"-minimap") ? cursor+"-minimap" : cursor; return CursorProvider.HasCursorSequence(cursor+"-minimap") ? cursor+"-minimap" : cursor;
} }
public override bool HandleInputInner(MouseInput mi) // TODO: RadarBinWidget doesn't support delegate methods for mouse input
public override bool HandleMouseInput(MouseInput mi)
{ {
if (!hasRadar || radarAnimating) return false; // we're not set up for this. if (!hasRadar || radarAnimating) return false; // we're not set up for this.
@@ -98,7 +99,6 @@ namespace OpenRA.Mods.RA.Widgets
if (mi.Event == MouseInputEvent.Down && mi.Button == MouseButton.Right) if (mi.Event == MouseInputEvent.Down && mi.Button == MouseButton.Right)
{ {
// fake a mousedown/mouseup here // fake a mousedown/mouseup here
var fakemi = new MouseInput var fakemi = new MouseInput
{ {
Event = MouseInputEvent.Down, Event = MouseInputEvent.Down,
@@ -110,9 +110,9 @@ namespace OpenRA.Mods.RA.Widgets
if (WorldInteractionController != null) if (WorldInteractionController != null)
{ {
var controller = Widget.RootWidget.GetWidget<WorldInteractionControllerWidget>(WorldInteractionController); var controller = Widget.RootWidget.GetWidget<WorldInteractionControllerWidget>(WorldInteractionController);
controller.HandleInputInner(fakemi); controller.HandleMouseInput(fakemi);
fakemi.Event = MouseInputEvent.Up; fakemi.Event = MouseInputEvent.Up;
controller.HandleInputInner(fakemi); controller.HandleMouseInput(fakemi);
} }
} }

View File

@@ -53,7 +53,8 @@ namespace OpenRA.Mods.RA.Widgets
get { return buttons.Any() ? buttons.Select(b => b.First).Aggregate(Rectangle.Union) : Bounds; } get { return buttons.Any() ? buttons.Select(b => b.First).Aggregate(Rectangle.Union) : Bounds; }
} }
public override bool HandleInputInner(MouseInput mi) // TODO: SpecialPowerBin doesn't support delegate methods for mouse input
public override bool HandleMouseInput(MouseInput mi)
{ {
if (mi.Event == MouseInputEvent.Down) if (mi.Event == MouseInputEvent.Down)
{ {