diff --git a/native/Avalonia.Native/src/OSX/StorageProvider.mm b/native/Avalonia.Native/src/OSX/StorageProvider.mm index 0fd77c6789..abf7f85c5f 100644 --- a/native/Avalonia.Native/src/OSX/StorageProvider.mm +++ b/native/Avalonia.Native/src/OSX/StorageProvider.mm @@ -173,8 +173,7 @@ public: if(initialDirectory != nullptr) { auto directoryString = [NSString stringWithUTF8String:initialDirectory]; - panel.directoryURL = [NSURL fileURLWithPath:directoryString - isDirectory:true]; + panel.directoryURL = [NSURL URLWithString:directoryString]; } auto handler = ^(NSModalResponse result) { @@ -239,8 +238,7 @@ public: if(initialDirectory != nullptr) { auto directoryString = [NSString stringWithUTF8String:initialDirectory]; - panel.directoryURL = [NSURL fileURLWithPath:directoryString - isDirectory:true]; + panel.directoryURL = [NSURL URLWithString:directoryString]; } if(initialFile != nullptr) @@ -309,8 +307,7 @@ public: if(initialDirectory != nullptr) { auto directoryString = [NSString stringWithUTF8String:initialDirectory]; - panel.directoryURL = [NSURL fileURLWithPath:directoryString - isDirectory:true]; + panel.directoryURL = [NSURL URLWithString:directoryString]; } if(initialFile != nullptr) diff --git a/src/Avalonia.Base/Layout/LayoutManager.cs b/src/Avalonia.Base/Layout/LayoutManager.cs index cffda3e84c..79d43239e6 100644 --- a/src/Avalonia.Base/Layout/LayoutManager.cs +++ b/src/Avalonia.Base/Layout/LayoutManager.cs @@ -213,9 +213,7 @@ namespace Avalonia.Layout void ILayoutManager.RegisterEffectiveViewportListener(Layoutable control) { _effectiveViewportChangedListeners ??= new List(); - _effectiveViewportChangedListeners.Add(new EffectiveViewportChangedListener( - control, - CalculateEffectiveViewport(control))); + _effectiveViewportChangedListeners.Add(new EffectiveViewportChangedListener(control)); } void ILayoutManager.UnregisterEffectiveViewportListener(Layoutable control) @@ -438,14 +436,13 @@ namespace Avalonia.Layout private class EffectiveViewportChangedListener { - public EffectiveViewportChangedListener(Layoutable listener, Rect viewport) + public EffectiveViewportChangedListener(Layoutable listener) { Listener = listener; - Viewport = viewport; } public Layoutable Listener { get; } - public Rect Viewport { get; set; } + public Rect? Viewport { get; set; } } private enum ArrangeResult diff --git a/tests/Avalonia.Base.UnitTests/Layout/LayoutableTests_EffectiveViewportChanged.cs b/tests/Avalonia.Base.UnitTests/Layout/LayoutableTests_EffectiveViewportChanged.cs index 94054f5245..09e4986da0 100644 --- a/tests/Avalonia.Base.UnitTests/Layout/LayoutableTests_EffectiveViewportChanged.cs +++ b/tests/Avalonia.Base.UnitTests/Layout/LayoutableTests_EffectiveViewportChanged.cs @@ -14,7 +14,7 @@ namespace Avalonia.Base.UnitTests.Layout public class LayoutableTests_EffectiveViewportChanged { [Fact] - public async Task EffectiveViewportChanged_Not_Raised_When_Control_Added_To_Tree() + public async Task EffectiveViewportChanged_Not_Raised_When_Control_Added_To_Tree_And_Layout_Pass_Has_Not_Run() { #pragma warning disable CS1998 // Async method lacks 'await' operators and will run synchronously await RunOnUIThread.Execute(async () => @@ -34,6 +34,60 @@ namespace Avalonia.Base.UnitTests.Layout Assert.Equal(0, raised); }); } + + [Fact] + public async Task EffectiveViewportChanged_Raised_When_Control_Added_To_Tree_And_Layout_Pass_Has_Run() + { +#pragma warning disable CS1998 // Async method lacks 'await' operators and will run synchronously + await RunOnUIThread.Execute(async () => +#pragma warning restore CS1998 // Async method lacks 'await' operators and will run synchronously + { + var root = CreateRoot(); + var target = new Canvas(); + var raised = 0; + + target.EffectiveViewportChanged += (s, e) => + { + ++raised; + }; + + root.Child = target; + + Assert.Equal(0, raised); + + await ExecuteInitialLayoutPass(root); + + Assert.Equal(1, raised); + }); + } + + [Fact] + public async Task EffectiveViewportChanged_Raised_When_Root_LayedOut_And_Then_Control_Added_To_Tree_And_Layout_Pass_Runs() + { +#pragma warning disable CS1998 // Async method lacks 'await' operators and will run synchronously + await RunOnUIThread.Execute(async () => +#pragma warning restore CS1998 // Async method lacks 'await' operators and will run synchronously + { + var root = CreateRoot(); + var target = new Canvas(); + var raised = 0; + + target.EffectiveViewportChanged += (s, e) => + { + ++raised; + }; + + await ExecuteInitialLayoutPass(root); + + root.Child = target; + + Assert.Equal(0, raised); + + await ExecuteInitialLayoutPass(root); + + Assert.Equal(1, raised); + }); + } [Fact] public async Task EffectiveViewportChanged_Raised_Before_LayoutUpdated() @@ -268,8 +322,11 @@ namespace Avalonia.Base.UnitTests.Layout root.Child = parent; - await ExecuteInitialLayoutPass(root); target.EffectiveViewportChanged += (s, e) => ++raised; + await ExecuteInitialLayoutPass(root); + + raised = 0; // The initial layout pass is expected to raise. + target.RenderTransform = new TranslateTransform { X = 8 }; target.InvalidateMeasure(); await ExecuteLayoutPass(root);