残念ながら、ヘッダーのExpanderTemplate内のContentPresenterは矢印と同じグリッドにあるため、HeaderTemplateを設定するだけでは役に立ちません。
Moleを使用すると、ToggleButtonに、円を表す楕円、矢印を表すPath、およびHeaderプロパティに設定した内容を表示するContentPresenterがあることがわかります。
エキスパンダーの実際のレイアウトがわかったので、それを変更する方法がいくつかあります。エキスパンダー用の新しいControlTemplateを作成するか、削除するパーツを取得して、それらを削除/非表示にします。
更新:Blendを入手しました。エキスパンダーのテンプレートを生成した後、各ToggleButtonスタイルから楕円とパスを通過して削除するだけです。
<Style x:Key="ExpanderHeaderFocusVisual">
<Setter Property="Control.Template">
<Setter.Value>
<ControlTemplate>
<Border>
<Rectangle SnapsToDevicePixels="true"
Margin="0"
Stroke="Black"
StrokeDashArray="1 2"
StrokeThickness="1" />
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
<Style x:Key="ExpanderDownHeaderStyle"
TargetType="{x:Type ToggleButton}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ToggleButton}">
<Border Padding="{TemplateBinding Padding}">
<Grid SnapsToDevicePixels="False"
Background="Transparent">
<ContentPresenter SnapsToDevicePixels="True"
HorizontalAlignment="Left"
VerticalAlignment="Center"
RecognizesAccessKey="True" />
</Grid>
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
<Style x:Key="ExpanderRightHeaderStyle"
TargetType="{x:Type ToggleButton}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ToggleButton}">
<Border Padding="{TemplateBinding Padding}">
<Grid SnapsToDevicePixels="False"
Background="Transparent">
<ContentPresenter SnapsToDevicePixels="True"
HorizontalAlignment="Center"
VerticalAlignment="Top"
RecognizesAccessKey="True" />
</Grid>
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
<Style x:Key="ExpanderUpHeaderStyle"
TargetType="{x:Type ToggleButton}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ToggleButton}">
<Border Padding="{TemplateBinding Padding}">
<Grid SnapsToDevicePixels="False"
Background="Transparent">
<ContentPresenter SnapsToDevicePixels="True"
HorizontalAlignment="Left"
VerticalAlignment="Center"
RecognizesAccessKey="True" />
</Grid>
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
<Style x:Key="ExpanderLeftHeaderStyle"
TargetType="{x:Type ToggleButton}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type ToggleButton}">
<Border Padding="{TemplateBinding Padding}">
<Grid SnapsToDevicePixels="False"
Background="Transparent">
<ContentPresenter SnapsToDevicePixels="True"
HorizontalAlignment="Center"
VerticalAlignment="Top"
RecognizesAccessKey="True" />
</Grid>
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
<Style x:Key="ArrowlessExpanderTemplate"
TargetType="{x:Type Expander}">
<Setter Property="Foreground"
Value="{DynamicResource {x:Static SystemColors.ControlTextBrushKey}}" />
<Setter Property="Background"
Value="Transparent" />
<Setter Property="HorizontalContentAlignment"
Value="Stretch" />
<Setter Property="VerticalContentAlignment"
Value="Stretch" />
<Setter Property="BorderBrush"
Value="Transparent" />
<Setter Property="BorderThickness"
Value="1" />
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type Expander}">
<Border SnapsToDevicePixels="true"
Background="{TemplateBinding Background}"
BorderBrush="{TemplateBinding BorderBrush}"
BorderThickness="{TemplateBinding BorderThickness}"
CornerRadius="3">
<DockPanel>
<ToggleButton FontFamily="{TemplateBinding FontFamily}"
FontSize="{TemplateBinding FontSize}"
FontStretch="{TemplateBinding FontStretch}"
FontStyle="{TemplateBinding FontStyle}"
FontWeight="{TemplateBinding FontWeight}"
Foreground="{TemplateBinding Foreground}"
HorizontalContentAlignment="{TemplateBinding HorizontalContentAlignment}"
Padding="{TemplateBinding Padding}"
VerticalContentAlignment="{TemplateBinding VerticalContentAlignment}"
FocusVisualStyle="{StaticResource ExpanderHeaderFocusVisual}"
Margin="1"
MinHeight="0"
MinWidth="0"
x:Name="HeaderSite"
Style="{StaticResource ExpanderDownHeaderStyle}"
Content="{TemplateBinding Header}"
ContentTemplate="{TemplateBinding HeaderTemplate}"
ContentTemplateSelector="{TemplateBinding HeaderTemplateSelector}"
DockPanel.Dock="Top"
IsChecked="{Binding Path=IsExpanded, Mode=TwoWay, RelativeSource={RelativeSource TemplatedParent}}" />
<ContentPresenter Focusable="false"
Visibility="Collapsed"
HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}"
Margin="{TemplateBinding Padding}"
x:Name="ExpandSite"
VerticalAlignment="{TemplateBinding VerticalContentAlignment}"
DockPanel.Dock="Bottom" />
</DockPanel>
</Border>
<ControlTemplate.Triggers>
<Trigger Property="IsExpanded"
Value="true">
<Setter Property="Visibility"
TargetName="ExpandSite"
Value="Visible" />
</Trigger>
<Trigger Property="ExpandDirection"
Value="Right">
<Setter Property="DockPanel.Dock"
TargetName="ExpandSite"
Value="Right" />
<Setter Property="DockPanel.Dock"
TargetName="HeaderSite"
Value="Left" />
<Setter Property="Style"
TargetName="HeaderSite"
Value="{StaticResource ExpanderRightHeaderStyle}" />
</Trigger>
<Trigger Property="ExpandDirection"
Value="Up">
<Setter Property="DockPanel.Dock"
TargetName="ExpandSite"
Value="Top" />
<Setter Property="DockPanel.Dock"
TargetName="HeaderSite"
Value="Bottom" />
<Setter Property="Style"
TargetName="HeaderSite"
Value="{StaticResource ExpanderUpHeaderStyle}" />
</Trigger>
<Trigger Property="ExpandDirection"
Value="Left">
<Setter Property="DockPanel.Dock"
TargetName="ExpandSite"
Value="Left" />
<Setter Property="DockPanel.Dock"
TargetName="HeaderSite"
Value="Right" />
<Setter Property="Style"
TargetName="HeaderSite"
Value="{StaticResource ExpanderLeftHeaderStyle}" />
</Trigger>
<Trigger Property="IsEnabled"
Value="false">
<Setter Property="Foreground"
Value="{DynamicResource {x:Static SystemColors.GrayTextBrushKey}}" />
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
また、AttachedPropertyを作成し、代わりに矢印と円の部分を折りたたむように設定することもできます。
AttachedPropertyは次のとおりです。
public class AttachedProperties
{
#region HideExpanderArrow AttachedProperty
[AttachedPropertyBrowsableForType(typeof(Expander))]
public static bool GetHideExpanderArrow(DependencyObject obj)
{
return (bool)obj.GetValue(HideExpanderArrowProperty);
}
[AttachedPropertyBrowsableForType(typeof(Expander))]
public static void SetHideExpanderArrow(DependencyObject obj, bool value)
{
obj.SetValue(HideExpanderArrowProperty, value);
}
// Using a DependencyProperty as the backing store for HideExpanderArrow. This enables animation, styling, binding, etc...
public static readonly DependencyProperty HideExpanderArrowProperty =
DependencyProperty.RegisterAttached("HideExpanderArrow", typeof(bool), typeof(AttachedProperties), new UIPropertyMetadata(false, OnHideExpanderArrowChanged));
private static void OnHideExpanderArrowChanged(DependencyObject o, DependencyPropertyChangedEventArgs e)
{
Expander expander = (Expander)o;
if (expander.IsLoaded)
{
UpdateExpanderArrow(expander, (bool)e.NewValue);
}
else
{
expander.Loaded += new RoutedEventHandler((x, y) => UpdateExpanderArrow(expander, (bool)e.NewValue));
}
}
private static void UpdateExpanderArrow(Expander expander, bool visible)
{
Grid headerGrid =
VisualTreeHelper.GetChild(
VisualTreeHelper.GetChild(
VisualTreeHelper.GetChild(
VisualTreeHelper.GetChild(
VisualTreeHelper.GetChild(
expander,
0),
0),
0),
0),
0) as Grid;
headerGrid.Children[0].Visibility = visible ? Visibility.Collapsed : Visibility.Visible; // Hide or show the Ellipse
headerGrid.Children[1].Visibility = visible ? Visibility.Collapsed : Visibility.Visible; // Hide or show the Arrow
headerGrid.Children[2].SetValue(Grid.ColumnProperty, visible ? 0 : 1); // If the Arrow is not visible, then shift the Header Content to the first column.
headerGrid.Children[2].SetValue(Grid.ColumnSpanProperty, visible ? 2 : 1); // If the Arrow is not visible, then set the Header Content to span both rows.
headerGrid.Children[2].SetValue(ContentPresenter.MarginProperty, visible ? new Thickness(0) : new Thickness(4,0,0,0)); // If the Arrow is not visible, then remove the margin from the Content.
}
#endregion
}
名前でコントロールを検索するのではなく、「矢印」とヘッダーコンテンツを含むグリッドに直接移動しているだけなので、エキスパンダーを別のテンプレートに再テンプレート化する場合、これはそのままでは機能しません。構造。含まれているグリッドを見つけたら、矢印と円を折りたたむように設定し、ヘッダーコンテンツが左端まで移動していることを確認します。
添付プロパティを使用するには、XAMLの要素に設定するだけです。
<StackPanel>
<Expander x:Name="uiExpander"
local:AttachedProperties.HideExpanderArrow="True">
<Expander.Header>
<Border>
<DockPanel Width="Auto">
<TextBlock DockPanel.Dock="Left"
FontSize="16"
Text="IronRuby in Action!" />
</DockPanel>
</Border>
</Expander.Header>
<Expander.Content>
<TextBlock Text="This is the decriprion!" />
</Expander.Content>
</Expander>
<Button Content="Click to Show/Hide Expander Arrow"
Click="Button_Click" />
</StackPanel>
そしてコードで:
void Button_Click(object sender, RoutedEventArgs e)
{
uiExpander.SetValue(
AttachedProperties.HideExpanderArrowProperty,
!(bool)uiExpander.GetValue(AttachedProperties.HideExpanderArrowProperty));
}