2009-02-24 10 views
6

Voglio creare una casella combinata modificabile con le seguenti proprietà:ComboBox modificabile

  1. associare la proprietà di testo al mio modello di dati.
  2. Il modello dati può sovrascrivere le modifiche nella GUI, anche in Selezione modificata. Per esempio. Posso scegliere tra 1, 2, 3 scelgo 2, ma qualche componente in giù sotto i cambiamenti a 3.
  3. Aggiornare il modello di dati sui seguenti eventi:

    1. Selezione cambiato
    2. perdere la concentrazione
    3. Inserire premuto (dovrebbe comportarsi come perso lo stato attivo).

Sono stato in grado di creare un tale controllo, ma è abbastanza brutto (usando molti hack) e speravo che c'è un modo più semplice ...

Grazie in anticipo

risposta

2

Ok, ecco quello che ho fatto, e non è quella brutta:

/// <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

il modo più semplice per farlo è quello di utilizzare la proprietà UpdateSourceTrigger sul legame. Potresti non essere in grado di eguagliare esattamente il tuo comportamento attuale, ma potresti scoprire che è comparabile.

La proprietà UpdateSourceTrigger controlla quando la destinazione del collegamento aggiorna la fonte. Diversi controlli WPF hanno valori predefiniti diversi per questa proprietà quando associati.

Ecco le opzioni:

UpdateSourceTrigger.Default = consentire il controllo di destinazione per determinare la modalità UpdateSourceTrigger.

UpdateSourceTrigger.Explicit = Aggiorna solo l'origine quando qualcuno chiama BindingExpression.UpdateSource();

UpdateSourceTrigger.LostFocus = Aggiorna automaticamente l'origine di associazione ogni volta che il target perde lo stato attivo. In questo modo è possibile completare una modifica e quindi il binding viene aggiornato dopo che l'utente si sposta.

UpdateSourceTrigger.PropertyChanged = Ogni volta che DependencyProperty sulla destinazione cambia valori, la sorgente viene aggiornata immediatamente. La maggior parte dei UserControls non esegue il default su questa proprietà perché richiede più aggiornamenti vincolanti (può essere un problema di prestazioni).