对Observable Collection的更改未更新DataGrid

时间:2014-11-17 18:52:51

标签: wpf mvvm prism

我的viewmodel中有一个可观察的集合,如下所示。不完美但只是代码,如下所示填充可观察集合并将其绑定到datagrid。我在datagrid旁边还有两个按钮,一个用于upcommand,另一个用于down命令。当我单击upbutton时,一切正常,所选行向上移动并且序列顺序更新,Observable Collection也会更新。但是这些更改并没有绑定到DataGrid。同样对于down命令。我的观点如下。只有视图没有更新,命令才能正常工作。 。请帮忙。 问题在于可观察的收集,向上移动和向下移动。

视图模型:

public class JobConfigurationViewModel : BindableBase
{


    public JobConfigurationLogic JobConfigurationLogic =
        new JobConfigurationLogic(new JobConfigurationResultsRepository());

    public SrcDestConfigurationLogic SrcDestConfigurationLogic =
        new SrcDestConfigurationLogic(new SrcDestCofigurationRepository());


    private string _enterprise;

    public string Enterprise
    {
        get { return _enterprise; }
        set { SetProperty(ref _enterprise, value); }
    }

    private int currentJobID;
    private int currentSequence;
    private int previousJobID;
    private int previousSequence;
    private string _site;

    public string Site
    {
        get { return _site; }
        set { SetProperty(ref _site, value); }
    }

    private int _siteID;

    public int SiteID
    {
        get { return _siteID; }
        set { SetProperty(ref _siteID, value); }
    }

    private ObservableCollection<JobConfigurationResults> _jobEntities;

    public ObservableCollection<JobConfigurationResults> JobEntities
    {
        get { return _jobEntities; }
        set
        {
            SetProperty(ref _jobEntities, value);
            //JobEntities.CollectionChanged += JobEntities_CollectionChanged;
            OnPropertyChanged("JobEntities");
        }
    }

    //void JobEntities_CollectionChanged(object sender, System.Collections.Specialized.NotifyCollectionChangedEventArgs e)
    //{
    //    if (e.OldItems != null)
    //    {
    //        foreach (var item in e.OldItems)
    //        {
    //            this.GetJobConfigurationResults();
    //        }
    //    }
    //}

    //Source System List for Job
    private List<SourceSiteSystem> _lstJobSrcSystems;

    public List<SourceSiteSystem> LstJobSrcSystems
    {
        get { return _lstJobSrcSystems; }
        set
        {
            //Using bindable base setproperty method instead of older inotify prop changed method
            SetProperty(ref _lstJobSrcSystems, value);
        }
    }

    //Deestination  System List for Job
    private List<DestinationSiteSystem> _lstJobDestSystems;

    public List<DestinationSiteSystem> LstJobDestSystems
    {
        get { return _lstJobDestSystems; }
        set
        {
            //Using bindable base setproperty method instead of older inotify prop changed method
            SetProperty(ref _lstJobDestSystems, value);
        }
    }

    //the Selected Source Site system ID 
    private int _selectedSrcSiteSystemId = 0;

    public int SelectedSrcSiteSystemId
    {
        get { return _selectedSrcSiteSystemId; }
        set
        {
            //Using bindable base setproperty method instead of older inotify prop changed method
            SetProperty(ref _selectedSrcSiteSystemId, value);
        }
    }

    //the Selected Source Site system from the dropdown
    private SourceSiteSystem _selectedSrcSiteSystem;

    public SourceSiteSystem SelectedSrcSiteSystem
    {
        get { return _selectedSrcSiteSystem; }
        set
        {
            //Using bindable base setproperty method instead of older inotify prop changed method
            if (value != null)
            {
                SetProperty(ref _selectedSrcSiteSystem, value);
                SelectedSrcSiteSystemId = SelectedSrcSiteSystem.SiteSystemId;
            }
        }
    }

    //the Selected Destination Site system ID 
    private int _selectedDestSiteSystemId = 0;

    public int SelectedDestSiteSystemId
    {
        get { return _selectedDestSiteSystemId; }
        set
        {
            //Using bindable base setproperty method instead of older inotify prop changed method
            SetProperty(ref _selectedDestSiteSystemId, value);
        }
    }

    //the Selected Destination Site system from the dropdown
    private DestinationSiteSystem _selectedDestSiteSystem;

