Frage

In meiner Anwendung kann der Benutzer auswählen, wie ein Datum angezeigt wird. Die meisten der Standard Datetime-Format-Strings können sein ausgewählt. Mein Problem ist nun, dass der durchschnittliche Benutzer doesnt den Unterschied zwischen „m“ verstehen und „D“. Was ich tun möchte, ist das, damit ändern, wie Excel tut, anstatt die Format-String zeigt, ich zeigen, wie ein beliebiges Datum wie mit diesem Format aussehen würde.

Die WPF Combobox SelectedItem ist mit einer Abhängigkeitseigenschaft in dem Datumsformat Picker cla gebunden, die die andere Steuer diese Datumsauswahl enthält auch binden.

Beispiel: :

  1. Der Benutzer wählt "Januar, 15", so dass die Abhängigkeitseigenschaft ist auf "m".
  2. Durch Code-behind, der Wert der Abhängigkeitseigenschaft auf „D“ gesetzt, die Combobox Display „Thursday, 15. Januar 1970“ aktualisiert wird als das ausgewählte Element.

Ich habe versucht, Konvertern aber ConvertBack war nicht möglich, da ich ein Format-String extrahieren kann nicht einen bestimmten Zeitpunkt zu erstellen.

War es hilfreich?

Lösung

Sie können eine Klasse DateFormatChoice erstellen, die eine Eigenschaft für den Formatcode enthält (beispielsweise „m“ oder „D“) und eine Eigenschaft für das aktuelle auf diese Weise formatierte Datum.

public class DateFormatChoice {
    public string FormatCode { get; private set; }
    public string CurrentDateExample {
        get { return DateTime.Now.ToString( FormatCode ) }
    }

    public DateFormatChoice( string standardcode ) {
        FormatCode = standardcode;
    }
}

Sie binden Ihre ComboBox auf eine Sammlung von diesen mit CurrentDateExample entweder in Ihrer DataTemplate oder als die DisplayMemberPath der ComboBox. Sie können entweder diese Objekte direkt mit Ihrem Datumsformat Picker Klasse und die DatePicker bindet an der FormatCode Eigenschaft des DateFormatChoice Objekts ausgewählt, oder Sie können die ValueMemberPath Eigenschaft auf dem ursprünglichen ComboBox zum FormatCode Eigentum und Nutzung SelectedValue auf der ComboBox-Set für immer / Einstellung, was gewählt wird. Nicht ValueMember mit vielleicht ein wenig einfacher sein.


Hier ist ein vollständiges Beispiel. Es nutzt die DateFormatChoice Klasse oben.

Zuerst wird eine Datensammlung.

public class DateFormatChoices : List<DateFormatChoice> {
    public DateFormatChoices() {
        this.Add( new DateFormatChoice( "m" ) );
        this.Add( new DateFormatChoice( "d" ) );
        this.Add( new DateFormatChoice( "D" ) );
    }
}

Dann habe ich einfach Ansichtsmodell für das Fenster:

public class ViewModel : INotifyPropertyChanged {
    public event PropertyChangedEventHandler PropertyChanged = ( s, e ) => {
    }; // the lambda ensures PropertyChanged is never null

    public DateFormatChoices Choices {
        get;
        private set;
    }

    DateFormatChoice _chosen;
    public DateFormatChoice Chosen {
        get {
            return _chosen;
        }
        set {
            _chosen = value;
            Notify( PropertyChanged, () => Chosen );
        }
    }

    public DateTime CurrentDateTime {
        get {
            return DateTime.Now;
        }
    }

    public ViewModel() {
        Choices = new DateFormatChoices();
    }

    // expression used to avoid string literals
    private void Notify<T>( PropertyChangedEventHandler handler, Expression<Func<T>> expression ) {
        var memberexpression = expression.Body as MemberExpression;
        handler( this, new PropertyChangedEventArgs( memberexpression.Member.Name ) );
    }
}

Ich habe keinen Date Picker habe, die den Standard-String-Format-Codes akzeptiert, so dass ich einen ganz stumm gemacht Usercontrol (mit vielen Ecken geschnitten) nur Erhalt des Formatcode zu demonstrieren. Ich habe es Abhängigkeitseigenschaft DateFormatProperty vom Typ string genannt und einen Wert geändert Rückruf in den UIPropertyMetadata angegeben.

<Grid>
    <TextBlock Name="datedisplayer" />
</Grid>

Der Rückruf:

private static void DateFormatChanged( DependencyObject obj, DependencyPropertyChangedEventArgs e ) {
    var uc = obj as UserControl1;
    string code;
    if ( null != ( code = e.NewValue as string ) ) {
        uc.datedisplayer.Text = DateTime.Now.ToString( code );
    }
}

Und das ist, wie ich band sie alle zusammen im Fenster.

<StackPanel>
    <StackPanel.DataContext>
        <local:ViewModel />
    </StackPanel.DataContext>
    <ComboBox
        ItemsSource="{Binding Choices}" DisplayMemberPath="CurrentDateExample"
        SelectedItem="{Binding Chosen, Mode=TwoWay}"/>
    <local:UserControl1
        DateFormatProperty="{Binding Chosen.FormatCode}" />
</StackPanel>
Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top