Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/mono/xwt.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorVinicius Jarina <viniciusjarina@gmail.com>2017-04-14 03:37:44 +0300
committerVinicius Jarina <viniciusjarina@gmail.com>2017-04-14 03:37:44 +0300
commit90964353cb46b5be0e4c667bd87edd23d9d8ce56 (patch)
tree74d58f320295948b89c33cac127096f5f1f59980
parentef545e1c206520c3cbfda7ec8cd060caa19b83cd (diff)
[Mac] Fixed using Popover with `NSView`.viniciusjarina_fix_popover_mac_crash
* Added a overload to `IPopoverBackend.Show` receiving an object. We can’t wrap and unwrap the NSView to be used with the Popover, because this will change the parent of the window when we unwrap it, invalidating the `NSView.Window`, making NSPopover throw a NSException, due the missing NSWindow inside the NSView. * This patch pass the NSView all the way down, without wrap it inside a EmbeddedNativeWidget, this way avoiding the NSView to lost the NSWindow.
-rw-r--r--Xwt.Gtk/Xwt.GtkBackend/PopoverBackend.cs22
-rw-r--r--Xwt.WPF/Xwt.WPFBackend/PopoverBackend.cs14
-rw-r--r--Xwt.XamMac/Xwt.Mac/PopoverBackend.cs35
-rw-r--r--Xwt/Xwt.Backends/IPopoverBackend.cs1
-rw-r--r--Xwt/Xwt/Popover.cs13
5 files changed, 73 insertions, 12 deletions
diff --git a/Xwt.Gtk/Xwt.GtkBackend/PopoverBackend.cs b/Xwt.Gtk/Xwt.GtkBackend/PopoverBackend.cs
index c7dfe1c2..9f5426ec 100644
--- a/Xwt.Gtk/Xwt.GtkBackend/PopoverBackend.cs
+++ b/Xwt.Gtk/Xwt.GtkBackend/PopoverBackend.cs
@@ -245,9 +245,23 @@ namespace Xwt.GtkBackend
{
}
+ public void Show (Xwt.Popover.Position orientation, object reference, Xwt.Rectangle positionRect, Widget child)
+ {
+ var nativeReference = reference as Gtk.Widget;
+ if (nativeReference == null)
+ return;
+ Show (orientation, nativeReference, positionRect, child);
+ }
+
public void Show (Xwt.Popover.Position orientation, Xwt.Widget reference, Xwt.Rectangle positionRect, Widget child)
{
- popover.Content = (Gtk.Widget)((WidgetBackend)Toolkit.GetBackend (child)).NativeWidget;
+ var nativeReference = (Gtk.Widget)((WidgetBackend)Toolkit.GetBackend (child)).NativeWidget;
+ Show (orientation, nativeReference, positionRect, child);
+ }
+
+ public void Show (Xwt.Popover.Position orientation, Gtk.Widget reference, Xwt.Rectangle positionRect, Widget child)
+ {
+ popover.Content = reference;
popover.ArrowPosition = orientation;
popover.BackgroundColor = BackgroundColor.ToCairoColor ();
popover.Padding = frontend.Padding;
@@ -262,10 +276,10 @@ namespace Xwt.GtkBackend
popover.Hidden += (o, args) => sink.OnClosed ();
- var screenBounds = reference.ScreenBounds;
+ var screenBounds = reference.Allocation;
if (positionRect == Rectangle.Zero)
- positionRect = new Rectangle (Point.Zero, screenBounds.Size);
- positionRect = positionRect.Offset (screenBounds.Location);
+ positionRect = new Rectangle (0, 0, screenBounds.Size.Width, screenBounds.Height);
+ positionRect = positionRect.Offset (screenBounds.Location.X, screenBounds.Y);
popover.Show ();
popover.Present ();
popover.GrabFocus ();
diff --git a/Xwt.WPF/Xwt.WPFBackend/PopoverBackend.cs b/Xwt.WPF/Xwt.WPFBackend/PopoverBackend.cs
index 3203682c..516560e1 100644
--- a/Xwt.WPF/Xwt.WPFBackend/PopoverBackend.cs
+++ b/Xwt.WPF/Xwt.WPFBackend/PopoverBackend.cs
@@ -94,8 +94,20 @@ namespace Xwt.WPFBackend
EventSink = sink;
}
+ public void Show (Xwt.Popover.Position orientation, object reference, Xwt.Rectangle positionRect, Widget child)
+ {
+ var nativeReference = (System.Windows.FrameworkElement)Context.Toolkit.GetNativeWidget (reference);
+ Show (orientation, nativeReference, positionRect, child);
+ }
+
public void Show (Xwt.Popover.Position orientation, Xwt.Widget reference, Xwt.Rectangle positionRect, Widget child)
{
+ var nativeReference = (System.Windows.FrameworkElement)Context.Toolkit.GetNativeWidget (reference);
+ Show (orientation, nativeReference, positionRect, child);
+ }
+
+ void Show (Xwt.Popover.Position orientation, System.Windows.FrameworkElement reference, Xwt.Rectangle positionRect, Widget child)
+ {
ActualPosition = orientation;
Border.Child = (System.Windows.FrameworkElement)Context.Toolkit.GetNativeWidget (child);
NativeWidget.CustomPopupPlacementCallback = (popupSize, targetSize, offset) => {
@@ -111,7 +123,7 @@ namespace Xwt.WPFBackend
new System.Windows.Controls.Primitives.CustomPopupPlacement (location, System.Windows.Controls.Primitives.PopupPrimaryAxis.Horizontal)
};
};
- NativeWidget.PlacementTarget = (System.Windows.FrameworkElement)Context.Toolkit.GetNativeWidget (reference);
+ NativeWidget.PlacementTarget = reference;
NativeWidget.IsOpen = true;
}
diff --git a/Xwt.XamMac/Xwt.Mac/PopoverBackend.cs b/Xwt.XamMac/Xwt.Mac/PopoverBackend.cs
index 09c1fcb8..860bd12d 100644
--- a/Xwt.XamMac/Xwt.Mac/PopoverBackend.cs
+++ b/Xwt.XamMac/Xwt.Mac/PopoverBackend.cs
@@ -200,6 +200,22 @@ namespace Xwt.Mac
}
}
+ public void Show (Popover.Position orientation, object reference, Rectangle positionRect, Widget child)
+ {
+ var refView = reference as NSView;
+ if (refView == null)
+ return;
+
+ // If the rect is empty, the coordinates of the rect will be ignored.
+ // Set the width and height, for the positioning to function correctly.
+ if (Math.Abs (positionRect.Width) < double.Epsilon)
+ positionRect.Width = refView.Frame.Size.Width;
+ if (Math.Abs (positionRect.Height) < double.Epsilon)
+ positionRect.Height = refView.Frame.Size.Height;
+
+ Show (orientation, refView, positionRect, child);
+ }
+
public void Show (Popover.Position orientation, Widget referenceWidget, Rectangle positionRect, Widget child)
{
var refBackend = Toolkit.GetBackend (referenceWidget) as IWidgetBackend;
@@ -214,20 +230,25 @@ namespace Xwt.Mac
positionRect.X += referenceWidget.WindowBounds.Location.X - rLocation.X;
positionRect.Y += referenceWidget.WindowBounds.Location.Y - rLocation.Y;
}
+
+ // If the rect is empty, the coordinates of the rect will be ignored.
+ // Set the width and height, for the positioning to function correctly.
+ if (Math.Abs (positionRect.Width) < double.Epsilon)
+ positionRect.Width = referenceWidget.Size.Width;
+ if (Math.Abs (positionRect.Height) < double.Epsilon)
+ positionRect.Height = referenceWidget.Size.Height;
+
} catch (Exception ex) {
throw new ArgumentException ("Widget belongs to an unsupported Toolkit", nameof (referenceWidget), ex);
}
} else if (referenceWidget.Surface.ToolkitEngine != ApplicationContext.Toolkit)
throw new ArgumentException ("Widget belongs to an unsupported Toolkit", nameof (referenceWidget));
}
+ Show (orientation, refView, positionRect, child);
+ }
- // If the rect is empty, the coordinates of the rect will be ignored.
- // Set the width and height, for the positioning to function correctly.
- if (Math.Abs (positionRect.Width) < double.Epsilon)
- positionRect.Width = referenceWidget.Size.Width;
- if (Math.Abs (positionRect.Height) < double.Epsilon)
- positionRect.Height = referenceWidget.Size.Height;
-
+ void Show (Popover.Position orientation, NSView refView, Rectangle positionRect, Widget child)
+ {
DestroyPopover ();
popover = new NSAppearanceCustomizationPopover {
diff --git a/Xwt/Xwt.Backends/IPopoverBackend.cs b/Xwt/Xwt.Backends/IPopoverBackend.cs
index 3036b044..26d5bb60 100644
--- a/Xwt/Xwt.Backends/IPopoverBackend.cs
+++ b/Xwt/Xwt.Backends/IPopoverBackend.cs
@@ -35,6 +35,7 @@ namespace Xwt.Backends
Color BackgroundColor { get; set; }
void Initialize (IPopoverEventSink sink);
void Show (Popover.Position arrowPosition, Widget referenceWidget, Xwt.Rectangle positionRect, Xwt.Widget child);
+ void Show (Popover.Position arrowPosition, object nativeWidget, Xwt.Rectangle positionRect, Xwt.Widget child);
void Hide ();
}
diff --git a/Xwt/Xwt/Popover.cs b/Xwt/Xwt/Popover.cs
index 1f2ada42..ac1ab534 100644
--- a/Xwt/Xwt/Popover.cs
+++ b/Xwt/Xwt/Popover.cs
@@ -143,11 +143,24 @@ namespace Xwt
{
}
+ public void Show (Position arrowPosition, object referenceWidget)
+ {
+ Show (arrowPosition, referenceWidget, Xwt.Rectangle.Zero);
+ }
+
public void Show (Position arrowPosition, Widget referenceWidget)
{
Show (arrowPosition, referenceWidget, Xwt.Rectangle.Zero);
}
+ public void Show (Position arrowPosition, object referenceWidget, Xwt.Rectangle positionRect)
+ {
+ if (content == null)
+ throw new InvalidOperationException ("A child widget source must be set before running the Popover");
+ Backend.Show (arrowPosition, referenceWidget, positionRect, content);
+ shown = true;
+ }
+
public void Show (Position arrowPosition, Widget referenceWidget, Xwt.Rectangle positionRect)
{
if (content == null)