IMultiValue Converter Issue - PullRequest
       1

IMultiValue Converter Issue

0 голосов
/ 09 июня 2018

ItemsSource DataGrid привязан к ObservableCollection.Два из DataGridColumns привязаны к свойству DateTime в коллекции, в то время как третий столбец используется для отображения разницы дат между ними с помощью конвертера IMultiValue.Поведение, которое я пытаюсь понять и найти, можно найти в Сценарии 2.

Сценарий 1: Нет проблем

Представление открыто, и DataGrid уже содержит записи, поскольку коллекция НЕ пуста.Если новый объект добавляется в коллекцию, он отображается в DataGrid, и в последнем столбце правильно отображается значение разницы дат.

Сценарий 2. Имеет проблему

Представление открыто, но DataGrid содержитнет записей, потому что коллекция пуста.Если новый объект добавляется в коллекцию, он отображается в DataGrid, но последний столбец (содержащий конвертер) пуст.Однако, если представление затем закрывается и повторно открывается, разница данных отображается корректно в DataGrid.

Мне бы хотелось, чтобы значение разницы дат отображалось в DataGridcolumn при первом добавлении объекта в пустую коллекцию.,Чего мне не хватает?

Класс объекта

public class Evaluation
{

    public int ID { get; set; }
    public DateTime BirthDate { get; set; }
    public DateTime TestDate { get; set; }
}

ViewModel

public class EvaluationViewModel : ViewModelBase  
{

private ObservableCollection<Evaluation> evaluations;

public class EvaluationViewModel()
{
    evaluations = Utility.Convert<Evaluation>(db.evaluationRepository.GetAllById(Subject.ID));
    TestView = (CollectionView)new CollectionViewSource { Source = Evaluations }.View;
    TestView.SortDescriptions.Add(new SortDescription("TestDate", ListSortDirection.Ascending));
}



    public ObservableCollection<Evaluation> Evaluations
    {
        get { return evaluations; }

    }

    public CollectionView TestView { get; set; }

}

Просмотр

public class Evaluation
{
    public int ID { get; set; }
    public DateTime BirthDate { get; set; }
    public DateTime TestDate { get; set; }
}


<Window.Resources>
    <converters:DateDiffMonthMultiConverter x:Key="DateConverter"/>
</Window.Resources>

    <DataGrid ItemsSource="{Binding TestView}">
        <DataGrid.Columns>
            <DataGridTextColumn Binding="{Binding Path=ID}" Visibility="Hidden"/>
            <DataGridTextColumn Header="Birth Date" Binding="{Binding BirthDate}"/>
            <DataGridTextColumn Header="Test Date" Binding="{Binding TestDate}"/>
            <DataGridTemplateColumn Header="Age When Tested">
                <DataGridTemplateColumn.CellTemplate>
                    <DataTemplate>
                        <TextBlock>
                            <TextBlock.Text>
                                <MultiBinding Converter="{StaticResource DateConverter}">
                                    <Binding Path="BirthDate"/>
                                    <Binding Path="TestDate"/>
                                </MultiBinding>
                            </TextBlock.Text>
                        </TextBlock>
                    </DataTemplate>
                </DataGridTemplateColumn.CellTemplate>
            </DataGridTemplateColumn>
        </DataGrid.Columns>
    </DataGrid>

Конвертер

public class DateDiffMonthMultiConverter : IMultiValueConverter
{        
    public object Convert(object[] values, Type targetType, object parameter, CultureInfo culture)
    {            
        string result = string.Empty;
        if(values[0] is DateTime && values[1] is DateTime)
        {
            DateTime start = (DateTime)values[1];
            DateTime end = (DateTime)values[0];
            TimeSpan ts = start - end;
            double avgDaysPerMonth = 30.4;
            double months = (double)ts.Days / avgDaysPerMonth;
            string suffix = months > 1 ? "mths" : "mth";
            result = string.Format("{0} {1}", months.ToString("0.0"), suffix);                 
        }           
        return result;
    }

    public object[] ConvertBack(object value, Type[] targetType, object parameter, CultureInfo culture)
    {
        return null;
    }
}

Ответы [ 2 ]

0 голосов
/ 13 июня 2018

Как выяснилось, конвертер не был проблемой, но вместо этого одним из значений, используемых конвертером, является DependencyProperty (мой плохой способ не распознавать это до сих пор), и он выдавал ошибку DependencyProperty.UnsetValue.Мне удалось решить проблему с помощью метода CreateNew () при добавлении нового объекта в коллекцию, поэтому свойство навигации было известно во время загрузки объекта в DataGrid.

0 голосов
/ 10 июня 2018

Я попробовал ваш код (добавление элемента в коллекцию ObservableCollection через 2 секунды), и он работает для меня.Вот мой код:

MainWindow.xaml.cs

public MainWindow()
{
    InitializeComponent();
    DataContext = new EvaluationViewModel();
    Loaded += MainWindow_Loaded;

}

private void MainWindow_Loaded(object sender, RoutedEventArgs e)
{
    Task.Factory.StartNew(() => Thread.Sleep(2000))
    .ContinueWith((t) =>
    {
        (DataContext as EvaluationViewModel).Evaluations.Add(
      new Evaluation() { ID = 2, BirthDate = DateTime.Now.AddYears(-22), TestDate = DateTime.Now });
    }, TaskScheduler.FromCurrentSynchronizationContext());
}

ViewModel

public EvaluationViewModel()
{
    Evaluations = new ObservableCollection<Evaluation>();
    TestView = (CollectionView)new CollectionViewSource { Source = Evaluations }.View;
    TestView.SortDescriptions.Add(new SortDescription("TestDate", ListSortDirection.Ascending));
}

public ObservableCollection<Evaluation> Evaluations { get; }
public CollectionView TestView { get; set; }
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...