Browse Source

Merge branch 'master' into fixes/HotKey_Command_Issues

pull/4737/head
Giuseppe Lippolis 6 years ago
parent
commit
204838b94f
  1. 1
      Avalonia.sln.DotSettings
  2. 4
      azure-pipelines.yml
  3. 2
      build.ps1
  4. BIN
      build/Assets/Icon.png
  5. 9
      build/SharedVersion.props
  6. 4
      build/SourceLink.props
  7. 4
      build/XUnit.props
  8. BIN
      build/avalonia.snk
  9. 1
      dirs.proj
  10. 6
      native/Avalonia.Native/src/OSX/window.mm
  11. 6
      nukebuild/BuildTasksPatcher.cs
  12. 2
      nukebuild/_build.csproj
  13. 3
      packages/Avalonia/AvaloniaBuildTasks.targets
  14. 2
      readme.md
  15. 20
      samples/BindingDemo/App.xaml.cs
  16. 1
      samples/ControlCatalog.Desktop/ControlCatalog.Desktop.csproj
  17. 10
      samples/ControlCatalog.Desktop/Program.cs
  18. 3
      samples/ControlCatalog.NetCore/ControlCatalog.NetCore.csproj
  19. 5
      samples/ControlCatalog.NetCore/Program.cs
  20. 10
      samples/ControlCatalog/App.xaml
  21. 1
      samples/ControlCatalog/MainView.xaml
  22. 11
      samples/ControlCatalog/Pages/AutoCompleteBoxPage.xaml
  23. 11
      samples/ControlCatalog/Pages/ButtonSpinnerPage.xaml
  24. 13
      samples/ControlCatalog/Pages/ComboBoxPage.xaml
  25. 20
      samples/ControlCatalog/Pages/DateTimePickerPage.xaml
  26. 42
      samples/ControlCatalog/Pages/LabelsPage.axaml
  27. 43
      samples/ControlCatalog/Pages/LabelsPage.axaml.cs
  28. 10
      samples/ControlCatalog/Pages/NumericUpDownPage.xaml
  29. 16
      samples/ControlCatalog/Pages/RelativePanelPage.axaml
  30. 10
      samples/ControlCatalog/Pages/SliderPage.xaml
  31. 47
      samples/ControlCatalog/Pages/TextBoxPage.xaml
  32. 10
      samples/Previewer/App.xaml.cs
  33. 15
      samples/Previewer/Program.cs
  34. 13
      samples/RenderDemo/App.xaml.cs
  35. 6
      samples/RenderDemo/Pages/GlyphRunPage.xaml
  36. 7
      samples/RenderDemo/Pages/GlyphRunPage.xaml.cs
  37. 2
      samples/Sandbox/Program.cs
  38. 8
      samples/VirtualizationDemo/App.xaml.cs
  39. 20
      samples/VirtualizationDemo/Program.cs
  40. 8
      samples/interop/Direct3DInteropSample/App.paml.cs
  41. 21
      samples/interop/Direct3DInteropSample/Program.cs
  42. 3
      samples/interop/NativeEmbedSample/NativeEmbedSample.csproj
  43. 5
      src/Avalonia.Animation/Properties/AssemblyInfo.cs
  44. 3
      src/Avalonia.Base/ApiCompatBaseline.txt
  45. 14
      src/Avalonia.Base/Logging/TraceLogSink.cs
  46. 39
      src/Avalonia.Base/Metadata/XmlnsPrefixAttribute.cs
  47. 8
      src/Avalonia.Base/Properties/AssemblyInfo.cs
  48. 2
      src/Avalonia.Build.Tasks/Avalonia.Build.Tasks.csproj
  49. 8
      src/Avalonia.Build.Tasks/CompileAvaloniaXamlTask.cs
  50. 26
      src/Avalonia.Build.Tasks/XamlCompilerTaskExecutor.cs
  51. 1
      src/Avalonia.Controls.DataGrid/DataGridColumn.cs
  52. 13
      src/Avalonia.Controls.DataGrid/DataGridColumnHeader.cs
  53. 7
      src/Avalonia.Controls.DataGrid/Properties/AssemblyInfo.cs
  54. 8
      src/Avalonia.Controls/ApiCompatBaseline.txt
  55. 13
      src/Avalonia.Controls/ContextMenu.cs
  56. 4
      src/Avalonia.Controls/DateTimePickers/DateTimePickerPanel.cs
  57. 2
      src/Avalonia.Controls/ItemsControl.cs
  58. 75
      src/Avalonia.Controls/Label.cs
  59. 19
      src/Avalonia.Controls/LoggingExtensions.cs
  60. 25
      src/Avalonia.Controls/Presenters/ContentPresenter.cs
  61. 7
      src/Avalonia.Controls/Presenters/ItemVirtualizerSimple.cs
  62. 20
      src/Avalonia.Controls/Presenters/TextPresenter.cs
  63. 1
      src/Avalonia.Controls/Primitives/IPopupHost.cs
  64. 1
      src/Avalonia.Controls/Primitives/Popup.cs
  65. 7
      src/Avalonia.Controls/Properties/AssemblyInfo.cs
  66. 12
      src/Avalonia.Controls/RelativePanel.AttachedProperties.cs
  67. 6
      src/Avalonia.Controls/ResolveByNameAttribute.cs
  68. 3
      src/Avalonia.Controls/Selection/SelectionModel.cs
  69. 54
      src/Avalonia.Controls/SplitView.cs
  70. 28
      src/Avalonia.Controls/Templates/FuncDataTemplate.cs
  71. 23
      src/Avalonia.Controls/TextBlock.cs
  72. 2
      src/Avalonia.Controls/Window.cs
  73. 7
      src/Avalonia.Diagnostics/Diagnostics/ViewModels/TreeNode.cs
  74. 6
      src/Avalonia.Diagnostics/Diagnostics/Views/ControlDetailsView.xaml
  75. 8
      src/Avalonia.Diagnostics/Diagnostics/Views/MainWindow.xaml.cs
  76. 3
      src/Avalonia.Diagnostics/Diagnostics/Views/TreePageView.xaml
  77. 1
      src/Avalonia.Dialogs/ApiCompatBaseline.txt
  78. 4
      src/Avalonia.FreeDesktop/Avalonia.FreeDesktop.csproj
  79. 20
      src/Avalonia.Input/MouseDevice.cs
  80. 6
      src/Avalonia.Layout/Properties/AssemblyInfo.cs
  81. 12
      src/Avalonia.Native/WindowImplBase.cs
  82. 10
      src/Avalonia.OpenGL/Angle/AngleEglInterface.cs
  83. 9
      src/Avalonia.OpenGL/Angle/AngleWin32EglDisplay.cs
  84. 6
      src/Avalonia.OpenGL/Egl/EglConsts.cs
  85. 1
      src/Avalonia.ReactiveUI.Events/Avalonia.ReactiveUI.Events.csproj
  86. 1
      src/Avalonia.ReactiveUI/Avalonia.ReactiveUI.csproj
  87. 18
      src/Avalonia.ReactiveUI/ReactiveUserControl.cs
  88. 18
      src/Avalonia.ReactiveUI/ReactiveWindow.cs
  89. 6
      src/Avalonia.Styling/Properties/AssemblyInfo.cs
  90. 3
      src/Avalonia.Themes.Default/DefaultTheme.xaml
  91. 17
      src/Avalonia.Themes.Default/Label.xaml
  92. 8
      src/Avalonia.Themes.Default/SplitView.xaml
  93. 99
      src/Avalonia.Themes.Fluent/ButtonSpinner.xaml
  94. 201
      src/Avalonia.Themes.Fluent/ComboBox.xaml
  95. 48
      src/Avalonia.Themes.Fluent/DataValidationErrors.xaml
  96. 143
      src/Avalonia.Themes.Fluent/DatePicker.xaml
  97. 3
      src/Avalonia.Themes.Fluent/FluentTheme.xaml
  98. 17
      src/Avalonia.Themes.Fluent/Label.xaml
  99. 2
      src/Avalonia.Themes.Fluent/NumericUpDown.xaml
  100. 204
      src/Avalonia.Themes.Fluent/Slider.xaml

1
Avalonia.sln.DotSettings

@ -37,4 +37,5 @@
<s:String x:Key="/Default/CodeStyle/Naming/CSharpNaming/PredefinedNamingRules/=StaticReadonly/@EntryIndexedValue">&lt;Policy Inspect="True" Prefix="" Suffix="" Style="AaBb" /&gt;</s:String>
<s:String x:Key="/Default/CodeStyle/Naming/CSharpNaming/PredefinedNamingRules/=TypeParameters/@EntryIndexedValue">&lt;Policy Inspect="False" Prefix="T" Suffix="" Style="AaBb" /&gt;</s:String>
<s:String x:Key="/Default/CodeStyle/Naming/CSharpNaming/PredefinedNamingRules/=TypesAndNamespaces/@EntryIndexedValue">&lt;Policy Inspect="False" Prefix="" Suffix="" Style="AaBb" /&gt;</s:String>
<s:Boolean x:Key="/Default/Environment/SettingsMigration/IsMigratorApplied/=JetBrains_002EReSharper_002EFeature_002EServices_002EDaemon_002ESettings_002EMigration_002ESwaWarningsModeSettingsMigrate/@EntryIndexedValue">True</s:Boolean>
<s:Boolean x:Key="/Default/UserDictionary/Words/=Avalonia/@EntryIndexedValue">True</s:Boolean></wpf:ResourceDictionary>

4
azure-pipelines.yml

@ -31,6 +31,8 @@ jobs:
condition: not(canceled())
- job: macOS
variables:
SolutionDir: '$(Build.SourcesDirectory)'
pool:
vmImage: 'macOS-10.14'
steps:
@ -97,6 +99,8 @@ jobs:
- job: Windows
pool:
vmImage: 'windows-2019'
variables:
SolutionDir: '$(Build.SourcesDirectory)'
steps:
- task: UseDotNet@2
displayName: 'Use .NET Core SDK 3.1.401'

2
build.ps1

@ -62,6 +62,8 @@ else {
} else {
ExecSafe { & $DotNetInstallFile -InstallDir $DotNetDirectory -Version $DotNetVersion -NoPath }
}
$env:PATH="$DotNetDirectory;$env:PATH"
}
Write-Output "Microsoft (R) .NET Core SDK version $(& $env:DOTNET_EXE --version)"

BIN
build/Assets/Icon.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 14 KiB

9
build/SharedVersion.props

@ -10,10 +10,17 @@
<NoWarn>CS1591</NoWarn>
<LangVersion>latest</LangVersion>
<PackageLicenseExpression>MIT</PackageLicenseExpression>
<PackageIconUrl>https://avatars2.githubusercontent.com/u/14075148?s=200</PackageIconUrl>
<PackageIcon>Icon.png</PackageIcon>
<PackageDescription>Avalonia is a WPF/UWP-inspired cross-platform XAML-based UI framework providing a flexible styling system and supporting a wide range of Operating Systems such as Windows (.NET Framework, .NET Core), Linux (via Xorg), MacOS and with experimental support for Android and iOS.</PackageDescription>
<PackageTags>avalonia;avaloniaui;mvvm;rx;reactive extensions;android;ios;mac;forms;wpf;net;netstandard;net461;uwp;xamarin</PackageTags>
<PackageReleaseNotes>https://github.com/AvaloniaUI/Avalonia/releases</PackageReleaseNotes>
<RepositoryType>git</RepositoryType>
<AssemblyOriginatorKeyFile>$(MSBuildThisFileDirectory)\avalonia.snk</AssemblyOriginatorKeyFile>
<SignAssembly>false</SignAssembly>
<DefineConstants Condition="$(SignAssembly) == true">$(DefineConstants);SIGNED_BUILD</DefineConstants>
</PropertyGroup>
<ItemGroup Label="PackageIcon">
<None Include="$(MSBuildThisFileDirectory)/Assets/Icon.png" Pack="true" PackagePath=""/>
</ItemGroup>
</Project>

4
build/SourceLink.props

@ -1,5 +1,5 @@
<Project>
<ItemGroup>
<PackageReference Include="SourceLink.Create.CommandLine" Version="2.8.0" PrivateAssets="All" />
<PackageReference Include="SourceLink.Create.CommandLine" Version="2.8.3" PrivateAssets="All" />
</ItemGroup>
</Project>
</Project>

4
build/XUnit.props

@ -11,4 +11,8 @@
<PackageReference Include="Xunit.SkippableFact" Version="1.3.6" />
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="15.7.0" />
</ItemGroup>
<PropertyGroup>
<AssemblyOriginatorKeyFile>$(MSBuildThisFileDirectory)\avalonia.snk</AssemblyOriginatorKeyFile>
<SignAssembly>False</SignAssembly>
</PropertyGroup>
</Project>

BIN
build/avalonia.snk

Binary file not shown.

1
dirs.proj

@ -21,6 +21,7 @@
<ItemGroup Condition="!$([MSBuild]::IsOsPlatform('Windows')) OR '$(MSBuildRuntimeType)' != 'Full'">
<ProjectReference Remove="src/Windows/Avalonia.Win32.Interop/Avalonia.Win32.Interop.csproj" />
<ProjectReference Remove="samples/interop/**/*.*proj" />
<ProjectReference Remove="samples/ControlCatalog.Desktop/*.*proj" />
</ItemGroup>
<ItemGroup>

6
native/Avalonia.Native/src/OSX/window.mm

@ -1338,6 +1338,12 @@ NSArray* AllLoopModes = [NSArray arrayWithObjects: NSDefaultRunLoopMode, NSEvent
}
_parent->BaseEvents->RunRenderPriorityJobs();
if (_parent == nullptr)
{
return;
}
_parent->BaseEvents->Paint();
}

6
nukebuild/BuildTasksPatcher.cs

@ -29,7 +29,11 @@ public class BuildTasksPatcher
InputAssemblies = new[]
{
temp, typeof(Mono.Cecil.AssemblyDefinition).Assembly.GetModules()[0]
.FullyQualifiedName
.FullyQualifiedName,
typeof(Mono.Cecil.Rocks.MethodBodyRocks).Assembly.GetModules()[0].FullyQualifiedName,
typeof(Mono.Cecil.Pdb.PdbReaderProvider).Assembly.GetModules()[0].FullyQualifiedName,
typeof(Mono.Cecil.Mdb.MdbReaderProvider).Assembly.GetModules()[0].FullyQualifiedName
},
SearchDirectories = new string[0],
OutputFile = output

2
nukebuild/_build.csproj

@ -16,7 +16,7 @@
<PackageReference Include="vswhere" Version="2.6.7" Condition=" '$(OS)' == 'Windows_NT' " />
<PackageReference Include="ILRepack.NETStandard" Version="2.0.4" />
<!-- Keep in sync with Avalonia.Build.Tasks -->
<PackageReference Include="Avalonia.Unofficial.Cecil" Version="20190417.2.0" />
<PackageReference Include="Mono.Cecil" Version="0.11.2" />
<PackageReference Include="Pharmacist.Core" Version="1.8.1" />
</ItemGroup>

3
packages/Avalonia/AvaloniaBuildTasks.targets

@ -87,6 +87,9 @@
ProjectDirectory="$(MSBuildProjectDirectory)"
VerifyIl="$(AvaloniaXamlIlVerifyIl)"
ReportImportance="$(AvaloniaXamlReportImportance)"
AssemblyOriginatorKeyFile="$(AssemblyOriginatorKeyFile)"
SignAssembly="$(SignAssembly)"
DelaySign="$(DelaySign)"
/>
<Exec
Condition="'$(_AvaloniaUseExternalMSBuild)' == 'true'"

2
readme.md

@ -39,7 +39,7 @@ Examples of UIs built with Avalonia
## JetBrains Rider
If you need to develop Avalonia app with JetBrains Rider, go and *vote* on [this issue](https://youtrack.jetbrains.com/issue/RIDER-39247) in their tracker. JetBrains won't do things without their users telling them that they want the feature, so only **YOU** can make it happen.
If you need to develop Avalonia app with JetBrains Rider you can use latest Rider [preview builds](https://www.jetbrains.com/rider/nextversion/).
## Bleeding Edge Builds

20
samples/BindingDemo/App.xaml.cs

@ -1,6 +1,5 @@
using System;
using Avalonia;
using Avalonia.Controls;
using Avalonia.Controls.ApplicationLifetimes;
using Avalonia.Markup.Xaml;
using Avalonia.ReactiveUI;
@ -13,13 +12,20 @@ namespace BindingDemo
AvaloniaXamlLoader.Load(this);
}
private static void Main()
public override void OnFrameworkInitializationCompleted()
{
AppBuilder.Configure<App>()
if (ApplicationLifetime is IClassicDesktopStyleApplicationLifetime desktop)
desktop.MainWindow = new MainWindow();
base.OnFrameworkInitializationCompleted();
}
public static int Main(string[] args)
=> BuildAvaloniaApp().StartWithClassicDesktopLifetime(args);
public static AppBuilder BuildAvaloniaApp()
=> AppBuilder.Configure<App>()
.UsePlatformDetect()
.UseReactiveUI()
.LogToDebug()
.Start<MainWindow>();
}
.LogToTrace();
}
}

1
samples/ControlCatalog.Desktop/ControlCatalog.Desktop.csproj

@ -3,6 +3,7 @@
<PropertyGroup>
<OutputType>Exe</OutputType>
<TargetFramework>net461</TargetFramework>
<PlatformTarget>x64</PlatformTarget>
</PropertyGroup>
<ItemGroup>

10
samples/ControlCatalog.Desktop/Program.cs