    public DestinationSiteSystem SelectedDestSiteSystem
    {
        get { return _selectedDestSiteSystem; }
        set
        {
            //Using bindable base setproperty method instead of older inotify prop changed method
            if (value != null)
            {
                SetProperty(ref _selectedDestSiteSystem, value);
                SelectedDestSiteSystemId = SelectedDestSiteSystem.SiteSystemId;
            }
        }
    }

    private JobConfigurationResults _jeJobConfigurationResults;

    public JobConfigurationResults JEJobConfigurationResults
    {
        get { return _jeJobConfigurationResults; }
        set { _jeJobConfigurationResults = value; }
    }

    private List<JobTaskConfiguration> _taskSelectionList = new List<JobTaskConfiguration>();

    private CancellationTokenSource _source;

    private RelayCommand<object> _commandSaveInstance;
    private RelayCommand<object> _hyperlinkInstance;
    private RelayCommand<object> _commandRunJob;
    private RelayCommand<object> _upCommand;
    private RelayCommand<object> _downCommand;
    private IEventAggregator _aggregator;


    /// <summary>
    /// This is a Subscriber to the Event published by EnterpriseViewModel
    /// </summary>
    /// <param name="agg"></param>
    public JobConfigurationViewModel(IEventAggregator agg)
    {
        _aggregator = agg;
        PubSubEvent<Message> evt = _aggregator.GetEvent<PubSubEvent<Message>>();
        evt.Subscribe(message => Enterprise = message.Enterprise.ToString(), ThreadOption.BackgroundThread);
        evt.Subscribe(message => Site = message.Site.ToString(), ThreadOption.BackgroundThread);
        evt.Subscribe(message => SiteID = message.SiteID, ThreadOption.BackgroundThread);
        //evt.Unsubscribe();
        StartPopulate();
    }

    private async void StartPopulate()
    {
        await TaskPopulate();
    }

    //This is to ensure that the publisher has published the data that is needed for display in this workspace
    private bool TaskProc()
    {
        Thread.Sleep(500);
        PubSubEvent<Message> evt = _aggregator.GetEvent<PubSubEvent<Message>>();
        evt.Subscribe(message => Enterprise = message.Enterprise.ToString(), ThreadOption.BackgroundThread);
        evt.Subscribe(message => Site = message.Site.ToString(), ThreadOption.BackgroundThread);
        evt.Subscribe(message => SiteID = message.SiteID, ThreadOption.BackgroundThread);
        return DoPopulate();
    }

    private Task<bool> TaskPopulate()
    {
        _source = new CancellationTokenSource();
        return Task.Factory.StartNew<bool>(TaskProc, _source.Token);
    }

    /// <summary>
    /// This method handles the populating of the Source and Destination Dropdowns and the Job entity and Task Datagrid
    ///   This is mainly driven by the Site selected in the previous workspace
    /// </summary>
    /// <returns></returns>

    private bool DoPopulate()
    {
        PopulateSourceDestinations(this.SiteID);

        return true;
    }

    /// <summary>
    /// this method displays all entities and tasks for the site.
    /// This is done async so that the Publisher thread is not held up
    /// </summary>
    public void GetJobConfigurationResults()
    {
        if (SelectedSrcSiteSystem == null)
        {
            SelectedSrcSiteSystem = LstJobSrcSystems[0];
        }
        if (SelectedDestSiteSystem == null)
        {
            SelectedDestSiteSystem = LstJobDestSystems[0];
        }
        SelectedSrcSiteSystemId = SelectedSrcSiteSystem.SiteSystemId;
        SelectedDestSiteSystemId = SelectedDestSiteSystem.SiteSystemId;
        var jobConfigurationResults = new JobConfigurationResults
        {
            SourceId = SelectedSrcSiteSystemId,
            DestinationId = SelectedDestSiteSystemId
        };
        JobEntities = new ObservableCollection<JobConfigurationResults>();
        JobEntities = JobConfigurationLogic.GetResults(jobConfigurationResults.SourceId,
            jobConfigurationResults.DestinationId);
        _taskSelectionList = new List<JobTaskConfiguration>(JobEntities.Count * 3);
    }

    /// <summary>
    /// //Adding a method to pupulate the Source and Destination dropdown lists. 
    /// This is done async so that the Publisher thread is not held up
    /// </summary>
    /// 
    /// 
    public async void PopulateSourceDestinations(int siteId)
    {
        this.LstJobSrcSystems = SrcDestConfigurationLogic.LoadSourceSiteSystems(siteId);
        this.LstJobDestSystems = SrcDestConfigurationLogic.LoadDestinationSystems(siteId);
        GetJobConfigurationResults();
    }

