wpf DataGrid 通过单击 UpdateSourceTrigger = SourceUpdated 来捕获单元格值更改事件
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/20174094/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
DataGrid catch cell value changed event with a single click on UpdateSourceTrigger = SourceUpdated
提问by Filippo Vigani
I'm struggling to catch an event with a DataGrid. What I want to achieve is that when the user clicks ONCE on a checkbox of a datagrid cell, an event fires and I can get the current cell value. However the CellChangedEvent fires only when the selection changes, and the CellEditingEvent either fires when the cell loses focus, OR never fires. It never fires if I try to make a checkbox modificable with a single click, by doing the following:
我正在努力用 DataGrid 捕捉事件。我想要实现的是,当用户在数据网格单元格的复选框上单击一次时,会触发一个事件,我可以获得当前单元格值。但是 CellChangedEvent 仅在选择更改时触发,而 CellEditingEvent 要么在单元格失去焦点时触发,要么从不触发。如果我尝试通过执行以下操作使复选框可修改,它永远不会触发:
<DataGrid Grid.ColumnSpan="2" Grid.Row="1" Grid.Column="0" AutoGenerateColumns="True" ItemsSource="{Binding MasterDataTable, Mode=TwoWay}" CanUserAddRows="False" Margin="10 5" CurrentCellChanged="DataGrid_CurrentCellChanged">
<DataGrid.Resources>
<Style TargetType="DataGridCell">
<Style.Triggers>
<Trigger Property="IsMouseOver" Value="True">
<Setter Property="IsEditing" Value="True" />
</Trigger>
</Style.Triggers>
</Style>
</DataGrid.Resources>
</DataGrid>
How can I call a method as soon as the user clicks on a checkbox inside a cell? Thanks in advance.
用户单击单元格内的复选框后,如何立即调用方法?提前致谢。
采纳答案by eran otzap
1) In your DataGrid register for TargetUpdatedevent .
1) 在您的 DataGrid 中注册TargetUpdated事件。
2) Specify a Column , and ideally set AutoGenerateColumns=False.
2) 指定一个 Column ,理想情况下设置AutoGenerateColumns=False。
3) In your Binding flag the NotifyOnTargetUpdatedproperty (your target is your checkbox).
3) 在您的 Binding 标志中,NotifyOnTargetUpdated属性(您的目标是您的复选框)。
4) In your Binding UpdateSourceTrigger=PropertyChangedand Mode=TwoWay(not the default behavior of the DataGrid).
4) 在您的绑定中UpdateSourceTrigger=PropertyChanged和Mode=TwoWay(不是 DataGrid 的默认行为)。
XAML :
XAML:
<DataGrid TargetUpdated="DataGrid_TargetUpdated"
AutoGenerateColumns="False"
ItemsSource="{Binding SomeValues, Mode=OneWay}" CanUserAddRows="False" >
<DataGrid.Columns>
<DataGridCheckBoxColumn Binding="{Binding Path=., NotifyOnTargetUpdated=True, UpdateSourceTrigger=PropertyChanged, Mode=TwoWay}" Width="*"/>
</DataGrid.Columns>
</DataGrid>
in CS: (where you might wan't to handle that event.)
在 CS 中:(您可能不想处理该事件。)
private void DataGrid_TargetUpdated(object sender, DataTransferEventArgs e)
{
// Do what ever...
}
回答by Filippo Vigani
This is how I solved it. It's not the best of the solution but it works for me. As stated by @eranotzap I set set AutoGenerateColumns=False and UpdateSourceTrigger = PropertyChanged. Then I did the following:
我就是这样解决的。这不是最好的解决方案,但对我有用。正如@eranotzap 所述,我设置了 set AutoGenerateColumns=False 和 UpdateSourceTrigger = PropertyChanged。然后我做了以下事情:
<DataGrid Grid.ColumnSpan="2" Grid.Row="1" Grid.Column="0"
AutoGenerateColumns="False"
ItemsSource="{Binding MasterDataTable, Mode=TwoWay}"
CanUserAddRows="False"
Margin="10 5">
<DataGrid.Columns>
<DataGridTextColumn Binding="{Binding Path=Fornitore}" Header="Fornitore" Width="Auto" IsReadOnly="True" />
<DataGridTextColumn Binding="{Binding Path=Stat}" Header="Stat" Width="Auto" IsReadOnly="True" />
<DataGridTextColumn Binding="{Binding Path=Intestazione}" Header="Intestazione" Width="*" IsReadOnly="True" >
<DataGridTextColumn.ElementStyle>
<Style TargetType="TextBlock">
<Setter Property="TextWrapping" Value="Wrap" />
</Style>
</DataGridTextColumn.ElementStyle>
<DataGridTextColumn.EditingElementStyle>
<Style TargetType="TextBox">
<Setter Property="TextWrapping" Value="Wrap" />
<Setter Property="AcceptsReturn" Value="true" />
</Style>
</DataGridTextColumn.EditingElementStyle>
</DataGridTextColumn>
<DataGridTextColumn Binding="{Binding Path=PrzVend}" Header="PrzVend" Width="Auto" IsReadOnly="True" />
<DataGridTextColumn Binding="{Binding Path=DatEXPO}" Header="DatEXPO" Width="Auto" IsReadOnly="True" />
<DataGridCheckBoxColumn Binding="{Binding Path=Sel, NotifyOnSourceUpdated=False, NotifyOnTargetUpdated=True, UpdateSourceTrigger=PropertyChanged, Mode=TwoWay}" Header="Sel" Width="Auto">
<DataGridCheckBoxColumn.CellStyle>
<Style TargetType="DataGridCell">
<EventSetter Event="CheckBox.Checked" Handler="CellChanged"/>
<EventSetter Event="CheckBox.Unchecked" Handler="CellChanged"/>
<Style.Triggers>
<MultiTrigger>
<MultiTrigger.Conditions>
<Condition Property="IsMouseOver" Value="True" />
<Condition Property="IsReadOnly" Value="False" />
</MultiTrigger.Conditions>
<Setter Property="IsEditing" Value="True" />
</MultiTrigger>
</Style.Triggers>
</Style>
</DataGridCheckBoxColumn.CellStyle>
</DataGridCheckBoxColumn>
<DataGridTextColumn Binding="{Binding Path=CodComp}" Header="CodComp" Width="Auto" IsReadOnly="True" />
</DataGrid.Columns>
</DataGrid>
In the code behind the method CellChanges is called every time the checkbox is checked or unchecked. To get the value I do the following:
在每次选中或取消选中复选框时,都会调用 CellChanges 方法背后的代码。为了获得价值,我执行以下操作:
void CellChanged(object sender, RoutedEventArgs e)
{
if (sender as DataGridCell != null && (sender as DataGridCell).Column != null && (sender as DataGridCell).Column.Header != null)
{
bool? isSelected = (e.OriginalSource as ToggleButton).IsChecked;
}
}
Hope it helps somebody.
希望它可以帮助某人。
回答by daniele3004
Try this simple way
试试这个简单的方法
private void myDataGrid_CellEditEnding(object sender, DataGridCellEditEndingEventArgs e)
{
if (e.Column.SortMemberPath.Equals("EndDate"))
{
if (((MyObjectInRow)e.Row.Item).DataFine.Equals(EndDate.MinValue))
{
((MyObjectInRow)e.Row.Item).Completed = 1;
}
else
{
((MyObjectInRow)e.Row.Item).Completed = 0;
}
}
}