Browse Source

Make ShowDialog respect WindowStartupLocation.

`SetWindowStartupLocation` needs to be called _after_ the window is shown as is done in `Show`. In addition, the owner window needs to be passed so we can get the correct screen.

Renamed the `parent` parameter to `ShowDialog` to `owner` as its `WindowStartupLocation.CenterOwner` not `CenterParent`.
pull/2250/head
Steven Kirk 7 years ago
parent
commit
db44faf4ad
  1. 44
      src/Avalonia.Controls/Window.cs

44
src/Avalonia.Controls/Window.cs

@ -394,39 +394,42 @@ namespace Avalonia.Controls
/// <summary>
/// Shows the window as a dialog.
/// </summary>
/// <param name="owner">The dialog's owner window.</param>
/// <returns>
/// A task that can be used to track the lifetime of the dialog.
/// </returns>
public Task ShowDialog(Window parent)
public Task ShowDialog(Window owner)
{
return ShowDialog<object>(parent);
return ShowDialog<object>(owner);
}
/// <summary>
/// Shows the window as a dialog.
/// </summary>
/// <typeparam name="TResult">
/// The type of the result produced by the dialog.
/// </typeparam>
/// <param name="owner">The dialog's owner window.</param>
/// <returns>.
/// A task that can be used to retrieve the result of the dialog when it closes.
/// </returns>
public Task<TResult> ShowDialog<TResult>(Window parent) => ShowDialog<TResult>(parent.PlatformImpl);
public Task<TResult> ShowDialog<TResult>(Window owner) => ShowDialog<TResult>(owner.PlatformImpl);
/// <summary>
/// Shows the window as a dialog.
/// </summary>
/// <typeparam name="TResult">
/// The type of the result produced by the dialog.
/// </typeparam>
/// <param name="owner">The dialog's owner window.</param>
/// <returns>.
/// A task that can be used to retrieve the result of the dialog when it closes.
/// </returns>
public Task<TResult> ShowDialog<TResult>(IWindowImpl parent)
public Task<TResult> ShowDialog<TResult>(IWindowImpl owner)
{
if(parent == null)
throw new ArgumentNullException(nameof(parent));
if(owner == null)
throw new ArgumentNullException(nameof(owner));
if (IsVisible)
{
throw new InvalidOperationException("The window is already being shown.");
@ -435,15 +438,15 @@ namespace Avalonia.Controls
AddWindow(this);
EnsureInitialized();
SetWindowStartupLocation();
IsVisible = true;
LayoutManager.ExecuteInitialLayoutPass(this);
var result = new TaskCompletionSource<TResult>();
using (BeginAutoSizing())
{
PlatformImpl?.ShowDialog(parent);
var result = new TaskCompletionSource<TResult>();
PlatformImpl?.ShowDialog(owner);
Renderer?.Start();
Observable.FromEventPattern<EventHandler, EventArgs>(
@ -452,17 +455,18 @@ namespace Avalonia.Controls
.Take(1)
.Subscribe(_ =>
{
parent.Activate();
owner.Activate();
result.SetResult((TResult)(_dialogResult ?? default(TResult)));
});
return result.Task;
}
SetWindowStartupLocation(owner);
return result.Task;
}
void SetWindowStartupLocation()
private void SetWindowStartupLocation(IWindowImpl owner = null)
{
var scaling = PlatformImpl?.Scaling ?? 1;
var scaling = owner?.Scaling ?? PlatformImpl?.Scaling ?? 1;
// TODO: We really need non-client size here.
var rect = new PixelRect(
@ -471,7 +475,7 @@ namespace Avalonia.Controls
if (WindowStartupLocation == WindowStartupLocation.CenterScreen)
{
var screen = Screens.ScreenFromPoint(Position);
var screen = Screens.ScreenFromPoint(owner?.Position ?? Position);
if (screen != null)
{
@ -480,12 +484,12 @@ namespace Avalonia.Controls
}
else if (WindowStartupLocation == WindowStartupLocation.CenterOwner)
{
if (Owner != null)
if (owner != null)
{
// TODO: We really need non-client size here.
var ownerRect = new PixelRect(
Owner.Position,
PixelSize.FromSize(Owner.ClientSize, scaling));
owner.Position,
PixelSize.FromSize(owner.ClientSize, scaling));
Position = ownerRect.CenterRect(rect).Position;
}
}

Loading…
Cancel
Save