0

我正在使用一个 UserControl,其中内部的主控件是一个数据网格。一切正常。但是,我的一些代码行是多余的,因为我在 48 列中的每一列中都实现了相同的触发器。

如何为以下代码片段的 datagridtemplatecolumn 制作模板?每列中唯一不同的是绑定属性。所有的触发器和格式都是一样的。

我会很感激你的帮助!

<DataGridTemplateColumn Header="5" MaxWidth="10">
    <DataGridTemplateColumn.CellTemplate>
        <DataTemplate>
            <TextBlock
                Background="{Binding _5, Converter={StaticResource  ResourceKey=hourSlotColorConverter}, UpdateSourceTrigger=PropertyChanged}"
                Margin="-1">
                <i:Interaction.Triggers>
                    <i:EventTrigger EventName="PreviewMouseLeftButtonDown">
                        <i:InvokeCommandAction
                            Command="{Binding RelativeSource={RelativeSource AncestorType={x:Type DataGrid}},
                                                                    Path=DataContext.StartCellCommand}">
                            <i:InvokeCommandAction.CommandParameter>
                                <MultiBinding Converter="{StaticResource dgInfoConverter}">
                                    <Binding Path="Column"
                                             RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                    <Binding Path="DataContext"
                                             RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                </MultiBinding>
                            </i:InvokeCommandAction.CommandParameter>
                        </i:InvokeCommandAction>
                    </i:EventTrigger>
                    <i:EventTrigger EventName="PreviewMouseLeftButtonUp">
                        <i:InvokeCommandAction
                            Command="{Binding RelativeSource={RelativeSource AncestorType={x:Type DataGrid}},
                                            Path=DataContext.LastCellCommand}">
                            <i:InvokeCommandAction.CommandParameter>
                                <MultiBinding Converter="{StaticResource dgInfoConverter}">
                                    <Binding Path="Column"
                                             RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                    <Binding Path="DataContext"
                                             RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                </MultiBinding>
                            </i:InvokeCommandAction.CommandParameter>
                        </i:InvokeCommandAction>
                    </i:EventTrigger>
                    <i:EventTrigger EventName="MouseMove">
                        <i:InvokeCommandAction
                            Command="{Binding RelativeSource={RelativeSource AncestorType={x:Type DataGrid}},
                                                                    Path=DataContext.MouseDragCom}">
                            <i:InvokeCommandAction.CommandParameter>
                                <MultiBinding Converter="{StaticResource dgInfoConverter}">
                                    <Binding Path="Column"
                                             RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                    <Binding Path="DataContext"
                                             RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                </MultiBinding>
                            </i:InvokeCommandAction.CommandParameter>
                        </i:InvokeCommandAction>
                    </i:EventTrigger>
                </i:Interaction.Triggers>
            </TextBlock>
        </DataTemplate>
    </DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>

<DataGridTemplateColumn Header="" MaxWidth="10">
    <DataGridTemplateColumn.CellTemplate>
        <DataTemplate>
            <TextBlock
                Background="{Binding _5_5, Converter={StaticResource  ResourceKey=hourSlotColorConverter}, UpdateSourceTrigger=PropertyChanged}"
                Margin="-1">
                <i:Interaction.Triggers>
                    <i:EventTrigger EventName="PreviewMouseLeftButtonDown">
                        <i:InvokeCommandAction
                            Command="{Binding RelativeSource={RelativeSource AncestorType={x:Type DataGrid}},
                                                                    Path=DataContext.StartCellCommand}">
                            <i:InvokeCommandAction.CommandParameter>
                                <MultiBinding Converter="{StaticResource dgInfoConverter}">
                                    <Binding Path="Column"
                                             RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                    <Binding Path="DataContext"
                                             RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                </MultiBinding>
                            </i:InvokeCommandAction.CommandParameter>
                        </i:InvokeCommandAction>
                    </i:EventTrigger>
                    <i:EventTrigger EventName="PreviewMouseLeftButtonUp">
                        <i:InvokeCommandAction
                            Command="{Binding RelativeSource={RelativeSource AncestorType={x:Type DataGrid}},
                                            Path=DataContext.LastCellCommand}">
                            <i:InvokeCommandAction.CommandParameter>
                                <MultiBinding Converter="{StaticResource dgInfoConverter}">
                                    <Binding Path="Column"
                                             RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                    <Binding Path="DataContext"
                                             RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                </MultiBinding>
                            </i:InvokeCommandAction.CommandParameter>
                        </i:InvokeCommandAction>
                    </i:EventTrigger>
                    <i:EventTrigger EventName="MouseMove">
                        <i:InvokeCommandAction
                            Command="{Binding RelativeSource={RelativeSource AncestorType={x:Type DataGrid}},
                                                                    Path=DataContext.MouseDragCom}">
                            <i:InvokeCommandAction.CommandParameter>
                                <MultiBinding Converter="{StaticResource dgInfoConverter}">
                                    <Binding Path="Column"
                                             RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                    <Binding Path="DataContext"
                                             RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                </MultiBinding>
                            </i:InvokeCommandAction.CommandParameter>
                        </i:InvokeCommandAction>
                    </i:EventTrigger>
                </i:Interaction.Triggers>
            </TextBlock>
        </DataTemplate>
    </DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>

