WPF:文本框文本未更新
我有一个在 DataTemplate
中使用的用户控件,此 UserControl
包含一个 TextBox
,它与 Value 绑定> 我的UserControl
的属性(声明为DependencyProperty
)。在数据模板中,我将此 Value 属性与我的实际属性 Name(也是 DependencyProperty
)绑定。它工作正常,我在加载时为 Name 属性分配一个值,并且我的 TextBox
显示它,我更改 TextBox
中的值,它更新我的名称属性也。 现在,当我在依赖项属性中添加 PropertyChangedEventHandler
时,问题出现了,我检查该值是否有效,如果有效则不执行任何操作,如果无效则分配旧值。如果值无效,当我为其分配旧值时,属性会更新,但它不会在 UserControl
的 TextBox
中显示更新的值。谁能告诉我为什么?
我的UserControl
的XAML:
<UserControl x:Name="usercontrol">
<StackPanel>
<TextBlock ......./>
<TextBox Binding={Binding ElementName=usercontrol, Path=Value, Mode=TwoWay}/>
</StackPanel>
</UserControl>
在Value后面的代码中是一个DependencyProperty
我在我的DataTemplate中使用它
:
<HierarchicalDataTemplate DataType="{x:Type myLib:myClass}" ItemsSource="{Binding Children}">
<Expander Header="{Binding}">
<WrapPanel>
<edproperty:TextPropertyEditor Caption="Name" Value="{Binding Name, Mode=TwoWay}"/>
<edproperty:TextPropertyEditor .................../>
<edproperty:TextPropertyEditor .................../>
<edproperty:TextPropertyEditor ...................../>
</WrapPanel>
</Expander>
</HierarchicalDataTemplate>
我在 TreeView
中使用这个模板。在 TreeView
中,我在 TextBox
中输入值,该值更新我的 UserControl
的 Value 属性,进而更新< myClass
的 em>Name 属性 我正在将 PropertyChangedCallback
分配给 myClass
中的 Name 属性,执行一些验证并在验证失败时重新分配 OldValue
。它反过来也会更新 Value 属性,但我仍然看到 TextBox
具有与我之前输入的值相同的值,而不是更新后的值。
public string Name
{
get
{
return (string)GetValue(NameProperty);
}
set
{
SetValue(NameProperty, value);
}
}
// Using a DependencyProperty as the backing store for Name. This enables animation, styling, binding, etc...
public static readonly DependencyProperty NameProperty =
DependencyProperty.Register("Name", typeof(string), typeof(myClass), new UIPropertyMetadata(null, OnNameChanged));
protected static void OnNameChanged(DependencyObject sender, DependencyPropertyChangedEventArgs args)
{
if(checkRequired && !IsValid(e.NewValue.ToString()))
{
checkRequired=false;
(sender as myClass).Name = args.OldValue.ToString();
}
}
private static bool IsValid(string name)
{
.............some logic here
}
I have a user control that i am using inside a DataTemplate
, this UserControl
contains a TextBox
which is binded with Value property(declared as a DependencyProperty
) of my UserControl
. In data template I bind this Value property with my actual property say Name (also a DependencyProperty
). It works properly, I assign a value to Name property while loading and my TextBox
displays it, i change the value from TextBox
and it updates my Name property also.
Now the problem comes while I add a PropertyChangedEventHandler
in the dependency property, I check for the value if it is valid, do nothing if valid and assign old value if not valid. In case of value not valid, when I assign it that old value, property updates but it is not displaying updated value in my TextBox
of UserControl
. Can anyone tell me why?
XAML of my UserControl
:
<UserControl x:Name="usercontrol">
<StackPanel>
<TextBlock ......./>
<TextBox Binding={Binding ElementName=usercontrol, Path=Value, Mode=TwoWay}/>
</StackPanel>
</UserControl>
In code behind Value is a DependencyProperty
I am using this in my DataTemplate
:
<HierarchicalDataTemplate DataType="{x:Type myLib:myClass}" ItemsSource="{Binding Children}">
<Expander Header="{Binding}">
<WrapPanel>
<edproperty:TextPropertyEditor Caption="Name" Value="{Binding Name, Mode=TwoWay}"/>
<edproperty:TextPropertyEditor .................../>
<edproperty:TextPropertyEditor .................../>
<edproperty:TextPropertyEditor ...................../>
</WrapPanel>
</Expander>
</HierarchicalDataTemplate>
This template I am using in a TreeView
. Inside TreeView
I enter value in the TextBox
which updates the Value property of my UserControl
, that in turn updates Name property of myClass
I am assigning a PropertyChangedCallback
to my Name Property in myClass
, performing some validation and reassigning the OldValue
if the validation fails. It in turn updates Value property also, but i am still seeing that the TextBox
has the same value that i entered earlier not the updated one.
public string Name
{
get
{
return (string)GetValue(NameProperty);
}
set
{
SetValue(NameProperty, value);
}
}
// Using a DependencyProperty as the backing store for Name. This enables animation, styling, binding, etc...
public static readonly DependencyProperty NameProperty =
DependencyProperty.Register("Name", typeof(string), typeof(myClass), new UIPropertyMetadata(null, OnNameChanged));
protected static void OnNameChanged(DependencyObject sender, DependencyPropertyChangedEventArgs args)
{
if(checkRequired && !IsValid(e.NewValue.ToString()))
{
checkRequired=false;
(sender as myClass).Name = args.OldValue.ToString();
}
}
private static bool IsValid(string name)
{
.............some logic here
}
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(4)
经过几天的环顾和大量搜索,我找到了问题的解决方案
在完成所有验证并分配旧值并更新依赖属性之后,我需要调用 UpdateTarget() 方法,以更新我的 TextBox 中的值。
这就是更好地解释解决方案的原因
http://social.msdn.microsoft.com/forums/en-US/wpf/thread/c404360c-8e31-4a85-9762-0324ed8812ef/
After days of looking around and a lot of search i found the solution of my problem
After all validation done and assigning old value and updating the dependecy property, i need to cal UpdateTarget() method, to Update the value in my TextBox.
This is what explains the solution better
http://social.msdn.microsoft.com/forums/en-US/wpf/thread/c404360c-8e31-4a85-9762-0324ed8812ef/
我知道这个问题是关于 TextBox 的,但对于 RichTextBox 你会使用 UpdateLayout()。
I know this question was about TextBox but for RichTextBox you would use UpdateLayout().
当您直接从后面的代码设置属性值时,看起来您正在破坏绑定。
您不应该以这种方式修改属性。使用值强制机制并验证强制值回调中的输入。
It looks like you are breaking binding when you set property value directly from code behind.
You shouldn't modify property that way. Use value coercion mechanism and validate input in the Coerce value callback.
Anurag,
我必须在这里做出很多假设,但我会尝试一下。
您可能有这样的事情......
这绝对不是验证数据的最佳方法。还有其他更有效的方法可以为您提供更大的灵活性。
不要使用 DependecyPropertyChanged 回调方法。使用注册的字符串属性并在您的设置器中应用逻辑,例如
再一次,正如您从我的回答中看到的那样,您仍然可以在问题中显示代码来帮助其他人回答您的问题,无论您的解决方案有多复杂(如果您想要一个好的答案,就需要付出努力去问一个好问题)。我的答案可能不适合你,但也许它可能会给你一些“谷歌搜索”的指导。希望有帮助。
Anurag,
There are a lot of assumptions I have to make here, but I'll give it a shot.
You probably have something like this...
This is definitely not the best approach to validate data. There are other, more efficient approaches that will give you more flexibility.
Don't use DependecyPropertyChanged callback method. Use a registered string Property and in your setter, apply logic, e.g.
Once again, as you can see from my answer that you can still show code in your question to help others answer your question no matter how complex your solution may be (if you want a good answer, you need to put in the effort to ask a good question). My answer may not work for you but maybe it might give you some "Googling" directions. Hope it helps.