[英]Simple TextBox Text Binding Fails WPF
我们正在将一个应用程序从Silverlight转换为WPF。 这是一个相当复杂的应用程序,但是代码共享约为95%以上。 除了XML名称空间定义等之外,XAML几乎相同。现在大约90%的应用程序都可以运行,但是有一些明显的问题使我感到困惑。 一个就是这个有约束力的问题。
我们有一个名为TaskInfo的模型对象。 它具有一个称为TaskNo的属性。 在Silverlight和WPF中,我们像这样绑定到此属性
<TextBox IsReadOnly="True" Grid.Column="0" Grid.Row="0" Margin="1" Text="{Binding Path=TaskNo}" Height="28" Background="#CAECF4" VerticalAlignment="Center" VerticalContentAlignment="Center" />
在WPF和Silverlight中,当TaskInfo模型首次设置为DataContext时,可以正确显示TaskNo。 在Silverlight中,如果我们创建一个新的TaskInfo,将其发送到服务器进行保存,然后返回带有新TaskNo的模型,则会成功显示TaskNo。 但是,在WPF中,从服务器返回保存的TaskInfo时,它仅显示0。 绑定存在一些问题。 这是我在输出窗口中看到的绑定错误:
System.Windows.Data信息:10:无法使用绑定来检索值,并且不存在有效的后备值;请参阅参考资料。 使用默认值代替。 BindingExpression:Path = TaskNo; DataItem = null; 目标元素是'TextBlock'(Name =''); 目标属性为“文本”(类型为“字符串”)
我检查了可视树,并按预期将TextBox的DataContext设置为TaskInfo。
因此,我关闭了绑定并尝试了此代码。 它是TextBox上DataContextChanging的事件处理程序。 此代码可以正常工作。 保存并返回新任务后,将在此处成功显示TaskNo:
private void TaskNoBox_DataContextChanging(object sender, DependencyPropertyChangedEventArgs e)
{
var task = TaskNoBox.DataContext as TaskInfo;
if (task == null)
{
throw new Exception("Ouch!");
}
TaskNoBox.Text = task.TaskNo.ToString();
}
为了进一步调试此问题,我在文本框中为GotFocus事件添加了此事件处理程序。 因此,在将任务保存在服务器端并返回并设置为DataContext之后,单击控件内部以触发此事件处理程序。 当我单步执行此代码时,可以看到DataContext是正确的,并且具有正确的TaskNo。 调用此代码仍然不会导致绑定发生。
private void TextBox_GotFocus(object sender, RoutedEventArgs e)
{
var textBox = (TextBox)sender;
var be = textBox.GetBindingExpression(TextBox.TextProperty);
be.UpdateSource();
be.UpdateTarget();
}
如何理解此绑定错误? Silverlight和WPF之间的绑定陷阱是什么? 我需要某种解决方法吗? 为什么绑定不起作用?
如果以前的DataContext根据Equals方法等效于新的DataContext,则WPF中的绑定永远不会更新。
Silverlight和WPF之间的区别似乎是,当DataContext更改时,WPF似乎使用Equals方法评估对象之间的差异,而Silverlight使用引用。 这意味着WPF与Xamarin.Forms相同。
我尝试了此代码,它导致TaskNo正确显示。 我认为正在发生的事情是因为调用Equals时,以前的DataContext等效于新的DataContext。 因此,这可以解决此问题。
private async void TaskPageHeader_DataContextChanged(object sender, DependencyPropertyChangedEventArgs e)
{
TaskNoBox.DataContext = new object();
TaskNoBox.DataContext = CurrentTask;
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.