DependencyProperty Setter调用After OnItemsSourceChanged

时间:2015-01-16 10:53:28

标签: c# wpf dependency-properties itemssource

当我的ItemsSource发生变化时,我需要访问一些数据,以便我可以在DataGrid中正确生成列和绑定。要做到这一点,我需要绑定不同的模板并选择它们(不幸的是,在这种情况下,CellTemplateSelector并不适合我。)

似乎在下面的代码中,TemplateListing的setter被称为AFTER OnItemsSourceChanged。任何人都可以解释为什么或如何解决这个问题?

public class SpreadsheetCellTemplateListing : DependencyObject
{
    public DataTemplate structTemplate { get; set; }
    public DataTemplate atomicTemplate { get; set; }
}

class SpreadsheetDataGrid : DataGrid
{
    public static readonly DependencyProperty TemplateListingProperty =
    DependencyProperty.Register("TemplateListing", typeof(SpreadsheetCellTemplateListing), typeof(SpreadsheetCellTemplateListing), new PropertyMetadata(null));

    public SpreadsheetCellTemplateListing TemplateListing
    {
        get { return (SpreadsheetCellTemplateListing)GetValue(TemplateListingProperty); }
        set { SetValue(TemplateListingProperty, value); }
    }

    protected override void OnItemsSourceChanged(System.Collections.IEnumerable oldValue, System.Collections.IEnumerable newValue)
    {
        base.OnItemsSourceChanged(oldValue, newValue);

        //Template listing is NULL
}}

1 个答案:

答案 0 :(得分:0)

我提出了一个解决方案来延迟初始化,直到列加载,然后所有属性都可用。

public class SpreadsheetCellTemplateListing : DependencyObject
{
    public DataTemplate structTemplate { get; set; }
    public DataTemplate atomicTemplate { get; set; }
}

internal class SpreadsheetDataGrid : DataGrid
{
    private bool InitializeColumnsOnLoad = false;

    public SpreadsheetDataGrid()
    {
        Loaded += OnLoaded;
    }

    private void OnLoaded(object sender, RoutedEventArgs routedEventArgs)
    {
        if (InitializeColumnsOnLoad)
        {
            InitializeColumns();
        }
    }

    public static readonly DependencyProperty TemplateListingProperty =
        DependencyProperty.Register("TemplateListing", typeof (SpreadsheetCellTemplateListing),
            typeof (SpreadsheetCellTemplateListing), new PropertyMetadata(null));

    public SpreadsheetCellTemplateListing TemplateListing
    {
        get { return (SpreadsheetCellTemplateListing) GetValue(TemplateListingProperty); }
        set { SetValue(TemplateListingProperty, value); }
    }

    protected override void OnItemsSourceChanged(System.Collections.IEnumerable oldValue,
        System.Collections.IEnumerable newValue)
    {
        base.OnItemsSourceChanged(oldValue, newValue);
        if (!IsLoaded)
        {
            InitializeColumnsOnLoad = true;
        }
        else
        {
            InitializeColumns();
        }
    }
}