@ -10,19 +10,15 @@ namespace ControlCatalog
internal class Program
{
[STAThread]
static void Main(string[] args)
{
// TODO: Make this work with GTK/Skia/Cairo depending on command-line args
// again.
BuildAvaloniaApp().Start<MainWindow>();
}
public static int Main(string[] args)
=> BuildAvaloniaApp().StartWithClassicDesktopLifetime(args);
/// <summary>
/// This method is needed for IDE previewer infrastructure
/// </summary>
public static AppBuilder BuildAvaloniaApp()
=> AppBuilder.Configure<App>()
.LogToDebug()
.LogToTrace()
.UsePlatformDetect()
.UseReactiveUI();

3
samples/ControlCatalog.NetCore/ControlCatalog.NetCore.csproj

@ -11,9 +11,8 @@
<ProjectReference Include="..\..\src\Avalonia.Dialogs\Avalonia.Dialogs.csproj" />
<ProjectReference Include="..\..\src\Linux\Avalonia.LinuxFramebuffer\Avalonia.LinuxFramebuffer.csproj" />
<ProjectReference Include="..\ControlCatalog\ControlCatalog.csproj" />
<ProjectReference Include="..\..\src\Avalonia.Desktop\Avalonia.Desktop.csproj" />
<ProjectReference Include="..\..\src\Avalonia.X11\Avalonia.X11.csproj" />
<PackageReference Include="Avalonia.Angle.Windows.Natives" Version="2.1.0.2019013001" />
<PackageReference Include="Avalonia.Angle.Windows.Natives" Version="2.1.0.2020091801" />
</ItemGroup>

5
samples/ControlCatalog.NetCore/Program.cs

@ -7,12 +7,11 @@ using System.Threading.Tasks;
using Avalonia;
using Avalonia.Controls;
using Avalonia.Controls.ApplicationLifetimes;
using Avalonia.Dialogs;
using Avalonia.Headless;
using Avalonia.LogicalTree;
using Avalonia.Skia;
using Avalonia.ReactiveUI;
using Avalonia.Threading;
using Avalonia.Dialogs;
namespace ControlCatalog.NetCore
{
@ -121,7 +120,7 @@ namespace ControlCatalog.NetCore
.UseSkia()
.UseReactiveUI()
.UseManagedSystemDialogs()
.LogToDebug();
.LogToTrace();
static void SilenceConsole()
{

10
samples/ControlCatalog/App.xaml

@ -12,6 +12,16 @@
<Style Selector="TextBlock.h3">
<Setter Property="FontSize" Value="12" />
</Style>
<Style Selector="Label.h1">
<Setter Property="FontSize" Value="16" />
<Setter Property="FontWeight" Value="Medium" />
</Style>
<Style Selector="Label.h2">
<Setter Property="FontSize" Value="14" />
</Style>
<Style Selector="Label.h3">
<Setter Property="FontSize" Value="12" />
</Style>
<StyleInclude Source="/SideBar.xaml"/>
</Application.Styles>
</Application>

1
samples/ControlCatalog/MainView.xaml

@ -44,6 +44,7 @@
ScrollViewer.HorizontalScrollBarVisibility="Disabled">
<pages:ItemsRepeaterPage/>
</TabItem>
<TabItem Header="Label"><pages:LabelsPage/></TabItem>
<TabItem Header="LayoutTransformControl"><pages:LayoutTransformControlPage/></TabItem>
<TabItem Header="ListBox"
ScrollViewer.VerticalScrollBarVisibility="Disabled">

11
samples/ControlCatalog/Pages/AutoCompleteBoxPage.xaml

@ -1,5 +1,6 @@
<UserControl xmlns="https://github.com/avaloniaui"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:sys="clr-namespace:System;assembly=netstandard"
x:Class="ControlCatalog.Pages.AutoCompleteBoxPage">
<StackPanel Orientation="Vertical" Spacing="4">
<TextBlock Classes="h1">AutoCompleteBox</TextBlock>
@ -56,6 +57,16 @@
Width="200"
Margin="0,0,0,8"
FilterMode="None"/>
<TextBlock Text="With Validation Errors"/>
<AutoCompleteBox Name="ValidationErrors"
Width="200"
Margin="0,0,0,8"
FilterMode="None">
<DataValidationErrors.Error>
<sys:Exception />
</DataValidationErrors.Error>
</AutoCompleteBox>
</StackPanel>
</StackPanel>
</StackPanel>

11
samples/ControlCatalog/Pages/ButtonSpinnerPage.xaml

@ -1,6 +1,7 @@
<UserControl xmlns="https://github.com/avaloniaui"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
x:Class="ControlCatalog.Pages.ButtonSpinnerPage">
x:Class="ControlCatalog.Pages.ButtonSpinnerPage"
xmlns:sys="clr-namespace:System;assembly=netstandard">
<StackPanel Orientation="Vertical" Spacing="4">
<TextBlock Classes="h1">ButtonSpinner</TextBlock>
@ -19,6 +20,14 @@
ShowButtonSpinner="{Binding #showSpinCheck.IsChecked}">
<TextBlock HorizontalAlignment="Center" VerticalAlignment="Center" Text="Everest"/>
</ButtonSpinner>
<ButtonSpinner MinHeight="30" Spin="OnSpin" ButtonSpinnerLocation="Left"
AllowSpin="{Binding #allowSpinCheck.IsChecked}"
ShowButtonSpinner="{Binding #showSpinCheck.IsChecked}">
<DataValidationErrors.Error>
<sys:Exception />
</DataValidationErrors.Error>
<TextBlock HorizontalAlignment="Center" VerticalAlignment="Center" Text="Everest"/>
</ButtonSpinner>
</StackPanel>
</StackPanel>

13
samples/ControlCatalog/Pages/ComboBoxPage.xaml

@ -1,6 +1,7 @@
<UserControl xmlns="https://github.com/avaloniaui"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
x:Class="ControlCatalog.Pages.ComboBoxPage">
x:Class="ControlCatalog.Pages.ComboBoxPage"
xmlns:sys="clr-namespace:System;assembly=netstandard">
<StackPanel Orientation="Vertical" Spacing="4">
<TextBlock Classes="h1">ComboBox</TextBlock>
<TextBlock Classes="h2">A drop-down list.</TextBlock>
@ -35,6 +36,16 @@
</DataTemplate>
</ComboBox.ItemTemplate>
</ComboBox>
<ComboBox PlaceholderText="Pick an Item">
<ComboBoxItem>Inline Items</ComboBoxItem>
<ComboBoxItem>Inline Item 2</ComboBoxItem>
<ComboBoxItem>Inline Item 3</ComboBoxItem>
<ComboBoxItem>Inline Item 4</ComboBoxItem>
<DataValidationErrors.Error>
<sys:Exception />
</DataValidationErrors.Error>
</ComboBox>
</StackPanel>
</StackPanel>

20
samples/ControlCatalog/Pages/DateTimePickerPage.xaml

@ -2,6 +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"
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450"
x:Class="ControlCatalog.Pages.DateTimePickerPage">
<StackPanel Orientation="Vertical" Spacing="4" HorizontalAlignment="Stretch">
@ -30,6 +31,16 @@
</Panel>
</StackPanel>
<Border BorderBrush="{DynamicResource SystemControlHighlightBaseLowBrush}"
BorderThickness="1" Padding="15">
<DatePicker Header="Pick a date">
<DataValidationErrors.Error>
<sys:Exception />
</DataValidationErrors.Error>
</DatePicker>
</Border>
<TextBlock FontSize="18">A DatePicker with day formatted and year hidden.</TextBlock>
<StackPanel Orientation="Vertical">
<Border BorderBrush="{DynamicResource SystemControlHighlightBaseLowBrush}"
@ -66,6 +77,15 @@
</TextBlock>
</Panel>
</StackPanel>
<Border BorderBrush="{DynamicResource SystemControlHighlightBaseLowBrush}"
BorderThickness="1" Padding="15">
<TimePicker Header="Pick a time">
<DataValidationErrors.Error>
<sys:Exception />
</DataValidationErrors.Error>
</TimePicker>
</Border>
<TextBlock FontSize="18">A TimePicker with a header and minute increments specified.</TextBlock>
<StackPanel Orientation="Vertical">

42
samples/ControlCatalog/Pages/LabelsPage.axaml

@ -0,0 +1,42 @@
<UserControl 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"
mc:Ignorable="d" d:DesignWidth="400" d:DesignHeight="250"
x:Class="ControlCatalog.Pages.LabelsPage"
x:Name="_labelsPage">
<UserControl.Styles>
<Style Selector="Label">
<Setter Property="VerticalAlignment" Value="Center"/>
<Setter Property="Margin" Value="6,3,0,3"/>
</Style>
<Style Selector="TextBox">
<Setter Property="VerticalAlignment" Value="Center"/>
<Setter Property="Margin" Value="0,3,6,3"/>
</Style>
<Style Selector="CheckBox">
<Setter Property="VerticalAlignment" Value="Center"/>
<Setter Property="Margin" Value="0,3,6,3"/>
</Style>
<Style Selector="Button[IsDefault=true]">
<Setter Property="Background" Value="{DynamicResource HighlightBrush}"/>
</Style>
</UserControl.Styles>
<ScrollViewer VerticalScrollBarVisibility="Auto"
HorizontalScrollBarVisibility="Hidden">
<Grid HorizontalAlignment="Left" VerticalAlignment="Top" RowDefinitions="Auto,Auto,Auto,Auto,Auto,*" ColumnDefinitions="Auto,6,*" Width="246">
<Label Target="firstNameEdit" Grid.Row="0" Grid.Column="0">_First name</Label>
<TextBox Name="firstNameEdit" Grid.Column="2" Grid.Row="0" Text="{Binding FirstName}"></TextBox>
<Label Target="lastNameEdit" Grid.Row="1" Grid.Column="0">_Last name</Label>
<TextBox Name="lastNameEdit" Grid.Column="2" Grid.Row="1" Text="{Binding LastName}"></TextBox>
<Label Target="bannedCheck" Grid.Row="2" Grid.Column="0">_Banned</Label>
<CheckBox Name="bannedCheck" Grid.Column="2" Grid.Row="2" IsChecked="{Binding IsBanned}"></CheckBox>
<GridSplitter Grid.Column="1" VerticalAlignment="Stretch" HorizontalAlignment="Stretch" Grid.RowSpan="3" >
</GridSplitter>
<StackPanel Grid.Column="0" Grid.Row="4" Grid.ColumnSpan="3" Orientation="Horizontal" HorizontalAlignment="Right">
<Button IsCancel="True" Command="{Binding #_labelsPage.DoCancel}">Cancel</Button>
<Button IsDefault="True" Command="{Binding #_labelsPage.DoSave}">Save</Button>
</StackPanel>
</Grid>
</ScrollViewer>
</UserControl>

43
samples/ControlCatalog/Pages/LabelsPage.axaml.cs

@ -0,0 +1,43 @@
using Avalonia;
using Avalonia.Controls;
using Avalonia.Markup.Xaml;
using ControlCatalog.Models;
using ReactiveUI;
namespace ControlCatalog.Pages
{
public class LabelsPage : UserControl
{
private Person _person;
public LabelsPage()
{
CreateDefaultPerson();
this.InitializeComponent();
}
private void CreateDefaultPerson()
{
DataContext = _person = new Person
{
FirstName = "John",
LastName = "Doe",
IsBanned = true,
};
}
private void InitializeComponent()
{
AvaloniaXamlLoader.Load(this);
}
public void DoSave()
{
}
public void DoCancel()
{
CreateDefaultPerson();
}
}
}

10
samples/ControlCatalog/Pages/NumericUpDownPage.xaml

@ -1,5 +1,6 @@
<UserControl xmlns="https://github.com/avaloniaui"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:sys="clr-namespace:System;assembly=netstandard"
x:Class="ControlCatalog.Pages.NumericUpDownPage">
<StackPanel Orientation="Vertical" Spacing="4">
<TextBlock Margin="2" Classes="h1">Numeric up-down control</TextBlock>
@ -75,6 +76,15 @@
<NumericUpDown Name="upDown" Minimum="0" Maximum="10" Increment="0.5"
CultureInfo="en-US" VerticalAlignment="Center"
Watermark="Enter text" FormatString="{Binding SelectedFormat.Value}"/>
<TextBlock FontSize="14" FontWeight="Bold" VerticalAlignment="Center">NumericUpDown with Validation Errors:</TextBlock>
<NumericUpDown Minimum="0" Maximum="10" Increment="0.5"
CultureInfo="en-US" VerticalAlignment="Center"
Watermark="Enter text" FormatString="{Binding SelectedFormat.Value}">
<DataValidationErrors.Error>
<sys:Exception />
</DataValidationErrors.Error>
</NumericUpDown>
</StackPanel>
</StackPanel>

16
samples/ControlCatalog/Pages/RelativePanelPage.axaml

@ -23,16 +23,16 @@
<Border Name="Rect6" Background="Green" Height="50" Width="50" RelativePanel.AlignBottomWithPanel="True" RelativePanel.AlignRightWithPanel="True">
<TextBlock Text="Rect6" Foreground="White" FontWeight="Bold" HorizontalAlignment="Center" VerticalAlignment="Center"/>
</Border>
<Border Name="Rect7" Background="Blue" Height="50" RelativePanel.RightOf="{Binding ElementName=Rect1}">
<Border Name="Rect7" Background="Blue" Height="50" RelativePanel.RightOf="Rect1">
<TextBlock Text="Rect7 (RightOf Rect1)" Padding="10,0" Foreground="White" FontWeight="Bold" HorizontalAlignment="Center" VerticalAlignment="Center"/>
</Border>
<Border Name="Rect8" Background="Green" Height="50" RelativePanel.Below="{Binding ElementName=Rect7}">
<Border Name="Rect8" Background="Green" Height="50" RelativePanel.Below="Rect7">
<TextBlock Text="Rect8 (Below Rect7)" Padding="10,0" Foreground="White" FontWeight="Bold" HorizontalAlignment="Center" VerticalAlignment="Center"/>
</Border>
<Border Name="Rect9" Background="Blue" Height="140" Width="460" RelativePanel.AlignHorizontalCenterWithPanel="True" RelativePanel.AlignVerticalCenterWithPanel="True">
<TextBlock Text="Rect9" Padding="10" Foreground="White" FontWeight="Bold" HorizontalAlignment="Center" VerticalAlignment="Top"/>
</Border>
<Border Name="Rect10" Background="Red" Width="50" RelativePanel.RightOf="{Binding ElementName=Rect9}" RelativePanel.AlignVerticalCenterWith="{Binding ElementName=Rect9}">
<Border Name="Rect10" Background="Red" Width="50" RelativePanel.RightOf="Rect9" RelativePanel.AlignVerticalCenterWith="Rect9">
<TextBlock Text="Rect14 (RightOf Rect9, AlignVerticalCenterWith Rect9)" Padding="10,0" Foreground="White" FontWeight="Bold" HorizontalAlignment="Center" VerticalAlignment="Center">
<TextBlock.RenderTransform>
<TransformGroup>
@ -41,19 +41,19 @@
</TextBlock.RenderTransform>
</TextBlock>
</Border>
<Border Name="Rect11" Background="Red" Height="50" RelativePanel.AlignBottomWith="{Binding ElementName=Rect9}" RelativePanel.AlignHorizontalCenterWith="{Binding ElementName=Rect9}">
<Border Name="Rect11" Background="Red" Height="50" RelativePanel.AlignBottomWith="Rect9" RelativePanel.AlignHorizontalCenterWith="Rect9">
<TextBlock Text="Rect11 (AlignBottomWith Rect9, AlignHorizontalCenterWith Rect9)" Padding="10,0" Foreground="White" FontWeight="Bold" HorizontalAlignment="Center" VerticalAlignment="Center"/>
</Border>
<Border Name="Rect12" Background="Red" Height="50" RelativePanel.Below="{Binding ElementName=Rect8}" RelativePanel.AlignLeftWith="{Binding ElementName=Rect7}">
<Border Name="Rect12" Background="Red" Height="50" RelativePanel.Below="Rect8" RelativePanel.AlignLeftWith="Rect7">
<TextBlock Text="Rect12 (Below Rect8, AlignLeftWith Rect7)" Padding="10,0" Foreground="White" FontWeight="Bold" HorizontalAlignment="Center" VerticalAlignment="Center"/>
</Border>
<Border Name="Rect13" Background="Blue" Height="50" RelativePanel.Below="{Binding ElementName=Rect12}" RelativePanel.AlignRightWith="{Binding ElementName=Rect12}">
<Border Name="Rect13" Background="Blue" Height="50" RelativePanel.Below="Rect12" RelativePanel.AlignRightWith="Rect12">
<TextBlock Text="Rect13 (Below Rect12, AlignRightWith Rect12)" Padding="10,0" Foreground="White" FontWeight="Bold" HorizontalAlignment="Center" VerticalAlignment="Center"/>
</Border>
<Border Name="Rect14" Background="Green" Height="50" RelativePanel.Above="{Binding ElementName=Rect9}" RelativePanel.AlignRightWith="{Binding ElementName=Rect9}">
<Border Name="Rect14" Background="Green" Height="50" RelativePanel.Above="Rect9" RelativePanel.AlignRightWith="Rect9">
<TextBlock Text="Rect14 (Above Rect9, AlignRightWith Rect9)" Padding="10,0" Foreground="White" FontWeight="Bold" HorizontalAlignment="Center" VerticalAlignment="Center"/>
</Border>
<Border Name="Rect15" Background="Red" Height="50" RelativePanel.LeftOf="{Binding ElementName=Rect2}" RelativePanel.AlignTopWith="{Binding ElementName=Rect9}">
<Border Name="Rect15" Background="Red" Height="50" RelativePanel.LeftOf="Rect2" RelativePanel.AlignTopWith="Rect9">
<TextBlock Text="Rect15 (LeftOf Rect2, AlignTopWith Rect9)" Padding="10,0" Foreground="White" FontWeight="Bold" HorizontalAlignment="Center" VerticalAlignment="Center"/>
</Border>
</RelativePanel>

10
samples/ControlCatalog/Pages/SliderPage.xaml

@ -1,5 +1,6 @@
<UserControl xmlns="https://github.com/avaloniaui"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:sys="clr-namespace:System;assembly=netstandard"
x:Class="ControlCatalog.Pages.SliderPage">
<StackPanel Orientation="Vertical" Spacing="4">
<TextBlock Classes="h1">Slider</TextBlock>
@ -21,6 +22,15 @@
IsSnapToTickEnabled="True"
Ticks="0,20,25,40,75,100"
Width="300" />
<Slider Value="0"
Minimum="0"
Maximum="100"
TickFrequency="10"
Width="300">
<DataValidationErrors.Error>
<sys:Exception />
</DataValidationErrors.Error>
</Slider>
</StackPanel>
<Slider Value="0"
Minimum="0"

47
samples/ControlCatalog/Pages/TextBoxPage.xaml

@ -1,9 +1,10 @@
<UserControl xmlns="https://github.com/avaloniaui"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
x:Class="ControlCatalog.Pages.TextBoxPage">
x:Class="ControlCatalog.Pages.TextBoxPage"
xmlns:sys="clr-namespace:System;assembly=netstandard">
<StackPanel Orientation="Vertical" Spacing="4">
<TextBlock Classes="h1">TextBox</TextBlock>
<TextBlock Classes="h2">A control into which the user can input text</TextBlock>
<Label Classes="h1">TextBox</Label>
<Label Classes="h2">A control into which the user can input text</Label>
<StackPanel Orientation="Horizontal"
Margin="0,16,0,0"
@ -11,12 +12,18 @@
Spacing="16">
<StackPanel Orientation="Vertical" Spacing="8">
<TextBox Text="Lorem ipsum dolor sit amet, consectetur adipiscing elit." Width="200" />
<TextBox Watermark="ReadOnly" IsReadOnly="True" Text="This is read only"/>
<TextBox Width="200" Watermark="ReadOnly" IsReadOnly="True" Text="This is read only"/>
<TextBox Width="200" Watermark="Watermark" />
<TextBox Width="200"
Watermark="Floating Watermark"
UseFloatingWatermark="True"
Text="Lorem ipsum dolor sit amet, consectetur adipiscing elit."/>
<TextBox Width="200" Text="Validation Error">
<DataValidationErrors.Error>
<sys:Exception />
</DataValidationErrors.Error>
</TextBox>
<TextBox Width="200"
Watermark="Password Box"
@ -38,24 +45,24 @@
Text="Multiline TextBox with TextWrapping.&#xD;&#xD;Lorem ipsum dolor sit amet, consectetur adipiscing elit. Vivamus magna. Cras in mi at felis aliquet congue. Ut a est eget ligula molestie gravida. Curabitur massa. Donec eleifend, libero at sagittis mollis, tellus est malesuada tellus, at luctus turpis elit sit amet quam. Vivamus pretium ornare est." />
<TextBox AcceptsReturn="True" Width="200" Height="125"
Text="Multiline TextBox with no TextWrapping.&#xD;&#xD;Lorem ipsum dolor sit amet, consectetur adipiscing elit. Vivamus magna. Cras in mi at felis aliquet congue. Ut a est eget ligula molestie gravida. Curabitur massa. Donec eleifend, libero at sagittis mollis, tellus est malesuada tellus, at luctus turpis elit sit amet quam. Vivamus pretium ornare est." />
<TextBox Classes="clearButton" Text="Clear Content" Width="200" FontWeight="Normal" FontStyle="Normal" Watermark="Watermark" FontFamily="avares://ControlCatalog/Assets/Fonts#Source Sans Pro"/>
</StackPanel>
<StackPanel Orientation="Vertical" Spacing="8">
<TextBlock Classes="h2">resm fonts</TextBlock>
<TextBox Width="200" Text="Custom font regular" FontWeight="Normal" FontStyle="Normal" FontFamily="resm:ControlCatalog.Assets.Fonts?assembly=ControlCatalog#Source Sans Pro"/>
<TextBox Width="200" Text="Custom font bold" FontWeight="Bold" FontStyle="Normal" FontFamily="resm:ControlCatalog.Assets.Fonts?assembly=ControlCatalog#Source Sans Pro"/>
<TextBox Width="200" Text="Custom font italic" FontWeight="Normal" FontStyle="Italic" FontFamily="resm:ControlCatalog.Assets.Fonts.SourceSansPro-Italic.ttf?assembly=ControlCatalog#Source Sans Pro"/>
<TextBox Width="200" Text="Custom font italic bold" FontWeight="Bold" FontStyle="Italic" FontFamily="resm:ControlCatalog.Assets.Fonts.SourceSansPro-*.ttf?assembly=ControlCatalog#Source Sans Pro"/>
</StackPanel>
<StackPanel Orientation="Vertical" Spacing="8">
<TextBlock Classes="h2">res fonts</TextBlock>
<TextBox Width="200" Text="Custom font regular" FontWeight="Normal" FontStyle="Normal" FontFamily="avares://ControlCatalog/Assets/Fonts#Source Sans Pro"/>
<TextBox Width="200" Text="Custom font bold" FontWeight="Bold" FontStyle="Normal" FontFamily="avares://ControlCatalog/Assets/Fonts#Source Sans Pro"/>
<TextBox Width="200" Text="Custom font italic" FontWeight="Normal" FontStyle="Italic" FontFamily="/Assets/Fonts/SourceSansPro-Italic.ttf#Source Sans Pro"/>
<TextBox Width="200" Text="Custom font italic bold" FontWeight="Bold" FontStyle="Italic" FontFamily="/Assets/Fonts/SourceSansPro-*.ttf#Source Sans Pro"/>
</StackPanel>
<StackPanel Orientation="Vertical" Spacing="8">
<Label Classes="h2" Target="{Binding #firstResMFont}">res_m fonts</Label>
<TextBox Width="200" x:Name="firstResMFont" Text="Custom font regular" FontWeight="Normal" FontStyle="Normal" FontFamily="resm:ControlCatalog.Assets.Fonts?assembly=ControlCatalog#Source Sans Pro"/>
<TextBox Width="200" Text="Custom font bold" FontWeight="Bold" FontStyle="Normal" FontFamily="resm:ControlCatalog.Assets.Fonts?assembly=ControlCatalog#Source Sans Pro"/>
<TextBox Width="200" Text="Custom font italic" FontWeight="Normal" FontStyle="Italic" FontFamily="resm:ControlCatalog.Assets.Fonts.SourceSansPro-Italic.ttf?assembly=ControlCatalog#Source Sans Pro"/>
<TextBox Width="200" Text="Custom font italic bold" FontWeight="Bold" FontStyle="Italic" FontFamily="resm:ControlCatalog.Assets.Fonts.SourceSansPro-*.ttf?assembly=ControlCatalog#Source Sans Pro"/>
</StackPanel>
<StackPanel Orientation="Vertical" Spacing="8">
<Label Classes="h2" Target="{Binding #firstResFont}">_res fonts</Label>
<TextBox Width="200" x:Name="firstResFont" Text="Custom font regular" FontWeight="Normal" FontStyle="Normal" FontFamily="avares://ControlCatalog/Assets/Fonts#Source Sans Pro"/>
<TextBox Width="200" Text="Custom font bold" FontWeight="Bold" FontStyle="Normal" FontFamily="avares://ControlCatalog/Assets/Fonts#Source Sans Pro"/>
<TextBox Width="200" Text="Custom font italic" FontWeight="Normal" FontStyle="Italic" FontFamily="/Assets/Fonts/SourceSansPro-Italic.ttf#Source Sans Pro"/>
<TextBox Width="200" Text="Custom font italic bold" FontWeight="Bold" FontStyle="Italic" FontFamily="/Assets/Fonts/SourceSansPro-*.ttf#Source Sans Pro"/>
</StackPanel>
</StackPanel>
</StackPanel>
</UserControl>

10
samples/Previewer/App.xaml.cs

@ -1,4 +1,5 @@
using Avalonia;
using Avalonia.Controls.ApplicationLifetimes;
using Avalonia.Markup.Xaml;
namespace Previewer
@ -9,6 +10,13 @@ namespace Previewer
{
AvaloniaXamlLoader.Load(this);
}
public override void OnFrameworkInitializationCompleted()
{
if (ApplicationLifetime is IClassicDesktopStyleApplicationLifetime desktop)
desktop.MainWindow = new MainWindow();
base.OnFrameworkInitializationCompleted();
}
}
}
}

