2009-04-22 6 views
1

Je suis en train d'implémenter un convertisseur de date personnalisé dans WPF, l'idée d'être plus intelligent sur la saisie de date, un Outlook (pouvoir entrer "aujourd'hui", etc.) J'ai donc écrit mon propre convertisseur . Il formate l'entrée de l'utilisateur au format M/j/aa. Par exemple, s'ils entrent: 8-2, ils verront le 02/08/09. Charmant.Forcer Convertir pour toujours exécuter lors de l'utilisation du convertisseur personnalisé dans WPF?

La question est: il y a plusieurs choses que l'utilisateur peut entrer qui aboutissent finalement à la même date. (8-2 et 8/2, étant des exemples faciles). Donc, disons simplement qu'ils commencent par entrer 8/2, qui se lance à travers ConvertBack et Convert, et s'affiche en tant que 02/08/09. Jusqu'ici tout va bien. Maintenant, disons qu'ils entrent 8-2 (ou 8/2 à nouveau) dans le même champ, juste après. Cela est exécuté par ConvertBack, ce qui génère la date SAME qui est déjà présente dans la propriété bound, donc cela ne dérange pas d'exécuter Convert, ce qui signifie que "8/2" est placé dans la zone de texte. Yick! Il n'y a pas de problème de données, juste un affichage, mais bon, la netteté compte.

Comment forcer WPF à fonctionner Convertir après TOUTES les entrées (sans erreur)?

Voici une version simplifiée du convertisseur:

public class DateConverter : IValueConverter 
{ 
    #region IValueConverter Members 

    public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture) 
    { 
     if (value != null) 
     { 
      string tempStr = value.ToString(); 
      return ((DateTime.Parse(tempStr)).ToString("M/d/yy")); 
     } 
     else 
     { 
      return null; 
     } 
    } 

    public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture) 
    { 
     return DateTime.Parse(value.ToString()); 
    } 

    #endregion 
} 

et voici ce que l'utilisation de celui-ci ressemble à:

 <local:FilteredTextBox.Text> 
     <Binding Path="Value" ElementName="root" Converter="{StaticResource DateConv}" 
      UpdateSourceTrigger="LostFocus" Mode="TwoWay" diagnostics:PresentationTraceSources.TraceLevel="High" 
     NotifyOnValidationError="True" ValidatesOnDataErrors="True" ValidatesOnExceptions="True"> 
      <Binding.ValidationRules> 
       <local:DateValidation/> 
      </Binding.ValidationRules> 
     </Binding> 
     </local:FilteredTextBox.Text> 

Merci! Scott

En réponse à un commentaire ci-dessous, voici la propriété de support:

 public DateTime? Value 
    { 
     get 
     { 
      return (DateTime?)GetValue(ValueProperty); 
     } 
     set 
     { 
      SetValue(ValueProperty, value); 
      OnPropertyChanged(new DependencyPropertyChangedEventArgs(ValueProperty, null, value)); // I just added this line, it makes no difference 
     } 
    } 

Répondre

0

Un grand merci à Josh G - avec son aide, j'ai trouvé la réponse (ou au moins une).

Ceci était pour une zone de texte dans un contrôle DatePicker que je suis en train de créer. Ainsi, plutôt que « verrouiller » la zone de texte directement à la valeur du contrôle, j'ai créé une propriété intermédiaire, qui appelle ensuite l'ensemble de la propriété de dépendance:

public DateTime? DateValue 
    { 
     get 
     { 
      return _dateValue; 
     } 
     set 
     { 
      _dateValue = value; 
      OnPropertyChanged("DateValue"); 
      SetValue(ValueProperty, _dateValue); 
     } 
    } 

et cela fonctionne tout à fait comme il se doit. Merci encore, Josh!

3

Est-il possible que la propriété de données de support est mise à feu ne PropertyChanged si elle change réellement de la valeur? Vous pouvez essayer de tirer PropertyChanged chaque fois que la fonction set est appelée, que la valeur change ou non. Cela entraînerait la mise à jour de la liaison.

+0

Dans ce cas, la propriété de données de sauvegarde définit toujours la valeur d'un DependencyProperty (ceci est utilisé dans un contrôle personnalisé) à l'aide de SetValue. J'ai ajouté le code ci-dessus. Et juste pour être sûr, j'ai appelé OnPropertyChanged par la suite aussi - pas de changement! Les rats! –

+0

Désolé, je n'ai pas réalisé que vous utilisiez une propriété de dépendance sur la source. Cela rend cette réponse non pertinente. –