WPF Multibinding:通过另一个绑定更新的来自 TextBox 的 OneWayToSource 绑定不起作用?
WPF Multibinding: OneWayToSource binding from TextBox updated via another binding doesnt work?
我有一个绑定到 People 集合的 DataGrid。我还有一个 TextBox,它应该接受所选行中的 Name 值。然后用户可以编辑该值或保留原样。关键点是:TextBox 中显示的文本,无论它来自集合还是用户键入,都必须传播到 属性 NewName。
我为 NewNameTextBox 设置了两个绑定:OneWay 绑定到 DataGrid 后面的 CollectionView,OneWayToSource 绑定到 属性:
<Window.Resources>
<CollectionViewSource x:Key="PeopleCollection"
Source="{Binding Path=People, Mode=OneWay}" />
<local:ConverterNewNamePrefill x:Key="ConverterNewNamePrefill" />
</Window.Resources>
<Grid>
<StackPanel>
<DataGrid ItemsSource="{Binding Source={StaticResource PeopleCollection}}"
AutoGenerateColumns="True"
IsReadOnly="True"
Margin="10">
</DataGrid>
<StackPanel Orientation="Horizontal" Margin="10">
<TextBox>
<TextBox.Text>
<MultiBinding Converter="{StaticResource ConverterNewNamePrefill}" >
<Binding Source="{StaticResource PeopleCollection}" Path="Name" Mode="OneWay" />
<Binding Path="NewName" Mode="OneWayToSource" />
</MultiBinding>
</TextBox.Text>
</TextBox>
</StackPanel>
</StackPanel>
</Grid>
我想 属性 应该在用户更改 DataGrid 中的选择时更新,但这并没有发生。 TextBox 得到更新并显示选定的 Name 值,但通过 OneWayToSource 绑定的 属性 保持不变。
如果用户在 TextBox 中键入内容,属性 会按预期更新。
所以问题是如何通过多绑定 TextBox 从两个来源更新 属性 而无需代码隐藏视图?
下面是window背后的代码:
public class Person
{
public string Name { get; set; }
public string Surname { get; set; }
}
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
}
private ObservableCollection<Person> _people = new ObservableCollection<Person> {
new Person() {Name = "Mitchell", Surname = "Sofia" },
new Person() {Name="Bush", Surname="Ethan" },
new Person() {Name="Ferrero", Surname="Emma" },
new Person() {Name="Thompson", Surname="Aiden" }
};
public ObservableCollection<Person> People => _people;
public string NewName { get; set; } = "Jackson";
}
public class ConverterNewNamePrefill : IMultiValueConverter
{
public object Convert(object[] values, Type targetType, object parameter, CultureInfo culture)
{
return values[0];
}
public object[] ConvertBack(object value, Type[] targetTypes, object parameter, CultureInfo culture)
{
return new[] { value, value };
}
}
转换器的方法 ConvertBack() 仅在用户输入时被调用,而不是在 TextBox.Text 从集合更新时被调用。
谢谢!
这就是绑定的工作原理。源或多个源不会更新,除非目标通过绑定本身以外的方式更改。 IE。假设如果目标刚刚从源更新,那么源已经是最新的并且不需要更新。
如果没有更多详细信息,则很难确定您想要什么。但似乎您可能希望 NewName
实际上是第二个绑定的 target,其中源相同 Name
属性用作 TextBox.Text
属性 的源,或者您想要订阅 TextBox.TextChanged
事件并且您的处理程序显式地将值写回到 NewName
属性引发该事件时。
在前一种情况下,您必须使 NewName
成为 MainWindow
的依赖项 属性。这是您可能不想处理的并发症。如果没有,那么我会推荐后一种方法。
我有一个绑定到 People 集合的 DataGrid。我还有一个 TextBox,它应该接受所选行中的 Name 值。然后用户可以编辑该值或保留原样。关键点是:TextBox 中显示的文本,无论它来自集合还是用户键入,都必须传播到 属性 NewName。
我为 NewNameTextBox 设置了两个绑定:OneWay 绑定到 DataGrid 后面的 CollectionView,OneWayToSource 绑定到 属性:
<Window.Resources>
<CollectionViewSource x:Key="PeopleCollection"
Source="{Binding Path=People, Mode=OneWay}" />
<local:ConverterNewNamePrefill x:Key="ConverterNewNamePrefill" />
</Window.Resources>
<Grid>
<StackPanel>
<DataGrid ItemsSource="{Binding Source={StaticResource PeopleCollection}}"
AutoGenerateColumns="True"
IsReadOnly="True"
Margin="10">
</DataGrid>
<StackPanel Orientation="Horizontal" Margin="10">
<TextBox>
<TextBox.Text>
<MultiBinding Converter="{StaticResource ConverterNewNamePrefill}" >
<Binding Source="{StaticResource PeopleCollection}" Path="Name" Mode="OneWay" />
<Binding Path="NewName" Mode="OneWayToSource" />
</MultiBinding>
</TextBox.Text>
</TextBox>
</StackPanel>
</StackPanel>
</Grid>
我想 属性 应该在用户更改 DataGrid 中的选择时更新,但这并没有发生。 TextBox 得到更新并显示选定的 Name 值,但通过 OneWayToSource 绑定的 属性 保持不变。
如果用户在 TextBox 中键入内容,属性 会按预期更新。
所以问题是如何通过多绑定 TextBox 从两个来源更新 属性 而无需代码隐藏视图?
下面是window背后的代码:
public class Person
{
public string Name { get; set; }
public string Surname { get; set; }
}
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
}
private ObservableCollection<Person> _people = new ObservableCollection<Person> {
new Person() {Name = "Mitchell", Surname = "Sofia" },
new Person() {Name="Bush", Surname="Ethan" },
new Person() {Name="Ferrero", Surname="Emma" },
new Person() {Name="Thompson", Surname="Aiden" }
};
public ObservableCollection<Person> People => _people;
public string NewName { get; set; } = "Jackson";
}
public class ConverterNewNamePrefill : IMultiValueConverter
{
public object Convert(object[] values, Type targetType, object parameter, CultureInfo culture)
{
return values[0];
}
public object[] ConvertBack(object value, Type[] targetTypes, object parameter, CultureInfo culture)
{
return new[] { value, value };
}
}
转换器的方法 ConvertBack() 仅在用户输入时被调用,而不是在 TextBox.Text 从集合更新时被调用。
谢谢!
这就是绑定的工作原理。源或多个源不会更新,除非目标通过绑定本身以外的方式更改。 IE。假设如果目标刚刚从源更新,那么源已经是最新的并且不需要更新。
如果没有更多详细信息,则很难确定您想要什么。但似乎您可能希望 NewName
实际上是第二个绑定的 target,其中源相同 Name
属性用作 TextBox.Text
属性 的源,或者您想要订阅 TextBox.TextChanged
事件并且您的处理程序显式地将值写回到 NewName
属性引发该事件时。
在前一种情况下,您必须使 NewName
成为 MainWindow
的依赖项 属性。这是您可能不想处理的并发症。如果没有,那么我会推荐后一种方法。