绑定到ObservableCollection的ComboBox不会更新

时间:2011-08-12 17:01:00

标签: c# wpf xaml data-binding

我有一个使用ObservableCollection作为源的ComboBox。我的源绑定如下

<ComboBox IsEditable="False"
          SelectedIndex="{Binding Source={x:Static Properties:CollectionControl.Settings}, Path=SamplingPeriodIndex, Mode=TwoWay}"
          SelectionChanged="onPeriodControlSelectionChanged"
          Name="PeriodControl"
          ItemsSource="{StaticResource test}">
    <ComboBox.ItemTemplate>
        <DataTemplate>
            <TextBlock Text="{Binding SamplingPeriod}" Visibility="{Binding Converter={StaticResource TrackVis}, ConverterParameter=GroupIndex}"/>
        </DataTemplate>
    </ComboBox.ItemTemplate>
</ComboBox>

TrackVis是一个转换器,用于确定元素是可见还是折叠,具体取决于实现了INotifyPropertyChanged的外部属性。

第一次显示ComboBox时,一切都按预期工作,但ComboBox永远不会刷新以反映更改。我必须遗漏一些东西,但截至目前,我所尝试的一切都失败了。

以下是转换器的代码

public class IsVisibleConverter : IValueConverter
{
    public object Convert(object value, Type targetType, object parameter, 
        System.Globalization.CultureInfo culture)
    {
        var tempObj = (SamplingPeriods) value;
        if (tempObj.GroupIndex >= CollectionControl.Settings.SamplingFrequencyIndex)
        {
            return Visibility.Visible;
        }

        return Visibility.Collapsed;
    }

    public object ConvertBack(object value, Type targetType, object parameter, 
        System.Globalization.CultureInfo culture)
    {
            throw new NotImplementedException();
    }
}

此外,这是集合

public class PeriodsCollection : ObservableCollection<SamplingPeriods>
{
    public PeriodsCollection()
    {
        Add(new SamplingPeriods("1/16 of a second", 13));
        Add(new SamplingPeriods("1/8 of a second", 12));
        Add(new SamplingPeriods("1/4 of a second", 11));
        Add(new SamplingPeriods("1/2 of a second", 10));
        Add(new SamplingPeriods("1 second", 9));
        Add(new SamplingPeriods("2 seconds", 8));
        Add(new SamplingPeriods("4 seconds", 7));
        Add(new SamplingPeriods("8 seconds", 6));
        Add(new SamplingPeriods("16 seconds", 5));
        Add(new SamplingPeriods("32 seconds", 4));
        Add(new SamplingPeriods("64 seconds", 3));
        Add(new SamplingPeriods("128 seconds", 2));
        Add(new SamplingPeriods("256 seconds", 1));
        Add(new SamplingPeriods("512 seconds", 0));
    }
}

public class SamplingPeriods
{
    public SamplingPeriods(string samplingPeriod, int groupIndex)
    {
        SamplingPeriod = samplingPeriod;
        GroupIndex = groupIndex;
    }

    public string SamplingPeriod { get; private set; }
    public int GroupIndex { get; private set; }
}

这个想法是选定的采样频率限制了可用的采样周期。采样频率索引的范围为0到11.例如,如果采样索引为9,则唯一有效的采样周期将具有GroupIndex&gt; = 9.其他抽样期将会崩溃。

3 个答案:

答案 0 :(得分:0)

您正在尝试跟踪采样频率指数。那么你必须绑定到具有这种属性的对象并实现INotifyPropertyChanged.Or,正如我已经说过的,将此事件传播到作为绑定源的对象,并在其上引发正确的propertychanged。否则,绑定引擎将不知道该属性的更改。 使用CollectionControl.Settings

绑定到Path = SamplingFrequencyIndex

答案 1 :(得分:0)

SamplingPeriods需要实现INotifyPropertyChanged,你需要在集合上调用NotifyPropertyChanged。我会相信CollectionControl.Settings.SamplingFrequencyIndex保存你期望从代码中获得的值代码不清楚你在哪里设置它。当您更改SamplingFrequencyIndex时,您需要在ObservabaleCollection上调用NotifyPropertyChanged以强制刷新。必须有一个更好的方法来做到这一点。更改SamplingPeriods并传递对SamplingFrequencyIndex的引用,以便更改您想要更改的实际对象。

   CollectionViewSource.GetDefaultView(lbFields.ItemsSource).Refresh();

答案 2 :(得分:0)

如果您的期间和频率都保持在同一个班级,为什么不公开可用期间列表呢?然后,您可以使用CollectionView过滤您的收藏而不是转换器&amp;能见度:

// initialize in your constructor
public PeriodsCollection AvailablePeriods { get; private set; }

public int SamplingFrequencyIndex
{
    get { return samplingFrequencyIndex; }
    set
    {
        samplingFrequencyIndex = value;
        RaisePropertyChanged("SamplingFrequencyIndex");
        var view = CollectionViewSource.GetDefaultView(AvailablePeriods) as ListCollectionView;
        view.Filter = o => ((SamplingPeriod)o).GroupIndex >= value;
    }
}