Skip to content

Commit 99c1eff

Browse files
committed
chore: add avalonia Expander demo.
1 parent 840493b commit 99c1eff

File tree

7 files changed

+671
-12
lines changed

7 files changed

+671
-12
lines changed

src/Avalonia/HandyControlDemo_Avalonia/UserControl/Styles/ExpanderDemo.axaml

+341
Large diffs are not rendered by default.
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
namespace HandyControlDemo.UserControl;
2+
3+
public partial class ExpanderDemo : Avalonia.Controls.UserControl
4+
{
5+
public ExpanderDemo()
6+
{
7+
InitializeComponent();
8+
}
9+
}
10+

src/Avalonia/HandyControl_Avalonia/Themes/Basic/Converters.axaml

+1
Original file line numberDiff line numberDiff line change
@@ -6,5 +6,6 @@
66
<converter:BorderCircularConverter x:Key="BorderCircularConverter" />
77
<converter:BorderCircularClipConverter x:Key="BorderCircularClipConverter" />
88
<converter:GeometrySpacingConverter x:Key="GeometrySpacingConverter" />
9+
<converter:CornerRadiusSplitConverter x:Key="CornerRadiusSplitConverter" />
910

1011
</ResourceDictionary>
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,266 @@
1+
<ResourceDictionary xmlns="https://github.com/avaloniaui"
2+
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
3+
xmlns:hc="clr-namespace:HandyControl.Controls">
4+
<ControlTemplate x:Key="ExpanderLeftTemplate"
5+
TargetType="Expander">
6+
<Grid ColumnDefinitions="*, Auto">
7+
<ToggleButton Grid.Column="1"
8+
VerticalAlignment="Stretch"
9+
VerticalContentAlignment="Stretch"
10+
Focusable="False"
11+
Padding="0,0,0,10"
12+
BorderBrush="{TemplateBinding BorderBrush}"
13+
BorderThickness="{TemplateBinding BorderThickness}"
14+
Background="{TemplateBinding Background}"
15+
Foreground="{TemplateBinding Foreground}"
16+
IsChecked="{Binding IsExpanded, Mode=TwoWay, RelativeSource={RelativeSource TemplatedParent}}"
17+
MinWidth="{TemplateBinding MinWidth}"
18+
Theme="{StaticResource ToggleButtonCustom}">
19+
<LayoutTransformControl>
20+
<LayoutTransformControl.LayoutTransform>
21+
<RotateTransform Angle="-90" />
22+
</LayoutTransformControl.LayoutTransform>
23+
<Grid ColumnDefinitions="*,30">
24+
<ContentPresenter Content="{TemplateBinding Header}"
25+
HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}"
26+
VerticalAlignment="{TemplateBinding VerticalContentAlignment}" />
27+
<Path x:Name="PathArrow"
28+
IsHitTestVisible="False"
29+
Grid.Column="1"
30+
Stretch="Uniform"
31+
Fill="{TemplateBinding Foreground}"
32+
Width="12"
33+
VerticalAlignment="{TemplateBinding VerticalContentAlignment}"
34+
HorizontalAlignment="Center" />
35+
</Grid>
36+
</LayoutTransformControl>
37+
</ToggleButton>
38+
<ContentPresenter Name="PART_ContentPresenter"
39+
IsVisible="{TemplateBinding IsExpanded}"
40+
Content="{TemplateBinding Content}"
41+
ContentTemplate="{TemplateBinding ContentTemplate}"
42+
Grid.Column="0" />
43+
</Grid>
44+
</ControlTemplate>
45+
46+
<ControlTemplate x:Key="ExpanderUpTemplate"
47+
TargetType="Expander">
48+
<Grid RowDefinitions="*,Auto">
49+
<ToggleButton Grid.Row="1"
50+
HorizontalAlignment="Stretch"
51+
HorizontalContentAlignment="Stretch"
52+
Focusable="False"
53+
Padding="10,0,0,0"
54+
BorderBrush="{TemplateBinding BorderBrush}"
55+
BorderThickness="{TemplateBinding BorderThickness}"
56+
Background="{TemplateBinding Background}"
57+
Foreground="{TemplateBinding Foreground}"
58+
IsChecked="{Binding IsExpanded, Mode=TwoWay, RelativeSource={RelativeSource TemplatedParent}}"
59+
MinHeight="{TemplateBinding MinHeight}"
60+
Theme="{StaticResource ToggleButtonCustom}">
61+
<Grid ColumnDefinitions="*,30">
62+
<ContentPresenter Content="{TemplateBinding Header}"
63+
HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}"
64+
VerticalAlignment="{TemplateBinding VerticalContentAlignment}" />
65+
<Path x:Name="PathArrow"
66+
IsHitTestVisible="False"
67+
Grid.Column="1"
68+
Stretch="Uniform"
69+
Fill="{TemplateBinding Foreground}"
70+
Width="12"
71+
VerticalAlignment="{TemplateBinding VerticalContentAlignment}"
72+
HorizontalAlignment="Center" />
73+
</Grid>
74+
</ToggleButton>
75+
<ContentPresenter x:Name="PART_ContentPresenter"
76+
IsVisible="{TemplateBinding IsExpanded}"
77+
Content="{TemplateBinding Content}"
78+
ContentTemplate="{TemplateBinding ContentTemplate}"
79+
Grid.Row="0" />
80+
</Grid>
81+
</ControlTemplate>
82+
83+
<ControlTemplate x:Key="ExpanderRightTemplate"
84+
TargetType="Expander">
85+
<Grid ColumnDefinitions="Auto,*">
86+
<ToggleButton VerticalAlignment="Stretch"
87+
VerticalContentAlignment="Stretch"
88+
Focusable="False"
89+
Padding="0,0,0,10"
90+
BorderBrush="{TemplateBinding BorderBrush}"
91+
BorderThickness="{TemplateBinding BorderThickness}"
92+
Background="{TemplateBinding Background}"
93+
Foreground="{TemplateBinding Foreground}"
94+
IsChecked="{Binding IsExpanded, Mode=TwoWay, RelativeSource={RelativeSource TemplatedParent}}"
95+
MinWidth="{TemplateBinding MinWidth}"
96+
Theme="{StaticResource ToggleButtonCustom}">
97+
<LayoutTransformControl>
98+
<LayoutTransformControl.LayoutTransform>
99+
<RotateTransform Angle="-90" />
100+
</LayoutTransformControl.LayoutTransform>
101+
<Grid ColumnDefinitions="*,30">
102+
<ContentPresenter Content="{TemplateBinding Header}"
103+
HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}"
104+
VerticalAlignment="{TemplateBinding VerticalContentAlignment}" />
105+
<Path x:Name="PathArrow"
106+
IsHitTestVisible="False"
107+
Grid.Column="1"
108+
Stretch="Uniform"
109+
Fill="{TemplateBinding Foreground}"
110+
Width="12"
111+
VerticalAlignment="{TemplateBinding VerticalContentAlignment}"
112+
HorizontalAlignment="Center" />
113+
</Grid>
114+
</LayoutTransformControl>
115+
</ToggleButton>
116+
<ContentPresenter x:Name="PART_ContentPresenter"
117+
IsVisible="{TemplateBinding IsExpanded}"
118+
Content="{TemplateBinding Content}"
119+
ContentTemplate="{TemplateBinding ContentTemplate}"
120+
Grid.Column="1" />
121+
</Grid>
122+
</ControlTemplate>
123+
124+
<ControlTemplate x:Key="ExpanderDownTemplate"
125+
TargetType="Expander">
126+
<Grid RowDefinitions="Auto,*">
127+
<ToggleButton HorizontalAlignment="Stretch"
128+
HorizontalContentAlignment="Stretch"
129+
Focusable="False"
130+
Padding="10,0,0,0"
131+
BorderBrush="{TemplateBinding BorderBrush}"
132+
BorderThickness="{TemplateBinding BorderThickness}"
133+
Background="{TemplateBinding Background}"
134+
Foreground="{TemplateBinding Foreground}"
135+
IsChecked="{Binding IsExpanded, Mode=TwoWay, RelativeSource={RelativeSource TemplatedParent}}"
136+
MinHeight="{TemplateBinding MinHeight}"
137+
Theme="{StaticResource ToggleButtonCustom}">
138+
<Grid ColumnDefinitions="*,30">
139+
<ContentPresenter Content="{TemplateBinding Header}"
140+
HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}"
141+
VerticalAlignment="{TemplateBinding VerticalContentAlignment}" />
142+
<Path x:Name="PathArrow"
143+
IsHitTestVisible="False"
144+
Grid.Column="1"
145+
Stretch="Uniform"
146+
Fill="{TemplateBinding Foreground}"
147+
Width="12"
148+
VerticalAlignment="{TemplateBinding VerticalContentAlignment}"
149+
HorizontalAlignment="Center" />
150+
</Grid>
151+
</ToggleButton>
152+
<ContentPresenter x:Name="PART_ContentPresenter"
153+
IsVisible="{TemplateBinding IsExpanded}"
154+
Content="{TemplateBinding Content}"
155+
ContentTemplate="{TemplateBinding ContentTemplate}"
156+
Grid.Row="1" />
157+
</Grid>
158+
</ControlTemplate>
159+
160+
<ControlTheme x:Key="ExpanderBaseStyle"
161+
TargetType="Expander">
162+
<Setter Property="Foreground"
163+
Value="{DynamicResource PrimaryTextBrush}" />
164+
<Setter Property="Background"
165+
Value="{DynamicResource SecondaryRegionBrush}" />
166+
<Setter Property="HorizontalContentAlignment"
167+
Value="Left" />
168+
<Setter Property="VerticalContentAlignment"
169+
Value="Center" />
170+
<Setter Property="BorderBrush"
171+
Value="{DynamicResource BorderBrush}" />
172+
<Setter Property="BorderThickness"
173+
Value="1" />
174+
<Setter Property="MinHeight"
175+
Value="{StaticResource DefaultControlHeight}" />
176+
<Setter Property="MinWidth"
177+
Value="{StaticResource DefaultControlHeight}" />
178+
<Setter Property="hc:BorderElement.CornerRadius"
179+
Value="{StaticResource DefaultCornerRadius}" />
180+
181+
<Style Selector="^:left">
182+
<Setter Property="Template"
183+
Value="{StaticResource ExpanderLeftTemplate}" />
184+
</Style>
185+
186+
<Style Selector="^:up">
187+
<Setter Property="Template"
188+
Value="{StaticResource ExpanderUpTemplate}" />
189+
</Style>
190+
191+
<Style Selector="^:right">
192+
<Setter Property="Template"
193+
Value="{StaticResource ExpanderRightTemplate}" />
194+
</Style>
195+
196+
<Style Selector="^:down">
197+
<Setter Property="Template"
198+
Value="{StaticResource ExpanderDownTemplate}" />
199+
</Style>
200+
201+
<Style Selector="^[IsExpanded=True]">
202+
<Style Selector="^:left /template/ ToggleButton">
203+
<Setter Property="hc:BorderElement.CornerRadius"
204+
Value="{Binding Path=(hc:BorderElement.CornerRadius),RelativeSource={RelativeSource TemplatedParent}, Converter={StaticResource CornerRadiusSplitConverter}, ConverterParameter='0,1,1,0'}">
205+
</Setter>
206+
</Style>
207+
<Style Selector="^:up /template/ ToggleButton">
208+
<Setter Property="hc:BorderElement.CornerRadius"
209+
Value="{Binding Path=(hc:BorderElement.CornerRadius),RelativeSource={RelativeSource TemplatedParent}, Converter={StaticResource CornerRadiusSplitConverter}, ConverterParameter='0,0,1,1'}">
210+
</Setter>
211+
</Style>
212+
<Style Selector="^:right /template/ ToggleButton">
213+
<Setter Property="hc:BorderElement.CornerRadius"
214+
Value="{Binding Path=(hc:BorderElement.CornerRadius),RelativeSource={RelativeSource TemplatedParent}, Converter={StaticResource CornerRadiusSplitConverter}, ConverterParameter='1,0,0,1'}">
215+
</Setter>
216+
</Style>
217+
<Style Selector="^:down /template/ ToggleButton">
218+
<Setter Property="hc:BorderElement.CornerRadius"
219+
Value="{Binding Path=(hc:BorderElement.CornerRadius),RelativeSource={RelativeSource TemplatedParent}, Converter={StaticResource CornerRadiusSplitConverter}, ConverterParameter='1,1,0,0'}">
220+
</Setter>
221+
</Style>
222+
<Style Selector="^:left /template/ Path#PathArrow, ^:up /template/ Path#PathArrow">
223+
<Setter Property="Data"
224+
Value="{StaticResource DownGeometry}" />
225+
</Style>
226+
<Style Selector="^:right /template/ Path#PathArrow, ^:down /template/ Path#PathArrow">
227+
<Setter Property="Data"
228+
Value="{StaticResource UpGeometry}" />
229+
</Style>
230+
</Style>
231+
232+
<Style Selector="^[IsExpanded=False]">
233+
<Style Selector="^ /template/ ToggleButton">
234+
<Setter Property="hc:BorderElement.CornerRadius"
235+
Value="{Binding Path=(hc:BorderElement.CornerRadius),RelativeSource={RelativeSource TemplatedParent}, Converter={StaticResource CornerRadiusSplitConverter}, ConverterParameter='1,1,1,1'}">
236+
</Setter>
237+
</Style>
238+
<Style Selector="^:left /template/ Path#PathArrow, ^:up /template/ Path#PathArrow">
239+
<Setter Property="Data"
240+
Value="{StaticResource UpGeometry}" />
241+
</Style>
242+
<Style Selector="^:right /template/ Path#PathArrow, ^:down /template/ Path#PathArrow">
243+
<Setter Property="Data"
244+
Value="{StaticResource DownGeometry}" />
245+
</Style>
246+
</Style>
247+
248+
<Style Selector="^:disabled">
249+
<Setter Property="Opacity"
250+
Value="0.4" />
251+
</Style>
252+
</ControlTheme>
253+
254+
<ControlTheme x:Key="{x:Type Expander}"
255+
BasedOn="{StaticResource ExpanderBaseStyle}"
256+
TargetType="Expander" />
257+
258+
<ControlTheme x:Key="Expander.Small"
259+
BasedOn="{StaticResource ExpanderBaseStyle}"
260+
TargetType="Expander">
261+
<Setter Property="MinHeight"
262+
Value="20" />
263+
<Setter Property="MinWidth"
264+
Value="20" />
265+
</ControlTheme>
266+
</ResourceDictionary>

