Я пишу пользовательский элемент управления со свойством зависимости для искомого текста под названием SearchText. Это - свойство зависимости, потому что я хочу позволить потребителям управления использовать привязку данных. Пользовательский элемент управления содержит WPF TextBox, где пользователь может ввести искомый текст.
Я мог использовать привязку данных для соединения свойства зависимости SearchText пользовательского элемента управления с текстовым свойством зависимости TextBox, но это обязательное только стреляет, когда текстовое поле освобождает фокус ввода. То, что я хочу, является SearchText, который будет обновлен после каждого изменения текста. Таким образом, я добавил обработчик событий TextChanged к пользовательскому элементу управления, где я установил SearchText на значение текста.
Моя проблема, привязка SearchText не работает, источник никогда не обновляется. Что я делаю неправильно?
Вот соответствующая часть кода пользовательских элементов управления - позади:
public partial class UserControlSearchTextBox : UserControl
{
public string SearchText
{
get { return (string)GetValue(SearchTextProperty); }
set { SetValue(SearchTextProperty, value); }
}
public static readonly DependencyProperty SearchTextProperty =
DependencyProperty.Register("SearchText", typeof(string), typeof(UserControlSearchTextBox), new UIPropertyMetadata(""));
private void TextBox_TextChanged(object sender, TextChangedEventArgs e)
{
SearchText = ((TextBox)sender).Text;
}
...
}
Окну, которое содержит экземпляр пользовательского элемента управления, установили его DataContext на объект, который имеет свойство также под названием SearchText.
<uc:UserControlSearchTextBox SearchText="{Binding SearchText}" />
Контекст данных Окна:
public class DataSourceUserManual : DataSourceBase
{
private string _searchText;
public string SearchText
{
get { return _searchText; }
set
{
_searchText = value;
...
OnPropertyChanged("SearchText");
}
}
}
К сожалению, этот метод set не называют, когда я ввожу в текстовое поле. Какие-либо идеи?
После следования за Quartermeisters подсказывают, что я удалил обработчик событий TextBox_TextChanged и установил привязку, которая сохраняет TextBox. Текст и UserControl. SearchText в синхронизации.
<TextBox Text="{Binding ElementName=root,
Path=SearchText,
UpdateSourceTrigger=PropertyChanged}" />
Эта привязка, кажется, работает. Но теперь привязка между пользовательским элементом управления и контекстом данных окна повреждается (источник никогда не обновляется). Я изменил его немного
<uc:UserControlSearchTextBox SearchText="{Binding Source={StaticResource ResourceKey=dataSource},
Path=SearchText}" />
но без эффекта.
Что-либо специальное я должен заботиться об оценке этой "цепочечной" привязки?
Вы можете заставить TextBox обновлять источник привязки каждый раз, когда текст изменяется, изменив UpdateSourceTrigger на PropertyChanged со значения по умолчанию LostFocus:
<TextBox Text="{Binding SearchText, UpdateSourceTrigger=PropertyChanged}" />
См. Статью MSDN на Binding.UpdateSourceTrigger .
Что касается вашего обновленного вопроса, похоже, что исходное свойство не обновляется, потому что вы выполняете одностороннюю привязку. Вы можете сделать эту привязку двусторонней в XAML, указав Mode :
<uc:UserControlSearchTextBox SearchText="{Binding Source={StaticResource ResourceKey=dataSource},
Mode=TwoWay,
Path=SearchText}" />
, либо вы можете указать FrameworkPropertyMetadataOptions.BindsTwoWayByDefault в своем свойстве зависимости, что и делает TextBox.Text. :
public static readonly DependencyProperty SearchTextProperty =
DependencyProperty.Register("SearchText", typeof(string), typeof(UserControlSearchTextBox), new FrameworkPropertyMetadata("", FrameworkPropertyMetadataOptions.BindsTwoWayByDefault));
Вам необходимо указать параметр PropertyChangedCallback
для конструктора UIPropertyMetadata
.
Эта статья CodeProject делает именно то, что вы хотите. См. Как использовать API поиска Windows Vista из приложения WPF на http://www.codeproject.com/KB/WPF/Vista_Search_in_WPF.aspx .
...
new UIPropertyMetadata(
default(string),
new PropertyChangedCallback(TextBox_TextChanged)
)
...
static void TextBox_TextChanged(DependencyObject sender, DependencyPropertyChangedEventArgs e) {
...
}