15
samples/Previewer/Program.cs

@ -1,13 +1,14 @@
using System;
using Avalonia;
using Avalonia;
namespace Previewer
{
class Program
{
static void Main(string[] args)
{
AppBuilder.Configure<App>().UsePlatformDetect().Start<MainWindow>();
}
public static AppBuilder BuildAvaloniaApp()
=> AppBuilder.Configure<App>()
.UsePlatformDetect();
public static int Main(string[] args)
=> BuildAvaloniaApp().StartWithClassicDesktopLifetime(args);
}
}
}

13
samples/RenderDemo/App.xaml.cs

@ -1,4 +1,5 @@
using Avalonia;
using Avalonia.Controls.ApplicationLifetimes;
using Avalonia.Markup.Xaml;
using Avalonia.ReactiveUI;
@ -11,9 +12,17 @@ namespace RenderDemo
AvaloniaXamlLoader.Load(this);
}
public override void OnFrameworkInitializationCompleted()
{
if (ApplicationLifetime is IClassicDesktopStyleApplicationLifetime desktop)
desktop.MainWindow = new MainWindow();
base.OnFrameworkInitializationCompleted();
}
// TODO: Make this work with GTK/Skia/Cairo depending on command-line args
// again.
static void Main(string[] args) => BuildAvaloniaApp().Start<MainWindow>();
static void Main(string[] args)
=> BuildAvaloniaApp().StartWithClassicDesktopLifetime(args);
// App configuration, used by the entry point and previewer
static AppBuilder BuildAvaloniaApp()
@ -24,6 +33,6 @@ namespace RenderDemo
})
.UsePlatformDetect()
.UseReactiveUI()
.LogToDebug();
.LogToTrace();
}
}

6
samples/RenderDemo/Pages/GlyphRunPage.xaml

@ -6,9 +6,9 @@
x:Class="RenderDemo.Pages.GlyphRunPage">
<Border
Background="White">
<DrawingPresenter
x:Name="drawingPresenter"
<Image
x:Name="imageControl"
Stretch="None">
</DrawingPresenter>
</Image>
</Border>
</UserControl>

7
samples/RenderDemo/Pages/GlyphRunPage.xaml.cs

@ -9,7 +9,7 @@ namespace RenderDemo.Pages
{
public class GlyphRunPage : UserControl
{
private DrawingPresenter _drawingPresenter;
private Image _imageControl;
private GlyphTypeface _glyphTypeface = Typeface.Default.GlyphTypeface;
private readonly Random _rand = new Random();
private ushort[] _glyphIndices = new ushort[1];
@ -25,7 +25,8 @@ namespace RenderDemo.Pages
{
AvaloniaXamlLoader.Load(this);
_drawingPresenter = this.FindControl<DrawingPresenter>("drawingPresenter");
_imageControl = this.FindControl<Image>("imageControl");
_imageControl.Source = new DrawingImage();
DispatcherTimer.Run(() =>
{
@ -73,7 +74,7 @@ namespace RenderDemo.Pages
drawingGroup.Children.Add(geometryDrawing);
_drawingPresenter.Drawing = drawingGroup;
(_imageControl.Source as DrawingImage).Drawing = drawingGroup;
}
}
}

2
samples/Sandbox/Program.cs

@ -10,7 +10,7 @@ namespace Sandbox
AppBuilder.Configure<App>()
.UsePlatformDetect()
.UseReactiveUI()
.LogToDebug()
.LogToTrace()
.StartWithClassicDesktopLifetime(args);
}
}

8
samples/VirtualizationDemo/App.xaml.cs

@ -1,4 +1,5 @@
using Avalonia;
using Avalonia.Controls.ApplicationLifetimes;
using Avalonia.Markup.Xaml;
namespace VirtualizationDemo
@ -9,5 +10,12 @@ namespace VirtualizationDemo
{
AvaloniaXamlLoader.Load(this);
}
public override void OnFrameworkInitializationCompleted()
{
if (ApplicationLifetime is IClassicDesktopStyleApplicationLifetime desktop)
desktop.MainWindow = new MainWindow();
base.OnFrameworkInitializationCompleted();
}
}
}

20
samples/VirtualizationDemo/Program.cs

@ -1,19 +1,17 @@
using System;
using Avalonia;
using Avalonia.Controls;
using Avalonia;
using Avalonia.ReactiveUI;
namespace VirtualizationDemo
{
class Program
{
static void Main(string[] args)
{
AppBuilder.Configure<App>()
.UsePlatformDetect()
.UseReactiveUI()
.LogToDebug()
.Start<MainWindow>();
}
public static AppBuilder BuildAvaloniaApp()
=> AppBuilder.Configure<App>()
.UsePlatformDetect()
.UseReactiveUI()
.LogToTrace();
public static int Main(string[] args)
=> BuildAvaloniaApp().StartWithClassicDesktopLifetime(args);
}
}

8
samples/interop/Direct3DInteropSample/App.paml.cs

@ -1,4 +1,5 @@
using Avalonia;
using Avalonia.Controls.ApplicationLifetimes;
using Avalonia.Markup.Xaml;
namespace Direct3DInteropSample
@ -9,5 +10,12 @@ namespace Direct3DInteropSample
{
AvaloniaXamlLoader.Load(this);
}
public override void OnFrameworkInitializationCompleted()
{
if (ApplicationLifetime is IClassicDesktopStyleApplicationLifetime desktop)
desktop.MainWindow = new MainWindow();
base.OnFrameworkInitializationCompleted();
}
}
}

21
samples/interop/Direct3DInteropSample/Program.cs

@ -1,19 +1,16 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Avalonia;
using Avalonia;
namespace Direct3DInteropSample
{
class Program
{
static void Main(string[] args)
{
AppBuilder.Configure<App>()
.With(new Win32PlatformOptions {UseDeferredRendering = false})
.UseWin32().UseDirect2D1().Start<MainWindow>();
}
public static AppBuilder BuildAvaloniaApp()
=> AppBuilder.Configure<App>()
.With(new Win32PlatformOptions { UseDeferredRendering = false })
.UseWin32()
.UseDirect2D1();
public static int Main(string[] args)
=> BuildAvaloniaApp().StartWithClassicDesktopLifetime(args);
}
}

3
samples/interop/NativeEmbedSample/NativeEmbedSample.csproj

@ -9,11 +9,10 @@
<ItemGroup>
<PackageReference Include="MonoMac.NetStandard" Version="0.0.4" />
<ProjectReference Include="..\..\..\src\Avalonia.Desktop\Avalonia.Desktop.csproj" />
<ProjectReference Include="..\..\..\src\Windows\Avalonia.Direct2D1\Avalonia.Direct2D1.csproj" />
<ProjectReference Include="..\..\..\src\Avalonia.Diagnostics\Avalonia.Diagnostics.csproj" />
<ProjectReference Include="..\..\..\src\Avalonia.X11\Avalonia.X11.csproj" />
<PackageReference Include="Avalonia.Angle.Windows.Natives" Version="2.1.0.2019013001" />
<PackageReference Include="Avalonia.Angle.Windows.Natives" Version="2.1.0.2020091801" />
<AvaloniaResource Include="**\*.xaml">
<SubType>Designer</SubType>

5
src/Avalonia.Animation/Properties/AssemblyInfo.cs

@ -6,5 +6,10 @@ using System.Runtime.CompilerServices;
[assembly: XmlnsDefinition("https://github.com/avaloniaui", "Avalonia.Animation.Easings")]
[assembly: XmlnsDefinition("https://github.com/avaloniaui", "Avalonia.Animation.Animators")]
#if SIGNED_BUILD
[assembly: InternalsVisibleTo("Avalonia.LeakTests, PublicKey=0024000004800000940000000602000000240000525341310004000001000100c1bba1142285fe0419326fb25866ba62c47e6c2b5c1ab0c95b46413fad375471232cb81706932e1cef38781b9ebd39d5100401bacb651c6c5bbf59e571e81b3bc08d2a622004e08b1a6ece82a7e0b9857525c86d2b95fab4bc3dce148558d7f3ae61aa3a234086902aeface87d9dfdd32b9d2fe3c6dd4055b5ab4b104998bd87")]
[assembly: InternalsVisibleTo("Avalonia.Animation.UnitTests, PublicKey=0024000004800000940000000602000000240000525341310004000001000100c1bba1142285fe0419326fb25866ba62c47e6c2b5c1ab0c95b46413fad375471232cb81706932e1cef38781b9ebd39d5100401bacb651c6c5bbf59e571e81b3bc08d2a622004e08b1a6ece82a7e0b9857525c86d2b95fab4bc3dce148558d7f3ae61aa3a234086902aeface87d9dfdd32b9d2fe3c6dd4055b5ab4b104998bd87")]
#else
[assembly: InternalsVisibleTo("Avalonia.LeakTests")]
[assembly: InternalsVisibleTo("Avalonia.Animation.UnitTests")]
#endif

3
src/Avalonia.Base/ApiCompatBaseline.txt

@ -1,3 +1,4 @@
Compat issues with assembly Avalonia.Base:
CannotAddAbstractMembers : Member 'protected System.IObservable<Avalonia.AvaloniaPropertyChangedEventArgs> Avalonia.AvaloniaProperty.GetChanged()' is abstract in the implementation but is missing in the contract.
Total Issues: 1
TypesMustExist : Type 'Avalonia.Logging.DebugLogSink' does not exist in the implementation but it does exist in the contract.
Total Issues: 2

14
src/Avalonia.Base/Logging/DebugLogSink.cs → src/Avalonia.Base/Logging/TraceLogSink.cs

@ -6,12 +6,12 @@ using Avalonia.Utilities;
namespace Avalonia.Logging
{
public class DebugLogSink : ILogSink
public class TraceLogSink : ILogSink
{
private readonly LogEventLevel _level;
private readonly IList<string> _areas;
public DebugLogSink(
public TraceLogSink(
LogEventLevel minimumLevel,
IList<string> areas = null)
{
@ -28,7 +28,7 @@ namespace Avalonia.Logging
{
if (IsEnabled(level, area))
{
Debug.WriteLine(Format<object, object, object>(area, messageTemplate, source));
Trace.WriteLine(Format<object, object, object>(area, messageTemplate, source));
}
}
@ -36,7 +36,7 @@ namespace Avalonia.Logging
{
if (IsEnabled(level, area))
{
Debug.WriteLine(Format<T0, object, object>(area, messageTemplate, source, propertyValue0));
Trace.WriteLine(Format<T0, object, object>(area, messageTemplate, source, propertyValue0));
}
}
@ -44,7 +44,7 @@ namespace Avalonia.Logging
{
if (IsEnabled(level, area))
{
Debug.WriteLine(Format<T0, T1, object>(area, messageTemplate, source, propertyValue0, propertyValue1));
Trace.WriteLine(Format<T0, T1, object>(area, messageTemplate, source, propertyValue0, propertyValue1));
}
}
@ -52,7 +52,7 @@ namespace Avalonia.Logging
{
if (IsEnabled(level, area))
{
Debug.WriteLine(Format(area, messageTemplate, source, propertyValue0, propertyValue1, propertyValue2));
Trace.WriteLine(Format(area, messageTemplate, source, propertyValue0, propertyValue1, propertyValue2));
}
}
@ -60,7 +60,7 @@ namespace Avalonia.Logging
{
if (IsEnabled(level, area))
{
Debug.WriteLine(Format(area, messageTemplate, source, propertyValues));
Trace.WriteLine(Format(area, messageTemplate, source, propertyValues));
}
}

39
src/Avalonia.Base/Metadata/XmlnsPrefixAttribute.cs

@ -0,0 +1,39 @@
using System;
namespace Avalonia.Metadata
{
/// <summary>
/// Use to predefine the prefix associated to an xml namespace in a xaml file
/// </summary>
/// <remarks>
/// example:
/// [assembly: XmlnsPrefix("https://github.com/avaloniaui", "av")]
/// xaml:
/// xmlns:av="https://github.com/avaloniaui"
/// </remarks>
[AttributeUsage(AttributeTargets.Assembly, AllowMultiple = true)]
public sealed class XmlnsPrefixAttribute : Attribute
{
/// <summary>
/// Constructor
/// </summary>
/// <param name="xmlNamespace">XML namespce</param>
/// <param name="prefix">recommended prefix</param>
public XmlnsPrefixAttribute(string xmlNamespace, string prefix)
{
XmlNamespace = xmlNamespace ?? throw new ArgumentNullException(nameof(xmlNamespace));
Prefix = prefix ?? throw new ArgumentNullException(nameof(prefix));
}
/// <summary>
/// XML Namespace
/// </summary>
public string XmlNamespace { get; }
/// <summary>
/// New Xml Namespace
/// </summary>
public string Prefix { get; }
}
}

8
src/Avalonia.Base/Properties/AssemblyInfo.cs

@ -5,8 +5,16 @@ using System.Runtime.CompilerServices;
using Avalonia.Metadata;
[assembly: XmlnsDefinition("https://github.com/avaloniaui", "Avalonia.Data.Converters")]
#if SIGNED_BUILD
[assembly: InternalsVisibleTo("Avalonia.Base.UnitTests, PublicKey=0024000004800000940000000602000000240000525341310004000001000100c1bba1142285fe0419326fb25866ba62c47e6c2b5c1ab0c95b46413fad375471232cb81706932e1cef38781b9ebd39d5100401bacb651c6c5bbf59e571e81b3bc08d2a622004e08b1a6ece82a7e0b9857525c86d2b95fab4bc3dce148558d7f3ae61aa3a234086902aeface87d9dfdd32b9d2fe3c6dd4055b5ab4b104998bd87")]
[assembly: InternalsVisibleTo("Avalonia.UnitTests, PublicKey=0024000004800000940000000602000000240000525341310004000001000100c1bba1142285fe0419326fb25866ba62c47e6c2b5c1ab0c95b46413fad375471232cb81706932e1cef38781b9ebd39d5100401bacb651c6c5bbf59e571e81b3bc08d2a622004e08b1a6ece82a7e0b9857525c86d2b95fab4bc3dce148558d7f3ae61aa3a234086902aeface87d9dfdd32b9d2fe3c6dd4055b5ab4b104998bd87")]
[assembly: InternalsVisibleTo("DynamicProxyGenAssembly2, PublicKey=0024000004800000940000000602000000240000525341310004000001000100c547cac37abd99c8db225ef2f6c8a3602f3b3606cc9891605d02baa56104f4cfc0734aa39b93bf7852f7d9266654753cc297e7d2edfe0bac1cdcf9f717241550e0a7b191195b7667bb4f64bcb8e2121380fd1d9d46ad2d92d2d15605093924cceaf74c4861eff62abf69b9291ed0a340e113be11e6a7d3113e92484cf7045cc7")]
[assembly: InternalsVisibleTo("Avalonia.Controls.DataGrid, PublicKey=0024000004800000940000000602000000240000525341310004000001000100c1bba1142285fe0419326fb25866ba62c47e6c2b5c1ab0c95b46413fad375471232cb81706932e1cef38781b9ebd39d5100401bacb651c6c5bbf59e571e81b3bc08d2a622004e08b1a6ece82a7e0b9857525c86d2b95fab4bc3dce148558d7f3ae61aa3a234086902aeface87d9dfdd32b9d2fe3c6dd4055b5ab4b104998bd87")]
[assembly: InternalsVisibleTo("Avalonia.Markup.Xaml.UnitTests, PublicKey=0024000004800000940000000602000000240000525341310004000001000100c1bba1142285fe0419326fb25866ba62c47e6c2b5c1ab0c95b46413fad375471232cb81706932e1cef38781b9ebd39d5100401bacb651c6c5bbf59e571e81b3bc08d2a622004e08b1a6ece82a7e0b9857525c86d2b95fab4bc3dce148558d7f3ae61aa3a234086902aeface87d9dfdd32b9d2fe3c6dd4055b5ab4b104998bd87")]
#else
[assembly: InternalsVisibleTo("Avalonia.Base.UnitTests")]
[assembly: InternalsVisibleTo("Avalonia.UnitTests")]
[assembly: InternalsVisibleTo("DynamicProxyGenAssembly2")]
[assembly: InternalsVisibleTo("Avalonia.Controls.DataGrid")]
[assembly: InternalsVisibleTo("Avalonia.Markup.Xaml.UnitTests")]
#endif

2
src/Avalonia.Build.Tasks/Avalonia.Build.Tasks.csproj

@ -59,7 +59,7 @@
</Compile>
<Compile Remove="../Markup/Avalonia.Markup.Xaml.Loader\xamlil.github\**\obj\**\*.cs" />
<Compile Remove="../Markup/Avalonia.Markup.Xaml.Loader\xamlil.github\src\XamlX\IL\SreTypeSystem.cs" />
<PackageReference Include="Avalonia.Unofficial.Cecil" Version="20190417.2.0" PrivateAssets="All" />
<PackageReference Include="Mono.Cecil" Version="0.11.2" />
<PackageReference Include="Microsoft.Build.Framework" Version="15.1.548" PrivateAssets="All" />
</ItemGroup>
</Project>

8
src/Avalonia.Build.Tasks/CompileAvaloniaXamlTask.cs

@ -39,7 +39,9 @@ namespace Avalonia.Build.Tasks
var res = XamlCompilerTaskExecutor.Compile(BuildEngine, input,
File.ReadAllLines(ReferencesFilePath).Where(l => !string.IsNullOrWhiteSpace(l)).ToArray(),
ProjectDirectory, OutputPath, VerifyIl, outputImportance);
ProjectDirectory, OutputPath, VerifyIl, outputImportance,
(SignAssembly && !DelaySign) ? AssemblyOriginatorKeyFile : null
);
if (!res.Success)
return false;
if (!res.WrittenFile)
@ -73,6 +75,10 @@ namespace Avalonia.Build.Tasks
public string OutputPath { get; set; }
public bool VerifyIl { get; set; }
public string AssemblyOriginatorKeyFile { get; set; }
public bool SignAssembly { get; set; }
public bool DelaySign { get; set; }
public string ReportImportance { get; set; }

26
src/Avalonia.Build.Tasks/XamlCompilerTaskExecutor.cs

@ -42,7 +42,7 @@ namespace Avalonia.Build.Tasks
}
public static CompileResult Compile(IBuildEngine engine, string input, string[] references, string projectDirectory,
string output, bool verifyIl, MessageImportance logImportance)
string output, bool verifyIl, MessageImportance logImportance, string strongNameKey)
{
var typeSystem = new CecilTypeSystem(references.Concat(new[] {input}), input);
var asm = typeSystem.TargetAssemblyDefinition;
@ -345,6 +345,20 @@ namespace Avalonia.Build.Tasks
}
res.Remove();
}
// Technically that's a hack, but it fixes corert incompatibility caused by deterministic builds
int dupeCounter = 1;
foreach (var grp in typeDef.NestedTypes.GroupBy(x => x.Name))
{
if (grp.Count() > 1)
{
foreach (var dupe in grp)
dupe.Name += "_dup" + dupeCounter++;
}
}
return true;
}
@ -361,10 +375,12 @@ namespace Avalonia.Build.Tasks
loaderDispatcherMethod.Body.Instructions.Add(Instruction.Create(OpCodes.Ldnull));
loaderDispatcherMethod.Body.Instructions.Add(Instruction.Create(OpCodes.Ret));
asm.Write(output, new WriterParameters
{
WriteSymbols = asm.MainModule.HasSymbols
});
var writerParameters = new WriterParameters { WriteSymbols = asm.MainModule.HasSymbols };
if (!string.IsNullOrWhiteSpace(strongNameKey))
writerParameters.StrongNameKeyBlob = File.ReadAllBytes(strongNameKey);
asm.Write(output, writerParameters);
return new CompileResult(true, true);
}

