如何将Observable Collection的Item属性绑定到Switch状态?

时间:2017-10-08 09:37:14

标签: c# xamarin mvvm xamarin.forms

我在ObservableCollectionRange中有一个社交媒体集合,我初始化如下:

public ObservableRangeCollection<SocialMediaEntity> CurrentSocialMedia { get; } = new ObservableRangeCollection<SocialMediaEntity>();

下面我获取这个Web服务列表,并将这些元素保存在集合中:

GetSonInformation().Subscribe((SonInformation) =>
                {
                    CurrentSon = SonInformation.Son;
                    CurrentSocialMedia.ReplaceRange(SonInformation.SocialMedia);

                });

在页面上,我有一个Switch组件,如果令牌有效,我想启用它,如果令牌无效或者集合中没有这样的社交媒体,则无效。

    <Switch Grid.Column="1" 
      VerticalOptions="Center"
    HorizontalOptions="End" 
   IsToggled="{Binding Path=CurrentSocialMedia,  
     Converter={StaticResource SocialMediaStatusToBoolConverter},
    ConverterParameter={StaticResource youtubeKey}}">

     <Switch.Behaviors>
       <behaviors:EventHandlerBehavior EventName="Toggled">
           <behaviors:InvokeCommandAction
                Command="{Binding ToggleYoutubeSocialMediaCommand}"
                 Converter="{StaticResource SwitchChangeEventArgsConverter}"/>

                                                    </behaviors:EventHandlerBehavior>

                                            </Switch.Behaviors>
                                        </Switch>

我接下来的方法是链接集合并使用一个转换器,该转换器返回一个布尔值和我前面提到的逻辑。

public class SocialMediaStatusToBoolConverter : IValueConverter
    {

        public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
        {

            IList<SocialMediaEntity> SocialMedias = (IList<SocialMediaEntity>)value;

            if (SocialMedias == null || SocialMedias.Count() == 0)
                return false;

            var socialMedia = SocialMedias.SingleOrDefault(social => social.Type.Equals((string)parameter));

            return socialMedia != null && !socialMedia.InvalidToken;
        }


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

问题是这只是第一次完成。当我通过替换所有项目或添加其他项目来更新集合时,不会更新任何内容。

谁能告诉我采取什么方法来做到这一点?提前谢谢。

2 个答案:

答案 0 :(得分:1)

我认为您必须将INotifyPropertyChanged实施到您的SocialMediaEntity

答案 1 :(得分:1)

由于Switch不期望IsToggled属性的集合,因此它不会监视绑定数据上的集合已更改事件。不像 a Picker would do for ItemsSource.

因此,责任又回到了视图模型。基本上,viewmodel需要确保每次更改集合时都会引发CurrentSocialMedia的属性更改事件。

例如:

void OnPropertyChanged(object sender, PropertyChangedEventArgs args)
{ 
    if(args.PropertyName != nameof(CurrentSocialMedia))
        return;

    var oldObservable = oldValue as INotifyCollectionChanged;
    if (oldObservable != null)
        oldObservable.CollectionChanged -= CollectionChanged;

    var newObservable = newValue as INotifyCollectionChanged;
    if (newObservable != null) {
        newObservable.CollectionChanged += CollectionChanged;
    }
}

void CollectionChanged(object sender, NotifyCollectionChangedEventArgs e)
{
    RaisePropertyChanged(nameof(CurrentSocialMedia));
}