src/Avalonia/HandyControl_Avalonia/Themes/Theme.axaml

+1
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,7 @@
3333
<MergeResourceInclude Source="/Themes/Styles/ListBox.axaml" />
3434
<MergeResourceInclude Source="/Themes/Styles/Label.axaml" />
3535
<MergeResourceInclude Source="/Themes/Styles/Slider.axaml" />
36+
<MergeResourceInclude Source="/Themes/Styles/Expander.axaml" />
3637
</ResourceDictionary.MergedDictionaries>
3738
</ResourceDictionary>
3839
</Styles.Resources>
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
using System;
2+
using System.Globalization;
3+
using Avalonia;
4+
using Avalonia.Data.Converters;
5+
6+
namespace HandyControl.Tools.Converter;
7+
8+
public class CornerRadiusSplitConverter : IValueConverter
9+
{
10+
public object? Convert(object? value, Type targetType, object? parameter, CultureInfo culture)
11+
{
12+
if (value is not CornerRadius cornerRadius)
13+
{
14+
return value;
15+
}
16+
17+
if (parameter is not string str)
18+
{
19+
return value;
20+
}
21+
22+
string[] arr = str.Split(',');
23+
if (arr.Length != 4)
24+
{
25+
return cornerRadius;
26+
}
27+
28+
return new CornerRadius(
29+
arr[0].Trim().Equals("1") ? cornerRadius.TopLeft : 0,
30+
arr[1].Trim().Equals("1") ? cornerRadius.TopRight : 0,
31+
arr[2].Trim().Equals("1") ? cornerRadius.BottomRight : 0,
32+
arr[3].Trim().Equals("1") ? cornerRadius.BottomLeft : 0);
33+
}
34+
35+
public object ConvertBack(object? value, Type targetType, object? parameter, CultureInfo culture) =>
36+
throw new NotImplementedException();
37+
}