    public ICommand HyperlinkCommand
    {
        get
        {
            if (_hyperlinkInstance == null)
                _hyperlinkInstance = new RelayCommand<object>(openDialog);
            return _hyperlinkInstance;
        }
    }

    private void openDialog(object obj)
    {
        JobConfigurationResults results = obj as JobConfigurationResults;
        JEJobConfigurationResults = JobEntities.SingleOrDefault(x => x.JobEntityId == results.JobEntityId);

    }

    public ICommand CommandSave
    {
        get
        {
            if (_commandSaveInstance == null)
                _commandSaveInstance = new RelayCommand<object>(saveJobConfigurationChanges);
            return _commandSaveInstance;
        }
    }

    public ICommand CommandRunJob
    {
        get { return _commandRunJob ?? (_commandRunJob = new RelayCommand<object>(RunJob)); }
    }

    /// <summary>
    /// this saves all the changes in the selection made by the user 
    /// </summary>
    /// <param name="ob"></param>
    public void saveJobConfigurationChanges(object ob)
    {
        foreach (var job in JobEntities)
        {
            JobConfigurationLogic.UpdateSequence(job.SequenceOrder, job.JobEntityId); //Save Sequence Changes
            int jobEntityId = job.JobEntityId;
            foreach (var task in job.TaskDetails)
            {
                int id = task.JobTask_ID;
                bool isSelected = task.IsSelected;
                _taskSelectionList.Add(task);
            }
        }
        JobConfigurationLogic.UpdateTaskSelection(_taskSelectionList);
    }


    public ICommand UpCommand
    {
        get
        {
            if (_upCommand == null)
                _upCommand = new RelayCommand<object>(MoveUp);
            return _upCommand;
        }
    }

    private void MoveUp(object obj)
    {
        if (obj != null)
        {
            JobConfigurationResults results = obj as JobConfigurationResults;
            currentJobID = results.JobEntityId;
            currentSequence = results.SequenceOrder - 1;

            JobConfigurationResults previousResult =
                JobEntities.FirstOrDefault(n => n.SequenceOrder == currentSequence);
            try
            {
                previousJobID = previousResult.JobId;
                previousSequence = previousResult.SequenceOrder;

                int newindex = JobEntities.IndexOf(results);
                int oldindex = JobEntities.IndexOf(previousResult);

                JobEntities[newindex].SequenceOrder = previousResult.SequenceOrder;
                JobEntities[oldindex].SequenceOrder = results.SequenceOrder + 1;


                //foreach (var i in JobEntities)
                //{
                //    MessageBox.Show(i.EntityName + " " + i.SequenceOrder);
                //}
            }
            catch (NullReferenceException)
            {
                MessageBox.Show("You have reached the top");
            }
        }

        else
        {
            MessageBox.Show("Select a row first");
        }
    }



    public ICommand DownCommand
    {
        get
        {
            if (_downCommand == null)
                _downCommand = new RelayCommand<object>(MoveDown);
            return _downCommand;
        }
    }

    private void MoveDown(object obj)
    {
        if (obj != null)
        {
            JobConfigurationResults results = obj as JobConfigurationResults;
            currentJobID = results.JobEntityId;
            currentSequence = results.SequenceOrder + 1;

            JobConfigurationResults previousResult =
                JobEntities.FirstOrDefault(n => n.SequenceOrder == currentSequence);
            try
            {
                previousJobID = previousResult.JobId;
                previousSequence = previousResult.SequenceOrder;


                int newindex = JobEntities.IndexOf(results);
                int oldindex = JobEntities.IndexOf(previousResult);

                JobEntities[newindex].SequenceOrder = previousResult.SequenceOrder;
                JobEntities[oldindex].SequenceOrder = results.SequenceOrder - 1;

                foreach (var i in JobEntities)
                {
                    MessageBox.Show(i.EntityName + " " + i.SequenceOrder);
                }
            }
            catch (NullReferenceException)
            {
                MessageBox.Show("You cannot move further down");
            }

        }

        else
        {
            MessageBox.Show("Select a row first");
        }
    }

    /// <summary>
    /// Execute an etl job using the current job id
    /// </summary>
    private void RunJob(object obj)
    {
        JobEngine jobEngine = new JobEngine();
        var jobId = JobEntities[0].JobId;
        jobEngine.ProcessJob(jobId);
    }
}

View.XAML:

