Refactor DataTemplate (XAML) to reduce duplication
I have the following datatemplates:
First One:
<DataTemplate DataType="{x:Type WIAssistant:DestinationField}">
<ContentControl Margin="5" MinWidth="60" MinHeight="70" >
<Border BorderThickness="2" BorderBrush="Black" CornerRadius="5">
<!--This text block seems un-needed. But it allows the whole control to be dragged. Without it only the border and the
text can be used to drag the control.-->
<TextBlock>
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<TextBlock FontWeight="Bold" TextWrapping="Wrap" HorizontalAlignment="Center" Margin="10"
开发者_如何学JAVA Text="{Binding DestField.Name}"/>
<TextBlock Grid.Row="1" TextWrapping="Wrap" HorizontalAlignment="Center" Margin="10"
Text="{Binding DestField.FieldType}"/>
</Grid>
</TextBlock>
</Border>
</ContentControl>
</DataTemplate>
Second One:
<DataTemplate DataType="{x:Type WIAssistant:SourceField}">
<ContentControl Margin="5" MinWidth="60" MinHeight="70" >
<Border BorderThickness="2" BorderBrush="Black" CornerRadius="5">
<!--This text block seems un-needed. But it allows the whole control to be dragged. Without it only the border and the
text can be used to drag the control.-->
<TextBlock>
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<TextBlock FontWeight="Bold" TextWrapping="Wrap" HorizontalAlignment="Center" Margin="10"
Text="{Binding SrcField.Name}"/>
<TextBlock Grid.Row="1" TextWrapping="Wrap" HorizontalAlignment="Center" Margin="10"
Text="{Binding SrcField.FieldType}"/>
</Grid>
</TextBlock>
</Border>
</ContentControl>
</DataTemplate>
They are 100% identical except for the stuff in the {}.
Is there a way to reduce the redundancy here? I fear I will make a change in one and forget to change the other.
As for your comment in the code - i think the problem can be solved by setting the Border
's Background
to Transparent
.
And to the main problem. You could probably have a style that describes the ContentControl
, which will include the DataTemplate for the type of the SrcField
and DestField
properties. Then bind in it to Name and FieldType, and use it the main 2 DataTemplates. Something like this:
<Style x:Key="SomeStyle" TargetType="ContentControl">
<Setter Property="Margin" Value="5" />
<Setter Property="MinWidth" Value="60" />
<Setter Property="MinHeight" Value="70" />
<Setter Property="ContentTemplate">
<Setter.Value>
<DataTemplate DataType=...> <!-- type of the `SrcField` and `DestField` properties -->
<Border Background="Transparent" BorderThickness="2" BorderBrush="Black" CornerRadius="5">
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<TextBlock FontWeight="Bold" TextWrapping="Wrap" HorizontalAlignment="Center" Margin="10"
Text="{Binding Name}"/>
<TextBlock Grid.Row="1" TextWrapping="Wrap" HorizontalAlignment="Center" Margin="10"
Text="{Binding FieldType}"/>
</Grid>
</Border>
</DataTemplate>
</Setter.Value>
</Setter>
</Style>
<DataTemplate DataType="{x:Type WIAssistant:DestinationField}">
<ContentControl
Style="{StaticResource SomeStyle}"
Content="{Binding DestField}"
/>
</DataTemplate>
<DataTemplate DataType="{x:Type WIAssistant:SourceField}">
<ContentControl
Style="{StaticResource SomeStyle}"
Content="{Binding SrcField}"
/>
</DataTemplate>
Yeah, I'd create a user control with public dependency properties called Name and FieldType and then use that control in your DataTemplates.
精彩评论