src/Shared/HandyControl_Shared/Tools/Converter/CornerRadiusSplitConverter.cs

+15-12
Original file line numberDiff line numberDiff line change
@@ -9,21 +9,24 @@ public class CornerRadiusSplitConverter : IValueConverter
99
{
1010
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
1111
{
12-
if (value is CornerRadius cornerRadius)
12+
if (value is not CornerRadius cornerRadius)
1313
{
14-
if (parameter is string str)
15-
{
16-
var arr = str.Split(',');
17-
if (arr.Length != 4) return cornerRadius;
14+
return value;
15+
}
1816

19-
return new CornerRadius(
20-
arr[0].Equals("1") ? cornerRadius.TopLeft : 0,
21-
arr[1].Equals("1") ? cornerRadius.TopRight : 0,
22-
arr[2].Equals("1") ? cornerRadius.BottomRight : 0,
23-
arr[3].Equals("1") ? cornerRadius.BottomLeft : 0);
24-
}
17+
if (parameter is not string str)
18+
{
19+
return value;
2520
}
26-
return value;
21+
22+
var arr = str.Split(',');
23+
if (arr.Length != 4) return cornerRadius;
24+
25+
return new CornerRadius(
26+
arr[0].Trim().Equals("1") ? cornerRadius.TopLeft : 0,
27+
arr[1].Trim().Equals("1") ? cornerRadius.TopRight : 0,
28+
arr[2].Trim().Equals("1") ? cornerRadius.BottomRight : 0,
29+
arr[3].Trim().Equals("1") ? cornerRadius.BottomLeft : 0);
2730
}
2831

2932
public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)

0 commit comments

Comments
 (0)