1
src/Avalonia.Controls.DataGrid/DataGridColumn.cs

@ -665,6 +665,7 @@ namespace Avalonia.Controls
/// <param name="dataItem">
/// The data item represented by the row that contains the intended cell.
/// </param>
/// <param name="binding">When the method returns, contains the applied binding.</param>
/// <returns>
/// A new editing element that is bound to the column's <see cref="P:Avalonia.Controls.DataGridBoundColumn.Binding" /> property value.
/// </returns>

13
src/Avalonia.Controls.DataGrid/DataGridColumnHeader.cs

@ -340,8 +340,6 @@ namespace Avalonia.Controls
if (OwningGrid != null && OwningGrid.ColumnHeaders != null)
{
args.Pointer.Capture(this);
_dragMode = DragMode.MouseDown;
_frozenColumnsWidth = OwningGrid.ColumnsInternal.GetVisibleFrozenEdgedColumnsWidth();
_lastMousePositionHeaders = this.Translate(OwningGrid.ColumnHeaders, mousePosition);
@ -413,8 +411,9 @@ namespace Avalonia.Controls
}
//TODO DragEvents
internal void OnMouseMove(ref bool handled, Point mousePosition, Point mousePositionHeaders)
internal void OnMouseMove(PointerEventArgs args, Point mousePosition, Point mousePositionHeaders)
{
var handled = args.Handled;
if (handled || OwningGrid == null || OwningGrid.ColumnHeaders == null)
{
return;
@ -438,7 +437,10 @@ namespace Avalonia.Controls
}
_lastMousePositionHeaders = mousePositionHeaders;
if (args.Pointer.Captured != this && _dragMode == DragMode.Drag)
args.Pointer.Capture(this);
SetDragCursor(mousePosition);
}
@ -506,8 +508,7 @@ namespace Avalonia.Controls
Point mousePosition = e.GetPosition(this);
Point mousePositionHeaders = e.GetPosition(OwningGrid.ColumnHeaders);
bool handled = false;
OnMouseMove(ref handled, mousePosition, mousePositionHeaders);
OnMouseMove(e, mousePosition, mousePositionHeaders);
}
/// <summary>

7
src/Avalonia.Controls.DataGrid/Properties/AssemblyInfo.cs

@ -1,10 +1,13 @@
using System.Reflection;
using System.Runtime.CompilerServices;
using Avalonia.Metadata;
#if SIGNED_BUILD
[assembly: InternalsVisibleTo("Avalonia.Controls.DataGrid.UnitTests, PublicKey=0024000004800000940000000602000000240000525341310004000001000100c1bba1142285fe0419326fb25866ba62c47e6c2b5c1ab0c95b46413fad375471232cb81706932e1cef38781b9ebd39d5100401bacb651c6c5bbf59e571e81b3bc08d2a622004e08b1a6ece82a7e0b9857525c86d2b95fab4bc3dce148558d7f3ae61aa3a234086902aeface87d9dfdd32b9d2fe3c6dd4055b5ab4b104998bd87")]
[assembly: InternalsVisibleTo("Avalonia.DesignerSupport, PublicKey=0024000004800000940000000602000000240000525341310004000001000100c1bba1142285fe0419326fb25866ba62c47e6c2b5c1ab0c95b46413fad375471232cb81706932e1cef38781b9ebd39d5100401bacb651c6c5bbf59e571e81b3bc08d2a622004e08b1a6ece82a7e0b9857525c86d2b95fab4bc3dce148558d7f3ae61aa3a234086902aeface87d9dfdd32b9d2fe3c6dd4055b5ab4b104998bd87")]
#else
[assembly: InternalsVisibleTo("Avalonia.Controls.DataGrid.UnitTests")]
[assembly: InternalsVisibleTo("Avalonia.DesignerSupport")]
#endif
[assembly: XmlnsDefinition("https://github.com/avaloniaui", "Avalonia.Controls")]
[assembly: XmlnsDefinition("https://github.com/avaloniaui", "Avalonia.Controls.Collections")]
[assembly: XmlnsDefinition("https://github.com/avaloniaui", "Avalonia.Controls.Primitives")]

8
src/Avalonia.Controls/ApiCompatBaseline.txt

@ -8,6 +8,12 @@ MembersMustExist : Member 'public void Avalonia.Controls.ListBox.Selection.set(A
TypesMustExist : Type 'Avalonia.Controls.SelectionModel' does not exist in the implementation but it does exist in the contract.
TypesMustExist : Type 'Avalonia.Controls.SelectionModelChildrenRequestedEventArgs' does not exist in the implementation but it does exist in the contract.
TypesMustExist : Type 'Avalonia.Controls.SelectionModelSelectionChangedEventArgs' does not exist in the implementation but it does exist in the contract.
MembersMustExist : Member 'public Avalonia.StyledProperty<Avalonia.Controls.IControl> Avalonia.StyledProperty<Avalonia.Controls.IControl> Avalonia.Controls.SplitView.ContentProperty' does not exist in the implementation but it does exist in the contract.
MembersMustExist : Member 'public Avalonia.StyledProperty<Avalonia.Controls.IControl> Avalonia.StyledProperty<Avalonia.Controls.IControl> Avalonia.Controls.SplitView.PaneProperty' does not exist in the implementation but it does exist in the contract.
MembersMustExist : Member 'public Avalonia.Controls.IControl Avalonia.Controls.SplitView.Content.get()' does not exist in the implementation but it does exist in the contract.
MembersMustExist : Member 'public void Avalonia.Controls.SplitView.Content.set(Avalonia.Controls.IControl)' does not exist in the implementation but it does exist in the contract.
MembersMustExist : Member 'public Avalonia.Controls.IControl Avalonia.Controls.SplitView.Pane.get()' does not exist in the implementation but it does exist in the contract.
MembersMustExist : Member 'public void Avalonia.Controls.SplitView.Pane.set(Avalonia.Controls.IControl)' does not exist in the implementation but it does exist in the contract.
MembersMustExist : Member 'public Avalonia.DirectProperty<Avalonia.Controls.TreeView, Avalonia.Controls.ISelectionModel> Avalonia.DirectProperty<Avalonia.Controls.TreeView, Avalonia.Controls.ISelectionModel> Avalonia.Controls.TreeView.SelectionProperty' does not exist in the implementation but it does exist in the contract.
MembersMustExist : Member 'public Avalonia.Interactivity.RoutedEvent<Avalonia.Controls.SelectionChangedEventArgs> Avalonia.Interactivity.RoutedEvent<Avalonia.Controls.SelectionChangedEventArgs> Avalonia.Controls.TreeView.SelectionChangedEvent' does not exist in the implementation but it does exist in the contract.
MembersMustExist : Member 'public Avalonia.Controls.ISelectionModel Avalonia.Controls.TreeView.Selection.get()' does not exist in the implementation but it does exist in the contract.
@ -17,4 +23,4 @@ InterfacesShouldHaveSameMembers : Interface member 'public System.String[] Avalo
MembersMustExist : Member 'public Avalonia.DirectProperty<Avalonia.Controls.Primitives.SelectingItemsControl, Avalonia.Controls.ISelectionModel> Avalonia.DirectProperty<Avalonia.Controls.Primitives.SelectingItemsControl, Avalonia.Controls.ISelectionModel> Avalonia.Controls.Primitives.SelectingItemsControl.SelectionProperty' does not exist in the implementation but it does exist in the contract.
MembersMustExist : Member 'protected Avalonia.Controls.ISelectionModel Avalonia.Controls.Primitives.SelectingItemsControl.Selection.get()' does not exist in the implementation but it does exist in the contract.
MembersMustExist : Member 'protected void Avalonia.Controls.Primitives.SelectingItemsControl.Selection.set(Avalonia.Controls.ISelectionModel)' does not exist in the implementation but it does exist in the contract.
Total Issues: 18
Total Issues: 24

13
src/Avalonia.Controls/ContextMenu.cs

@ -62,6 +62,12 @@ namespace Avalonia.Controls
public static readonly StyledProperty<Rect?> PlacementRectProperty =
AvaloniaProperty.Register<Popup, Rect?>(nameof(PlacementRect));
/// <summary>
/// Defines the <see cref="WindowManagerAddShadowHint"/> property.
/// </summary>
public static readonly StyledProperty<bool> WindowManagerAddShadowHintProperty =
Popup.WindowManagerAddShadowHintProperty.AddOwner<ContextMenu>();
/// <summary>
/// Defines the <see cref="PlacementTarget"/> property.
/// </summary>
@ -158,6 +164,12 @@ namespace Avalonia.Controls
set { SetValue(PlacementModeProperty, value); }
}
public bool WindowManagerAddShadowHint
{
get { return GetValue(WindowManagerAddShadowHintProperty); }
set { SetValue(WindowManagerAddShadowHintProperty, value); }
}
/// <summary>
/// Gets or sets the the anchor rectangle within the parent that the context menu will be placed
/// relative to when <see cref="PlacementMode"/> is <see cref="PlacementMode.AnchorAndGravity"/>.
@ -267,6 +279,7 @@ namespace Avalonia.Controls
PlacementTarget = PlacementTarget ?? control,
IsLightDismissEnabled = true,
OverlayDismissEventPassThrough = true,
WindowManagerAddShadowHint = WindowManagerAddShadowHint,
};
_popup.Opened += PopupOpened;

4
src/Avalonia.Controls/DateTimePickers/DateTimePickerPanel.cs

