2009-02-24 27 views
6

Ich mag mit den folgenden Eigenschaften editierbare Combo-Box erstellen:ComboBox

  1. Bind der Text-Eigenschaft auf mein Datenmodell.
  2. Das Datenmodell kann die Änderungen in der GUI überschreiben, auch wenn Selection geändert wurde. Z.B. Ich kann aus 1, 2, 3 I 2 wählen, aber einige Komponenten unter Veränderungen, die sie auf 3.
  3. aktualisieren das Datenmodell auf der folgenden Ereignisse:

    1. Auswahl geändert
    2. Verliere Fokus
    3. Eingabe gedrückt (sollte sich wie verlorener Fokus verhalten).

Ich habe in der Lage gewesen, eine solche Kontrolle zu schaffen, aber es ist ziemlich hässlich (viele Hacks verwendet wird) und ich hoffte, es gibt einen einfacheren Weg ...

Vielen Dank im Voraus

Antwort

2

Ok, ich hier ist das, was ich getan habe, und es ist nicht so hässlich:

/// <summary> 
/// Editable combo box which updates the data model on the following: 
/// 1. Select## Heading ##ion changed 
/// 2. Lost focus 
/// 3. Enter or Return pressed 
/// 
/// In order for this to work, the EditableComboBox requires the follows, when binding: 
/// The data model value should be bounded to the Text property of the ComboBox 
/// The binding expression UpdateSourceTrigger property should be set to LostFocus 
/// e.g. in XAML: 
/// <PmsEditableComboBox Text="{Binding Path=MyValue, UpdateSourceTrigger=LostFocus}" 
/// ItemsSource="{Binding Path=MyMenu}"/> 
/// </summary> 
public class PmsEditableComboBox : ComboBox 
{ 
    /// <summary> 
    /// Initializes a new instance of the <see cref="PmsEditableComboBox"/> class. 
    /// </summary> 
    public PmsEditableComboBox() 
     : base() 
    { 
     // When TextSearch enabled we'll get some unwanted behaviour when typing 
     // (i.e. the content is taken from the DropDown instead from the text) 
     IsTextSearchEnabled = false; 
     IsEditable = true; 
    } 

    /// <summary> 
    /// Use KeyUp and not KeyDown because when the DropDown is opened and Enter is pressed 
    /// We'll get only KeyUp event 
    /// </summary> 
    protected override void OnKeyUp(KeyEventArgs e) 
    { 
     base.OnKeyUp(e); 

     // Update binding source on Enter 
     if (e.Key == Key.Return || e.Key == Key.Enter) 
     { 
      UpdateDataSource(); 
     } 
    } 

    /// <summary> 
    /// The Text property binding will be updated when selection changes 
    /// </summary> 
    protected override void OnSelectionChanged(SelectionChangedEventArgs e) 
    { 
     base.OnSelectionChanged(e); 
     UpdateDataSource(); 
    } 

    /// <summary> 
    /// Updates the data source. 
    /// </summary> 
    private void UpdateDataSource() 
    { 
     BindingExpression expression = GetBindingExpression(ComboBox.TextProperty); 
     if (expression != null) 
     { 
      expression.UpdateSource(); 
     } 
    } 

} 
0

der einfachste Weg, dies zu tun ist, um die Update Eigenschaft auf der Bindung zu verwenden. Sie sind möglicherweise nicht in der Lage, Ihr aktuelles Verhalten genau zu vergleichen, aber Sie können feststellen, dass es vergleichbar ist.

Die Eigenschaft UpdateSourceTrigger steuert, ob das Ziel der Bindung die Quelle aktualisiert. Verschiedene WPF-Steuerelemente haben unterschiedliche Standardwerte für diese Eigenschaft gebunden.

Hier sind Ihre Möglichkeiten:

UpdateSourceTrigger.Default = Kontrolle zulassen Zielupdatemodus zu bestimmen.

UpdateSourceTrigger.Explicit = Aktualisiere die Quelle nur, wenn jemand BindingExpression.UpdateSource() aufruft;

UpdateSourceTrigger.LostFocus = Automatische Aktualisierung der Bindungsquelle, wenn das Ziel den Fokus verliert. Auf diese Weise kann eine Änderung abgeschlossen werden, und dann wird die Bindung aktualisiert, nachdem der Benutzer weitergegangen ist.

UpdateSourceTrigger.PropertyChanged = Immer wenn die DependencyProperty auf dem Ziel Werte ändert, wird die Quelle sofort aktualisiert. Die meisten UserControls verwenden diese Eigenschaft nicht standardmäßig, da sie mehr verbindliche Updates erfordert (kann ein Leistungsproblem sein).