<UserControl.Resources>
        <DataTemplate x:Key="ItemTemplate1">
            <StackPanel>
                <TextBlock Text="{Binding Name}"/>
            </StackPanel>
        </DataTemplate>
        <DataTemplate x:Key="ItemTemplate2">
            <StackPanel>
                <TextBlock Text="{Binding Status}"/>
            </StackPanel>
        </DataTemplate>

        <Style TargetType="{x:Type Border}">
            <Setter Property="Background" Value="Bisque" />
            <Setter Property="TextBlock.FontSize" Value="14" />
            <Setter Property="BorderBrush" Value="Black" />
            <Setter Property="BorderThickness" Value="1" />
            <Setter Property="HorizontalAlignment" Value="Stretch" />
        </Style>
    </UserControl.Resources>
    <Grid>

        <Grid.RowDefinitions>
            <RowDefinition Height="Auto"></RowDefinition>
            <RowDefinition Height="Auto"></RowDefinition>
            <RowDefinition Height="3*"></RowDefinition>
            <RowDefinition Height="Auto"></RowDefinition>
            <RowDefinition Height="*"></RowDefinition>
        </Grid.RowDefinitions>
        <Grid.ColumnDefinitions>
            <ColumnDefinition Width="*"></ColumnDefinition>
            <ColumnDefinition Width="0.14*"></ColumnDefinition>
        </Grid.ColumnDefinitions>
        <StackPanel Grid.Row="0" Grid.ColumnSpan="2">
            <TextBlock>
                <Label FontSize="16">Enterprise:</Label>
                <Label Name="lblEnterprise"  FontSize="16" Content="{Binding Enterprise}" />
                <Label FontSize="16">Site:</Label>
                <Label Name="lblSite" FontSize="16" Content="{Binding Site}" HorizontalAlignment="Right" />
            </TextBlock>
        </StackPanel>
        <StackPanel Grid.Row="1" Grid.Column="0">
            <TextBlock>
                <Label FontSize="16">Source System:</Label>
                <ComboBox Name="CmbSource" Margin="3" SelectedIndex="0" Width="220" ItemsSource="{Binding LstJobSrcSystems}" SelectedItem="{Binding SelectedSrcSiteSystem, Mode=TwoWay}" DisplayMemberPath ="SourceSystemType"></ComboBox>
            </TextBlock>
        </StackPanel>
        <StackPanel Grid.Column="0" Grid.Row="1">
            <TextBlock HorizontalAlignment="Right" Margin="2,2,14,2">
            <Label FontSize="16">Destination System:</Label>
            <ComboBox Name="CmbDestination" SelectedIndex="0" Margin="2" Width="220" ItemsSource="{Binding LstJobDestSystems}" SelectedItem="{Binding SelectedDestSiteSystem, Mode=TwoWay}" DisplayMemberPath ="DestinationSystemType"></ComboBox>
            </TextBlock>
        </StackPanel>
        <StackPanel Grid.Row="2" Grid.ColumnSpan="2" Margin="0,2,0,46" Grid.RowSpan="3">
            <Border BorderThickness="1" Width="{Binding ElementName=dgEntities,Path=Width}" Margin="35,48,60,48" Height="{Binding ElementName=grd,Path=Height}">
                <Grid Name="grd" Height="30" Width="{Binding ElementName=JobConfigCol,Path=Width}" ShowGridLines="True">
                    <Grid.ColumnDefinitions>
                        <ColumnDefinition x:Name="c1" Width="82*"/>
                        <ColumnDefinition x:Name="c2" Width="83*"/>
                        <ColumnDefinition x:Name="c3" Width="83*"/>
                        <ColumnDefinition x:Name="c4" Width="96*"/>
                    </Grid.ColumnDefinitions>
                    <Label Grid.Column="0" HorizontalAlignment="Center" FontWeight="Bold" FontSize="16" Margin="24,0,78,0" Width="62" Content="Extract"/>
                    <Label Grid.Column="1" HorizontalAlignment="Center" FontWeight="Bold" FontSize="16" Margin="40,0,38,0" Width="88" Content="Transform"/>
                    <Label Grid.Column="2" HorizontalAlignment="Center" FontWeight="Bold" FontSize="16" Margin="66,0,54,0" Width="46" Content="Load"/>
                </Grid>
            </Border>

            <DataGrid x:Name="dgEntities" Width="690" Height="370" Margin="40,-48,65,-8" CanUserAddRows="false" SelectionMode="Single" ItemsSource="{Binding}" AutoGenerateColumns="False" CanUserSortColumns="False">
                <DataGrid.DataContext>
                    <CollectionViewSource x:Name="CollectionViewSource" Source="{Binding Path=JobEntities,Mode=TwoWay,NotifyOnTargetUpdated=True}">
                    </CollectionViewSource>
                </DataGrid.DataContext>
                <DataGrid.Columns>
                    <DataGridTemplateColumn Header="Status" Width="138" MaxWidth="138">
                        <DataGridTemplateColumn.CellTemplate>
                            <DataTemplate>
                                <Button Margin="5" Content="{Binding TaskDetails[0].Status,Mode=TwoWay,NotifyOnTargetUpdated=True}" Command="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type UserControl}}, Path=DataContext.HyperlinkCommand}" CommandParameter="{Binding ElementName=dgEntities,Path=SelectedItem}" Foreground="Blue" Cursor="Hand" MouseDoubleClick="Control_OnMouseDoubleClick" >
                                    <Button.Template>
                                        <ControlTemplate TargetType="Button">
                                            <TextBlock TextDecorations="Underline">
                                             <ContentPresenter />
                                            </TextBlock>
                                        </ControlTemplate>
                                    </Button.Template>
                                </Button>
                            </DataTemplate>
                        </DataGridTemplateColumn.CellTemplate>
                    </DataGridTemplateColumn>

                    <DataGridTemplateColumn MinWidth="{Binding ElementName=c1,Path=ActualWidth}">
                        <DataGridTemplateColumn.Header>
                            <CheckBox Name="chkHeaderExtract" Checked="ChkHeaderExtract_OnChecked" Unchecked="ChkHeaderExtract_OnUnchecked"></CheckBox>
                        </DataGridTemplateColumn.Header>

                        <DataGridTemplateColumn.CellTemplate>

                            <DataTemplate>

                                <CheckBox HorizontalAlignment="Center" VerticalAlignment="Center" Name="chkExtract" IsChecked="{Binding TaskDetails[0].IsSelected,Mode=TwoWay,NotifyOnTargetUpdated=True,UpdateSourceTrigger=PropertyChanged}"></CheckBox>

                            </DataTemplate>

                        </DataGridTemplateColumn.CellTemplate>

                    </DataGridTemplateColumn>

                    <DataGridTemplateColumn Header="Status" Width="138" MaxWidth="138">
                        <DataGridTemplateColumn.CellTemplate>
                            <DataTemplate>
                                <Button Margin="5" Content="{Binding TaskDetails[1].Status,Mode=TwoWay,NotifyOnTargetUpdated=True,UpdateSourceTrigger=PropertyChanged}" Command="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type UserControl}}, Path=DataContext.HyperlinkCommand}" CommandParameter="{Binding ElementName=dgEntities,Path=SelectedItem}" Cursor="Hand" Foreground="Blue" MouseDoubleClick="Control_OnMouseDoubleClick_2" >
                                    <Button.Template>
                                        <ControlTemplate TargetType="Button">
                                            <TextBlock TextDecorations="Underline">
                                             <ContentPresenter />
                                            </TextBlock>
                                        </ControlTemplate>
                                    </Button.Template>
                                </Button>

                            </DataTemplate>
                        </DataGridTemplateColumn.CellTemplate>
                    </DataGridTemplateColumn>
                    <DataGridTemplateColumn MinWidth="{Binding ElementName=c2,Path=ActualWidth}">
                        <DataGridTemplateColumn.Header>
                            <CheckBox Name="chkHeaderTransform" Checked="ChkHeaderTransform_OnChecked" Unchecked="ChkHeaderTransform_OnUnchecked"></CheckBox>
                        </DataGridTemplateColumn.Header>
                        <DataGridTemplateColumn.CellTemplate>
                            <DataTemplate>

                                <CheckBox HorizontalAlignment="Center" VerticalAlignment="Center" Name="chkTransform" IsChecked="{Binding TaskDetails[1].IsSelected,Mode=TwoWay,NotifyOnTargetUpdated=True,UpdateSourceTrigger=PropertyChanged}"></CheckBox>

                            </DataTemplate>
                        </DataGridTemplateColumn.CellTemplate>
                    </DataGridTemplateColumn>

                    <DataGridTemplateColumn Header="Status" Width="138" MaxWidth="138">
                        <DataGridTemplateColumn.CellTemplate>
                            <DataTemplate>
                                <Button Margin="5" Content="{Binding TaskDetails[2].Status,Mode=TwoWay,NotifyOnTargetUpdated=True}" Command="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type UserControl}}, Path=DataContext.HyperlinkCommand}" CommandParameter="{Binding ElementName=dgEntities,Path=SelectedItem}" Cursor="Hand" Foreground="Blue" MouseDoubleClick="Control_OnMouseDoubleClick" >
                                    <Button.Template>
                                        <ControlTemplate TargetType="Button">
                                            <TextBlock TextDecorations="Underline">
                                             <ContentPresenter />
                                            </TextBlock>
                                        </ControlTemplate>
                                    </Button.Template>

                                </Button>

                            </DataTemplate>
                        </DataGridTemplateColumn.CellTemplate>
                    </DataGridTemplateColumn>
                    <DataGridTemplateColumn MinWidth="{Binding ElementName=c3,Path=ActualWidth}">
                        <DataGridTemplateColumn.Header>
                            <CheckBox Name="chkHeaderLoad" Checked="ChkHeaderLoad_OnChecked" Unchecked="ChkHeaderLoad_OnUnchecked"></CheckBox>
                        </DataGridTemplateColumn.Header>
                        <DataGridTemplateColumn.CellTemplate>
                            <DataTemplate>

                                <CheckBox HorizontalAlignment="Center" VerticalAlignment="Center" Name="chkLoad" IsChecked="{Binding TaskDetails[2].IsSelected,Mode=TwoWay,NotifyOnTargetUpdated=True,UpdateSourceTrigger=PropertyChanged}"></CheckBox>

                            </DataTemplate>
                        </DataGridTemplateColumn.CellTemplate>
                    </DataGridTemplateColumn>

                    <DataGridTextColumn Binding="{Binding EntityName}"  Header="Entity" Width="{Binding ElementName=c4,Path=ActualWidth}"/>
                </DataGrid.Columns>
            </DataGrid>



            <StackPanel HorizontalAlignment="Right" Margin="0,-388,43,0" Height="108">
                <TextBlock HorizontalAlignment="Right" VerticalAlignment="Top"><InlineUIContainer>
                        <Button Height="40" Width="40" x:Name="btnup" Command="{Binding UpCommand}" CommandParameter="{Binding ElementName=dgEntities,Path=SelectedItem}" Click="Btnup_OnClick">
                            <Image x:Name="Up" Source="../Images/up.jpg" Height="40" />
                        </Button>
                    </InlineUIContainer></TextBlock>
                <TextBlock HorizontalAlignment="Right" VerticalAlignment="Bottom" Margin="0,2"><InlineUIContainer>
                        <Button Height="40" Width="40" x:Name="btndown" Command="{Binding DownCommand}" CommandParameter="{Binding ElementName=dgEntities,Path=SelectedItem}" Click="btndown_Click">
                            <Image x:Name="Down" Source="../Images/Down.jpg" Height="40" />
                        </Button>
                    </InlineUIContainer></TextBlock>
            </StackPanel>

        </StackPanel>
        <StackPanel Grid.Row="4" Grid.Column="0">
            <TextBlock Name="tbldemo" HorizontalAlignment="Right">
                <Button Name="btnRun" Height="30" Width="90" FontSize="18" Margin="9" Command="{Binding CommandRunJob}" >Run</Button>
                <Button Name="btnSave" Height="30" Width="90" FontSize="18" Margin="9" Command="{Binding CommandSave, Mode=OneWay}">Save</Button>
            </TextBlock>
        </StackPanel>

        <StackPanel Grid.Row="4" Grid.Column="0">
            <TextBlock HorizontalAlignment="Left">
               <Button Name="btnclose" Height="30" Width="90" FontSize="18" Margin="19,9">Close</Button>
            </TextBlock>
        </StackPanel>
    </Grid>
</UserControl>

CS:我说的是CollectionViewSource.View.Refresh();

1 个答案:

答案 0 :(得分:1)

我相信你走在正确的轨道上。当您从视图模型更改集合中的属性时,视图未更新的原因是因为当您使用ObservableCollection使其按照您描述的方式正常工作时,您需要确保类型您在集合中绑定的实现INotifyProperyChanged。执行此操作后,ObservableCollection将收到此消息,然后通知您查看更改并最终导致视图更新。

因此,在您的情况下,您需要确保JobConfigurationResults类型实现INotifyPropertyChanged接口。

作为参考,您可以查看此链接,并在页面底部找到描述我建议的注释。 http://msdn.microsoft.com/en-us/library/ms748365(v=vs.110).aspx