首页 > 解决方案 > 如何根据源对象中的值设置样式中的边距?

问题描述

我正在使用 WPF .NET Core 3.0 。我有一个数据网格,我想使用一种样式根据源对象中属性的值来设置行的边距。我正在尝试这段代码:

<Style TargetType="{x:Type DataGridCell}" x:Key="DataGridCellStyle">
    <Setter Property="Background" Value="LightGray"/>
    <Setter Property="Margin" Value="-1,10,0,0"/>
    <Setter Property="FontSize" Value="9"/>
    <Setter Property="Height" Value="18"/>
    <Setter Property="FontWeight" Value="Bold"/>
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="{x:Type DataGridCell}">
                <Grid Background="{TemplateBinding Background}" >
                    <Border Padding="9,0,0,0">
                        <ContentPresenter HorizontalAlignment="Left" VerticalAlignment="Center"/>
                    </Border>
                </Grid>

                <ControlTemplate.Triggers>
                    <DataTrigger Binding="{Binding Path=MyPropertyInSource, RelativeSource={RelativeSource Self}}" Value="-1">
                        <Setter Property="Margin" Value="-1,-30,0,0"/>
                    </DataTrigger>
                </ControlTemplate.Triggers>
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>



<DataGrid Name="MyDataGrid"
              ItemsSource="{Binding Data}">
    <DataGrid.Columns>
        <DataGridTextColumn Header="Title" Binding="{Binding MyPropertyTitle}" Width="29.7cm"
                            CellStyle="{StaticResource DataGridCellStyle}"/>
    </DataGrid.Columns>
</DataGrid>

在样式中,在数据触发器中,我尝试绑定源的属性,如果它等于-1,则将上边距设置为-30,如果不是,则使用设置为值的默认边距或10.我检查了源对象在属性中有-1值,但是没有抛出数据触发器。

我想使用一种样式,因为我有一些使用相同逻辑的数据网格,如果可以避免每次都复制,我想重用该样式。

编辑:我将使用用作数据源的类添加更多代码。

<DataGrid Name="MainDataGrid" VerticalAlignment="Stretch" HorizontalAlignment="Stretch" Margin="0,0,0,0" Grid.Column="0" Grid.Row="0"
            Style="{StaticResource DataGridMainStyle}"
            RowStyle="{DynamicResource DataGridMainRowStyle}"
            ItemsSource="{Binding Data}">
    <DataGrid.Columns>
    </DataGrid.Columns>

    <DataGrid.RowDetailsTemplate>
        <DataTemplate>
            <DataGrid Name="DetailsDataGrid"
                          Style="{StaticResource DataGridDetailsStyle}"
                          CellStyle="{StaticResource DataGridDetailsCellStyle}"
                          ItemsSource="{Binding MyCollectionDetails}">
                <DataGrid.Columns>
                    <DataGridTextColumn Header="Title" Binding="{Binding DatailsProperty}" Width="29.7cm"/>
                </DataGrid.Columns>
            </DataGrid>
        </DataTemplate>
    </DataGrid.RowDetailsTemplate>
</DataGrid>





<Style x:Key="DataGridMainStyle" TargetType="{x:Type DataGrid}">
    <Setter Property="HeadersVisibility" Value="Column"/>
    <Setter Property="BorderBrush" Value="Black"/>
    <Setter Property="BorderThickness" Value="1"/>
    <Setter Property="VerticalGridLinesBrush" Value="Black"/>
    <Setter Property="HorizontalGridLinesBrush" Value="Black"/>
</Style>




<Style x:Key="DataGridDetailsStyle" TargetType="{x:Type DataGrid}">
    <Setter Property="HorizontalAlignment" Value="Stretch"/>
</Style>



<Style TargetType="{x:Type DataGridCell}" x:Key="DataGridCellStyle">
    <Setter Property="Background" Value="LightGray"/>
    <Setter Property="Margin" Value="-1,10,0,0"/>
    <Setter Property="FontSize" Value="9"/>
    <Setter Property="Height" Value="18"/>
    <Setter Property="FontWeight" Value="Bold"/>
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="{x:Type DataGridCell}">
                <Grid Background="{TemplateBinding Background}" >
                    <Border Padding="9,0,0,0">
                        <ContentPresenter HorizontalAlignment="Left" VerticalAlignment="Center"/>
                    </Border>
                </Grid>

                <ControlTemplate.Triggers>
                    <DataTrigger Binding="{Binding Path=MyPropertyInSource, RelativeSource={RelativeSource Self}}" Value="-1">
                        <Setter Property="Margin" Value="-1,-30,0,0"/>
                    </DataTrigger>
                </ControlTemplate.Triggers>
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>








public class Datos : BaseViewModel
{
    private ObservableCollection<Details> _details = new ObservableCollection<Details>();
    public ObservableCollection<Details> Details
    {
        get { return _details; }
        set
        {
            _details = value;
            base.RaisePropertyChangedEvent(nameof(Details));
        }
    }
}




public class Details
{
    private MyType _myPrerty;
    public MyType MyPrerty
    {
        get { return _myPrerty; }
        set
        {
            _myPrerty = value;
            base.RaisePropertyChangedEvent(nameof(MyPrerty));
        }
    }
}




private ObservableCollection<Data> _data = new ObservableCollection<Data>();
public ObservableCollection<Datos> Data
{
    get { return _data; }
    set
    {
        _data = value;
        base.RaisePropertyChangedEvent(nameof(Data));
    }
}

标签: wpfdatagrid

解决方案


RelativeSource={RelativeSource Self}从触发器中删除,因为单元格的默认情况下DataContext是当前项:ItemsSource

<ControlTemplate TargetType="{x:Type DataGridCell}">
    <Grid Background="{TemplateBinding Background}" >
        <Border Padding="9,0,0,0">
            <ContentPresenter HorizontalAlignment="Left" VerticalAlignment="Center"/>
        </Border>
    </Grid>
    <ControlTemplate.Triggers>
        <DataTrigger Binding="{Binding Path=MyPropertyInSource}" Value="-1">
            <Setter Property="Margin" Value="-1,-30,0,0"/>
        </DataTrigger>
    </ControlTemplate.Triggers>
</ControlTemplate>

推荐阅读