<DataGridTemplateColumn Header="6" MaxWidth="10">
    <DataGridTemplateColumn.CellTemplate>
        <DataTemplate>
            <TextBlock
                Background="{Binding _6, Converter={StaticResource  ResourceKey=hourSlotColorConverter}, UpdateSourceTrigger=PropertyChanged}"
                Margin="-1">
                <i:Interaction.Triggers>
                    <i:EventTrigger EventName="PreviewMouseLeftButtonDown">
                        <i:InvokeCommandAction
                            Command="{Binding RelativeSource={RelativeSource AncestorType={x:Type DataGrid}},
                                                                    Path=DataContext.StartCellCommand}">
                            <i:InvokeCommandAction.CommandParameter>
                                <MultiBinding Converter="{StaticResource dgInfoConverter}">
                                    <Binding Path="Column"
                                             RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                    <Binding Path="DataContext"
                                             RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                </MultiBinding>
                            </i:InvokeCommandAction.CommandParameter>
                        </i:InvokeCommandAction>
                    </i:EventTrigger>
                    <i:EventTrigger EventName="PreviewMouseLeftButtonUp">
                        <i:InvokeCommandAction
                            Command="{Binding RelativeSource={RelativeSource AncestorType={x:Type DataGrid}},
                                            Path=DataContext.LastCellCommand}">
                            <i:InvokeCommandAction.CommandParameter>
                                <MultiBinding Converter="{StaticResource dgInfoConverter}">
                                    <Binding Path="Column"
                                             RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                    <Binding Path="DataContext"
                                             RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                </MultiBinding>
                            </i:InvokeCommandAction.CommandParameter>
                        </i:InvokeCommandAction>
                    </i:EventTrigger>
                    <i:EventTrigger EventName="MouseMove">
                        <i:InvokeCommandAction
                            Command="{Binding RelativeSource={RelativeSource AncestorType={x:Type DataGrid}},
                                                                    Path=DataContext.MouseDragCom}">
                            <i:InvokeCommandAction.CommandParameter>
                                <MultiBinding Converter="{StaticResource dgInfoConverter}">
                                    <Binding Path="Column"
                                             RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                    <Binding Path="DataContext"
                                             RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                </MultiBinding>
                            </i:InvokeCommandAction.CommandParameter>
                        </i:InvokeCommandAction>
                    </i:EventTrigger>
                </i:Interaction.Triggers>
            </TextBlock>
        </DataTemplate>
    </DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>

编辑

因此,我按照 Sheridan 的建议进行了一些修改,以使其更短更简单。虽然我们的项目负责人之前建议过这种方法,但在 Sheridan 提出意见之前,我不知道如何实施。给他点赞

这是我们使用的 UserControl 的代码。它包含的触发器与我们在上面的原始代码中使用的触发器完全相同:

<UserControl x:Class="Widget5.View.DGInfo"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
             xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
             xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactivity"
             xmlns:converter="clr-namespace:Widget5.Converter"  
             xmlns:dg="clr-namespace:Widget5.View"
             mc:Ignorable="d" 
             d:DesignHeight="20" d:DesignWidth="20">

    <UserControl.Resources>
        <converter:DataGridInfoToParamConverter x:Key="dgInfoConverter" />
    </UserControl.Resources>

    <TextBlock  Background="{Binding Background, RelativeSource={RelativeSource AncestorType={x:Type dg:DGInfo}}}" Margin="-1">
        <i:Interaction.Triggers>
            <i:EventTrigger EventName="PreviewMouseLeftButtonDown">
                                        <i:InvokeCommandAction Command="{Binding RelativeSource={RelativeSource AncestorType={x:Type DataGrid}},
                                                                Path=DataContext.StartCellCommand}" >
                                            <i:InvokeCommandAction.CommandParameter>
                                                <MultiBinding Converter="{StaticResource dgInfoConverter}">
                                                    <Binding Path="Column" RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                                    <Binding Path="DataContext" RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                                </MultiBinding>
                                            </i:InvokeCommandAction.CommandParameter>
                                        </i:InvokeCommandAction>
                                    </i:EventTrigger>
                                    <i:EventTrigger EventName="PreviewMouseLeftButtonUp">
                                        <i:InvokeCommandAction Command="{Binding RelativeSource={RelativeSource AncestorType={x:Type DataGrid}},
                                        Path=DataContext.LastCellCommand}" >
                                            <i:InvokeCommandAction.CommandParameter>
                                                <MultiBinding Converter="{StaticResource dgInfoConverter}">
                                                    <Binding Path="Column" RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                                    <Binding Path="DataContext" RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                                </MultiBinding>
                                            </i:InvokeCommandAction.CommandParameter>
                                        </i:InvokeCommandAction>
                                    </i:EventTrigger>
                                    <i:EventTrigger EventName="MouseMove">
                                        <i:InvokeCommandAction Command="{Binding RelativeSource={RelativeSource AncestorType={x:Type DataGrid}},
                                                                Path=DataContext.MouseDragCom}" >
                                            <i:InvokeCommandAction.CommandParameter>
                                                <MultiBinding Converter="{StaticResource dgInfoConverter}">
                                                    <Binding Path="Column" RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                                    <Binding Path="DataContext" RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                                </MultiBinding>
                                            </i:InvokeCommandAction.CommandParameter>
                                        </i:InvokeCommandAction>
                                    </i:EventTrigger>
        </i:Interaction.Triggers>
        </TextBlock>
</UserControl>

在 DataGridTemplateColumn 本身上,我们只是添加了 UserControl(DGInfo) 并像以前一样设置它的背景。因此节省了数千行。

<DataGrid ...>
...
<DataGridTemplateColumn Header="6" MaxWidth="10">
   <DataGridTemplateColumn.CellTemplate>
       <DataTemplate>
          <View:DGInfo Background="{Binding _6, Converter={StaticResource  ResourceKey=hourSlotColorConverter}, UpdateSourceTrigger=PropertyChanged}"/>
          </DataTemplate>
       </DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>
...
</DataGrid>
4

1 回答 1

0

如果您DataTemplate的 s 完全相同,则只需将一个放入一个Resources部分,然后简单地引用它:

<DataGrid.Resources>
    <DataTemplate x:Key="TheDataTemplate">
        <TextBlock
            Background="{Binding _5_5, Converter={StaticResource  ResourceKey=hourSlotColorConverter}, UpdateSourceTrigger=PropertyChanged}"
            Margin="-1">
            <i:Interaction.Triggers>
                <i:EventTrigger EventName="PreviewMouseLeftButtonDown">
                    <i:InvokeCommandAction
                        Command="{Binding RelativeSource={RelativeSource AncestorType={x:Type DataGrid}},
                                                                Path=DataContext.StartCellCommand}">
                        <i:InvokeCommandAction.CommandParameter>
                            <MultiBinding Converter="{StaticResource dgInfoConverter}">
                                <Binding Path="Column"
                                         RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                <Binding Path="DataContext"
                                         RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                            </MultiBinding>
                        </i:InvokeCommandAction.CommandParameter>
                    </i:InvokeCommandAction>
                </i:EventTrigger>
                <i:EventTrigger EventName="PreviewMouseLeftButtonUp">
                    <i:InvokeCommandAction
                        Command="{Binding RelativeSource={RelativeSource AncestorType={x:Type DataGrid}},
                                        Path=DataContext.LastCellCommand}">
                        <i:InvokeCommandAction.CommandParameter>
                            <MultiBinding Converter="{StaticResource dgInfoConverter}">
                                <Binding Path="Column"
                                         RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                <Binding Path="DataContext"
                                         RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                            </MultiBinding>
                        </i:InvokeCommandAction.CommandParameter>
                    </i:InvokeCommandAction>
                </i:EventTrigger>
                <i:EventTrigger EventName="MouseMove">
                    <i:InvokeCommandAction
                        Command="{Binding RelativeSource={RelativeSource AncestorType={x:Type DataGrid}},
                                                                Path=DataContext.MouseDragCom}">
                        <i:InvokeCommandAction.CommandParameter>
                            <MultiBinding Converter="{StaticResource dgInfoConverter}">
                                <Binding Path="Column"
                                         RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                                <Binding Path="DataContext"
                                         RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=DataGridCell}" />
                            </MultiBinding>
                        </i:InvokeCommandAction.CommandParameter>
                    </i:InvokeCommandAction>
                </i:EventTrigger>
            </i:Interaction.Triggers>
        </TextBlock>
    </DataTemplate>
</DataGrid.Resources>
...
<DataGridTemplateColumn CellTemplate="{StaticResource TheDataTemplate}" 
Header="" MaxWidth="10" />
...

更新>>>

好的,所以如果Bindings 里面有不同的 s DataTemplate,那么你必须使用 aUserControl代替。然后,您将能够DependencyProperty为变量属性声明 s 并从以下位置绑定到它们DataGridColumn

<UserControl ... >
    <TextBlock
        Background="{Binding Background, RelativeSource={RelativeSource AncestorType={x:Type yourXmlNamespacePrefix:YourUserControl}}}"
        Margin="-1">
        <i:Interaction.Triggers>
            <i:EventTrigger EventName="PreviewMouseLeftButtonDown">
                <i:InvokeCommandAction
                    Command="{Binding StartCellCommand, RelativeSource={RelativeSource AncestorType={x:Type yourXmlNamespacePrefix:YourUserControl}}}">
                    <i:InvokeCommandAction.CommandParameter>
                        <MultiBinding Converter="{StaticResource dgInfoConverter}">
                            <Binding Path="Column"
                                     RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType={x:Type yourXmlNamespacePrefix:YourUserControl}}" />
                            <Binding Path="SomeProperty"
                                     RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType={x:Type yourXmlNamespacePrefix:YourUserControl}}" />
                        </MultiBinding>
                    </i:InvokeCommandAction.CommandParameter>
                </i:InvokeCommandAction>
            </i:EventTrigger>
            ...
        </i:Interaction.Triggers>
    </TextBlock>
</UserControl>

如果您DependencyProperty为每个不同的 定义 a Binding,那么您将能够像这样设置它们:

...
<DataGridTemplateColumn Header="" MaxWidth="10">
    <DataGridTemplateColumn.CellTemplate>
        <DataTemplate>
            <yourXmlNamespacePrefix:YourUserControl Background="{Binding _5_5, 
Converter={StaticResource  ResourceKey=hourSlotColorConverter}, 
UpdateSourceTrigger=PropertyChanged}" StartCellCommand="{Binding RelativeSource=
{RelativeSource AncestorType={x:Type DataGrid}}, Path=DataContext.StartCellCommand}" 
Column="{Binding Column, RelativeSource={RelativeSource AncestorType={x:Type 
DataGridCell}}}" SomeProperty="{Binding DataContext, RelativeSource={RelativeSource 
AncestorType={x:Type DataGridCell}}}" />
        </DataTemplate>
    </DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn >
...

它仍然有很多代码,但比以前少了很多。我没有为你的所有属性完成这个例子,但我猜你会明白的。

于 2013-12-05T09:39:09.153 回答