2009-10-05 3 views
0

У меня есть ComboBox с национальностью, как показано ниже, и вы хотите сделать это так, чтобы пользователь мог набирать буквы до узким на выбор. Я мог бы решить это так, как я начал снижать, добавив логику в метод CitizensComboBox_KeyDown.Это лучший способ создать AutoSuggest в WPF ComboBox?

Это лучший способ создать AutoSuggest в ComboBox или есть встроенный способ сделать то же самое?

XAML:

<ComboBox x:Class="TestComboSuggest343.NationalityComboBox" 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
    Height="300" Width="300"> 
    <ComboBox.ItemTemplate> 
     <DataTemplate> 
      <TextBlock Text="{Binding Value}"/> 
     </DataTemplate>   
    </ComboBox.ItemTemplate> 
</ComboBox> 

Code-Behind:

public partial class NationalityComboBox : ComboBox 
{ 
    public NationalityComboBox() 
    { 
     InitializeComponent(); 

     Items.Add(new KeyValuePair<string, string>(null, "Please choose...")); 
     Items.Add(new KeyValuePair<string, string>(null, "American")); 
     Items.Add(new KeyValuePair<string, string>(null, "Australian")); 
     Items.Add(new KeyValuePair<string, string>(null, "Belgian")); 
     Items.Add(new KeyValuePair<string, string>(null, "French")); 
     Items.Add(new KeyValuePair<string, string>(null, "German")); 
     Items.Add(new KeyValuePair<string, string>(null, "Georgian")); 
     SelectedIndex = 0; 

     KeyDown += new KeyEventHandler(NationalityComboBox_KeyDown); 

    } 

    void NationalityComboBox_KeyDown(object sender, KeyEventArgs e) 
    { 
     SelectedIndex = 4; // can create logic here to handle key presses, e.g. "G", "E", "O".... 
    } 
} 

ответ

1

Я написал вложенное свойство, чтобы сделать это:

public class ComboBoxAutoFilter 
{ 
    public static bool GetEnabled(DependencyObject obj) 
    { 
     return (bool)obj.GetValue(EnabledProperty); 
    } 

    public static void SetEnabled(DependencyObject obj, bool value) 
    { 
     obj.SetValue(EnabledProperty, value); 
    } 

    // Using a DependencyProperty as the backing store for Enabled. This enables animation, styling, binding, etc... 
    public static readonly DependencyProperty EnabledProperty = 
     DependencyProperty.RegisterAttached(
      "Enabled", 
      typeof(bool), 
      typeof(ComboBoxAutoFilter), 
      new UIPropertyMetadata(false, Enabled_Changed) 
     ); 

    private static void Enabled_Changed(DependencyObject sender, DependencyPropertyChangedEventArgs e) 
    { 
     ComboBox combo = sender as ComboBox; 
     if (combo != null) 
     { 
      if (combo.Template != null) 
       SetTextChangedHandler(combo); 
      else 
       combo.Loaded += new RoutedEventHandler(combo_Loaded); 
     } 
    } 

    static void combo_Loaded(object sender, RoutedEventArgs e) 
    { 
     ComboBox combo = sender as ComboBox; 
     combo.Loaded -= combo_Loaded; 
     if (combo.Template != null) 
      SetTextChangedHandler(combo); 
    } 

    private static void SetTextChangedHandler(ComboBox combo) 
    { 
     TextBox textBox = combo.Template.FindName("PART_EditableTextBox", combo) as TextBox; 
     if (textBox != null) 
     { 
      bool enabled = GetEnabled(combo); 
      if (enabled) 
       textBox.TextChanged += textBox_TextChanged; 
      else 
       textBox.TextChanged -= textBox_TextChanged; 
     } 
    } 

    private static void textBox_TextChanged(object sender, RoutedEventArgs e) 
    { 
     TextBox textBox = sender as TextBox; 
     ComboBox combo = textBox.TemplatedParent as ComboBox; 
     combo.IsDropDownOpen = true; 
     string text = textBox.Text.Substring(0, textBox.SelectionStart); 
     combo.Items.Filter = value => value.ToString().StartsWith(text); 
    } 

} 

Вы можете использовать его так:

<ComboBox IsEditable="True" 
       local:ComboBoxAutoFilter.Enabled="True"> 
     <sys:String>American</sys:String> 
     <sys:String>Australian</sys:String> 
     <sys:String>Belgian</sys:String> 
     <sys:String>French</sys:String> 
     <sys:String>German</sys:String> 
     <sys:String>Georgian</sys:String> 
     ... 
    </ComboBox> 
+0

1) Существует Свойство из коробки «IsSearchFilterEnabled». 2) Проблема в том, что когда это свойство включено, оно автоматически завершает слово. Есть ли вообще избежать этого? – Shimmy

0

Заканчивать автоматическое заполнение текстовых полей, представленные в Silverlight Toolkit. Я считаю, что они доступны и для WPF.

Вы можете увидеть это в действии в этом XBAP demo. Ищите AutoCompleteBox.