diff --git a/azure-pipelines-integrationtests.yml b/azure-pipelines-integrationtests.yml
index 4fba4ca36f..43253ac6be 100644
--- a/azure-pipelines-integrationtests.yml
+++ b/azure-pipelines-integrationtests.yml
@@ -18,9 +18,9 @@ jobs:
version: 6.0.401
- task: UseDotNet@2
- displayName: 'Use .NET Core SDK 7.0.100-rc.2.22477.23'
+ displayName: 'Use .NET Core SDK 7.0.100'
inputs:
- version: 7.0.100-rc.2.22477.23
+ version: 7.0.100
- script: system_profiler SPDisplaysDataType |grep Resolution
@@ -32,7 +32,7 @@ jobs:
rm -rf $(osascript -e "POSIX path of (path to application id \"net.avaloniaui.avalonia.integrationtestapp\")")
pkill IntegrationTestApp
./samples/IntegrationTestApp/bundle.sh
- open -n ./samples/IntegrationTestApp/bin/Debug/net6.0/osx-arm64/publish/IntegrationTestApp.app
+ open -n ./samples/IntegrationTestApp/bin/Debug/net7.0/osx-arm64/publish/IntegrationTestApp.app
pkill IntegrationTestApp
- task: DotNetCoreCLI@2
@@ -56,9 +56,9 @@ jobs:
version: 6.0.401
- task: UseDotNet@2
- displayName: 'Use .NET Core SDK 7.0.100-rc.2.22477.23'
+ displayName: 'Use .NET Core SDK 7.0.100'
inputs:
- version: 7.0.100-rc.2.22477.23
+ version: 7.0.100
- task: Windows Application Driver@0
inputs:
diff --git a/build/BuildTargets.targets b/build/BuildTargets.targets
index a5543cd050..481dbf06b2 100644
--- a/build/BuildTargets.targets
+++ b/build/BuildTargets.targets
@@ -3,6 +3,7 @@
$(MSBuildThisFileDirectory)\..\src\Avalonia.Build.Tasks\bin\$(Configuration)\netstandard2.0\Avalonia.Build.Tasks.dll
true
true
+ true
diff --git a/native/Avalonia.Native/src/OSX/menu.h b/native/Avalonia.Native/src/OSX/menu.h
index ce46ac11e0..405938318c 100644
--- a/native/Avalonia.Native/src/OSX/menu.h
+++ b/native/Avalonia.Native/src/OSX/menu.h
@@ -59,11 +59,20 @@ public:
void RaiseOnClicked();
};
+class AvnAppMenu;
+
+@interface AvnMenuDelegate : NSObject
+- (id) initWithParent: (AvnAppMenu*) parent;
+- (void) parentDestroyed;
+@end
+
+
class AvnAppMenu : public ComSingleObject
{
private:
AvnMenu* _native;
ComPtr _baseEvents;
+ AvnMenuDelegate* _delegate;
public:
FORWARD_IUNKNOWN()
@@ -83,12 +92,10 @@ public:
virtual HRESULT SetTitle (char* utf8String) override;
virtual HRESULT Clear () override;
+ virtual ~AvnAppMenu() override;
};
-@interface AvnMenuDelegate : NSObject
-- (id) initWithParent: (AvnAppMenu*) parent;
-@end
#endif
diff --git a/native/Avalonia.Native/src/OSX/menu.mm b/native/Avalonia.Native/src/OSX/menu.mm
index b05588a441..cd1871de21 100644
--- a/native/Avalonia.Native/src/OSX/menu.mm
+++ b/native/Avalonia.Native/src/OSX/menu.mm
@@ -292,8 +292,13 @@ void AvnAppMenuItem::RaiseOnClicked()
AvnAppMenu::AvnAppMenu(IAvnMenuEvents* events)
{
_baseEvents = events;
- id del = [[AvnMenuDelegate alloc] initWithParent: this];
- _native = [[AvnMenu alloc] initWithDelegate: del];
+ _delegate = [[AvnMenuDelegate alloc] initWithParent: this];
+ _native = [[AvnMenu alloc] initWithDelegate: _delegate];
+}
+
+AvnAppMenu::~AvnAppMenu()
+{
+ [_delegate parentDestroyed];
}
@@ -394,7 +399,7 @@ HRESULT AvnAppMenu::Clear()
@implementation AvnMenuDelegate
{
- ComPtr _parent;
+ AvnAppMenu* _parent;
}
- (id) initWithParent:(AvnAppMenu *)parent
{
@@ -402,6 +407,12 @@ HRESULT AvnAppMenu::Clear()
_parent = parent;
return self;
}
+
+- (void) parentDestroyed
+{
+ _parent = nullptr;
+}
+
- (BOOL)menu:(NSMenu *)menu updateItem:(NSMenuItem *)item atIndex:(NSInteger)index shouldCancel:(BOOL)shouldCancel
{
if(shouldCancel)
@@ -416,17 +427,20 @@ HRESULT AvnAppMenu::Clear()
- (void)menuNeedsUpdate:(NSMenu *)menu
{
- _parent->RaiseNeedsUpdate();
+ if(_parent)
+ _parent->RaiseNeedsUpdate();
}
- (void)menuWillOpen:(NSMenu *)menu
{
- _parent->RaiseOpening();
+ if(_parent)
+ _parent->RaiseOpening();
}
- (void)menuDidClose:(NSMenu *)menu
{
- _parent->RaiseClosed();
+ if(_parent)
+ _parent->RaiseClosed();
}
@end
diff --git a/packages/Avalonia/AvaloniaBuildTasks.targets b/packages/Avalonia/AvaloniaBuildTasks.targets
index 4b9e33ffe8..01bf303a20 100644
--- a/packages/Avalonia/AvaloniaBuildTasks.targets
+++ b/packages/Avalonia/AvaloniaBuildTasks.targets
@@ -4,6 +4,7 @@
<_AvaloniaUseExternalMSBuild Condition="'$(_AvaloniaForceInternalMSBuild)' == 'true'">false
low
<_AvaloniaSkipXamlCompilation Condition="'$(_AvaloniaSkipXamlCompilation)' == ''">false
+ false
@@ -43,7 +44,7 @@
$(BuildAvaloniaResourcesDependsOn);AddAvaloniaResources;ResolveReferences;_GenerateAvaloniaResourcesDependencyCache
-
+
@@ -106,6 +107,7 @@
DelaySign="$(DelaySign)"
SkipXamlCompilation="$(_AvaloniaSkipXamlCompilation)"
DebuggerLaunch="$(AvaloniaXamlIlDebuggerLaunch)"
+ DefaultCompileBindings="$(AvaloniaUseCompiledBindingsByDefault)"
/>
-
+
diff --git a/samples/BindingDemo/TestItemView.xaml b/samples/BindingDemo/TestItemView.xaml
index 46c34c6507..6edade34b2 100644
--- a/samples/BindingDemo/TestItemView.xaml
+++ b/samples/BindingDemo/TestItemView.xaml
@@ -1,8 +1,10 @@
+ xmlns:viewModels="using:BindingDemo.ViewModels"
+ x:Class="BindingDemo.TestItemView"
+ x:DataType="viewModels:TestItem">
-
\ No newline at end of file
+
diff --git a/samples/ControlCatalog.Blazor.Web/Properties/launchSettings.json b/samples/ControlCatalog.Blazor.Web/Properties/launchSettings.json
index e4da60f7ca..ad2b1e30f6 100644
--- a/samples/ControlCatalog.Blazor.Web/Properties/launchSettings.json
+++ b/samples/ControlCatalog.Blazor.Web/Properties/launchSettings.json
@@ -8,14 +8,6 @@
}
},
"profiles": {
- "ControlCatalog.Web - IIS Express": {
- "commandName": "IISExpress",
- "launchBrowser": true,
- "inspectUri": "{wsProtocol}://{url.hostname}:{url.port}/_framework/debug/ws-proxy?browser={browserInspectUri}",
- "environmentVariables": {
- "ASPNETCORE_ENVIRONMENT": "Development"
- }
- },
"ControlCatalog.Web": {
"commandName": "Project",
"dotnetRunMessages": "true",
diff --git a/samples/ControlCatalog.NetCore/ControlCatalog.NetCore.csproj b/samples/ControlCatalog.NetCore/ControlCatalog.NetCore.csproj
index 6c17e9ac43..e4c83dca49 100644
--- a/samples/ControlCatalog.NetCore/ControlCatalog.NetCore.csproj
+++ b/samples/ControlCatalog.NetCore/ControlCatalog.NetCore.csproj
@@ -5,7 +5,7 @@
net6.0
true
true
- 6.0.9
+ 6.0.8
diff --git a/samples/ControlCatalog/App.xaml b/samples/ControlCatalog/App.xaml
index b228e72f72..5570ada27b 100644
--- a/samples/ControlCatalog/App.xaml
+++ b/samples/ControlCatalog/App.xaml
@@ -2,7 +2,6 @@
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:vm="using:ControlCatalog.ViewModels"
x:DataType="vm:ApplicationViewModel"
- x:CompileBindings="True"
Name="Avalonia ControlCatalog"
x:Class="ControlCatalog.App">
diff --git a/samples/ControlCatalog/ControlCatalog.csproj b/samples/ControlCatalog/ControlCatalog.csproj
index 2654574a3e..6b550a30be 100644
--- a/samples/ControlCatalog/ControlCatalog.csproj
+++ b/samples/ControlCatalog/ControlCatalog.csproj
@@ -14,9 +14,6 @@
-
-
-
@@ -35,17 +32,5 @@
-
-
- MSBuild:Compile
-
-
-
-
-
- %(Filename)
-
-
-
diff --git a/samples/ControlCatalog/DecoratedWindow.xaml b/samples/ControlCatalog/DecoratedWindow.xaml
index c778b31c42..997ae54f41 100644
--- a/samples/ControlCatalog/DecoratedWindow.xaml
+++ b/samples/ControlCatalog/DecoratedWindow.xaml
@@ -2,7 +2,7 @@
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
x:Class="ControlCatalog.DecoratedWindow"
Title="Avalonia Control Gallery"
- xmlns:local="clr-namespace:ControlCatalog" SystemDecorations="None" Name="Window">
+ SystemDecorations="None" Name="Window">
@@ -43,8 +43,13 @@
Hello world!
- Decorated
-
+
+
+ None
+ BorderOnly
+ Full
+
+
CanResize
diff --git a/samples/ControlCatalog/MainView.xaml b/samples/ControlCatalog/MainView.xaml
index ec198c6bba..b5a09b5fbd 100644
--- a/samples/ControlCatalog/MainView.xaml
+++ b/samples/ControlCatalog/MainView.xaml
@@ -1,9 +1,11 @@
+ xmlns:controls="using:ControlSamples"
+ xmlns:models="using:ControlCatalog.Models"
+ xmlns:pages="using:ControlCatalog.Pages"
+ xmlns:viewModels="using:ControlCatalog.ViewModels"
+ x:DataType="viewModels:MainWindowViewModel">
-
-
+
+
@@ -118,6 +120,9 @@
+
+
+
@@ -130,7 +135,7 @@
-
+
diff --git a/samples/ControlCatalog/MainWindow.xaml b/samples/ControlCatalog/MainWindow.xaml
index d5513904c0..cebb3e0916 100644
--- a/samples/ControlCatalog/MainWindow.xaml
+++ b/samples/ControlCatalog/MainWindow.xaml
@@ -1,19 +1,20 @@
+ x:Class="ControlCatalog.MainWindow" WindowState="{Binding WindowState, Mode=TwoWay}"
+ x:DataType="vm:MainWindowViewModel">
diff --git a/samples/ControlCatalog/MainWindow.xaml.cs b/samples/ControlCatalog/MainWindow.xaml.cs
index c61296ac8f..c589f41442 100644
--- a/samples/ControlCatalog/MainWindow.xaml.cs
+++ b/samples/ControlCatalog/MainWindow.xaml.cs
@@ -11,23 +11,13 @@ namespace ControlCatalog
{
public class MainWindow : Window
{
- private WindowNotificationManager _notificationArea;
private NativeMenu? _recentMenu;
public MainWindow()
{
this.InitializeComponent();
- //Renderer.DrawFps = true;
- //Renderer.DrawDirtyRects = Renderer.DrawFps = true;
-
- _notificationArea = new WindowNotificationManager(this)
- {
- Position = NotificationPosition.TopRight,
- MaxItems = 3
- };
-
- DataContext = new MainWindowViewModel(_notificationArea);
+ DataContext = new MainWindowViewModel();
_recentMenu = ((NativeMenu.GetMenu(this)?.Items[0] as NativeMenuItem)?.Menu?.Items[2] as NativeMenuItem)?.Menu;
}
diff --git a/samples/ControlCatalog/Models/StateData.cs b/samples/ControlCatalog/Models/StateData.cs
new file mode 100644
index 0000000000..bd6d186252
--- /dev/null
+++ b/samples/ControlCatalog/Models/StateData.cs
@@ -0,0 +1,20 @@
+namespace ControlCatalog.Models;
+
+public class StateData
+{
+ public string Name { get; private set; }
+ public string Abbreviation { get; private set; }
+ public string Capital { get; private set; }
+
+ public StateData(string name, string abbreviatoin, string capital)
+ {
+ Name = name;
+ Abbreviation = abbreviatoin;
+ Capital = capital;
+ }
+
+ public override string ToString()
+ {
+ return Name;
+ }
+}
\ No newline at end of file
diff --git a/samples/ControlCatalog/Pages/AutoCompleteBoxPage.xaml b/samples/ControlCatalog/Pages/AutoCompleteBoxPage.xaml
index faa12bc8da..a492808f1d 100644
--- a/samples/ControlCatalog/Pages/AutoCompleteBoxPage.xaml
+++ b/samples/ControlCatalog/Pages/AutoCompleteBoxPage.xaml
@@ -2,8 +2,8 @@
xmlns="https://github.com/avaloniaui"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
- xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
- xmlns:sys="clr-namespace:System;assembly=netstandard"
+ xmlns:sys="using:System"
+ xmlns:models="using:ControlCatalog.Models"
d:DesignHeight="600"
d:DesignWidth="400">
-
+
diff --git a/samples/ControlCatalog/Pages/AutoCompleteBoxPage.xaml.cs b/samples/ControlCatalog/Pages/AutoCompleteBoxPage.xaml.cs
index bc18327f12..8d9cd74ea7 100644
--- a/samples/ControlCatalog/Pages/AutoCompleteBoxPage.xaml.cs
+++ b/samples/ControlCatalog/Pages/AutoCompleteBoxPage.xaml.cs
@@ -8,30 +8,12 @@ using System.Threading;
using System.Threading.Tasks;
using Avalonia.Data.Converters;
using Avalonia.Data;
+using ControlCatalog.Models;
namespace ControlCatalog.Pages
{
public class AutoCompleteBoxPage : UserControl
{
- public class StateData
- {
- public string Name { get; private set; }
- public string Abbreviation { get; private set; }
- public string Capital { get; private set; }
-
- public StateData(string name, string abbreviatoin, string capital)
- {
- Name = name;
- Abbreviation = abbreviatoin;
- Capital = capital;
- }
-
- public override string ToString()
- {
- return Name;
- }
- }
-
private StateData[] BuildAllStates()
{
return new StateData[]
diff --git a/samples/ControlCatalog/Pages/BorderPage.xaml b/samples/ControlCatalog/Pages/BorderPage.xaml
index bfc4f86698..7ec7e81e80 100644
--- a/samples/ControlCatalog/Pages/BorderPage.xaml
+++ b/samples/ControlCatalog/Pages/BorderPage.xaml
@@ -1,7 +1,6 @@
diff --git a/samples/ControlCatalog/Pages/ButtonSpinnerPage.xaml b/samples/ControlCatalog/Pages/ButtonSpinnerPage.xaml
index 323d6d36e9..900e304559 100644
--- a/samples/ControlCatalog/Pages/ButtonSpinnerPage.xaml
+++ b/samples/ControlCatalog/Pages/ButtonSpinnerPage.xaml
@@ -1,7 +1,7 @@
+ xmlns:sys="using:System">
The ButtonSpinner control allows you to add button spinners to any element and then respond to the Spin event to manipulate that element.
diff --git a/samples/ControlCatalog/Pages/CalendarDatePickerPage.xaml b/samples/ControlCatalog/Pages/CalendarDatePickerPage.xaml
index aef96802f4..7a22c0ddab 100644
--- a/samples/ControlCatalog/Pages/CalendarDatePickerPage.xaml
+++ b/samples/ControlCatalog/Pages/CalendarDatePickerPage.xaml
@@ -1,6 +1,6 @@
diff --git a/samples/ControlCatalog/Pages/ColorPickerPage.xaml b/samples/ControlCatalog/Pages/ColorPickerPage.xaml
index c0bb95ae92..649256ba83 100644
--- a/samples/ControlCatalog/Pages/ColorPickerPage.xaml
+++ b/samples/ControlCatalog/Pages/ColorPickerPage.xaml
@@ -2,9 +2,7 @@
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
- xmlns:controls="clr-namespace:Avalonia.Controls;assembly=Avalonia.Controls.ColorPicker"
- xmlns:primitives="clr-namespace:Avalonia.Controls.Primitives;assembly=Avalonia.Controls"
- xmlns:pc="clr-namespace:Avalonia.Controls.Primitives.Converters;assembly=Avalonia.Controls.ColorPicker"
+ xmlns:controls="using:Avalonia.Controls"
mc:Ignorable="d"
d:DesignWidth="800"
d:DesignHeight="450"
diff --git a/samples/ControlCatalog/Pages/ComboBoxPage.xaml b/samples/ControlCatalog/Pages/ComboBoxPage.xaml
index 9f2fbb88f3..748a46c447 100644
--- a/samples/ControlCatalog/Pages/ComboBoxPage.xaml
+++ b/samples/ControlCatalog/Pages/ComboBoxPage.xaml
@@ -3,7 +3,9 @@
xmlns="https://github.com/avaloniaui"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:col="using:System.Collections"
- xmlns:sys="using:System">
+ xmlns:sys="using:System"
+ xmlns:viewModels="using:ControlCatalog.ViewModels"
+ x:DataType="viewModels:ComboBoxPageViewModel">
A drop-down list.
@@ -39,7 +41,7 @@
-
+
@@ -71,7 +73,7 @@
SelectedIndex="0"
WrapSelection="{Binding WrapSelection}">
-
+
diff --git a/samples/ControlCatalog/Pages/CompositionPage.axaml b/samples/ControlCatalog/Pages/CompositionPage.axaml
index 22c5c88941..403f45b8eb 100644
--- a/samples/ControlCatalog/Pages/CompositionPage.axaml
+++ b/samples/ControlCatalog/Pages/CompositionPage.axaml
@@ -1,6 +1,6 @@
Implicit animations
@@ -42,4 +42,4 @@
-
\ No newline at end of file
+
diff --git a/samples/ControlCatalog/Pages/ContextFlyoutPage.xaml b/samples/ControlCatalog/Pages/ContextFlyoutPage.xaml
index 871efa5b7a..6ef6a202b6 100644
--- a/samples/ControlCatalog/Pages/ContextFlyoutPage.xaml
+++ b/samples/ControlCatalog/Pages/ContextFlyoutPage.xaml
@@ -3,9 +3,11 @@
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
+ xmlns:viewModels="using:ControlCatalog.ViewModels"
d:DesignHeight="450"
d:DesignWidth="800"
- mc:Ignorable="d">
+ mc:Ignorable="d"
+ x:DataType="viewModels:ContextPageViewModel">
diff --git a/samples/ControlCatalog/Pages/DataGridPage.xaml b/samples/ControlCatalog/Pages/DataGridPage.xaml
index 27272a9ff7..f1fcd8035a 100644
--- a/samples/ControlCatalog/Pages/DataGridPage.xaml
+++ b/samples/ControlCatalog/Pages/DataGridPage.xaml
@@ -4,13 +4,13 @@
x:Class="ControlCatalog.Pages.DataGridPage">
-
+
-
+
@@ -49,15 +49,15 @@
AlternatingRowBackground="#1fff">
-
-
+
-
-
+
+
+ IsVisible="{Binding #ShowGDP.IsChecked}"
+ x:DataType="local:Country" />
@@ -65,11 +65,11 @@
-
-
-
-
-
+
+
+
+
+
@@ -77,9 +77,9 @@
-
-
-
+
+
+
diff --git a/samples/ControlCatalog/Pages/DateTimePickerPage.xaml b/samples/ControlCatalog/Pages/DateTimePickerPage.xaml
index 6217d39b21..47753f56b6 100644
--- a/samples/ControlCatalog/Pages/DateTimePickerPage.xaml
+++ b/samples/ControlCatalog/Pages/DateTimePickerPage.xaml
@@ -2,7 +2,7 @@
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
- xmlns:sys="clr-namespace:System;assembly=netstandard"
+ xmlns:sys="using:System"
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450"
x:Class="ControlCatalog.Pages.DateTimePickerPage">
diff --git a/samples/ControlCatalog/Pages/ExpanderPage.xaml b/samples/ControlCatalog/Pages/ExpanderPage.xaml
index 8c8702c665..f0a80fd7ab 100644
--- a/samples/ControlCatalog/Pages/ExpanderPage.xaml
+++ b/samples/ControlCatalog/Pages/ExpanderPage.xaml
@@ -1,6 +1,8 @@
+ xmlns:viewModels="using:ControlCatalog.ViewModels"
+ x:Class="ControlCatalog.Pages.ExpanderPage"
+ x:DataType="viewModels:ExpanderPageViewModel">
Expands to show nested content
diff --git a/samples/ControlCatalog/Pages/ItemsRepeaterPage.xaml b/samples/ControlCatalog/Pages/ItemsRepeaterPage.xaml
index 1d42b92096..5ca4ca9bdd 100644
--- a/samples/ControlCatalog/Pages/ItemsRepeaterPage.xaml
+++ b/samples/ControlCatalog/Pages/ItemsRepeaterPage.xaml
@@ -1,6 +1,8 @@
+ xmlns:viewModels="using:ControlCatalog.ViewModels"
+ x:Class="ControlCatalog.Pages.ItemsRepeaterPage"
+ x:DataType="viewModels:ItemsRepeaterPageViewModel">
diff --git a/samples/ControlCatalog/Pages/NotificationsPage.xaml b/samples/ControlCatalog/Pages/NotificationsPage.xaml
index d48b338fe8..46c1fe52de 100644
--- a/samples/ControlCatalog/Pages/NotificationsPage.xaml
+++ b/samples/ControlCatalog/Pages/NotificationsPage.xaml
@@ -1,6 +1,8 @@
+ xmlns:viewModels="using:ControlCatalog.ViewModels"
+ x:Class="ControlCatalog.Pages.NotificationsPage"
+ x:DataType="viewModels:NotificationViewModel">
diff --git a/samples/ControlCatalog/Pages/NotificationsPage.xaml.cs b/samples/ControlCatalog/Pages/NotificationsPage.xaml.cs
index eadf92b602..bfd49a2c00 100644
--- a/samples/ControlCatalog/Pages/NotificationsPage.xaml.cs
+++ b/samples/ControlCatalog/Pages/NotificationsPage.xaml.cs
@@ -1,18 +1,33 @@
+using Avalonia;
using Avalonia.Controls;
using Avalonia.Markup.Xaml;
+using ControlCatalog.ViewModels;
namespace ControlCatalog.Pages
{
public class NotificationsPage : UserControl
{
+ private NotificationViewModel _viewModel;
+
public NotificationsPage()
{
this.InitializeComponent();
+
+ _viewModel = new NotificationViewModel();
+
+ DataContext = _viewModel;
}
private void InitializeComponent()
{
AvaloniaXamlLoader.Load(this);
}
+
+ protected override void OnAttachedToVisualTree(VisualTreeAttachmentEventArgs e)
+ {
+ base.OnAttachedToVisualTree(e);
+
+ _viewModel.NotificationManager = new Avalonia.Controls.Notifications.WindowNotificationManager(VisualRoot as TopLevel);
+ }
}
}
diff --git a/samples/ControlCatalog/Pages/NumericUpDownPage.xaml b/samples/ControlCatalog/Pages/NumericUpDownPage.xaml
index 045ba4a059..e76787f184 100644
--- a/samples/ControlCatalog/Pages/NumericUpDownPage.xaml
+++ b/samples/ControlCatalog/Pages/NumericUpDownPage.xaml
@@ -1,8 +1,10 @@
+ xmlns:sys="using:System"
+ xmlns:converter="using:ControlCatalog.Converter"
+ xmlns:pages="using:ControlCatalog.Pages"
+ x:Class="ControlCatalog.Pages.NumericUpDownPage"
+ x:DataType="pages:NumbersPageViewModel">
Numeric up-down control provides a TextBox with button spinners that allow incrementing and decrementing numeric values by using the spinner buttons, keyboard up/down arrows, or mouse wheel.
@@ -43,7 +45,7 @@
VerticalAlignment="Center" Margin="2"/>
CultureInfo:
-
Watermark:
@@ -77,6 +79,7 @@
diff --git a/samples/ControlCatalog/Pages/NumericUpDownPage.xaml.cs b/samples/ControlCatalog/Pages/NumericUpDownPage.xaml.cs
index edd4921632..8785eac354 100644
--- a/samples/ControlCatalog/Pages/NumericUpDownPage.xaml.cs
+++ b/samples/ControlCatalog/Pages/NumericUpDownPage.xaml.cs
@@ -3,6 +3,7 @@ using System.Collections.Generic;
using System.Globalization;
using System.Linq;
using Avalonia.Controls;
+using Avalonia.Data.Converters;
using Avalonia.Markup.Xaml;
using MiniMvvm;
@@ -22,6 +23,8 @@ namespace ControlCatalog.Pages
AvaloniaXamlLoader.Load(this);
}
+ public static IValueConverter CultureConverter =
+ new FuncValueConverter(c => (c ?? CultureInfo.CurrentCulture).NumberFormat);
}
public class NumbersPageViewModel : ViewModelBase
diff --git a/samples/ControlCatalog/Pages/OpenGlPage.xaml b/samples/ControlCatalog/Pages/OpenGlPage.xaml
index 0eb09004ba..2a97956e30 100644
--- a/samples/ControlCatalog/Pages/OpenGlPage.xaml
+++ b/samples/ControlCatalog/Pages/OpenGlPage.xaml
@@ -1,7 +1,7 @@
+ xmlns:pages="using:ControlCatalog.Pages">
diff --git a/samples/ControlCatalog/Pages/PlatformInfoPage.xaml b/samples/ControlCatalog/Pages/PlatformInfoPage.xaml
new file mode 100644
index 0000000000..f02741d2da
--- /dev/null
+++ b/samples/ControlCatalog/Pages/PlatformInfoPage.xaml
@@ -0,0 +1,53 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/samples/ControlCatalog/Pages/PlatformInfoPage.xaml.cs b/samples/ControlCatalog/Pages/PlatformInfoPage.xaml.cs
new file mode 100644
index 0000000000..1f37451782
--- /dev/null
+++ b/samples/ControlCatalog/Pages/PlatformInfoPage.xaml.cs
@@ -0,0 +1,20 @@
+using Avalonia.Controls;
+using Avalonia.Markup.Xaml;
+using ControlCatalog.ViewModels;
+
+namespace ControlCatalog.Pages
+{
+ public class PlatformInfoPage : UserControl
+ {
+ public PlatformInfoPage()
+ {
+ this.InitializeComponent();
+ DataContext = new PlatformInformationViewModel();
+ }
+
+ private void InitializeComponent()
+ {
+ AvaloniaXamlLoader.Load(this);
+ }
+ }
+}
diff --git a/samples/ControlCatalog/Pages/ProgressBarPage.xaml b/samples/ControlCatalog/Pages/ProgressBarPage.xaml
index 8e73f1d0f5..dcddcd5965 100644
--- a/samples/ControlCatalog/Pages/ProgressBarPage.xaml
+++ b/samples/ControlCatalog/Pages/ProgressBarPage.xaml
@@ -31,7 +31,7 @@
+ Minimum="{Binding #minimum.Value}" Maximum="{Binding #maximum.Value}"/>
diff --git a/samples/ControlCatalog/Pages/ScrollViewerPage.xaml b/samples/ControlCatalog/Pages/ScrollViewerPage.xaml
index 1b3771ccb5..1903e50ed7 100644
--- a/samples/ControlCatalog/Pages/ScrollViewerPage.xaml
+++ b/samples/ControlCatalog/Pages/ScrollViewerPage.xaml
@@ -1,6 +1,8 @@
+ xmlns:pages="using:ControlCatalog.Pages"
+ x:Class="ControlCatalog.Pages.ScrollViewerPage"
+ x:DataType="pages:ScrollViewerPageViewModel">
Allows for horizontal and vertical content scrolling.
diff --git a/samples/ControlCatalog/Pages/SliderPage.xaml b/samples/ControlCatalog/Pages/SliderPage.xaml
index b2375922c2..9aa4322ad5 100644
--- a/samples/ControlCatalog/Pages/SliderPage.xaml
+++ b/samples/ControlCatalog/Pages/SliderPage.xaml
@@ -1,6 +1,6 @@
A control that lets the user select from a range of values by moving a Thumb control along a Track.
diff --git a/samples/ControlCatalog/Pages/SplitViewPage.xaml b/samples/ControlCatalog/Pages/SplitViewPage.xaml
index 6902b27715..61bfb490b8 100644
--- a/samples/ControlCatalog/Pages/SplitViewPage.xaml
+++ b/samples/ControlCatalog/Pages/SplitViewPage.xaml
@@ -2,8 +2,10 @@
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
+ xmlns:viewModels="using:ControlCatalog.ViewModels"
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450"
- x:Class="ControlCatalog.Pages.SplitViewPage">
+ x:Class="ControlCatalog.Pages.SplitViewPage"
+ x:DataType="viewModels:SplitViewPageViewModel">
@@ -51,7 +53,7 @@
diff --git a/samples/ControlCatalog/Pages/TabControlPage.xaml b/samples/ControlCatalog/Pages/TabControlPage.xaml
index cba6fcd0ad..a830ce69ac 100644
--- a/samples/ControlCatalog/Pages/TabControlPage.xaml
+++ b/samples/ControlCatalog/Pages/TabControlPage.xaml
@@ -1,7 +1,9 @@
+ xmlns="https://github.com/avaloniaui"
+ xmlns:viewModels="using:ControlCatalog.ViewModels"
+ x:DataType="viewModels:TabControlPageViewModel">
-
+
-
+
@@ -68,7 +70,7 @@
-
diff --git a/samples/ControlCatalog/Pages/TabControlPage.xaml.cs b/samples/ControlCatalog/Pages/TabControlPage.xaml.cs
index bd0214c72e..74e9928b24 100644
--- a/samples/ControlCatalog/Pages/TabControlPage.xaml.cs
+++ b/samples/ControlCatalog/Pages/TabControlPage.xaml.cs
@@ -5,8 +5,7 @@ using Avalonia.Controls;
using Avalonia.Markup.Xaml;
using Avalonia.Media.Imaging;
using Avalonia.Platform;
-
-using MiniMvvm;
+using ControlCatalog.ViewModels;
namespace ControlCatalog.Pages
{
@@ -18,23 +17,23 @@ namespace ControlCatalog.Pages
{
InitializeComponent();
- DataContext = new PageViewModel
+ DataContext = new TabControlPageViewModel
{
Tabs = new[]
{
- new TabItemViewModel
+ new TabControlPageViewModelItem
{
Header = "Arch",
Text = "This is the first templated tab page.",
Image = LoadBitmap("avares://ControlCatalog/Assets/delicate-arch-896885_640.jpg"),
},
- new TabItemViewModel
+ new TabControlPageViewModelItem
{
Header = "Leaf",
Text = "This is the second templated tab page.",
Image = LoadBitmap("avares://ControlCatalog/Assets/maple-leaf-888807_640.jpg"),
},
- new TabItemViewModel
+ new TabControlPageViewModelItem
{
Header = "Disabled",
Text = "You should not see this.",
@@ -55,26 +54,5 @@ namespace ControlCatalog.Pages
var assets = AvaloniaLocator.Current!.GetService()!;
return new Bitmap(assets.Open(new Uri(uri)));
}
-
- private class PageViewModel : ViewModelBase
- {
- private Dock _tabPlacement;
-
- public TabItemViewModel[]? Tabs { get; set; }
-
- public Dock TabPlacement
- {
- get { return _tabPlacement; }
- set { this.RaiseAndSetIfChanged(ref _tabPlacement, value); }
- }
- }
-
- private class TabItemViewModel
- {
- public string? Header { get; set; }
- public string? Text { get; set; }
- public IBitmap? Image { get; set; }
- public bool IsEnabled { get; set; } = true;
- }
}
}
diff --git a/samples/ControlCatalog/Pages/TabStripPage.xaml b/samples/ControlCatalog/Pages/TabStripPage.xaml
index 163665ef92..533590b48d 100644
--- a/samples/ControlCatalog/Pages/TabStripPage.xaml
+++ b/samples/ControlCatalog/Pages/TabStripPage.xaml
@@ -1,6 +1,8 @@
+ xmlns="https://github.com/avaloniaui"
+ xmlns:viewModels="using:ControlCatalog.ViewModels"
+ x:DataType="viewModels:TabControlPageViewModel">
A control which displays a selectable strip of tabs
@@ -16,14 +18,14 @@
Dynamically generated
-
+
-
-
+
diff --git a/samples/ControlCatalog/Pages/TabStripPage.xaml.cs b/samples/ControlCatalog/Pages/TabStripPage.xaml.cs
index 6d7135a90f..20fae13bbf 100644
--- a/samples/ControlCatalog/Pages/TabStripPage.xaml.cs
+++ b/samples/ControlCatalog/Pages/TabStripPage.xaml.cs
@@ -1,9 +1,6 @@
-using System;
-using Avalonia;
using Avalonia.Controls;
using Avalonia.Markup.Xaml;
-using Avalonia.Media.Imaging;
-using Avalonia.Platform;
+using ControlCatalog.ViewModels;
namespace ControlCatalog.Pages
{
@@ -13,21 +10,24 @@ namespace ControlCatalog.Pages
{
InitializeComponent();
- DataContext = new[]
+ DataContext = new TabControlPageViewModel
{
- new TabStripItemViewModel
+ Tabs = new []
{
- Header = "Item 1",
- },
- new TabStripItemViewModel
- {
- Header = "Item 2",
- },
- new TabStripItemViewModel
- {
- Header = "Disabled",
- IsEnabled = false,
- },
+ new TabControlPageViewModelItem()
+ {
+ Header = "Item 1",
+ },
+ new TabControlPageViewModelItem
+ {
+ Header = "Item 2",
+ },
+ new TabControlPageViewModelItem
+ {
+ Header = "Disabled",
+ IsEnabled = false,
+ },
+ }
};
}
@@ -35,11 +35,5 @@ namespace ControlCatalog.Pages
{
AvaloniaXamlLoader.Load(this);
}
-
- private class TabStripItemViewModel
- {
- public string? Header { get; set; }
- public bool IsEnabled { get; set; } = true;
- }
}
}
diff --git a/samples/ControlCatalog/Pages/TextBoxPage.xaml b/samples/ControlCatalog/Pages/TextBoxPage.xaml
index e3d0c5e4e2..6a4d9b7d0e 100644
--- a/samples/ControlCatalog/Pages/TextBoxPage.xaml
+++ b/samples/ControlCatalog/Pages/TextBoxPage.xaml
@@ -1,7 +1,7 @@
+ xmlns:sys="using:System">
diff --git a/samples/ControlCatalog/Pages/TransitioningContentControlPage.axaml b/samples/ControlCatalog/Pages/TransitioningContentControlPage.axaml
index a410577d27..42042652e3 100644
--- a/samples/ControlCatalog/Pages/TransitioningContentControlPage.axaml
+++ b/samples/ControlCatalog/Pages/TransitioningContentControlPage.axaml
@@ -3,11 +3,10 @@
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:vm="using:ControlCatalog.ViewModels"
- xmlns:converter="clr-namespace:ControlCatalog.Converter"
+ xmlns:converter="using:ControlCatalog.Converter"
xmlns:system="using:System"
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450"
x:DataType="vm:TransitioningContentControlPageViewModel"
- x:CompileBindings="True"
x:Class="ControlCatalog.Pages.TransitioningContentControlPage">
diff --git a/samples/ControlCatalog/Pages/TreeViewPage.xaml b/samples/ControlCatalog/Pages/TreeViewPage.xaml
index 31f4d73581..1665a59c0a 100644
--- a/samples/ControlCatalog/Pages/TreeViewPage.xaml
+++ b/samples/ControlCatalog/Pages/TreeViewPage.xaml
@@ -1,6 +1,8 @@
+ xmlns:viewModels="using:ControlCatalog.ViewModels"
+ x:Class="ControlCatalog.Pages.TreeViewPage"
+ x:DataType="viewModels:TreeViewPageViewModel">
Displays a hierachical tree of data.
diff --git a/samples/ControlCatalog/Pages/ViewboxPage.xaml b/samples/ControlCatalog/Pages/ViewboxPage.xaml
index e7e3007d35..a31a52d238 100644
--- a/samples/ControlCatalog/Pages/ViewboxPage.xaml
+++ b/samples/ControlCatalog/Pages/ViewboxPage.xaml
@@ -1,6 +1,6 @@
diff --git a/samples/ControlCatalog/Pages/WindowCustomizationsPage.xaml b/samples/ControlCatalog/Pages/WindowCustomizationsPage.xaml
index caab42e98c..f1403905c4 100644
--- a/samples/ControlCatalog/Pages/WindowCustomizationsPage.xaml
+++ b/samples/ControlCatalog/Pages/WindowCustomizationsPage.xaml
@@ -2,8 +2,10 @@
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
+ xmlns:viewModels="using:ControlCatalog.ViewModels"
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450"
- x:Class="ControlCatalog.Pages.WindowCustomizationsPage">
+ x:Class="ControlCatalog.Pages.WindowCustomizationsPage"
+ x:DataType="viewModels:MainWindowViewModel">
diff --git a/samples/ControlCatalog/ViewModels/CursorPageViewModel.cs b/samples/ControlCatalog/ViewModels/CursorPageViewModel.cs
index d73ab810eb..8a3f0ba947 100644
--- a/samples/ControlCatalog/ViewModels/CursorPageViewModel.cs
+++ b/samples/ControlCatalog/ViewModels/CursorPageViewModel.cs
@@ -27,18 +27,18 @@ namespace ControlCatalog.ViewModels
public IEnumerable StandardCursors { get; }
public Cursor CustomCursor { get; }
-
- public class StandardCursorModel
+ }
+
+ public class StandardCursorModel
+ {
+ public StandardCursorModel(StandardCursorType type)
{
- public StandardCursorModel(StandardCursorType type)
- {
- Type = type;
- Cursor = new Cursor(type);
- }
+ Type = type;
+ Cursor = new Cursor(type);
+ }
- public StandardCursorType Type { get; }
+ public StandardCursorType Type { get; }
- public Cursor Cursor { get; }
- }
+ public Cursor Cursor { get; }
}
}
diff --git a/samples/ControlCatalog/ViewModels/ItemsRepeaterPageViewModel.cs b/samples/ControlCatalog/ViewModels/ItemsRepeaterPageViewModel.cs
index 3973c73662..8f8a959867 100644
--- a/samples/ControlCatalog/ViewModels/ItemsRepeaterPageViewModel.cs
+++ b/samples/ControlCatalog/ViewModels/ItemsRepeaterPageViewModel.cs
@@ -10,25 +10,25 @@ namespace ControlCatalog.ViewModels
{
private int _newItemIndex = 1;
private int _newGenerationIndex = 0;
- private ObservableCollection- _items;
+ private ObservableCollection _items;
public ItemsRepeaterPageViewModel()
{
_items = CreateItems();
}
- public ObservableCollection
- Items
+ public ObservableCollection Items
{
get => _items;
set => this.RaiseAndSetIfChanged(ref _items, value);
}
- public Item? SelectedItem { get; set; }
+ public ItemsRepeaterPageViewModelItem? SelectedItem { get; set; }
public void AddItem()
{
var index = SelectedItem != null ? Items.IndexOf(SelectedItem) : -1;
- Items.Insert(index + 1, new Item(index + 1, $"New Item {_newItemIndex++}"));
+ Items.Insert(index + 1, new ItemsRepeaterPageViewModelItem(index + 1, $"New Item {_newItemIndex++}"));
}
public void RemoveItem()
@@ -59,33 +59,33 @@ namespace ControlCatalog.ViewModels
Items = CreateItems();
}
- private ObservableCollection
- CreateItems()
+ private ObservableCollection CreateItems()
{
var suffix = _newGenerationIndex == 0 ? string.Empty : $"[{_newGenerationIndex.ToString()}]";
_newGenerationIndex++;
- return new ObservableCollection
- (
- Enumerable.Range(1, 100000).Select(i => new Item(i, $"Item {i.ToString()} {suffix}")));
+ return new ObservableCollection(
+ Enumerable.Range(1, 100000).Select(i => new ItemsRepeaterPageViewModelItem(i, $"Item {i.ToString()} {suffix}")));
}
+ }
+
+ public class ItemsRepeaterPageViewModelItem : ViewModelBase
+ {
+ private double _height = double.NaN;
- public class Item : ViewModelBase
+ public ItemsRepeaterPageViewModelItem(int index, string text)
{
- private double _height = double.NaN;
-
- public Item(int index, string text)
- {
- Index = index;
- Text = text;
- }
- public int Index { get; }
- public string Text { get; }
+ Index = index;
+ Text = text;
+ }
+ public int Index { get; }
+ public string Text { get; }
- public double Height
- {
- get => _height;
- set => this.RaiseAndSetIfChanged(ref _height, value);
- }
+ public double Height
+ {
+ get => _height;
+ set => this.RaiseAndSetIfChanged(ref _height, value);
}
}
}
diff --git a/samples/ControlCatalog/ViewModels/MainWindowViewModel.cs b/samples/ControlCatalog/ViewModels/MainWindowViewModel.cs
index c2c2462246..b79eff780c 100644
--- a/samples/ControlCatalog/ViewModels/MainWindowViewModel.cs
+++ b/samples/ControlCatalog/ViewModels/MainWindowViewModel.cs
@@ -24,25 +24,8 @@ namespace ControlCatalog.ViewModels
private bool _preferSystemChromeEnabled;
private double _titleBarHeight;
- public MainWindowViewModel(IManagedNotificationManager notificationManager)
+ public MainWindowViewModel()
{
- _notificationManager = notificationManager;
-
- ShowCustomManagedNotificationCommand = MiniCommand.Create(() =>
- {
- NotificationManager.Show(new NotificationViewModel(NotificationManager) { Title = "Hey There!", Message = "Did you know that Avalonia now supports Custom In-Window Notifications?" });
- });
-
- ShowManagedNotificationCommand = MiniCommand.Create(() =>
- {
- NotificationManager.Show(new Avalonia.Controls.Notifications.Notification("Welcome", "Avalonia now supports Notifications.", NotificationType.Information));
- });
-
- ShowNativeNotificationCommand = MiniCommand.Create(() =>
- {
- NotificationManager.Show(new Avalonia.Controls.Notifications.Notification("Error", "Native Notifications are not quite ready. Coming soon.", NotificationType.Error));
- });
-
AboutCommand = MiniCommand.CreateFromTask(async () =>
{
var dialog = new AboutAvaloniaDialog();
@@ -52,7 +35,6 @@ namespace ControlCatalog.ViewModels
await dialog.ShowDialog(mainWindow);
}
});
-
ExitCommand = MiniCommand.Create(() =>
{
(App.Current?.ApplicationLifetime as IClassicDesktopStyleApplicationLifetime)?.Shutdown();
@@ -143,24 +125,12 @@ namespace ControlCatalog.ViewModels
set { this.RaiseAndSetIfChanged(ref _windowStates, value); }
}
- public IManagedNotificationManager NotificationManager
- {
- get { return _notificationManager; }
- set { this.RaiseAndSetIfChanged(ref _notificationManager, value); }
- }
-
public bool IsMenuItemChecked
{
get { return _isMenuItemChecked; }
set { this.RaiseAndSetIfChanged(ref _isMenuItemChecked, value); }
}
- public MiniCommand ShowCustomManagedNotificationCommand { get; }
-
- public MiniCommand ShowManagedNotificationCommand { get; }
-
- public MiniCommand ShowNativeNotificationCommand { get; }
-
public MiniCommand AboutCommand { get; }
public MiniCommand ExitCommand { get; }
diff --git a/samples/ControlCatalog/ViewModels/NotificationViewModel.cs b/samples/ControlCatalog/ViewModels/NotificationViewModel.cs
index b714c319a6..a31f164a2a 100644
--- a/samples/ControlCatalog/ViewModels/NotificationViewModel.cs
+++ b/samples/ControlCatalog/ViewModels/NotificationViewModel.cs
@@ -6,16 +6,33 @@ namespace ControlCatalog.ViewModels
{
public class NotificationViewModel
{
- public NotificationViewModel(INotificationManager manager)
+ public WindowNotificationManager? NotificationManager { get; set; }
+
+ public NotificationViewModel()
{
+ ShowCustomManagedNotificationCommand = MiniCommand.Create(() =>
+ {
+ NotificationManager?.Show(new NotificationViewModel() { Title = "Hey There!", Message = "Did you know that Avalonia now supports Custom In-Window Notifications?" , NotificationManager = NotificationManager});
+ });
+
+ ShowManagedNotificationCommand = MiniCommand.Create(() =>
+ {
+ NotificationManager?.Show(new Avalonia.Controls.Notifications.Notification("Welcome", "Avalonia now supports Notifications.", NotificationType.Information));
+ });
+
+ ShowNativeNotificationCommand = MiniCommand.Create(() =>
+ {
+ NotificationManager?.Show(new Avalonia.Controls.Notifications.Notification("Error", "Native Notifications are not quite ready. Coming soon.", NotificationType.Error));
+ });
+
YesCommand = MiniCommand.Create(() =>
{
- manager.Show(new Avalonia.Controls.Notifications.Notification("Avalonia Notifications", "Start adding notifications to your app today."));
+ NotificationManager?.Show(new Avalonia.Controls.Notifications.Notification("Avalonia Notifications", "Start adding notifications to your app today."));
});
NoCommand = MiniCommand.Create(() =>
{
- manager.Show(new Avalonia.Controls.Notifications.Notification("Avalonia Notifications", "Start adding notifications to your app today. To find out more visit..."));
+ NotificationManager?.Show(new Avalonia.Controls.Notifications.Notification("Avalonia Notifications", "Start adding notifications to your app today. To find out more visit..."));
});
}
@@ -26,5 +43,11 @@ namespace ControlCatalog.ViewModels
public MiniCommand NoCommand { get; }
+ public MiniCommand ShowCustomManagedNotificationCommand { get; }
+
+ public MiniCommand ShowManagedNotificationCommand { get; }
+
+ public MiniCommand ShowNativeNotificationCommand { get; }
+
}
}
diff --git a/samples/ControlCatalog/ViewModels/PlatformInformationViewModel.cs b/samples/ControlCatalog/ViewModels/PlatformInformationViewModel.cs
new file mode 100644
index 0000000000..e4f6c3ac73
--- /dev/null
+++ b/samples/ControlCatalog/ViewModels/PlatformInformationViewModel.cs
@@ -0,0 +1,54 @@
+using Avalonia;
+using Avalonia.Platform;
+using MiniMvvm;
+
+namespace ControlCatalog.ViewModels;
+#nullable enable
+
+public class PlatformInformationViewModel : ViewModelBase
+{
+ public PlatformInformationViewModel()
+ {
+ var runtimeInfo = AvaloniaLocator.Current.GetService()?.GetRuntimeInfo();
+
+ if (runtimeInfo is { } info)
+ {
+ if (info.IsBrowser)
+ {
+ if (info.IsDesktop)
+ {
+ PlatformInfo = "Platform: Desktop (browser)";
+ }
+ else if (info.IsMobile)
+ {
+ PlatformInfo = "Platform: Mobile (browser)";
+ }
+ else
+ {
+ PlatformInfo = "Platform: Unknown (browser) - please report";
+ }
+ }
+ else
+ {
+ if (info.IsDesktop)
+ {
+ PlatformInfo = "Platform: Desktop (native)";
+ }
+ else if (info.IsMobile)
+ {
+ PlatformInfo = "Platform: Mobile (native)";
+ }
+ else
+ {
+ PlatformInfo = "Platform: Unknown (native) - please report";
+ }
+ }
+ }
+ else
+ {
+
+ }
+ }
+
+ public string PlatformInfo { get; }
+}
diff --git a/samples/ControlCatalog/ViewModels/TabControlPageViewModel.cs b/samples/ControlCatalog/ViewModels/TabControlPageViewModel.cs
new file mode 100644
index 0000000000..b0e560b001
--- /dev/null
+++ b/samples/ControlCatalog/ViewModels/TabControlPageViewModel.cs
@@ -0,0 +1,26 @@
+using Avalonia.Controls;
+using Avalonia.Media.Imaging;
+using MiniMvvm;
+
+namespace ControlCatalog.ViewModels;
+
+public class TabControlPageViewModel : ViewModelBase
+{
+ private Dock _tabPlacement;
+
+ public TabControlPageViewModelItem[]? Tabs { get; set; }
+
+ public Dock TabPlacement
+ {
+ get { return _tabPlacement; }
+ set { this.RaiseAndSetIfChanged(ref _tabPlacement, value); }
+ }
+}
+
+public class TabControlPageViewModelItem
+{
+ public string? Header { get; set; }
+ public string? Text { get; set; }
+ public IBitmap? Image { get; set; }
+ public bool IsEnabled { get; set; } = true;
+}
diff --git a/samples/ControlCatalog/Views/CustomNotificationView.xaml b/samples/ControlCatalog/Views/CustomNotificationView.xaml
index 5b99ed8e4d..f06ea029a8 100644
--- a/samples/ControlCatalog/Views/CustomNotificationView.xaml
+++ b/samples/ControlCatalog/Views/CustomNotificationView.xaml
@@ -1,6 +1,8 @@
+ xmlns:viewModels="using:ControlCatalog.ViewModels"
+ x:Class="ControlCatalog.Views.CustomNotificationView"
+ x:DataType="viewModels:NotificationViewModel">
diff --git a/samples/IntegrationTestApp/IntegrationTestApp.csproj b/samples/IntegrationTestApp/IntegrationTestApp.csproj
index 4284399357..0a761d70ba 100644
--- a/samples/IntegrationTestApp/IntegrationTestApp.csproj
+++ b/samples/IntegrationTestApp/IntegrationTestApp.csproj
@@ -1,7 +1,7 @@
WinExe
- net6.0
+ net7.0
enable
diff --git a/samples/IntegrationTestApp/MainWindow.axaml b/samples/IntegrationTestApp/MainWindow.axaml
index 76ecfcc622..038ced4e5c 100644
--- a/samples/IntegrationTestApp/MainWindow.axaml
+++ b/samples/IntegrationTestApp/MainWindow.axaml
@@ -2,10 +2,12 @@
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
+ xmlns:integrationTestApp="using:IntegrationTestApp"
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450"
x:Class="IntegrationTestApp.MainWindow"
Name="MainWindow"
- Title="IntegrationTestApp">
+ Title="IntegrationTestApp"
+ x:DataType="integrationTestApp:MainWindow">
@@ -126,6 +128,12 @@
CenterScreen
CenterOwner
+
+ Normal
+ Minimized
+ Maximized
+ FullScreen
+
diff --git a/samples/IntegrationTestApp/MainWindow.axaml.cs b/samples/IntegrationTestApp/MainWindow.axaml.cs
index e8fb455c35..c1acc7ca88 100644
--- a/samples/IntegrationTestApp/MainWindow.axaml.cs
+++ b/samples/IntegrationTestApp/MainWindow.axaml.cs
@@ -59,6 +59,7 @@ namespace IntegrationTestApp
var sizeTextBox = this.GetControl("ShowWindowSize");
var modeComboBox = this.GetControl("ShowWindowMode");
var locationComboBox = this.GetControl("ShowWindowLocation");
+ var stateComboBox = this.GetControl("ShowWindowState");
var size = !string.IsNullOrWhiteSpace(sizeTextBox.Text) ? Size.Parse(sizeTextBox.Text) : (Size?)null;
var owner = (Window)this.GetVisualRoot()!;
@@ -85,6 +86,7 @@ namespace IntegrationTestApp
}
sizeTextBox.Text = string.Empty;
+ window.WindowState = (WindowState)stateComboBox.SelectedIndex;
switch (modeComboBox.SelectedIndex)
{
diff --git a/samples/IntegrationTestApp/ShowWindowTest.axaml b/samples/IntegrationTestApp/ShowWindowTest.axaml
index 17c359df51..c3a0d8d2e2 100644
--- a/samples/IntegrationTestApp/ShowWindowTest.axaml
+++ b/samples/IntegrationTestApp/ShowWindowTest.axaml
@@ -2,6 +2,7 @@
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
x:Class="IntegrationTestApp.ShowWindowTest"
Name="SecondaryWindow"
+ x:DataType="Window"
Title="Show Window Test">
@@ -29,7 +30,7 @@
Normal
Minimized
Maximized
- Fullscreen
+ FullScreen
diff --git a/samples/MobileSandbox/App.xaml b/samples/MobileSandbox/App.xaml
index f3210e8941..85c97c9dbe 100644
--- a/samples/MobileSandbox/App.xaml
+++ b/samples/MobileSandbox/App.xaml
@@ -1,6 +1,5 @@
diff --git a/samples/MobileSandbox/MainView.xaml b/samples/MobileSandbox/MainView.xaml
index 5f9f41f3a9..1eab13aa75 100644
--- a/samples/MobileSandbox/MainView.xaml
+++ b/samples/MobileSandbox/MainView.xaml
@@ -1,6 +1,8 @@
+ xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
+ xmlns:mobileSandbox="using:MobileSandbox"
+ x:DataType="mobileSandbox:MainView">
diff --git a/samples/MobileSandbox/Views/CustomNotificationView.xaml b/samples/MobileSandbox/Views/CustomNotificationView.xaml
index 29033ca5df..f07116583c 100644
--- a/samples/MobileSandbox/Views/CustomNotificationView.xaml
+++ b/samples/MobileSandbox/Views/CustomNotificationView.xaml
@@ -7,12 +7,12 @@
-
+
-
-
+
+
-
+
diff --git a/samples/RenderDemo/MainWindow.xaml b/samples/RenderDemo/MainWindow.xaml
index 823a0fbbef..20cc6c43e1 100644
--- a/samples/RenderDemo/MainWindow.xaml
+++ b/samples/RenderDemo/MainWindow.xaml
@@ -1,9 +1,11 @@
diff --git a/samples/RenderDemo/Pages/AnimationsPage.xaml b/samples/RenderDemo/Pages/AnimationsPage.xaml
index 9043bac33e..3f89a9d5f7 100644
--- a/samples/RenderDemo/Pages/AnimationsPage.xaml
+++ b/samples/RenderDemo/Pages/AnimationsPage.xaml
@@ -1,7 +1,9 @@
diff --git a/samples/RenderDemo/Pages/CustomAnimatorPage.xaml b/samples/RenderDemo/Pages/CustomAnimatorPage.xaml
index b386636cae..0c625b6a77 100644
--- a/samples/RenderDemo/Pages/CustomAnimatorPage.xaml
+++ b/samples/RenderDemo/Pages/CustomAnimatorPage.xaml
@@ -1,7 +1,7 @@
diff --git a/samples/RenderDemo/Pages/GlyphRunPage.xaml b/samples/RenderDemo/Pages/GlyphRunPage.xaml
index 7db58e5286..e267b458bd 100644
--- a/samples/RenderDemo/Pages/GlyphRunPage.xaml
+++ b/samples/RenderDemo/Pages/GlyphRunPage.xaml
@@ -2,7 +2,7 @@
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
- xmlns:local="clr-namespace:RenderDemo.Pages"
+ xmlns:local="using:RenderDemo.Pages"
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450"
x:Class="RenderDemo.Pages.GlyphRunPage">
diff --git a/samples/RenderDemo/Pages/Transform3DPage.axaml b/samples/RenderDemo/Pages/Transform3DPage.axaml
index 30ed35bbac..7f3636648c 100644
--- a/samples/RenderDemo/Pages/Transform3DPage.axaml
+++ b/samples/RenderDemo/Pages/Transform3DPage.axaml
@@ -2,8 +2,10 @@
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
+ xmlns:viewModels="using:RenderDemo.ViewModels"
mc:Ignorable="d" d:DesignWidth="600" d:DesignHeight="700"
- x:Class="RenderDemo.Pages.Transform3DPage">
+ x:Class="RenderDemo.Pages.Transform3DPage"
+ x:DataType="viewModels:Transform3DPageViewModel">
diff --git a/samples/RenderDemo/Pages/TransitionsPage.xaml b/samples/RenderDemo/Pages/TransitionsPage.xaml
index 71b6ea0713..006c2eb20b 100644
--- a/samples/RenderDemo/Pages/TransitionsPage.xaml
+++ b/samples/RenderDemo/Pages/TransitionsPage.xaml
@@ -1,7 +1,9 @@
diff --git a/samples/SampleControls/HamburgerMenu/HamburgerMenu.xaml b/samples/SampleControls/HamburgerMenu/HamburgerMenu.xaml
index fbc51414e3..f36b79224a 100644
--- a/samples/SampleControls/HamburgerMenu/HamburgerMenu.xaml
+++ b/samples/SampleControls/HamburgerMenu/HamburgerMenu.xaml
@@ -194,7 +194,7 @@
VerticalAlignment="Center"
Classes="h1"
Margin="{StaticResource HeaderMarginExpandedPane}"
- Text="{Binding $parent[TabControl].SelectedItem.Header, FallbackValue=''}">
+ Text="{Binding $parent[TabControl].SelectedItem.(TabItem.Header), FallbackValue=''}">
diff --git a/src/Avalonia.Diagnostics/Diagnostics/Views/LayoutExplorerView.axaml b/src/Avalonia.Diagnostics/Diagnostics/Views/LayoutExplorerView.axaml
index c404a5c382..0d2e739b2b 100644
--- a/src/Avalonia.Diagnostics/Diagnostics/Views/LayoutExplorerView.axaml
+++ b/src/Avalonia.Diagnostics/Diagnostics/Views/LayoutExplorerView.axaml
@@ -1,9 +1,10 @@
+ xmlns:controls="using:Avalonia.Diagnostics.Controls"
+ xmlns:converters="using:Avalonia.Diagnostics.Converters"
+ xmlns:viewModels="using:Avalonia.Diagnostics.ViewModels"
+ x:DataType="viewModels:ControlLayoutViewModel">
diff --git a/src/Avalonia.Diagnostics/Diagnostics/Views/MainView.xaml b/src/Avalonia.Diagnostics/Diagnostics/Views/MainView.xaml
index 35c9e27f1a..97e21079c1 100644
--- a/src/Avalonia.Diagnostics/Diagnostics/Views/MainView.xaml
+++ b/src/Avalonia.Diagnostics/Diagnostics/Views/MainView.xaml
@@ -1,7 +1,9 @@
+ xmlns:views="using:Avalonia.Diagnostics.Views"
+ xmlns:viewModels="using:Avalonia.Diagnostics.ViewModels"
+ x:Class="Avalonia.Diagnostics.Views.MainView"
+ x:DataType="viewModels:MainViewModel">
diff --git a/src/Avalonia.Themes.Fluent/Controls/ProgressBar.xaml b/src/Avalonia.Themes.Fluent/Controls/ProgressBar.xaml
index dc591ede12..253d85852e 100644
--- a/src/Avalonia.Themes.Fluent/Controls/ProgressBar.xaml
+++ b/src/Avalonia.Themes.Fluent/Controls/ProgressBar.xaml
@@ -1,7 +1,6 @@
+ xmlns:converters="using:Avalonia.Controls.Converters">
diff --git a/src/Avalonia.Themes.Fluent/Controls/ScrollViewer.xaml b/src/Avalonia.Themes.Fluent/Controls/ScrollViewer.xaml
index 2c727b4435..71df4d419f 100644
--- a/src/Avalonia.Themes.Fluent/Controls/ScrollViewer.xaml
+++ b/src/Avalonia.Themes.Fluent/Controls/ScrollViewer.xaml
@@ -1,7 +1,6 @@
+ xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
diff --git a/src/Avalonia.Themes.Fluent/Controls/Slider.xaml b/src/Avalonia.Themes.Fluent/Controls/Slider.xaml
index f2351dd5be..1e3f51f7ef 100644
--- a/src/Avalonia.Themes.Fluent/Controls/Slider.xaml
+++ b/src/Avalonia.Themes.Fluent/Controls/Slider.xaml
@@ -1,6 +1,6 @@
+ xmlns:sys="using:System">
diff --git a/src/Avalonia.Themes.Fluent/Controls/SplitButton.xaml b/src/Avalonia.Themes.Fluent/Controls/SplitButton.xaml
index 9a93b2625b..1a7e72462a 100644
--- a/src/Avalonia.Themes.Fluent/Controls/SplitButton.xaml
+++ b/src/Avalonia.Themes.Fluent/Controls/SplitButton.xaml
@@ -1,6 +1,5 @@
diff --git a/src/Avalonia.Themes.Fluent/Controls/TabItem.xaml b/src/Avalonia.Themes.Fluent/Controls/TabItem.xaml
index c8376480d0..b11ad4e03a 100644
--- a/src/Avalonia.Themes.Fluent/Controls/TabItem.xaml
+++ b/src/Avalonia.Themes.Fluent/Controls/TabItem.xaml
@@ -1,7 +1,6 @@
+ xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
diff --git a/src/Avalonia.Themes.Fluent/Controls/TabStripItem.xaml b/src/Avalonia.Themes.Fluent/Controls/TabStripItem.xaml
index fab8ba87aa..d5440025ae 100644
--- a/src/Avalonia.Themes.Fluent/Controls/TabStripItem.xaml
+++ b/src/Avalonia.Themes.Fluent/Controls/TabStripItem.xaml
@@ -1,7 +1,6 @@
+ xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
diff --git a/src/Avalonia.Themes.Fluent/Controls/TextBox.xaml b/src/Avalonia.Themes.Fluent/Controls/TextBox.xaml
index 224264b51d..c6da9f72a3 100644
--- a/src/Avalonia.Themes.Fluent/Controls/TextBox.xaml
+++ b/src/Avalonia.Themes.Fluent/Controls/TextBox.xaml
@@ -1,6 +1,5 @@
+ xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
@@ -240,7 +239,7 @@
+ IsVisible="{Binding !$parent[ToggleButton].IsChecked}"/>
diff --git a/src/Avalonia.Themes.Fluent/Controls/TimePicker.xaml b/src/Avalonia.Themes.Fluent/Controls/TimePicker.xaml
index 2414ce096e..71ff0eaebc 100644
--- a/src/Avalonia.Themes.Fluent/Controls/TimePicker.xaml
+++ b/src/Avalonia.Themes.Fluent/Controls/TimePicker.xaml
@@ -7,8 +7,7 @@
+ xmlns:sys="using:System">
diff --git a/src/Avalonia.Themes.Fluent/Controls/ToggleSwitch.xaml b/src/Avalonia.Themes.Fluent/Controls/ToggleSwitch.xaml
index 90993fcc64..c88839f7d2 100644
--- a/src/Avalonia.Themes.Fluent/Controls/ToggleSwitch.xaml
+++ b/src/Avalonia.Themes.Fluent/Controls/ToggleSwitch.xaml
@@ -1,7 +1,6 @@
+ xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
diff --git a/src/Avalonia.Themes.Fluent/Controls/ToolTip.xaml b/src/Avalonia.Themes.Fluent/Controls/ToolTip.xaml
index bc9dceb545..8b086a8d10 100644
--- a/src/Avalonia.Themes.Fluent/Controls/ToolTip.xaml
+++ b/src/Avalonia.Themes.Fluent/Controls/ToolTip.xaml
@@ -1,7 +1,6 @@
+ xmlns:sys="using:System">
diff --git a/src/Avalonia.Themes.Fluent/Controls/TreeViewItem.xaml b/src/Avalonia.Themes.Fluent/Controls/TreeViewItem.xaml
index 83abe7848c..9171791a0f 100644
--- a/src/Avalonia.Themes.Fluent/Controls/TreeViewItem.xaml
+++ b/src/Avalonia.Themes.Fluent/Controls/TreeViewItem.xaml
@@ -1,6 +1,6 @@
+ xmlns:converters="using:Avalonia.Controls.Converters">
diff --git a/src/Avalonia.Themes.Fluent/FluentDark.xaml b/src/Avalonia.Themes.Fluent/FluentDark.xaml
index 50b12efd78..aad71b18fa 100644
--- a/src/Avalonia.Themes.Fluent/FluentDark.xaml
+++ b/src/Avalonia.Themes.Fluent/FluentDark.xaml
@@ -1,6 +1,6 @@
+ xmlns:sys="using:System">
diff --git a/src/Avalonia.Themes.Fluent/FluentLight.xaml b/src/Avalonia.Themes.Fluent/FluentLight.xaml
index feb043c5f3..907efe7ee6 100644
--- a/src/Avalonia.Themes.Fluent/FluentLight.xaml
+++ b/src/Avalonia.Themes.Fluent/FluentLight.xaml
@@ -1,6 +1,6 @@
+ xmlns:sys="using:System">
diff --git a/src/Avalonia.Themes.Simple/Controls/ButtonSpinner.xaml b/src/Avalonia.Themes.Simple/Controls/ButtonSpinner.xaml
index 9798e5290b..57d6eabea4 100644
--- a/src/Avalonia.Themes.Simple/Controls/ButtonSpinner.xaml
+++ b/src/Avalonia.Themes.Simple/Controls/ButtonSpinner.xaml
@@ -1,6 +1,5 @@
+ xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
+ xmlns:sys="using:System">
diff --git a/src/Avalonia.Themes.Simple/Controls/CalendarItem.xaml b/src/Avalonia.Themes.Simple/Controls/CalendarItem.xaml
index 2a9ae7cf8d..f022746bf5 100644
--- a/src/Avalonia.Themes.Simple/Controls/CalendarItem.xaml
+++ b/src/Avalonia.Themes.Simple/Controls/CalendarItem.xaml
@@ -162,7 +162,7 @@
-
+
+ xmlns:sys="using:System">
diff --git a/src/Avalonia.Themes.Simple/Controls/DateTimePickerShared.xaml b/src/Avalonia.Themes.Simple/Controls/DateTimePickerShared.xaml
index 8639a2baa2..5f1dea692f 100644
--- a/src/Avalonia.Themes.Simple/Controls/DateTimePickerShared.xaml
+++ b/src/Avalonia.Themes.Simple/Controls/DateTimePickerShared.xaml
@@ -6,9 +6,7 @@
-->
+ xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
diff --git a/src/Avalonia.Themes.Simple/Controls/ManagedFileChooser.xaml b/src/Avalonia.Themes.Simple/Controls/ManagedFileChooser.xaml
index 3416b5406e..61dae9b445 100644
--- a/src/Avalonia.Themes.Simple/Controls/ManagedFileChooser.xaml
+++ b/src/Avalonia.Themes.Simple/Controls/ManagedFileChooser.xaml
@@ -1,6 +1,7 @@
+ xmlns:dialogs="using:Avalonia.Dialogs"
+ xmlns:internal="using:Avalonia.Dialogs.Internal">
-
+
-
+
-
+
-
-
+
@@ -179,7 +180,7 @@
-
+
diff --git a/src/Avalonia.Themes.Simple/Controls/NativeMenuBar.xaml b/src/Avalonia.Themes.Simple/Controls/NativeMenuBar.xaml
index 8c51ec8609..160acd5872 100644
--- a/src/Avalonia.Themes.Simple/Controls/NativeMenuBar.xaml
+++ b/src/Avalonia.Themes.Simple/Controls/NativeMenuBar.xaml
@@ -1,6 +1,6 @@
+ xmlns:default="using:Avalonia.Themes.Simple">
@@ -11,16 +11,17 @@
diff --git a/src/Avalonia.Themes.Simple/Controls/ProgressBar.xaml b/src/Avalonia.Themes.Simple/Controls/ProgressBar.xaml
index 5adb5bde7e..3eb158d5b6 100644
--- a/src/Avalonia.Themes.Simple/Controls/ProgressBar.xaml
+++ b/src/Avalonia.Themes.Simple/Controls/ProgressBar.xaml
@@ -1,6 +1,6 @@
+ xmlns:converters="using:Avalonia.Controls.Converters">
diff --git a/src/Avalonia.Themes.Simple/Controls/SplitButton.xaml b/src/Avalonia.Themes.Simple/Controls/SplitButton.xaml
index f0d22aac97..3c621a981d 100644
--- a/src/Avalonia.Themes.Simple/Controls/SplitButton.xaml
+++ b/src/Avalonia.Themes.Simple/Controls/SplitButton.xaml
@@ -1,6 +1,5 @@
@@ -747,13 +768,49 @@ namespace Avalonia.Markup.Xaml.UnitTests.MarkupExtensions
";
var contentControl = AvaloniaRuntimeXamlLoader.Parse(xaml);
+ contentControl.DataContext = new TestDataContext(); // should be ignored
contentControl.Measure(new Size(10, 10));
var result = contentControl.GetTemplateChildren().OfType().First();
- Assert.Equal("Hello", result.Content);
+ Assert.Equal(false, result.Focusable);
}
}
+ [Fact]
+ public void ResolvesRelativeSourceBindingFromStyleSelector()
+ {
+ using (UnitTestApplication.Start(TestServices.StyledWindow))
+ {
+ var xaml = @"
+
+
+
+
+
+";
+
+ var textBox = AvaloniaRuntimeXamlLoader.Parse(xaml);
+ textBox.DataContext = new TestDataContext(); // should be ignored
+ textBox.Measure(new Size(10, 10));
+
+ var result = textBox.GetTemplateChildren().OfType().First();
+ Assert.Equal(textBox.InnerLeftContent, result.Content);
+ }
+ }
+
[Fact]
public void ResolvesElementNameInTemplate()
{
@@ -1569,6 +1626,27 @@ namespace Avalonia.Markup.Xaml.UnitTests.MarkupExtensions
}
}
+ [Fact]
+ public void Uses_RuntimeLoader_Configuration_To_Enabled_Compiled()
+ {
+ using (UnitTestApplication.Start(TestServices.StyledWindow))
+ {
+ var xaml = @"
+";
+ var control = (AssignBindingControl)AvaloniaRuntimeXamlLoader.Load(xaml, new RuntimeXamlLoaderConfiguration
+ {
+ UseCompiledBindingsByDefault = true
+ });
+ var compiledPath = ((CompiledBindingExtension)control.X).Path;
+
+ var node = Assert.IsType(Assert.Single(compiledPath.Elements));
+ Assert.Equal(typeof(string), node.Property.PropertyType);
+ }
+ }
+
void Throws(string type, Action cb)
{
try
@@ -1659,7 +1737,9 @@ namespace Avalonia.Markup.Xaml.UnitTests.MarkupExtensions
string IHasExplicitProperty.ExplicitProperty => "Hello";
- public string ExplicitProperty => "Bye";
+ public string ExplicitProperty => "Bye";
+
+ public static string StaticProperty => "World";
public class NonIntegerIndexer : NotifyingBase, INonIntegerIndexerDerived
{
diff --git a/tests/Avalonia.Markup.Xaml.UnitTests/MarkupExtensions/OnFormFactorExtensionTests.cs b/tests/Avalonia.Markup.Xaml.UnitTests/MarkupExtensions/OnFormFactorExtensionTests.cs
new file mode 100644
index 0000000000..783e647738
--- /dev/null
+++ b/tests/Avalonia.Markup.Xaml.UnitTests/MarkupExtensions/OnFormFactorExtensionTests.cs
@@ -0,0 +1,71 @@
+using Avalonia.Controls;
+using Avalonia.Platform;
+using Xunit;
+
+namespace Avalonia.Markup.Xaml.UnitTests.MarkupExtensions;
+
+public class OnFormFactorExtensionTests : XamlTestBase
+{
+ [Fact]
+ public void Should_Resolve_Default_Value()
+ {
+ using (AvaloniaLocator.EnterScope())
+ {
+ AvaloniaLocator.CurrentMutable.Bind()
+ .ToConstant(new TestRuntimePlatform(false, false));
+
+ var xaml = @"
+
+
+";
+
+ var userControl = (UserControl)AvaloniaRuntimeXamlLoader.Load(xaml);
+ var textBlock = (TextBlock)userControl.Content!;
+
+ Assert.Equal("Hello World", textBlock.Text);
+ }
+ }
+
+ [Theory]
+ [InlineData(false, true, "Im Mobile")]
+ [InlineData(true, false, "Im Desktop")]
+ [InlineData(false, false, "Default value")]
+ public void Should_Resolve_Expected_Value_Per_Platform(bool isDesktop, bool isMobile, string expectedResult)
+ {
+ using (AvaloniaLocator.EnterScope())
+ {
+ AvaloniaLocator.CurrentMutable.Bind()
+ .ToConstant(new TestRuntimePlatform(isDesktop, isMobile));
+
+ var xaml = @"
+
+
+";
+
+ var userControl = (UserControl)AvaloniaRuntimeXamlLoader.Load(xaml);
+ var textBlock = (TextBlock)userControl.Content!;
+
+ Assert.Equal(expectedResult, textBlock.Text);
+ }
+ }
+
+ private class TestRuntimePlatform : StandardRuntimePlatform
+ {
+ private readonly bool _isDesktop;
+ private readonly bool _isMobile;
+
+ public TestRuntimePlatform(bool isDesktop, bool isMobile)
+ {
+ _isDesktop = isDesktop;
+ _isMobile = isMobile;
+ }
+
+ public override RuntimePlatformInfo GetRuntimeInfo()
+ {
+ return new RuntimePlatformInfo() { IsDesktop = _isDesktop, IsMobile = _isMobile };
+ }
+ }
+}
diff --git a/tests/Avalonia.Markup.Xaml.UnitTests/MarkupExtensions/OnPlatformExtensionTests.cs b/tests/Avalonia.Markup.Xaml.UnitTests/MarkupExtensions/OnPlatformExtensionTests.cs
new file mode 100644
index 0000000000..1d37378010
--- /dev/null
+++ b/tests/Avalonia.Markup.Xaml.UnitTests/MarkupExtensions/OnPlatformExtensionTests.cs
@@ -0,0 +1,75 @@
+using Avalonia.Controls;
+using Avalonia.Platform;
+using Xunit;
+
+namespace Avalonia.Markup.Xaml.UnitTests.MarkupExtensions;
+
+public class OnPlatformExtensionTests : XamlTestBase
+{
+ [Fact]
+ public void Should_Resolve_Default_Value()
+ {
+ using (AvaloniaLocator.EnterScope())
+ {
+ AvaloniaLocator.CurrentMutable.Bind()
+ .ToConstant(new TestRuntimePlatform(OperatingSystemType.Unknown));
+
+ var xaml = @"
+
+
+";
+
+ var userControl = (UserControl)AvaloniaRuntimeXamlLoader.Load(xaml);
+ var textBlock = (TextBlock)userControl.Content!;
+
+ Assert.Equal("Hello World", textBlock.Text);
+ }
+ }
+
+ [Theory]
+ [InlineData(OperatingSystemType.WinNT, "Im Windows")]
+ [InlineData(OperatingSystemType.OSX, "Im macOS")]
+ [InlineData(OperatingSystemType.Linux, "Im Linux")]
+ [InlineData(OperatingSystemType.Android, "Im Android")]
+ [InlineData(OperatingSystemType.iOS, "Im iOS")]
+ [InlineData(OperatingSystemType.Browser, "Im Browser")]
+ [InlineData(OperatingSystemType.Unknown, "Default value")]
+ public void Should_Resolve_Expected_Value_Per_Platform(OperatingSystemType currentPlatform, string expectedResult)
+ {
+ using (AvaloniaLocator.EnterScope())
+ {
+ AvaloniaLocator.CurrentMutable.Bind()
+ .ToConstant(new TestRuntimePlatform(currentPlatform));
+
+ var xaml = @"
+
+
+";
+
+ var userControl = (UserControl)AvaloniaRuntimeXamlLoader.Load(xaml);
+ var textBlock = (TextBlock)userControl.Content!;
+
+ Assert.Equal(expectedResult, textBlock.Text);
+ }
+ }
+
+ private class TestRuntimePlatform : StandardRuntimePlatform
+ {
+ private readonly OperatingSystemType _operatingSystemType;
+
+ public TestRuntimePlatform(OperatingSystemType operatingSystemType)
+ {
+ _operatingSystemType = operatingSystemType;
+ }
+
+ public override RuntimePlatformInfo GetRuntimeInfo()
+ {
+ return new RuntimePlatformInfo() { OperatingSystem = _operatingSystemType };
+ }
+ }
+}
diff --git a/tests/Avalonia.Markup.Xaml.UnitTests/MarkupExtensions/OptionsMarkupExtensionTests.cs b/tests/Avalonia.Markup.Xaml.UnitTests/MarkupExtensions/OptionsMarkupExtensionTests.cs
new file mode 100644
index 0000000000..2d1f961743
--- /dev/null
+++ b/tests/Avalonia.Markup.Xaml.UnitTests/MarkupExtensions/OptionsMarkupExtensionTests.cs
@@ -0,0 +1,605 @@
+using System;
+using System.Reactive.Disposables;
+using System.Runtime.InteropServices;
+using Avalonia.Controls;
+using Avalonia.Markup.Xaml.MarkupExtensions;
+using Avalonia.Media;
+using Avalonia.Metadata;
+using Xunit;
+
+namespace Avalonia.Markup.Xaml.UnitTests.MarkupExtensions;
+
+public class OptionsMarkupExtensionTests : XamlTestBase
+{
+ public static Func