@ -486,9 +486,9 @@ namespace Avalonia.Controls.Primitives
switch (panelType)
{
case DateTimePickerPanelType.Year:
return new DateTime(value, FormatDate.Month, FormatDate.Day).ToString(ItemFormat);
return new DateTime(value, 1, 1).ToString(ItemFormat);
case DateTimePickerPanelType.Month:
return new DateTime(FormatDate.Year, value, FormatDate.Day).ToString(ItemFormat);
return new DateTime(FormatDate.Year, value, 1).ToString(ItemFormat);
case DateTimePickerPanelType.Day:
return new DateTime(FormatDate.Year, FormatDate.Month, value).ToString(ItemFormat);
case DateTimePickerPanelType.Hour:

2
src/Avalonia.Controls/ItemsControl.cs

@ -169,7 +169,7 @@ namespace Avalonia.Controls
/// </summary>
/// <param name="items">The collection.</param>
/// <param name="index">The index.</param>
/// <returns>The index of the item or -1 if the item was not found.</returns>
/// <returns>The item at the given index or null if the index is out of bounds.</returns>
protected static object ElementAt(IEnumerable items, int index)
{
if (index != -1 && index < items.Count())

75
src/Avalonia.Controls/Label.cs

@ -0,0 +1,75 @@
using System;
using System.Collections.Generic;
using System.Runtime.CompilerServices;
using System.Text;
using Avalonia.Controls.Primitives;
using Avalonia.Controls.Templates;
using Avalonia.Data;
using Avalonia.Input;
using Avalonia.Interactivity;
namespace Avalonia.Controls
{
/// <summary>
/// Label control. Focuses <see cref="Target"/> on pointer click or access key press (Alt + accessKey)
/// </summary>
public class Label : ContentControl
{
/// <summary>
/// Defines the <see cref="Target"/> Direct property
/// </summary>
public static readonly DirectProperty<Label, IInputElement> TargetProperty =
AvaloniaProperty.RegisterDirect<Label, IInputElement>(nameof(Target), lbl => lbl.Target, (lbl, inp) => lbl.Target = inp);
/// <summary>
/// Label focus target storage field
/// </summary>
private IInputElement _target;
/// <summary>
/// Label focus Target
/// </summary>
[ResolveByName]
public IInputElement Target
{
get => _target;
set => SetAndRaise(TargetProperty, ref _target, value);
}
static Label()
{
AccessKeyHandler.AccessKeyPressedEvent.AddClassHandler<Label>((lbl, args) => lbl.LabelActivated(args));
// IsTabStopProperty.OverrideDefaultValue<Label>(false)
FocusableProperty.OverrideDefaultValue<Label>(false);
}
/// <summary>
/// Initializes instance of <see cref="Label"/> control
/// </summary>
public Label()
{
}
/// <summary>
/// Method which focuses <see cref="Target"/> input element
/// </summary>
private void LabelActivated(RoutedEventArgs args)
{
Target?.Focus();
args.Handled = Target != null;
}
/// <summary>
/// Handler of <see cref="IInputElement.PointerPressed"/> event
/// </summary>
/// <param name="e">Event Arguments</param>
protected override void OnPointerPressed(PointerPressedEventArgs e)
{
if (e.GetCurrentPoint(this).Properties.PointerUpdateKind == PointerUpdateKind.LeftButtonPressed)
{
LabelActivated(e);
}
base.OnPointerPressed(e);
}
}
}

19
src/Avalonia.Controls/LoggingExtensions.cs

@ -1,25 +1,36 @@
using Avalonia.Controls;
using System;
using Avalonia.Controls;
using Avalonia.Logging;
namespace Avalonia
{
public static class LoggingExtensions
{
[Obsolete("Use LogToTrace")]
public static T LogToDebug<T>(
this T builder,
LogEventLevel level = LogEventLevel.Warning,
params string[] areas)
where T : AppBuilderBase<T>, new()
{
return LogToTrace(builder, level, areas);
}
/// <summary>
/// Logs Avalonia events to the <see cref="System.Diagnostics.Debug"/> sink.
/// Logs Avalonia events to the <see cref="System.Diagnostics.Trace"/> sink.
/// </summary>
/// <typeparam name="T">The application class type.</typeparam>
/// <param name="builder">The app builder instance.</param>
/// <param name="level">The minimum level to log.</param>
/// <param name="areas">The areas to log. Valid values are listed in <see cref="LogArea"/>.</param>
/// <returns>The app builder instance.</returns>
public static T LogToDebug<T>(
public static T LogToTrace<T>(
this T builder,
LogEventLevel level = LogEventLevel.Warning,
params string[] areas)
where T : AppBuilderBase<T>, new()
{
Logger.Sink = new DebugLogSink(level, areas);
Logger.Sink = new TraceLogSink(level, areas);
return builder;
}
}

25
src/Avalonia.Controls/Presenters/ContentPresenter.cs

@ -85,10 +85,19 @@ namespace Avalonia.Controls.Presenters
public static readonly StyledProperty<Thickness> PaddingProperty =
Decorator.PaddingProperty.AddOwner<ContentPresenter>();
/// <summary>
/// Defines the <see cref="RecognizesAccessKey"/> property
/// </summary>
public static readonly DirectProperty<ContentPresenter, bool> RecognizesAccessKeyProperty =
AvaloniaProperty.RegisterDirect<ContentPresenter, bool>(
nameof(RecognizesAccessKey),
cp => cp.RecognizesAccessKey, (cp, value) => cp.RecognizesAccessKey = value);
private IControl _child;
private bool _createdChild;
private IRecyclingDataTemplate _recyclingDataTemplate;
private readonly BorderRenderHelper _borderRenderer = new BorderRenderHelper();
private bool _recognizesAccessKey;
/// <summary>
/// Initializes static members of the <see cref="ContentPresenter"/> class.
@ -208,6 +217,15 @@ namespace Avalonia.Controls.Presenters
set { SetValue(PaddingProperty, value); }
}
/// <summary>
/// Determine if <see cref="ContentPresenter"/> should use <see cref="AccessText"/> in its style
/// </summary>
public bool RecognizesAccessKey
{
get => _recognizesAccessKey;
set => SetAndRaise(RecognizesAccessKeyProperty, ref _recognizesAccessKey, value);
}
/// <summary>
/// Gets the host content control.
/// </summary>
@ -311,7 +329,12 @@ namespace Avalonia.Controls.Presenters
if (content != null && newChild == null)
{
var dataTemplate = this.FindDataTemplate(content, ContentTemplate) ?? FuncDataTemplate.Default;
var dataTemplate = this.FindDataTemplate(content, ContentTemplate) ??
(
RecognizesAccessKey
? FuncDataTemplate.Access
: FuncDataTemplate.Default
);
if (dataTemplate is IRecyclingDataTemplate rdt)
{

7
src/Avalonia.Controls/Presenters/ItemVirtualizerSimple.cs

@ -512,6 +512,13 @@ namespace Avalonia.Controls.Presenters
var generator = Owner.ItemContainerGenerator;
var newOffset = -1.0;
//better not trigger any container generation/recycle while or layout stuff
//before panel is attached/visible
if (!panel.IsAttachedToVisualTree)
{
return null;
}
if (!panel.IsMeasureValid && panel.PreviousMeasure.HasValue)
{
//before any kind of scrolling we need to make sure panel measure is valid

20
src/Avalonia.Controls/Presenters/TextPresenter.cs

@ -4,6 +4,7 @@ using Avalonia.Media;
using Avalonia.Metadata;
using Avalonia.Threading;
using Avalonia.VisualTree;
using Avalonia.Layout;
namespace Avalonia.Controls.Presenters
{
@ -312,7 +313,24 @@ namespace Avalonia.Controls.Presenters
context.FillRectangle(background, new Rect(Bounds.Size));
}
context.DrawText(Foreground, new Point(), FormattedText);
double top = 0;
var textSize = FormattedText.Bounds.Size;
if (Bounds.Height < textSize.Height)
{
switch (VerticalAlignment)
{
case VerticalAlignment.Center:
top += (Bounds.Height - textSize.Height) / 2;
break;
case VerticalAlignment.Bottom:
top += (Bounds.Height - textSize.Height);
break;
}
}
context.DrawText(Foreground, new Point(0, top), FormattedText);
}
public override void Render(DrawingContext context)

1
src/Avalonia.Controls/Primitives/IPopupHost.cs

@ -47,6 +47,7 @@ namespace Avalonia.Controls.Primitives
/// <param name="offset">The offset, in device-independent pixels.</param>
/// <param name="anchor">The anchor point.</param>
/// <param name="gravity">The popup gravity.</param>
/// <param name="constraintAdjustment">Defines how a popup position will be adjusted if the unadjusted position would result in the popup being partly constrained.</param>
/// <param name="rect">
/// The anchor rect. If null, the bounds of <paramref name="target"/> will be used.
/// </param>

1
src/Avalonia.Controls/Primitives/Popup.cs

@ -265,6 +265,7 @@ namespace Avalonia.Controls.Primitives
/// <summary>
/// Gets or sets the control that is used to determine the popup's position.
/// </summary>
[ResolveByName]
public Control? PlacementTarget
{
get { return GetValue(PlacementTargetProperty); }

7
src/Avalonia.Controls/Properties/AssemblyInfo.cs

@ -1,10 +1,13 @@
using System.Reflection;
using System.Runtime.CompilerServices;
using Avalonia.Metadata;
#if SIGNED_BUILD
[assembly: InternalsVisibleTo("Avalonia.Controls.UnitTests, PublicKey=0024000004800000940000000602000000240000525341310004000001000100c1bba1142285fe0419326fb25866ba62c47e6c2b5c1ab0c95b46413fad375471232cb81706932e1cef38781b9ebd39d5100401bacb651c6c5bbf59e571e81b3bc08d2a622004e08b1a6ece82a7e0b9857525c86d2b95fab4bc3dce148558d7f3ae61aa3a234086902aeface87d9dfdd32b9d2fe3c6dd4055b5ab4b104998bd87")]
[assembly: InternalsVisibleTo("Avalonia.DesignerSupport, PublicKey=0024000004800000940000000602000000240000525341310004000001000100c1bba1142285fe0419326fb25866ba62c47e6c2b5c1ab0c95b46413fad375471232cb81706932e1cef38781b9ebd39d5100401bacb651c6c5bbf59e571e81b3bc08d2a622004e08b1a6ece82a7e0b9857525c86d2b95fab4bc3dce148558d7f3ae61aa3a234086902aeface87d9dfdd32b9d2fe3c6dd4055b5ab4b104998bd87")]
#else
[assembly: InternalsVisibleTo("Avalonia.Controls.UnitTests")]
[assembly: InternalsVisibleTo("Avalonia.DesignerSupport")]
#endif
[assembly: XmlnsDefinition("https://github.com/avaloniaui", "Avalonia")]
[assembly: XmlnsDefinition("https://github.com/avaloniaui", "Avalonia.Controls")]
[assembly: XmlnsDefinition("https://github.com/avaloniaui", "Avalonia.Controls.Embedding")]

12
src/Avalonia.Controls/RelativePanel.AttachedProperties.cs

@ -55,6 +55,7 @@ namespace Avalonia.Controls
/// </summary>
/// <param name="obj">The object to which the property value is written.</param>
/// <param name="value">The value to set. (The element to position this element above.)</param>
[ResolveByName]
public static void SetAbove(AvaloniaObject obj, object value)
{
obj.SetValue(AboveProperty, value);
@ -121,6 +122,7 @@ namespace Avalonia.Controls
/// </summary>
/// <param name="obj">The object to which the property value is written.</param>
/// <param name="value">The value to set. (The element to align this element's bottom edge with.)</param>
[ResolveByName]
public static void SetAlignBottomWith(AvaloniaObject obj, object value)
{
obj.SetValue(AlignBottomWithProperty, value);
@ -185,6 +187,7 @@ namespace Avalonia.Controls
/// </summary>
/// <param name="obj">The object to which the property value is written.</param>
/// <param name="value">The value to set. (The element to align this element's horizontal center with.)</param>
[ResolveByName]
public static void SetAlignHorizontalCenterWith(AvaloniaObject obj, object value)
{
obj.SetValue(AlignHorizontalCenterWithProperty, value);
@ -250,6 +253,7 @@ namespace Avalonia.Controls
/// </summary>
/// <param name="obj">The object to which the property value is written.</param>
/// <param name="value">The value to set. (The element to align this element's left edge with.)</param>
[ResolveByName]
public static void SetAlignLeftWith(AvaloniaObject obj, object value)
{
obj.SetValue(AlignLeftWithProperty, value);
@ -315,6 +319,7 @@ namespace Avalonia.Controls
/// </summary>
/// <param name="obj">The object to which the property value is written.</param>
/// <param name="value">The value to set. (The element to align this element's right edge with.)</param>
[ResolveByName]
public static void SetAlignRightWith(AvaloniaObject obj, object value)
{
obj.SetValue(AlignRightWithProperty, value);
@ -376,6 +381,7 @@ namespace Avalonia.Controls
/// </summary>
/// <param name="obj">The object to which the property value is written.</param>
/// <param name="value">The value to set. (The element to align this element's top edge with.)</param>
[ResolveByName]
public static void SetAlignTopWith(AvaloniaObject obj, object value)
{
obj.SetValue(AlignTopWithProperty, value);
@ -437,7 +443,7 @@ namespace Avalonia.Controls
/// </summary>
/// <param name="obj">The object to which the property value is written.</param>
/// <param name="value">The value to set. (The element to align this element's horizontal center with.)</param>
[ResolveByName]
public static void SetAlignVerticalCenterWith(AvaloniaObject obj, object value)
{
obj.SetValue(AlignVerticalCenterWithProperty, value);
@ -468,7 +474,7 @@ namespace Avalonia.Controls
/// </summary>
/// <param name="obj">The object to which the property value is written.</param>
/// <param name="value">The value to set. (The element to position this element below.)</param>
[ResolveByName]
public static void SetBelow(AvaloniaObject obj, object value)
{
obj.SetValue(BelowProperty, value);
@ -500,6 +506,7 @@ namespace Avalonia.Controls
/// </summary>
/// <param name="obj">The object to which the property value is written.</param>
/// <param name="value">The value to set. (The element to position this element to the left of.)</param>
[ResolveByName]
public static void SetLeftOf(AvaloniaObject obj, object value)
{
obj.SetValue(LeftOfProperty, value);
@ -531,6 +538,7 @@ namespace Avalonia.Controls
/// </summary>
/// <param name="obj">The object to which the property value is written.</param>
/// <param name="value">The value to set. (The element to position this element to the right of.)</param>
[ResolveByName]
public static void SetRightOf(AvaloniaObject obj, object value)
{
obj.SetValue(RightOfProperty, value);

6
src/Avalonia.Controls/ResolveByNameAttribute.cs

@ -2,8 +2,12 @@
namespace Avalonia.Controls
{
/// <summary>
/// Indicates that the property resolves an element by Name or x:Name.
/// When applying this to attached properties, ensure to put on both
/// the Getter and Setter methods.
/// </summary>
public class ResolveByNameAttribute : Attribute
{
}
}

3
src/Avalonia.Controls/Selection/SelectionModel.cs

@ -442,7 +442,8 @@ namespace Avalonia.Controls.Selection
RaisePropertyChanged(nameof(SelectedIndex));
}
if (e.Action == NotifyCollectionChangedAction.Remove && e.OldStartingIndex <= oldSelectedIndex)
if ((e.Action == NotifyCollectionChangedAction.Remove && e.OldStartingIndex <= oldSelectedIndex) ||
e.Action == NotifyCollectionChangedAction.Reset)
{
RaisePropertyChanged(nameof(SelectedItem));
}

54
src/Avalonia.Controls/SplitView.cs

@ -9,6 +9,8 @@ using Avalonia.Platform;
using Avalonia.VisualTree;
using System;
using System.Reactive.Disposables;
using Avalonia.Controls.Presenters;
using Avalonia.Controls.Templates;
namespace Avalonia.Controls
{
@ -78,7 +80,7 @@ namespace Avalonia.Controls
[PseudoClasses(":compactoverlay", ":compactinline", ":overlay", ":inline")]
[PseudoClasses(":left", ":right")]
[PseudoClasses(":lightdismiss")]
public class SplitView : TemplatedControl
public class SplitView : ContentControl
{
/*
Pseudo classes & combos
@ -87,12 +89,6 @@ namespace Avalonia.Controls
:left :right
*/
/// <summary>
/// Defines the <see cref="Content"/> property
/// </summary>
public static readonly StyledProperty<IControl> ContentProperty =
AvaloniaProperty.Register<SplitView, IControl>(nameof(Content));
/// <summary>
/// Defines the <see cref="CompactPaneLength"/> property
/// </summary>
@ -133,8 +129,14 @@ namespace Avalonia.Controls
/// <summary>
/// Defines the <see cref="Pane"/> property
/// </summary>
public static readonly StyledProperty<IControl> PaneProperty =
AvaloniaProperty.Register<SplitView, IControl>(nameof(Pane));
public static readonly StyledProperty<object?> PaneProperty =
AvaloniaProperty.Register<SplitView, object?>(nameof(Pane));
/// <summary>
/// Defines the <see cref="HeaderTemplate"/> property.
/// </summary>
public static readonly StyledProperty<IDataTemplate?> PaneTemplateProperty =
AvaloniaProperty.Register<HeaderedContentControl, IDataTemplate?>(nameof(PaneTemplate));
/// <summary>
/// Defines the <see cref="UseLightDismissOverlayMode"/> property
@ -166,16 +168,7 @@ namespace Avalonia.Controls
CompactPaneLengthProperty.Changed.AddClassHandler<SplitView>((x, v) => x.OnCompactPaneLengthChanged(v));
PanePlacementProperty.Changed.AddClassHandler<SplitView>((x, v) => x.OnPanePlacementChanged(v));
DisplayModeProperty.Changed.AddClassHandler<SplitView>((x, v) => x.OnDisplayModeChanged(v));
}
/// <summary>
/// Gets or sets the content of the SplitView
/// </summary>
[Content]
public IControl Content
{
get => GetValue(ContentProperty);
set => SetValue(ContentProperty, value);
}
/// <summary>
@ -265,11 +258,20 @@ namespace Avalonia.Controls
/// <summary>
/// Gets or sets the Pane for the SplitView
/// </summary>
public IControl Pane
public object Pane
{
get => GetValue(PaneProperty);
set => SetValue(PaneProperty, value);
}
/// <summary>
/// Gets or sets the data template used to display the header content of the control.
/// </summary>
public IDataTemplate? PaneTemplate
{
get => GetValue(PaneTemplateProperty);
set => SetValue(PaneTemplateProperty, value);
}
/// <summary>
/// Gets or sets whether WinUI equivalent LightDismissOverlayMode is enabled
@ -312,6 +314,18 @@ namespace Avalonia.Controls
/// </summary>
public event EventHandler<EventArgs> PaneOpening;
protected override bool RegisterContentPresenter(IContentPresenter presenter)
{
var result = base.RegisterContentPresenter(presenter);
if (presenter.Name == "PART_PanePresenter")
{
return true;
}
return result;
}
protected override void OnApplyTemplate(TemplateAppliedEventArgs e)
{
base.OnApplyTemplate(e);

28
src/Avalonia.Controls/Templates/FuncDataTemplate.cs

@ -1,5 +1,6 @@
using System;
using System.Reactive.Linq;
using Avalonia.Controls.Primitives;
namespace Avalonia.Controls.Templates
{
@ -30,6 +31,31 @@ namespace Avalonia.Controls.Templates
},
true);
/// <summary>
/// The default data template used in the case where no matching data template is found
/// but <see cref="AccessText"/> should be used.
/// </summary>
public static readonly FuncDataTemplate Access =
new FuncDataTemplate<object>(
(data, s) =>
{
if (data != null)
{
var result = new AccessText();
result.Bind(TextBlock.TextProperty,
result.GetObservable(Control.DataContextProperty).Select(x => x?.ToString()));
return result;
}
else
{
return null;
}
},
true);
/// <summary>
/// The implementation of the <see cref="Match"/> method.
/// </summary>
private readonly Func<object, bool> _match;
private readonly bool _supportsRecycling;
@ -42,7 +68,7 @@ namespace Avalonia.Controls.Templates
/// </param>
/// <param name="supportsRecycling">Whether the control can be recycled.</param>
public FuncDataTemplate(
Type type,
Type type,
Func<object, INameScope, IControl> build,
bool supportsRecycling = false)
: this(o => IsInstance(o, type), build, supportsRecycling)

23
src/Avalonia.Controls/TextBlock.cs

@ -3,6 +3,7 @@ using Avalonia.LogicalTree;
using Avalonia.Media;
using Avalonia.Media.TextFormatting;
using Avalonia.Metadata;
using Avalonia.Layout;
namespace Avalonia.Controls
{
@ -427,14 +428,32 @@ namespace Avalonia.Controls
case TextAlignment.Center:
offsetX = (width - TextLayout.Size.Width) / 2;
break;
case TextAlignment.Right:
offsetX = width - TextLayout.Size.Width;
offsetX = width - TextLayout.Size.Width;
break;
}
var padding = Padding;
using (context.PushPostTransform(Matrix.CreateTranslation(padding.Left + offsetX, padding.Top)))
var top = padding.Top;
var textSize = TextLayout.Size;
if (Bounds.Height < textSize.Height)
{
switch (VerticalAlignment)
{
case VerticalAlignment.Center:
top += (Bounds.Height - textSize.Height) / 2;
break;
case VerticalAlignment.Bottom:
top += (Bounds.Height - textSize.Height);
break;
}
}
using (context.PushPostTransform(Matrix.CreateTranslation(padding.Left + offsetX, top)))
{
TextLayout.Draw(context);
}

2
src/Avalonia.Controls/Window.cs

@ -451,7 +451,7 @@ namespace Avalonia.Controls
/// </summary>
/// <param name="dialogResult">The dialog result.</param>
/// <remarks>
/// When the window is shown with the <see cref="ShowDialog{TResult}(IWindowImpl)"/>
/// When the window is shown with the <see cref="ShowDialog{TResult}(Window)"/>
/// or <see cref="ShowDialog{TResult}(Window)"/> method, the
/// resulting task will produce the <see cref="_dialogResult"/> value when the window
/// is closed.

7
src/Avalonia.Diagnostics/Diagnostics/ViewModels/TreeNode.cs

@ -23,6 +23,8 @@ namespace Avalonia.Diagnostics.ViewModels
if (visual is IControl control)
{
ElementName = control.Name;
var removed = Observable.FromEventPattern<LogicalTreeAttachmentEventArgs>(
x => control.DetachedFromLogicalTree += x,
x => control.DetachedFromLogicalTree -= x);
@ -61,6 +63,11 @@ namespace Avalonia.Diagnostics.ViewModels
private set { RaiseAndSetIfChanged(ref _classes, value); }
}
public string ElementName
{
get;
}
public IVisual Visual
{
get;

6
src/Avalonia.Diagnostics/Diagnostics/Views/ControlDetailsView.xaml

@ -26,6 +26,12 @@
<DataGridTextColumn Header="Type" Binding="{Binding Type}" />
<DataGridTextColumn Header="Priority" Binding="{Binding Priority}" IsReadOnly="True" />
</DataGrid.Columns>
<DataGrid.Styles>
<Style Selector="DataGridRow TextBox">
<Setter Property="SelectionBrush" Value="LightBlue"/>
</Style>
</DataGrid.Styles>
</DataGrid>
</Grid>

8
src/Avalonia.Diagnostics/Diagnostics/Views/MainWindow.xaml.cs

@ -76,7 +76,13 @@ namespace Avalonia.Diagnostics.Views
if (e.Modifiers == modifiers)
{
var point = (Root as IInputRoot)?.MouseDevice?.GetPosition(Root) ?? default;
var control = Root.GetVisualsAt(point, x => (!(x is AdornerLayer) && x.IsVisible))
var control = Root.GetVisualsAt(point, x =>
{
if (x is AdornerLayer || !x.IsVisible) return false;
if (!(x is IInputElement ie)) return true;
return ie.IsHitTestVisible;
})
.FirstOrDefault();
if (control != null)

3
src/Avalonia.Diagnostics/Diagnostics/Views/TreePageView.xaml

@ -2,7 +2,7 @@
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:vm="clr-namespace:Avalonia.Diagnostics.ViewModels"
x:Class="Avalonia.Diagnostics.Views.TreePageView">
<Grid ColumnDefinitions="*,4,3*">
<Grid ColumnDefinitions="0.8*,4,*">
<TreeView Name="tree"
BorderThickness="0"
Items="{Binding Nodes}"
@ -13,6 +13,7 @@
<StackPanel Orientation="Horizontal" Spacing="8">
<TextBlock Text="{Binding Type}"/>
<TextBlock Text="{Binding Classes}"/>
<TextBlock Foreground="Gray" Text="{Binding ElementName}"/>
</StackPanel>
</TreeDataTemplate>
</TreeView.DataTemplates>

1
src/Avalonia.Dialogs/ApiCompatBaseline.txt

@ -0,0 +1 @@
Total Issues: 0

4
src/Avalonia.FreeDesktop/Avalonia.FreeDesktop.csproj

@ -6,9 +6,7 @@
<ItemGroup>
<ProjectReference Include="..\Avalonia.Controls\Avalonia.Controls.csproj" />
<PackageReference Include="Tmds.DBus" Version="0.9.0" />
</ItemGroup>
<ItemGroup>
<PackageReference Include="Tmds.DBus" Version="0.7.0" />
</ItemGroup>
</Project>

20
src/Avalonia.Input/MouseDevice.cs

@ -19,6 +19,7 @@ namespace Avalonia.Input
private readonly Pointer _pointer;
private bool _disposed;
private PixelPoint? _position;
public MouseDevice(Pointer? pointer = null)
{
@ -39,10 +40,11 @@ namespace Avalonia.Input
/// <summary>
/// Gets the mouse position, in screen coordinates.
/// </summary>
[Obsolete("Use events instead")]
public PixelPoint Position
{
get;
protected set;
get => _position ?? new PixelPoint(-1, -1);
protected set => _position = value;
}
/// <summary>
@ -91,7 +93,16 @@ namespace Avalonia.Input
public void SceneInvalidated(IInputRoot root, Rect rect)
{
var clientPoint = root.PointToClient(Position);
// Pointer is outside of the target area
if (_position == null )
{
if (root.PointerOverElement != null)
ClearPointerOver(this, 0, root, PointerPointProperties.None, KeyModifiers.None);
return;
}
var clientPoint = root.PointToClient(_position.Value);
if (rect.Contains(clientPoint))
{
@ -132,7 +143,7 @@ namespace Avalonia.Input
if(mouse._disposed)
return;
Position = e.Root.PointToScreen(e.Position);
_position = e.Root.PointToScreen(e.Position);
var props = CreateProperties(e);
var keyModifiers = KeyModifiersUtils.ConvertToKey(e.InputModifiers);
switch (e.Type)
@ -176,6 +187,7 @@ namespace Avalonia.Input
device = device ?? throw new ArgumentNullException(nameof(device));
root = root ?? throw new ArgumentNullException(nameof(root));
_position = null;
ClearPointerOver(this, timestamp, root, properties, inputModifiers);
}

6
src/Avalonia.Layout/Properties/AssemblyInfo.cs

@ -1,7 +1,9 @@
using System.Runtime.CompilerServices;
using Avalonia.Metadata;
#if SIGNED_BUILD
[assembly: InternalsVisibleTo("Avalonia.Layout.UnitTests, PublicKey=0024000004800000940000000602000000240000525341310004000001000100c1bba1142285fe0419326fb25866ba62c47e6c2b5c1ab0c95b46413fad375471232cb81706932e1cef38781b9ebd39d5100401bacb651c6c5bbf59e571e81b3bc08d2a622004e08b1a6ece82a7e0b9857525c86d2b95fab4bc3dce148558d7f3ae61aa3a234086902aeface87d9dfdd32b9d2fe3c6dd4055b5ab4b104998bd87")]
#else
[assembly: InternalsVisibleTo("Avalonia.Layout.UnitTests")]
#endif
[assembly: XmlnsDefinition("https://github.com/avaloniaui", "Avalonia.Layout")]

12
src/Avalonia.Native/WindowImplBase.cs

@ -251,6 +251,9 @@ namespace Avalonia.Native
public bool RawTextInputEvent(uint timeStamp, string text)
{
if (_inputRoot is null)
return false;
Dispatcher.UIThread.RunJobs(DispatcherPriority.Input + 1);
var args = new RawTextInputEventArgs(_keyboard, timeStamp, _inputRoot, text);
@ -262,6 +265,9 @@ namespace Avalonia.Native
public bool RawKeyEvent(AvnRawKeyEventType type, uint timeStamp, AvnInputModifiers modifiers, uint key)
{
if (_inputRoot is null)
return false;
Dispatcher.UIThread.RunJobs(DispatcherPriority.Input + 1);
var args = new RawKeyEventArgs(_keyboard, timeStamp, _inputRoot, (RawKeyEventType)type, (Key)key, (RawInputModifiers)modifiers);
@ -278,6 +284,9 @@ namespace Avalonia.Native
public void RawMouseEvent(AvnRawMouseEventType type, uint timeStamp, AvnInputModifiers modifiers, AvnPoint point, AvnVector delta)
{
if (_inputRoot is null)
return;
Dispatcher.UIThread.RunJobs(DispatcherPriority.Input + 1);
switch (type)
@ -332,8 +341,7 @@ namespace Avalonia.Native
public void Invalidate(Rect rect)
{
if (!_deferredRendering && _native != null)
_native.Invalidate(new AvnRect { Height = rect.Height, Width = rect.Width, X = rect.X, Y = rect.Y });
_native?.Invalidate(new AvnRect { Height = rect.Height, Width = rect.Width, X = rect.X, Y = rect.Y });
}
public void SetInputRoot(IInputRoot inputRoot)

10
src/Avalonia.OpenGL/Angle/AngleEglInterface.cs

@ -1,15 +1,13 @@
using System;
using System.Runtime.InteropServices;
using Avalonia.OpenGL.Egl;
using Avalonia.Platform;
using Avalonia.Platform.Interop;
namespace Avalonia.OpenGL.Angle
{
public class AngleEglInterface : EglInterface
{
[DllImport("libegl.dll", CharSet = CharSet.Ansi)]
static extern IntPtr eglGetProcAddress(string proc);
[DllImport("av_libGLESv2.dll", CharSet = CharSet.Ansi)]
static extern IntPtr EGL_GetProcAddress(string proc);
public AngleEglInterface() : base(LoadAngle())
{
@ -20,14 +18,14 @@ namespace Avalonia.OpenGL.Angle
{
if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows))
{
var disp = eglGetProcAddress("eglGetPlatformDisplayEXT");
var disp = EGL_GetProcAddress("eglGetPlatformDisplayEXT");
if (disp == IntPtr.Zero)
{
throw new OpenGlException("libegl.dll doesn't have eglGetPlatformDisplayEXT entry point");
}
return eglGetProcAddress;
return EGL_GetProcAddress;
}
throw new PlatformNotSupportedException();

9
src/Avalonia.OpenGL/Angle/AngleWin32EglDisplay.cs

@ -82,7 +82,14 @@ namespace Avalonia.OpenGL.Angle
{
if (PlatformApi != AngleOptions.PlatformApi.DirectX11)
throw new InvalidOperationException("Current platform API is " + PlatformApi);
return egl.CreatePBufferFromClientBuffer(EGL_D3D_TEXTURE_ANGLE, handle, new[] { EGL_NONE, EGL_NONE });
return egl.CreatePBufferFromClientBuffer(EGL_D3D_TEXTURE_ANGLE, handle, new[] { EGL_NONE, EGL_NONE });
}
public EglSurface WrapDirect3D11Texture(EglPlatformOpenGlInterface egl, IntPtr handle, int offsetX, int offsetY, int width, int height)
{
if (PlatformApi != AngleOptions.PlatformApi.DirectX11)
throw new InvalidOperationException("Current platform API is " + PlatformApi);
return egl.CreatePBufferFromClientBuffer(EGL_D3D_TEXTURE_ANGLE, handle, new[] { EGL_WIDTH, width, EGL_HEIGHT, height, EGL_FLEXIBLE_SURFACE_COMPATIBILITY_SUPPORTED_ANGLE, EGL_TRUE, EGL_TEXTURE_OFFSET_X_ANGLE, offsetX, EGL_TEXTURE_OFFSET_Y_ANGLE, offsetY, EGL_NONE });
}
}
}

6
src/Avalonia.OpenGL/Egl/EglConsts.cs

@ -205,5 +205,11 @@ namespace Avalonia.OpenGL.Egl
public const int EGL_D3D_TEXTURE_2D_SHARE_HANDLE_ANGLE = 0x3200;
public const int EGL_D3D_TEXTURE_ANGLE = 0x33A3;
public const int EGL_TEXTURE_OFFSET_X_ANGLE = 0x3490;
public const int EGL_TEXTURE_OFFSET_Y_ANGLE = 0x3491;
public const int EGL_FLEXIBLE_SURFACE_COMPATIBILITY_SUPPORTED_ANGLE = 0x33A6;
}
}

1
src/Avalonia.ReactiveUI.Events/Avalonia.ReactiveUI.Events.csproj

@ -2,6 +2,7 @@
<PropertyGroup>
<TargetFramework>netstandard2.0</TargetFramework>
<PackageId>Avalonia.ReactiveUI.Events</PackageId>
<SignAssembly>false</SignAssembly>
</PropertyGroup>
<ItemGroup>
<ProjectReference Include="..\..\packages\Avalonia\Avalonia.csproj" />

1
src/Avalonia.ReactiveUI/Avalonia.ReactiveUI.csproj

@ -2,6 +2,7 @@
<PropertyGroup>
<TargetFramework>netstandard2.0</TargetFramework>
<PackageId>Avalonia.ReactiveUI</PackageId>
<SignAssembly>false</SignAssembly>
</PropertyGroup>
<ItemGroup>
<ProjectReference Include="..\..\packages\Avalonia\Avalonia.csproj" />

18
src/Avalonia.ReactiveUI/ReactiveUserControl.cs

@ -1,3 +1,6 @@
using System;
using System.Reactive.Disposables;
using System.Reactive.Linq;
using Avalonia;
using Avalonia.VisualTree;
using Avalonia.Controls;
@ -6,8 +9,10 @@ using ReactiveUI;
namespace Avalonia.ReactiveUI
{
/// <summary>
/// A ReactiveUI UserControl that implements <see cref="IViewFor{TViewModel}"/>
/// and will activate your ViewModel automatically if it supports activation.
/// A ReactiveUI <see cref="UserControl"/> that implements the <see cref="IViewFor{TViewModel}"/> interface and
/// will activate your ViewModel automatically if the view model implements <see cref="IActivatableViewModel"/>.
/// When the DataContext property changes, this class will update the ViewModel property with the new DataContext
/// value, and vice versa.
/// </summary>
/// <typeparam name="TViewModel">ViewModel type.</typeparam>
public class ReactiveUserControl<TViewModel> : UserControl, IViewFor<TViewModel> where TViewModel : class
@ -20,7 +25,14 @@ namespace Avalonia.ReactiveUI
/// </summary>
public ReactiveUserControl()
{
DataContextChanged += (sender, args) => ViewModel = DataContext as TViewModel;
// This WhenActivated block calls ViewModel's WhenActivated
// block if the ViewModel implements IActivatableViewModel.
this.WhenActivated(disposables => { });
this.ObservableForProperty(x => x.ViewModel, false, true)
.Subscribe(args => DataContext = args.Value);
this.ObservableForProperty(x => x.DataContext, false, true)
.Subscribe(args => ViewModel = args.Value as TViewModel);
}
/// <summary>

18
src/Avalonia.ReactiveUI/ReactiveWindow.cs

@ -1,3 +1,6 @@
using System;
using System.Reactive.Disposables;
using System.Reactive.Linq;
using Avalonia;
using Avalonia.VisualTree;
using Avalonia.Controls;
@ -6,8 +9,10 @@ using ReactiveUI;
namespace Avalonia.ReactiveUI
{
/// <summary>
/// A ReactiveUI Window that implements <see cref="IViewFor{TViewModel}"/>
/// and will activate your ViewModel automatically if it supports activation.
/// A ReactiveUI <see cref="Window"/> that implements the <see cref="IViewFor{TViewModel}"/> interface and will
/// activate your ViewModel automatically if the view model implements <see cref="IActivatableViewModel"/>. When
/// the DataContext property changes, this class will update the ViewModel property with the new DataContext value,
/// and vice versa.
/// </summary>
/// <typeparam name="TViewModel">ViewModel type.</typeparam>
public class ReactiveWindow<TViewModel> : Window, IViewFor<TViewModel> where TViewModel : class
@ -20,7 +25,14 @@ namespace Avalonia.ReactiveUI
/// </summary>
public ReactiveWindow()
{
DataContextChanged += (sender, args) => ViewModel = DataContext as TViewModel;
// This WhenActivated block calls ViewModel's WhenActivated
// block if the ViewModel implements IActivatableViewModel.
this.WhenActivated(disposables => { });
this.ObservableForProperty(x => x.ViewModel, false, true)
.Subscribe(args => DataContext = args.Value);
this.ObservableForProperty(x => x.DataContext, false, true)
.Subscribe(args => ViewModel = args.Value as TViewModel);
}
/// <summary>

6
src/Avalonia.Styling/Properties/AssemblyInfo.cs

@ -5,4 +5,8 @@ using Avalonia.Metadata;
[assembly: XmlnsDefinition("https://github.com/avaloniaui", "Avalonia.Controls")]
[assembly: XmlnsDefinition("https://github.com/avaloniaui", "Avalonia.LogicalTree")]
[assembly: XmlnsDefinition("https://github.com/avaloniaui", "Avalonia.Styling")]
[assembly: InternalsVisibleTo("Avalonia.Styling.UnitTests")]
#if SIGNED_BUILD
[assembly: InternalsVisibleTo("Avalonia.Styling.UnitTests, PublicKey=0024000004800000940000000602000000240000525341310004000001000100c1bba1142285fe0419326fb25866ba62c47e6c2b5c1ab0c95b46413fad375471232cb81706932e1cef38781b9ebd39d5100401bacb651c6c5bbf59e571e81b3bc08d2a622004e08b1a6ece82a7e0b9857525c86d2b95fab4bc3dce148558d7f3ae61aa3a234086902aeface87d9dfdd32b9d2fe3c6dd4055b5ab4b104998bd87")]
#else
[assembly: InternalsVisibleTo("Avalonia.Styling.UnitTests")]
#endif

3
src/Avalonia.Themes.Default/DefaultTheme.xaml

@ -12,7 +12,8 @@
<StyleInclude Source="resm:Avalonia.Themes.Default.CaptionButtons.xaml?assembly=Avalonia.Themes.Default"/>
<StyleInclude Source="resm:Avalonia.Themes.Default.ComboBox.xaml?assembly=Avalonia.Themes.Default"/>
<StyleInclude Source="resm:Avalonia.Themes.Default.ComboBoxItem.xaml?assembly=Avalonia.Themes.Default"/>
<StyleInclude Source="resm:Avalonia.Themes.Default.ContentControl.xaml?assembly=Avalonia.Themes.Default"/>
<StyleInclude Source="resm:Avalonia.Themes.Default.ContentControl.xaml?assembly=Avalonia.Themes.Default"/>
<StyleInclude Source="resm:Avalonia.Themes.Default.Label.xaml?assembly=Avalonia.Themes.Default"/>
<StyleInclude Source="resm:Avalonia.Themes.Default.GridSplitter.xaml?assembly=Avalonia.Themes.Default"/>
<StyleInclude Source="resm:Avalonia.Themes.Default.ItemsControl.xaml?assembly=Avalonia.Themes.Default"/>
<StyleInclude Source="resm:Avalonia.Themes.Default.ListBox.xaml?assembly=Avalonia.Themes.Default"/>

17
src/Avalonia.Themes.Default/Label.xaml

@ -0,0 +1,17 @@
<Style xmlns="https://github.com/avaloniaui" Selector="Label">
<Setter Property="Padding" Value="3"/>
<Setter Property="Template">
<ControlTemplate>
<ContentPresenter Name="PART_ContentPresenter"
Background="{TemplateBinding Background}"
BorderBrush="{TemplateBinding BorderBrush}"
BorderThickness="{TemplateBinding BorderThickness}"
ContentTemplate="{TemplateBinding ContentTemplate}"
Content="{TemplateBinding Content}"
Padding="{TemplateBinding Padding}"
RecognizesAccessKey="True"
VerticalContentAlignment="{TemplateBinding VerticalContentAlignment}"
HorizontalContentAlignment="{TemplateBinding HorizontalContentAlignment}"/>
</ControlTemplate>
</Setter>
</Style>

8
src/Avalonia.Themes.Default/SplitView.xaml

@ -32,12 +32,12 @@
ClipToBounds="True"
HorizontalAlignment="Left"
ZIndex="100">
<Border Child="{TemplateBinding Pane}"/>
<ContentPresenter x:Name="PART_PanePresenter" Content="{TemplateBinding Pane}" ContentTemplate="{TemplateBinding PaneTemplate}" />
<Rectangle Name="HCPaneBorder" Fill="{DynamicResource SystemControlForegroundTransparentBrush}" Width="1" HorizontalAlignment="Right" />
</Panel>
<Panel Name="ContentRoot">
<Border Child="{TemplateBinding Content}" />
<ContentPresenter x:Name="PART_ContentPresenter" Content="{TemplateBinding Content}" ContentTemplate="{TemplateBinding ContentTemplate}" />
<Rectangle Name="LightDismissLayer"/>
</Panel>
@ -106,14 +106,14 @@
ClipToBounds="True"
HorizontalAlignment="Right"
ZIndex="100">
<Border Child="{TemplateBinding Pane}"/>
<ContentPresenter x:Name="PART_PanePresenter" Content="{TemplateBinding Pane}" ContentTemplate="{TemplateBinding PaneTemplate}"/>
<Rectangle Name="HCPaneBorder"
Fill="{DynamicResource SystemControlForegroundTransparentBrush}"
Width="1" HorizontalAlignment="Left" />
</Panel>
<Panel Name="ContentRoot">
<Border Child="{TemplateBinding Content}" />
<ContentPresenter x:Name="PART_ContentPresenter" Content="{TemplateBinding Content}" ContentTemplate="{TemplateBinding ContentTemplate}" />
<Rectangle Name="LightDismissLayer"/>
</Panel>

99
src/Avalonia.Themes.Fluent/ButtonSpinner.xaml

@ -65,56 +65,59 @@
<Setter Property="VerticalContentAlignment" Value="Center" />
<Setter Property="Template">
<ControlTemplate>
<Border Background="{TemplateBinding Background}"
BorderBrush="{TemplateBinding BorderBrush}"
BorderThickness="{TemplateBinding BorderThickness}"
CornerRadius="{DynamicResource ControlCornerRadius}">
<Grid ColumnDefinitions="Auto,*,Auto">
<ContentPresenter Name="PART_ContentPresenter"
Grid.Column="1"
ContentTemplate="{TemplateBinding ContentTemplate}"
Content="{TemplateBinding Content}"
HorizontalContentAlignment="{TemplateBinding HorizontalContentAlignment}"
VerticalContentAlignment="{TemplateBinding VerticalContentAlignment}"
Padding="{TemplateBinding Padding}" />
<DataValidationErrors>
<Border Background="{TemplateBinding Background}"
BorderBrush="{TemplateBinding BorderBrush}"
BorderThickness="{TemplateBinding BorderThickness}"
CornerRadius="{DynamicResource ControlCornerRadius}"
MinHeight="{TemplateBinding MinHeight}">
<Grid ColumnDefinitions="Auto,*,Auto">
<ContentPresenter Name="PART_ContentPresenter"
Grid.Column="1"
ContentTemplate="{TemplateBinding ContentTemplate}"
Content="{TemplateBinding Content}"
HorizontalContentAlignment="{TemplateBinding HorizontalContentAlignment}"
VerticalContentAlignment="{TemplateBinding VerticalContentAlignment}"
Padding="{TemplateBinding Padding}" />
<StackPanel Name="PART_SpinnerPanel"
Orientation="Horizontal"
IsVisible="{TemplateBinding ShowButtonSpinner}">
<RepeatButton Name="PART_IncreaseButton"
Classes="ButtonSpinnerRepeatButton"
VerticalContentAlignment="Center"
Foreground="{TemplateBinding Foreground}"
BorderBrush="{TemplateBinding BorderBrush}"
Background="{TemplateBinding Background}"
FontSize="{TemplateBinding FontSize}">
<Path Fill="{TemplateBinding Foreground}"
Width="16"
Height="8"
Stretch="Uniform"
HorizontalAlignment="Center"
VerticalAlignment="Center"
Data="{StaticResource ButtonSpinnerIncreaseButtonIcon}" />
</RepeatButton>
<StackPanel Name="PART_SpinnerPanel"
Orientation="Horizontal"
IsVisible="{TemplateBinding ShowButtonSpinner}">
<RepeatButton Name="PART_IncreaseButton"
Classes="ButtonSpinnerRepeatButton"
VerticalContentAlignment="Center"
Foreground="{TemplateBinding Foreground}"
BorderBrush="{TemplateBinding BorderBrush}"
Background="{TemplateBinding Background}"
FontSize="{TemplateBinding FontSize}">
<Path Fill="{TemplateBinding Foreground}"
Width="16"
Height="8"
Stretch="Uniform"
HorizontalAlignment="Center"
VerticalAlignment="Center"
Data="{StaticResource ButtonSpinnerIncreaseButtonIcon}" />
</RepeatButton>
<RepeatButton Name="PART_DecreaseButton"
Classes="ButtonSpinnerRepeatButton"
Foreground="{TemplateBinding Foreground}"
BorderBrush="{TemplateBinding BorderBrush}"
Background="{TemplateBinding Background}"
VerticalContentAlignment="Center"
FontSize="{TemplateBinding FontSize}">
<Path Fill="{TemplateBinding Foreground}"
Width="16"
Height="8"
Stretch="Uniform"
HorizontalAlignment="Center"
VerticalAlignment="Center"
Data="{StaticResource ButtonSpinnerDecreaseButtonIcon}" />
</RepeatButton>
</StackPanel>
</Grid>
</Border>
<RepeatButton Name="PART_DecreaseButton"
Classes="ButtonSpinnerRepeatButton"
Foreground="{TemplateBinding Foreground}"
BorderBrush="{TemplateBinding BorderBrush}"
Background="{TemplateBinding Background}"
VerticalContentAlignment="Center"
FontSize="{TemplateBinding FontSize}">
<Path Fill="{TemplateBinding Foreground}"
Width="16"
Height="8"
Stretch="Uniform"
HorizontalAlignment="Center"
VerticalAlignment="Center"
Data="{StaticResource ButtonSpinnerDecreaseButtonIcon}" />
</RepeatButton>
</StackPanel>
</Grid>
</Border>
</DataValidationErrors>
</ControlTemplate>
</Setter>
</Style>

201
src/Avalonia.Themes.Fluent/ComboBox.xaml

@ -44,105 +44,107 @@
<Setter Property="PlaceholderForeground" Value="{DynamicResource ComboBoxPlaceHolderForeground}" />
<Setter Property="Template">
<ControlTemplate>
<Grid RowDefinitions="Auto, *, Auto"
ColumnDefinitions="*,32">
<ContentPresenter x:Name="HeaderContentPresenter"
Grid.Row="0"
<DataValidationErrors>
<Grid RowDefinitions="Auto, *, Auto"
ColumnDefinitions="*,32">
<ContentPresenter x:Name="HeaderContentPresenter"
Grid.Row="0"
Grid.Column="0"
Grid.ColumnSpan="2"
IsVisible="False"
TextBlock.FontWeight="{DynamicResource ComboBoxHeaderThemeFontWeight}"
Margin="{DynamicResource ComboBoxTopHeaderMargin}"
VerticalAlignment="Top" />
<Border x:Name="Background"
Grid.Row="1"
Grid.Column="0"
Grid.ColumnSpan="2"
Background="{TemplateBinding Background}"
BorderBrush="{TemplateBinding BorderBrush}"
BorderThickness="{TemplateBinding BorderThickness}"
MinWidth="{DynamicResource ComboBoxThemeMinWidth}" />
<Border x:Name="HighlightBackground"
Grid.Row="1"
Grid.Column="0"
Grid.ColumnSpan="2"
Background="{DynamicResource ComboBoxBackgroundUnfocused}"
BorderBrush="{DynamicResource ComboBoxBackgroundBorderBrushUnfocused}"
BorderThickness="{TemplateBinding BorderThickness}" />
<TextBlock x:Name="PlaceholderTextBlock"
Grid.Row="1"
Grid.Column="0"
HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}"
VerticalAlignment="{TemplateBinding VerticalContentAlignment}"
Margin="{TemplateBinding Padding}"
Text="{TemplateBinding PlaceholderText}"
Foreground="{TemplateBinding PlaceholderForeground}"
IsVisible="{TemplateBinding SelectionBoxItem, Converter={x:Static ObjectConverters.IsNull}}" />
<ContentControl x:Name="ContentPresenter"
Content="{TemplateBinding SelectionBoxItem}"
ContentTemplate="{TemplateBinding ItemTemplate}"
Grid.Row="1"
Grid.Column="0"
Grid.ColumnSpan="2"
IsVisible="False"
TextBlock.FontWeight="{DynamicResource ComboBoxHeaderThemeFontWeight}"
Margin="{DynamicResource ComboBoxTopHeaderMargin}"
VerticalAlignment="Top" />
<Border x:Name="Background"
Grid.Row="1"
Grid.Column="0"
Grid.ColumnSpan="2"
Background="{TemplateBinding Background}"
BorderBrush="{TemplateBinding BorderBrush}"
BorderThickness="{TemplateBinding BorderThickness}"
MinWidth="{DynamicResource ComboBoxThemeMinWidth}" />
<Border x:Name="HighlightBackground"
Grid.Row="1"
Grid.Column="0"
Grid.ColumnSpan="2"
Background="{DynamicResource ComboBoxBackgroundUnfocused}"
BorderBrush="{DynamicResource ComboBoxBackgroundBorderBrushUnfocused}"
BorderThickness="{TemplateBinding BorderThickness}" />
<TextBlock x:Name="PlaceholderTextBlock"
Margin="{TemplateBinding Padding}"
HorizontalContentAlignment="{TemplateBinding HorizontalContentAlignment}"
VerticalContentAlignment="{TemplateBinding VerticalContentAlignment}" />
<Border x:Name="DropDownOverlay"
Grid.Row="1"
Grid.Column="1"
Background="Transparent"
Margin="0,1,1,1"
Width="30"
IsVisible="False"
HorizontalAlignment="Right" />
<Viewbox UseLayoutRounding="False"
MinHeight="{DynamicResource ComboBoxMinHeight}"
Grid.Row="1"
Grid.Column="0"
HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}"
VerticalAlignment="{TemplateBinding VerticalContentAlignment}"
Margin="{TemplateBinding Padding}"
Text="{TemplateBinding PlaceholderText}"
Foreground="{TemplateBinding PlaceholderForeground}"
IsVisible="{TemplateBinding SelectionBoxItem, Converter={x:Static ObjectConverters.IsNull}}" />
<ContentControl x:Name="ContentPresenter"
Content="{TemplateBinding SelectionBoxItem}"
ContentTemplate="{TemplateBinding ItemTemplate}"
Grid.Row="1"
Grid.Column="0"
Margin="{TemplateBinding Padding}"
HorizontalContentAlignment="{TemplateBinding HorizontalContentAlignment}"
VerticalContentAlignment="{TemplateBinding VerticalContentAlignment}" />
<Border x:Name="DropDownOverlay"
Grid.Row="1"
Grid.Column="1"
Background="Transparent"
Margin="0,1,1,1"
Width="30"
IsVisible="False"
HorizontalAlignment="Right" />
<Viewbox UseLayoutRounding="False"
MinHeight="{DynamicResource ComboBoxMinHeight}"
Grid.Row="1"
Grid.Column="1"
IsHitTestVisible="False"
Margin="0,0,10,0"
Height="12"
Width="12"
HorizontalAlignment="Right"
VerticalAlignment="Center">
<Panel>
<Panel Height="12"
Width="12" />
<Path x:Name="DropDownGlyph"
Stretch="Uniform"
VerticalAlignment="Center"
Data="M1939 486L2029 576L1024 1581L19 576L109 486L1024 1401L1939 486Z" />
</Panel>
</Viewbox>
<Popup Name="PART_Popup"
WindowManagerAddShadowHint="False"
IsOpen="{TemplateBinding IsDropDownOpen, Mode=TwoWay}"
MinWidth="{Binding Bounds.Width, RelativeSource={RelativeSource TemplatedParent}}"
MaxHeight="{TemplateBinding MaxDropDownHeight}"
PlacementTarget="{TemplateBinding}"
IsLightDismissEnabled="True">
<Border x:Name="PopupBorder"
Background="{DynamicResource ComboBoxDropDownBackground}"
BorderBrush="{DynamicResource ComboBoxDropDownBorderBrush}"
BorderThickness="{DynamicResource ComboBoxDropdownBorderThickness}"
Margin="0,-1,0,-1"
Padding="{DynamicResource ComboBoxDropdownBorderPadding}"
HorizontalAlignment="Stretch"
CornerRadius="{DynamicResource OverlayCornerRadius}">
<ScrollViewer HorizontalScrollBarVisibility="{TemplateBinding ScrollViewer.HorizontalScrollBarVisibility}"
VerticalScrollBarVisibility="{TemplateBinding ScrollViewer.VerticalScrollBarVisibility}">
<ItemsPresenter Name="PART_ItemsPresenter"
Items="{TemplateBinding Items}"
Margin="{DynamicResource ComboBoxDropdownContentMargin}"
ItemsPanel="{TemplateBinding ItemsPanel}"
ItemTemplate="{TemplateBinding ItemTemplate}"
VirtualizationMode="{TemplateBinding VirtualizationMode}" />
</ScrollViewer>
</Border>
</Popup>
</Grid>
Grid.Column="1"
IsHitTestVisible="False"
Margin="0,0,10,0"
Height="12"
Width="12"
HorizontalAlignment="Right"
VerticalAlignment="Center">
<Panel>
<Panel Height="12"
Width="12" />
<Path x:Name="DropDownGlyph"
Stretch="Uniform"
VerticalAlignment="Center"
Data="M1939 486L2029 576L1024 1581L19 576L109 486L1024 1401L1939 486Z" />
</Panel>
</Viewbox>
<Popup Name="PART_Popup"
WindowManagerAddShadowHint="False"
IsOpen="{TemplateBinding IsDropDownOpen, Mode=TwoWay}"
MinWidth="{Binding Bounds.Width, RelativeSource={RelativeSource TemplatedParent}}"
MaxHeight="{TemplateBinding MaxDropDownHeight}"
PlacementTarget="Background"
IsLightDismissEnabled="True">
<Border x:Name="PopupBorder"
Background="{DynamicResource ComboBoxDropDownBackground}"
BorderBrush="{DynamicResource ComboBoxDropDownBorderBrush}"
BorderThickness="{DynamicResource ComboBoxDropdownBorderThickness}"
Margin="0,-1,0,-1"
Padding="{DynamicResource ComboBoxDropdownBorderPadding}"
HorizontalAlignment="Stretch"
CornerRadius="{DynamicResource OverlayCornerRadius}">
<ScrollViewer HorizontalScrollBarVisibility="{TemplateBinding ScrollViewer.HorizontalScrollBarVisibility}"
VerticalScrollBarVisibility="{TemplateBinding ScrollViewer.VerticalScrollBarVisibility}">
<ItemsPresenter Name="PART_ItemsPresenter"
Items="{TemplateBinding Items}"
Margin="{DynamicResource ComboBoxDropdownContentMargin}"
ItemsPanel="{TemplateBinding ItemsPanel}"
ItemTemplate="{TemplateBinding ItemTemplate}"
VirtualizationMode="{TemplateBinding VirtualizationMode}" />
</ScrollViewer>
</Border>
</Popup>
</Grid>
</DataValidationErrors>
</ControlTemplate>
</Setter>
</Style>
@ -232,4 +234,9 @@
<Style Selector="ComboBox /template/ Border#HighlightBackground">
<Setter Property="CornerRadius" Value="{DynamicResource ControlCornerRadius}" />
</Style>
<!-- Error State -->
<Style Selector="ComboBox:error /template/ Border#Background">
<Setter Property="BorderBrush" Value="{DynamicResource SystemControlErrorTextForegroundBrush}"/>
</Style>
</Styles>

48
src/Avalonia.Themes.Fluent/DataValidationErrors.xaml

@ -14,39 +14,31 @@
<Setter Property="Template">
<ControlTemplate>
<DockPanel LastChildFill="True">
<ContentControl DockPanel.Dock="Right"
ContentTemplate="{TemplateBinding ErrorTemplate}"
DataContext="{TemplateBinding Owner}"
Content="{Binding (DataValidationErrors.Errors)}"
IsVisible="{Binding (DataValidationErrors.HasErrors)}"/>
<ContentPresenter Name="PART_ContentPresenter"
Background="{TemplateBinding Background}"
BorderBrush="{TemplateBinding BorderBrush}"
BorderThickness="{TemplateBinding BorderThickness}"
ContentTemplate="{TemplateBinding ContentTemplate}"
Content="{TemplateBinding Content}"
Padding="{TemplateBinding Padding}"/>
<ContentControl Margin="0 4 0 0"
DockPanel.Dock="Bottom"
ContentTemplate="{TemplateBinding ErrorTemplate}"
DataContext="{TemplateBinding Owner}"
Content="{Binding (DataValidationErrors.Errors)}"
IsVisible="{Binding (DataValidationErrors.HasErrors)}" />
<ContentPresenter
Name="PART_ContentPresenter"
Background="{TemplateBinding Background}"
BorderThickness="{TemplateBinding BorderThickness}"
ContentTemplate="{TemplateBinding ContentTemplate}"
Content="{TemplateBinding Content}"
Padding="{TemplateBinding Padding}" />
</DockPanel>
</ControlTemplate>
</Setter>
<Setter Property="ErrorTemplate">
<DataTemplate>
<Canvas Name="PART_ErrorTemplateCanvas"
Width="14" Height="14" Margin="4 0 1 0"
Background="Transparent">
<Canvas.Styles>
<Style Selector="Canvas#PART_ErrorTemplateCanvas ToolTip">
<Setter Property="BorderBrush" Value="{DynamicResource SystemControlErrorTextForegroundBrush}"/>
</Style>
<Style Selector="Canvas#PART_ErrorTemplateCanvas ToolTip TextBlock">
<Setter Property="TextWrapping" Value="Wrap" />
</Style>
</Canvas.Styles>
<ToolTip.Tip>
<ItemsControl Items="{Binding}"/>
</ToolTip.Tip>
<Path Data="M14,7 A7,7 0 0,0 0,7 M0,7 A7,7 0 1,0 14,7 M7,3l0,5 M7,9l0,2" Stroke="{DynamicResource SystemControlErrorTextForegroundBrush}" StrokeThickness="2"/>
</Canvas>
<ItemsControl Items="{Binding}">
<ItemsControl.ItemTemplate>
<DataTemplate>
<TextBlock Text="{Binding Message}" Foreground="{DynamicResource SystemControlErrorTextForegroundBrush}" TextWrapping="Wrap" />
</DataTemplate>
</ItemsControl.ItemTemplate>
</ItemsControl>
</DataTemplate>
</Setter>
</Style>

143
src/Avalonia.Themes.Fluent/DatePicker.xaml

@ -125,77 +125,79 @@
<Setter Property="VerticalAlignment" Value="Center" />
<Setter Property="Template">
<ControlTemplate>
<Grid Name="LayoutRoot" Margin="{TemplateBinding Padding}" RowDefinitions="Auto,*">
<ContentPresenter Name="HeaderContentPresenter" Grid.Row="0"
Content="{TemplateBinding Header}"
ContentTemplate="{TemplateBinding HeaderTemplate}"
Margin="{DynamicResource DatePickerTopHeaderMargin}"
MaxWidth="{DynamicResource DatePickerThemeMaxWidth}"
HorizontalAlignment="Stretch"
VerticalAlignment="Top"/>
<DataValidationErrors>
<Grid Name="LayoutRoot" Margin="{TemplateBinding Padding}" RowDefinitions="Auto,*">
<ContentPresenter Name="HeaderContentPresenter" Grid.Row="0"
Content="{TemplateBinding Header}"
ContentTemplate="{TemplateBinding HeaderTemplate}"
Margin="{DynamicResource DatePickerTopHeaderMargin}"
MaxWidth="{DynamicResource DatePickerThemeMaxWidth}"
HorizontalAlignment="Stretch"
VerticalAlignment="Top"/>
<Button Name="FlyoutButton" Grid.Row="1"
Foreground="{TemplateBinding Foreground}"
Background="{TemplateBinding Background}"
BorderBrush="{TemplateBinding BorderBrush}"
BorderThickness="{TemplateBinding BorderThickness}"
IsEnabled="{TemplateBinding IsEnabled}"
MinWidth="{StaticResource DatePickerThemeMinWidth}"
MaxWidth="{StaticResource DatePickerThemeMaxWidth}"
HorizontalAlignment="Stretch"
VerticalAlignment="Stretch"
HorizontalContentAlignment="Stretch"
VerticalContentAlignment="Stretch"
TemplatedControl.IsTemplateFocusTarget="True">
<Button.Template>
<ControlTemplate>
<ContentPresenter Name="ContentPresenter"
BorderBrush="{TemplateBinding BorderBrush}"
Background="{TemplateBinding Background}"
BorderThickness="{TemplateBinding BorderThickness}"
Content="{TemplateBinding Content}"
TextBlock.Foreground="{TemplateBinding Foreground}"
HorizontalContentAlignment="Stretch"
VerticalContentAlignment="Stretch"
CornerRadius="{DynamicResource ControlCornerRadius}"/>
</ControlTemplate>
</Button.Template>
<Grid Name="ButtonContentGrid" ColumnDefinitions="78*,Auto,132*,Auto,78*">
<TextBlock Name="DayText" Text="day" HorizontalAlignment="Center"
Padding="{DynamicResource DatePickerHostPadding}"
FontFamily="{TemplateBinding FontFamily}"
FontWeight="{TemplateBinding FontWeight}"
FontSize="{TemplateBinding FontSize}"/>
<TextBlock Name="MonthText" Text="month" TextAlignment="Left"
Padding="{DynamicResource DatePickerHostMonthPadding}"
FontFamily="{TemplateBinding FontFamily}"
FontWeight="{TemplateBinding FontWeight}"
FontSize="{TemplateBinding FontSize}"/>
<TextBlock Name="YearText" Text="year" HorizontalAlignment="Center"
Padding="{DynamicResource DatePickerHostPadding}"
FontFamily="{TemplateBinding FontFamily}"
FontWeight="{TemplateBinding FontWeight}"
FontSize="{TemplateBinding FontSize}"/>
<Rectangle x:Name="FirstSpacer"
Fill="{DynamicResource DatePickerSpacerFill}"
HorizontalAlignment="Center"
Width="1"
Grid.Column="1" />
<Rectangle x:Name="SecondSpacer"
Fill="{DynamicResource DatePickerSpacerFill}"
HorizontalAlignment="Center"
Width="1"
Grid.Column="3" />
</Grid>
</Button>
<Button Name="FlyoutButton" Grid.Row="1"
Foreground="{TemplateBinding Foreground}"
Background="{TemplateBinding Background}"
BorderBrush="{TemplateBinding BorderBrush}"
BorderThickness="{TemplateBinding BorderThickness}"
IsEnabled="{TemplateBinding IsEnabled}"
MinWidth="{StaticResource DatePickerThemeMinWidth}"
MaxWidth="{StaticResource DatePickerThemeMaxWidth}"
HorizontalAlignment="Stretch"
VerticalAlignment="Stretch"
HorizontalContentAlignment="Stretch"
VerticalContentAlignment="Stretch"
TemplatedControl.IsTemplateFocusTarget="True">
<Button.Template>
<ControlTemplate>
<ContentPresenter Name="ContentPresenter"
BorderBrush="{TemplateBinding BorderBrush}"
Background="{TemplateBinding Background}"
BorderThickness="{TemplateBinding BorderThickness}"
Content="{TemplateBinding Content}"
TextBlock.Foreground="{TemplateBinding Foreground}"
HorizontalContentAlignment="Stretch"
VerticalContentAlignment="Stretch"
CornerRadius="{DynamicResource ControlCornerRadius}"/>
</ControlTemplate>
</Button.Template>
<Grid Name="ButtonContentGrid" ColumnDefinitions="78*,Auto,132*,Auto,78*">
<TextBlock Name="DayText" Text="day" HorizontalAlignment="Center"
Padding="{DynamicResource DatePickerHostPadding}"
FontFamily="{TemplateBinding FontFamily}"
FontWeight="{TemplateBinding FontWeight}"
FontSize="{TemplateBinding FontSize}"/>
<TextBlock Name="MonthText" Text="month" TextAlignment="Left"
Padding="{DynamicResource DatePickerHostMonthPadding}"
FontFamily="{TemplateBinding FontFamily}"
FontWeight="{TemplateBinding FontWeight}"
FontSize="{TemplateBinding FontSize}"/>
<TextBlock Name="YearText" Text="year" HorizontalAlignment="Center"
Padding="{DynamicResource DatePickerHostPadding}"
FontFamily="{TemplateBinding FontFamily}"
FontWeight="{TemplateBinding FontWeight}"
FontSize="{TemplateBinding FontSize}"/>
<Rectangle x:Name="FirstSpacer"
Fill="{DynamicResource DatePickerSpacerFill}"
HorizontalAlignment="Center"
Width="1"
Grid.Column="1" />
<Rectangle x:Name="SecondSpacer"
Fill="{DynamicResource DatePickerSpacerFill}"
HorizontalAlignment="Center"
Width="1"
Grid.Column="3" />
</Grid>
</Button>
<Popup Name="Popup" WindowManagerAddShadowHint="False"
IsLightDismissEnabled="True" PlacementTarget="{TemplateBinding}"
PlacementMode="Bottom">
<DatePickerPresenter Name="PickerPresenter" />
</Popup>
<Popup Name="Popup" WindowManagerAddShadowHint="False"
IsLightDismissEnabled="True" PlacementTarget="{TemplateBinding}"
PlacementMode="Bottom">
<DatePickerPresenter Name="PickerPresenter" />
</Popup>
</Grid>
</Grid>
</DataValidationErrors>
</ControlTemplate>
</Setter>
</Style>
@ -228,6 +230,11 @@
<Style Selector="DatePicker:hasnodate /template/ Button#FlyoutButton TextBlock">
<Setter Property="Foreground" Value="{DynamicResource TextControlPlaceholderForeground}"/>
</Style>
<Style Selector="DatePicker:error /template/ Button#FlyoutButton /template/ ContentPresenter">
<Setter Property="BorderBrush" Value="{DynamicResource SystemControlErrorTextForegroundBrush}"/>
</Style>
<!--WinUI: DatePickerFlyoutPresenter-->
<Style Selector="DatePickerPresenter">

3
src/Avalonia.Themes.Fluent/FluentTheme.xaml

@ -11,7 +11,8 @@
<StyleInclude Source="avares://Avalonia.Themes.Fluent/CheckBox.xaml"/>
<StyleInclude Source="avares://Avalonia.Themes.Fluent/ComboBox.xaml"/>
<StyleInclude Source="avares://Avalonia.Themes.Fluent/ComboBoxItem.xaml"/>
<StyleInclude Source="avares://Avalonia.Themes.Fluent/ContentControl.xaml"/>
<StyleInclude Source="avares://Avalonia.Themes.Fluent/ContentControl.xaml"/>
<StyleInclude Source="avares://Avalonia.Themes.Fluent/Label.xaml"/>
<StyleInclude Source="avares://Avalonia.Themes.Fluent/GridSplitter.xaml"/>
<StyleInclude Source="avares://Avalonia.Themes.Fluent/ItemsControl.xaml"/>
<StyleInclude Source="avares://Avalonia.Themes.Fluent/ListBox.xaml"/>

17
src/Avalonia.Themes.Fluent/Label.xaml

@ -0,0 +1,17 @@
<Style xmlns="https://github.com/avaloniaui" Selector="Label">
<Setter Property="Padding" Value="3"/>
<Setter Property="Template">
<ControlTemplate>
<ContentPresenter Name="PART_ContentPresenter"
Background="{TemplateBinding Background}"
BorderBrush="{TemplateBinding BorderBrush}"
BorderThickness="{TemplateBinding BorderThickness}"
ContentTemplate="{TemplateBinding ContentTemplate}"
Content="{TemplateBinding Content}"
Padding="{TemplateBinding Padding}"
RecognizesAccessKey="True"
VerticalContentAlignment="{TemplateBinding VerticalContentAlignment}"
HorizontalContentAlignment="{TemplateBinding HorizontalContentAlignment}"/>
</ControlTemplate>
</Setter>
</Style>

2
src/Avalonia.Themes.Fluent/NumericUpDown.xaml

@ -39,6 +39,7 @@
VerticalContentAlignment="Stretch"
AllowSpin="{TemplateBinding AllowSpin}"
ShowButtonSpinner="{TemplateBinding ShowButtonSpinner}"
DataValidationErrors.Errors="{TemplateBinding (DataValidationErrors.Errors)}"
ButtonSpinnerLocation="{TemplateBinding ButtonSpinnerLocation}">
<TextBox Name="PART_TextBox"
Background="Transparent"
@ -46,7 +47,6 @@
Margin="-1"
Padding="{TemplateBinding Padding}"
Watermark="{TemplateBinding Watermark}"
DataValidationErrors.Errors="{TemplateBinding (DataValidationErrors.Errors)}"
IsReadOnly="{TemplateBinding IsReadOnly}"
Text="{TemplateBinding Text}"
AcceptsReturn="False"

204
src/Avalonia.Themes.Fluent/Slider.xaml

@ -42,56 +42,58 @@
<Setter Property="FontSize" Value="{DynamicResource ControlContentThemeFontSize}" />
<Setter Property="Template">
<ControlTemplate>
<Border BorderThickness="{TemplateBinding BorderThickness}" BorderBrush="{TemplateBinding BorderBrush}" CornerRadius="{DynamicResource ControlCornerRadius}">
<Grid Name="grid" Margin="{TemplateBinding Padding}" RowDefinitions="Auto, *">
<ContentPresenter x:Name="HeaderContentPresenter" Grid.Row="0" TextBlock.FontWeight="{DynamicResource SliderHeaderThemeFontWeight}" TextBlock.Foreground="{DynamicResource SliderHeaderForeground}"
Margin="{DynamicResource SliderTopHeaderMargin}" />
<Grid x:Name="SliderContainer" Grid.Row="1">
<Grid.Styles>
<Style Selector="TickBar">
<Setter Property="ReservedSpace" Value="{Binding #PART_Track.Thumb.Bounds}" />
</Style>
</Grid.Styles>
<Grid x:Name="HorizontalTemplate" ColumnDefinitions="Auto,Auto,*" MinHeight="{DynamicResource SliderHorizontalHeight}">
<Grid.RowDefinitions>
<RowDefinition Height="{DynamicResource SliderPreContentMargin}" />
<RowDefinition Height="Auto" />
<RowDefinition Height="{DynamicResource SliderPostContentMargin}" />
</Grid.RowDefinitions>
<TickBar Name="TopTickBar" Placement="Top" Height="{DynamicResource SliderOutsideTickBarThemeHeight}" VerticalAlignment="Bottom" Margin="0,0,0,4" Grid.ColumnSpan="3" />
<!-- <TickBar Name="HorizontalInlineTickBar" Placement="Top" Fill="{DynamicResource SliderInlineTickBarFill}" Height="{DynamicResource SliderTrackThemeHeight}" Grid.Row="1" Grid.ColumnSpan="3" /> -->
<TickBar Name="BottomTickBar" Placement="Bottom" Height="{DynamicResource SliderOutsideTickBarThemeHeight}" VerticalAlignment="Top" Margin="0,4,0,0" Grid.Row="2" Grid.ColumnSpan="3" />
<Track Name="PART_Track" Grid.Row="1" Grid.ColumnSpan="3" Orientation="Horizontal">
<Track.DecreaseButton>
<RepeatButton Name="PART_DecreaseButton" Background="{TemplateBinding Foreground}" HorizontalAlignment="Stretch" VerticalAlignment="Stretch">
<RepeatButton.Template>
<ControlTemplate>
<Grid>
<Border Name="FocusTarget" Background="Transparent" Margin="0,-10" />
<Border Name="TrackBackground" Background="{TemplateBinding Background}" CornerRadius="{DynamicResource ControlCornerRadius}" Height="{DynamicResource SliderTrackThemeHeight}" VerticalAlignment="Center" />
</Grid>
</ControlTemplate>
</RepeatButton.Template>
</RepeatButton>
</Track.DecreaseButton>
<Track.IncreaseButton>
<RepeatButton Name="PART_IncreaseButton" Background="{TemplateBinding Background}" HorizontalAlignment="Stretch" VerticalAlignment="Stretch">
<RepeatButton.Template>
<ControlTemplate>
<Grid>
<Border Name="FocusTarget" Background="Transparent" Margin="0,-10" />
<Border Name="TrackBackground" Background="{TemplateBinding Background}" CornerRadius="{DynamicResource ControlCornerRadius}" Height="{DynamicResource SliderTrackThemeHeight}" VerticalAlignment="Center" />
</Grid>
</ControlTemplate>
</RepeatButton.Template>
</RepeatButton>
</Track.IncreaseButton>
<Thumb Classes="SliderThumbStyle" Name="thumb" Margin="0" Padding="0" DataContext="{TemplateBinding Value}" Height="{DynamicResource SliderHorizontalThumbHeight}" Width="{DynamicResource SliderHorizontalThumbWidth}" />
</Track>
<DataValidationErrors>
<Border BorderThickness="{TemplateBinding BorderThickness}" BorderBrush="{TemplateBinding BorderBrush}" CornerRadius="{DynamicResource ControlCornerRadius}">
<Grid Name="grid" Margin="{TemplateBinding Padding}" RowDefinitions="Auto, *">
<ContentPresenter x:Name="HeaderContentPresenter" Grid.Row="0" TextBlock.FontWeight="{DynamicResource SliderHeaderThemeFontWeight}" TextBlock.Foreground="{DynamicResource SliderHeaderForeground}"
Margin="{DynamicResource SliderTopHeaderMargin}" />
<Grid x:Name="SliderContainer" Grid.Row="1">
<Grid.Styles>
<Style Selector="TickBar">
<Setter Property="ReservedSpace" Value="{Binding #PART_Track.Thumb.Bounds}" />
</Style>
</Grid.Styles>
<Grid x:Name="HorizontalTemplate" ColumnDefinitions="Auto,Auto,*" MinHeight="{DynamicResource SliderHorizontalHeight}">
<Grid.RowDefinitions>
<RowDefinition Height="{DynamicResource SliderPreContentMargin}" />
<RowDefinition Height="Auto" />
<RowDefinition Height="{DynamicResource SliderPostContentMargin}" />
</Grid.RowDefinitions>
<TickBar Name="TopTickBar" Placement="Top" Height="{DynamicResource SliderOutsideTickBarThemeHeight}" VerticalAlignment="Bottom" Margin="0,0,0,4" Grid.ColumnSpan="3" />
<!-- <TickBar Name="HorizontalInlineTickBar" Placement="Top" Fill="{DynamicResource SliderInlineTickBarFill}" Height="{DynamicResource SliderTrackThemeHeight}" Grid.Row="1" Grid.ColumnSpan="3" /> -->
<TickBar Name="BottomTickBar" Placement="Bottom" Height="{DynamicResource SliderOutsideTickBarThemeHeight}" VerticalAlignment="Top" Margin="0,4,0,0" Grid.Row="2" Grid.ColumnSpan="3" />
<Track Name="PART_Track" Grid.Row="1" Grid.ColumnSpan="3" Orientation="Horizontal">
<Track.DecreaseButton>
<RepeatButton Name="PART_DecreaseButton" Background="{TemplateBinding Foreground}" HorizontalAlignment="Stretch" VerticalAlignment="Stretch">
<RepeatButton.Template>
<ControlTemplate>
<Grid>
<Border Name="FocusTarget" Background="Transparent" Margin="0,-10" />
<Border Name="TrackBackground" Background="{TemplateBinding Background}" CornerRadius="{DynamicResource ControlCornerRadius}" Height="{DynamicResource SliderTrackThemeHeight}" VerticalAlignment="Center" />
</Grid>
</ControlTemplate>
</RepeatButton.Template>
</RepeatButton>
</Track.DecreaseButton>
<Track.IncreaseButton>
<RepeatButton Name="PART_IncreaseButton" Background="{TemplateBinding Background}" HorizontalAlignment="Stretch" VerticalAlignment="Stretch">
<RepeatButton.Template>
<ControlTemplate>
<Grid>
<Border Name="FocusTarget" Background="Transparent" Margin="0,-10" />
<Border Name="TrackBackground" Background="{TemplateBinding Background}" CornerRadius="{DynamicResource ControlCornerRadius}" Height="{DynamicResource SliderTrackThemeHeight}" VerticalAlignment="Center" />
</Grid>
</ControlTemplate>
</RepeatButton.Template>
</RepeatButton>
</Track.IncreaseButton>
<Thumb Classes="SliderThumbStyle" Name="thumb" Margin="0" Padding="0" DataContext="{TemplateBinding Value}" Height="{DynamicResource SliderHorizontalThumbHeight}" Width="{DynamicResource SliderHorizontalThumbWidth}" />
</Track>
</Grid>
</Grid>
</Grid>
</Grid>
</Border>
</Border>
</DataValidationErrors>
</ControlTemplate>
</Setter>
</Style>
@ -102,56 +104,58 @@
<Setter Property="FontSize" Value="{DynamicResource ControlContentThemeFontSize}" />
<Setter Property="Template">
<ControlTemplate>
<Border BorderThickness="{TemplateBinding BorderThickness}" BorderBrush="{TemplateBinding BorderBrush}" CornerRadius="{DynamicResource ControlCornerRadius}">
<Grid Name="grid" Margin="{TemplateBinding Padding}" RowDefinitions="Auto, *">
<ContentPresenter x:Name="HeaderContentPresenter" Grid.Row="0" TextBlock.FontWeight="{DynamicResource SliderHeaderThemeFontWeight}" TextBlock.Foreground="{DynamicResource SliderHeaderForeground}"
Margin="{DynamicResource SliderTopHeaderMargin}" />
<Grid x:Name="SliderContainer" Grid.Row="1">
<Grid.Styles>
<Style Selector="TickBar">
<Setter Property="ReservedSpace" Value="{Binding #PART_Track.Thumb.Bounds}" />
</Style>
</Grid.Styles>
<Grid x:Name="VerticalTemplate" RowDefinitions="*,Auto,Auto" MinWidth="{DynamicResource SliderVerticalWidth}">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="{DynamicResource SliderPreContentMargin}" />
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="{DynamicResource SliderPostContentMargin}" />
</Grid.ColumnDefinitions>
<TickBar Name="LeftTickBar" Placement="Left" Width="{DynamicResource SliderOutsideTickBarThemeHeight}" HorizontalAlignment="Right" Margin="0,0,4,0" Grid.RowSpan="3" />
<!-- <TickBar Name="VerticalInlineTickBar" Placement="Inline" Fill="{DynamicResource SliderInlineTickBarFill}" Width="{DynamicResource SliderTrackThemeHeight}" Grid.Column="1" Grid.RowSpan="3" /> -->
<TickBar Name="RightTickBar" Placement="Right" Width="{DynamicResource SliderOutsideTickBarThemeHeight}" HorizontalAlignment="Left" Margin="4,0,0,0" Grid.Column="2" Grid.RowSpan="3" />
<Track Name="PART_Track" Grid.Column="1" Grid.ColumnSpan="1" Grid.RowSpan="3" Orientation="Vertical">
<Track.DecreaseButton>
<RepeatButton Name="PART_DecreaseButton" Background="{TemplateBinding Foreground}" VerticalAlignment="Stretch" HorizontalAlignment="Stretch">
<RepeatButton.Template>
<ControlTemplate>
<Grid>
<Border Name="FocusTarget" Background="Transparent" Margin="0,-10" />
<Border Name="TrackBackground" Background="{TemplateBinding Background}" CornerRadius="{DynamicResource ControlCornerRadius}" Width="{DynamicResource SliderTrackThemeHeight}" HorizontalAlignment="Center" />
</Grid>
</ControlTemplate>
</RepeatButton.Template>
</RepeatButton>
</Track.DecreaseButton>
<Track.IncreaseButton>
<RepeatButton Name="PART_IncreaseButton" Background="{TemplateBinding Background}" VerticalAlignment="Stretch" HorizontalAlignment="Stretch">
<RepeatButton.Template>
<ControlTemplate>
<Grid>
<Border Name="FocusTarget" Background="Transparent" Margin="0,-10" />
<Border Name="TrackBackground" Background="{TemplateBinding Background}" CornerRadius="{DynamicResource ControlCornerRadius}" Width="{DynamicResource SliderTrackThemeHeight}" HorizontalAlignment="Center" />
</Grid>
</ControlTemplate>
</RepeatButton.Template>
</RepeatButton>
</Track.IncreaseButton>
<Thumb Classes="SliderThumbStyle" Name="SliderThumb" Margin="0" Padding="0" DataContext="{TemplateBinding Value}" Height="{DynamicResource SliderVerticalThumbHeight}" Width="{DynamicResource SliderVerticalThumbWidth}" />
</Track>
<DataValidationErrors>
<Border BorderThickness="{TemplateBinding BorderThickness}" BorderBrush="{TemplateBinding BorderBrush}" CornerRadius="{DynamicResource ControlCornerRadius}">
<Grid Name="grid" Margin="{TemplateBinding Padding}" RowDefinitions="Auto, *">
<ContentPresenter x:Name="HeaderContentPresenter" Grid.Row="0" TextBlock.FontWeight="{DynamicResource SliderHeaderThemeFontWeight}" TextBlock.Foreground="{DynamicResource SliderHeaderForeground}"
Margin="{DynamicResource SliderTopHeaderMargin}" />
<Grid x:Name="SliderContainer" Grid.Row="1">
<Grid.Styles>
<Style Selector="TickBar">
<Setter Property="ReservedSpace" Value="{Binding #PART_Track.Thumb.Bounds}" />
</Style>
</Grid.Styles>
<Grid x:Name="VerticalTemplate" RowDefinitions="*,Auto,Auto" MinWidth="{DynamicResource SliderVerticalWidth}">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="{DynamicResource SliderPreContentMargin}" />
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="{DynamicResource SliderPostContentMargin}" />
</Grid.ColumnDefinitions>
<TickBar Name="LeftTickBar" Placement="Left" Width="{DynamicResource SliderOutsideTickBarThemeHeight}" HorizontalAlignment="Right" Margin="0,0,4,0" Grid.RowSpan="3" />
<!-- <TickBar Name="VerticalInlineTickBar" Placement="Inline" Fill="{DynamicResource SliderInlineTickBarFill}" Width="{DynamicResource SliderTrackThemeHeight}" Grid.Column="1" Grid.RowSpan="3" /> -->
<TickBar Name="RightTickBar" Placement="Right" Width="{DynamicResource SliderOutsideTickBarThemeHeight}" HorizontalAlignment="Left" Margin="4,0,0,0" Grid.Column="2" Grid.RowSpan="3" />
<Track Name="PART_Track" Grid.Column="1" Grid.ColumnSpan="1" Grid.RowSpan="3" Orientation="Vertical">
<Track.DecreaseButton>
<RepeatButton Name="PART_DecreaseButton" Background="{TemplateBinding Foreground}" VerticalAlignment="Stretch" HorizontalAlignment="Stretch">
<RepeatButton.Template>
<ControlTemplate>
<Grid>
<Border Name="FocusTarget" Background="Transparent" Margin="0,-10" />
<Border Name="TrackBackground" Background="{TemplateBinding Background}" CornerRadius="{DynamicResource ControlCornerRadius}" Width="{DynamicResource SliderTrackThemeHeight}" HorizontalAlignment="Center" />
</Grid>
</ControlTemplate>
</RepeatButton.Template>
</RepeatButton>
</Track.DecreaseButton>
<Track.IncreaseButton>
<RepeatButton Name="PART_IncreaseButton" Background="{TemplateBinding Background}" VerticalAlignment="Stretch" HorizontalAlignment="Stretch">
<RepeatButton.Template>
<ControlTemplate>
<Grid>
<Border Name="FocusTarget" Background="Transparent" Margin="0,-10" />
<Border Name="TrackBackground" Background="{TemplateBinding Background}" CornerRadius="{DynamicResource ControlCornerRadius}" Width="{DynamicResource SliderTrackThemeHeight}" HorizontalAlignment="Center" />
</Grid>
</ControlTemplate>
</RepeatButton.Template>
</RepeatButton>
</Track.IncreaseButton>
<Thumb Classes="SliderThumbStyle" Name="SliderThumb" Margin="0" Padding="0" DataContext="{TemplateBinding Value}" Height="{DynamicResource SliderVerticalThumbHeight}" Width="{DynamicResource SliderVerticalThumbWidth}" />
</Track>
</Grid>
</Grid>
</Grid>
</Grid>
</Border>
</Border>
</DataValidationErrors>
</ControlTemplate>
</Setter>
</Style>
@ -260,4 +264,12 @@
<Style Selector="Slider:pointerover /template/ RepeatButton#PART_DecreaseButton">
<Setter Property="Background" Value="{DynamicResource SliderTrackValueFillPressed}" />
</Style>
<Style Selector="Slider:error /template/ Thumb.SliderThumbStyle">
<Setter Property="Background" Value="{DynamicResource SystemControlErrorTextForegroundBrush}" />
</Style>
<Style Selector="Slider:error">
<Setter Property="Foreground" Value="{DynamicResource SystemControlErrorTextForegroundBrush}" />
</Style>
</Styles>

Some files were not shown because too many files changed in this diff

Loading…
Cancel
Save