1 changed files with 147 additions and 0 deletions
@ -0,0 +1,147 @@ |
|||
using System.Collections.Generic; |
|||
using System.Runtime.CompilerServices; |
|||
using Avalonia.Controls; |
|||
using Avalonia.Controls.Primitives; |
|||
using Avalonia.Controls.Templates; |
|||
using Avalonia.Media; |
|||
using Avalonia.Styling; |
|||
using BenchmarkDotNet.Attributes; |
|||
|
|||
#nullable enable |
|||
|
|||
namespace Avalonia.Benchmarks.Styling |
|||
{ |
|||
[MemoryDiagnoser] |
|||
public class ControlTheme_Apply |
|||
{ |
|||
private ControlTheme _theme; |
|||
private ControlTheme _otherTheme; |
|||
private List<Style> _styles = new(); |
|||
|
|||
public ControlTheme_Apply() |
|||
{ |
|||
RuntimeHelpers.RunClassConstructor(typeof(TestControl).TypeHandle); |
|||
|
|||
_theme = CreateControlTheme(Brushes.Red); |
|||
_otherTheme = CreateControlTheme(Brushes.Orange); |
|||
|
|||
for (var i = 0; i < 100; ++i) |
|||
{ |
|||
_styles.Add(new Style(x => x.OfType<TestControl>()) |
|||
{ |
|||
Setters = { new Setter(TestControl.BackgroundProperty, Brushes.Yellow) } |
|||
}); |
|||
} |
|||
} |
|||
|
|||
[Benchmark] |
|||
public void Apply_Control_Theme() |
|||
{ |
|||
var target = new TestControl(); |
|||
|
|||
target.BeginBatchUpdate(); |
|||
|
|||
_theme.TryAttach(target, null); |
|||
target.ApplyTemplate(); |
|||
_theme.TryAttach(target.VisualChild, null); |
|||
|
|||
target.EndBatchUpdate(); |
|||
} |
|||
|
|||
|
|||
[Benchmark] |
|||
public void Apply_Remove_Control_Theme() |
|||
{ |
|||
var target = new TestControl(); |
|||
|
|||
target.BeginBatchUpdate(); |
|||
|
|||
_theme.TryAttach(target, null); |
|||
target.ApplyTemplate(); |
|||
_theme.TryAttach(target.VisualChild, null); |
|||
|
|||
target.EndBatchUpdate(); |
|||
|
|||
// Switching to another theme will cause the current theme to be removed but won't
|
|||
// immediately apply the new theme, so for the benefit of the benchmark it has the
|
|||
// effect of simply removing the theme.
|
|||
target.Theme = _otherTheme; |
|||
} |
|||
|
|||
[Benchmark] |
|||
public void Apply_Control_Theme_With_Styles() |
|||
{ |
|||
var target = new TestControl(); |
|||
|
|||
target.BeginBatchUpdate(); |
|||
|
|||
_theme.TryAttach(target, null); |
|||
target.ApplyTemplate(); |
|||
_theme.TryAttach(target.VisualChild, null); |
|||
|
|||
foreach (var style in _styles) |
|||
style.TryAttach(target, null); |
|||
|
|||
target.EndBatchUpdate(); |
|||
} |
|||
|
|||
[Benchmark] |
|||
public void Apply_Remove_Control_Theme_With_Styles() |
|||
{ |
|||
var target = new TestControl(); |
|||
|
|||
target.BeginBatchUpdate(); |
|||
|
|||
_theme.TryAttach(target, null); |
|||
target.ApplyTemplate(); |
|||
_theme.TryAttach(target.VisualChild, null); |
|||
|
|||
foreach (var style in _styles) |
|||
style.TryAttach(target, null); |
|||
|
|||
target.EndBatchUpdate(); |
|||
|
|||
// Switching to another theme will cause the current theme to be removed but won't
|
|||
// immediately apply the new theme, so for the benefit of the benchmark it has the
|
|||
// effect of simply removing the theme.
|
|||
target.Theme = _otherTheme; |
|||
} |
|||
|
|||
private static ControlTheme CreateControlTheme(IBrush background) |
|||
{ |
|||
return new ControlTheme(typeof(TestControl)) |
|||
{ |
|||
Setters = |
|||
{ |
|||
new Setter(TestControl.BackgroundProperty, Brushes.Transparent), |
|||
new Setter(TestControl.TemplateProperty, new FuncControlTemplate<TestControl>((_, x) => |
|||
new Border())), |
|||
}, |
|||
Children = |
|||
{ |
|||
new Style(x => x.Nesting().Template().OfType<Border>()) |
|||
{ |
|||
Setters = { new Setter(TestControl.BackgroundProperty, Brushes.Red), } |
|||
}, |
|||
new Style(x => x.Nesting().Class(":pointerover").Template().OfType<Border>()) |
|||
{ |
|||
Setters = { new Setter(TestControl.BackgroundProperty, Brushes.Green), } |
|||
}, |
|||
new Style(x => x.Nesting().Class(":pressed").Template().OfType<Border>()) |
|||
{ |
|||
Setters = { new Setter(TestControl.BackgroundProperty, Brushes.Blue), } |
|||
}, |
|||
} |
|||
}; |
|||
} |
|||
|
|||
private class TestControl : TemplatedControl |
|||
{ |
|||
public IStyleable VisualChild => (IStyleable)VisualChildren[0]; |
|||
} |
|||
|
|||
private class TestClass2 : Control |
|||
{ |
|||
} |
|||
} |
|||
} |
|||
Loading…
Reference in new issue