Пользователь выбирает что-то в combobox, что-то еще отправляется в свойство dependency

StackOverflow https://stackoverflow.com/questions/2287190

Вопрос

В моем приложении пользователь может выбрать способ отображения даты.Большая часть стандартные строки формата даты и времени может быть выбран.Моя проблема сейчас в том, что среднестатистический пользователь не понимает разницы между "m" и "D". То, что я хочу сделать, это измените это так, чтобы, как это делает Excel, вместо отображения строки формата я показывал, как будет выглядеть произвольная дата при использовании этого формата.

WPF combobox SelectedItem привязан к свойству зависимости в классе средств выбора формата даты, к которому также привязывается другой элемент управления, содержащий это средство выбора даты.

Пример:

  1. Пользователь выбирает "15 января", поэтому свойству dependency присваивается значение "m".
  2. С помощью кода ниже значение свойства dependency устанавливается равным "D", поле со списком обновляется, чтобы отображать "Четверг, 15 января 1970" в качестве выбранного элемента.

Я пытался использовать конвертеры, но обратный конвертация была невозможна, так как я не могу извлечь строку формата, используемую для создания определенной даты.

Это было полезно?

Решение

Вы могли бы создать класс DateFormatChoice который содержит свойство для кода формата (например, "m" или "D") и свойство для текущей даты, отформатированной таким образом.

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

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

Вы привязываете свой ComboBox к их коллекции, используя CurrentDateExample в любом из ваших DataTemplate или в виде выпадающего списка DisplayMemberPath.Вы можете либо использовать эти объекты непосредственно с вашим классом выбора формата даты, либо DatePicker привязывается к FormatCode свойство выбранного DateFormatChoice объект, или вы можете установить ValueMemberPath свойство в исходном выпадающем списке для FormatCode собственность и использование SelectedValue в выпадающем списке для получения / настройки того, что выбрано.Не использующий ValueMember могло бы быть немного проще.


Вот более полный пример.Он использует DateFormatChoice классом выше.

Во-первых, сбор данных.

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

Затем я создал простую ViewModel для окна:

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 ) );
    }
}

У меня не было элемента управления date picker, который принимал стандартные коды формата string, поэтому я создал довольно тупой UserControl (со многими обрезанными углами), просто чтобы продемонстрировать получение им кода формата.Я дал ему свойство зависимости, называемое DateFormatProperty типа string и указал измененное значение обратного вызова в UIPropertyMetadata.

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

Обратный вызов:

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 );
    }
}

И вот как я связал все это вместе на Витрине.

<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>
Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top