微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

如何在 Xamarin Forms MVVM Prism 的选择器中隐藏单个元素?

如何解决如何在 Xamarin Forms MVVM Prism 的选择器中隐藏单个元素?

我正在使用 MVVM Prism。我想在我的选择器中隐藏一个元素,但是。我尝试使用 IsVisible 属性,但它不起作用。

这是我的 XAML

                               <Picker
                                    HorizontalOptions="End"
                                    WidthRequest="180"
                                    HeightRequest="40"
                                    IsVisible="{Binding IsDeductibleVisible,Mode=TwoWay}"
                                    ItemsSource="{Binding Deductibles}"
                                    ItemdisplayBinding="{Binding displayName}"
                                    FontSize="14"
                                    SelectedItem="{Binding SelectedDeductible}">
                              <Picker.Behaviors>
                                    <behavior:EventToCommandBehavior
                                       Command="{Binding Path=BindingContext.SelectDeductibleCommand,Source={x:Reference Name=CustomizePage}}"
                                       EventName="SelectedindexChanged"/>
                                    </Picker.Behaviors>
                                </Picker>

这是我的视图模型。第一个记录是我想隐藏的记录。 Remove 不是一个选项,因为在计算中使用了 DeductiblesEnum.Zero。

Deductibles = new List<Deductible>
        {
            new Deductible{ Id = (int)DeductiblesEnum.Zero,Amount = 0,displayName = "NIL",IsDeductibleVisible = false },new Deductible{ Id = (int)DeductiblesEnum.Thousand_100,Amount = 100000,displayName = "100,000 per insured" },new Deductible{ Id = (int)DeductiblesEnum.Thousand_150,Amount = 150000,displayName = "150,new Deductible{ Id = (int)DeductiblesEnum.Thousand_200,Amount = 200000,displayName = "200,000 per insured" }
        };

解决方法

您的场景是从 ViewModel 的列表中删除一个项目,并且您正在使用 MVVM 设计模式。 Prism 是一个框架,不会对此代码产生任何影响。 IsVisible 属性不起作用的原因是它不是正确的属性。 IsVisiblePicker 的一个属性,它将确定 Picker 是否可见。

您需要做的是更改您的 Picker.ItemSource 以删除您不想要的值。有几种方法可以解决此问题,但我将向您展示我推荐的最常用的 Xamarin 方法:

使用价值转换器

值转换器是一种强大的工具,可以将 ViewModel 中的对象映射到 UI,而无需在 ViewModel 中编写大量代码。毕竟您的 ViewModel 不应该知道它所连接的任何视图。 Read about them here

您的 ViewModel 看起来像这样,我已将您的列表转换为 ObservableCollection,因为这是最佳做法

// BaseViewModel comes from Refractored.MVVMHelpers
public class DeductiblesViewModel : BaseViewModel
{
    public ObservableCollection<Deductible> Deductibles { get; }

    public DeductiblesViewModel()
    {
        Title = "Deductibles";

        var deductibles = new List<Deductible>
        {
            new Deductible{ Id = (int)DeductiblesEnum.Zero,Amount = 0,DisplayName = "NIL",IsDeductibleVisible = false },new Deductible{ Id = (int)DeductiblesEnum.Thousand_100,Amount = 100000,DisplayName = "100,000 per insured",IsDeductibleVisible = true },new Deductible{ Id = (int)DeductiblesEnum.Thousand_150,Amount = 150000,DisplayName = "150,new Deductible{ Id = (int)DeductiblesEnum.Thousand_200,Amount = 200000,DisplayName = "200,IsDeductibleVisible = true }
        };

        Deductibles = new ObservableCollection<Deductible>(deductibles);
    }
}

然后您将创建一个新的 ValueConverter

public class DeductibleVisibilityConverter : IValueConverter
{
    public object Convert(object value,Type targetType,object parameter,CultureInfo culture)
    {
        if (value.GetType() != typeof(ObservableCollection<Deductible>))
        {
            throw new NotSupportedException($"Object must be of type: {typeof(ObservableCollection<Deductible>)}");
        }

        var deductibles = (ObservableCollection<Deductible>)value;

        return deductibles.Where(d => d.IsDeductibleVisible).ToList();
    }

    public object ConvertBack(object value,CultureInfo culture)
    {
        throw new NotImplementedException("We won't be using this method");
    }
}

并将其添加到您的 XAML:

<ContentPage
    ...
    /* Reference the xml namespace for your converter */
    xmlns:converters="clr-namespace:YourNamespace.Converters"
    ...>

    /* Add the converter as a resource to your page (or wherever you keep your resources) */
    <ContentPage.Resources>
        <ResourceDictionary>
            <converters:DeductibleVisibilityConverter x:Key="deductibleVisibilityConverter"/>
        </ResourceDictionary>
    </ContentPage.Resources>

    <ContentPage.Content>
        <StackLayout Padding="20">
            <Label Text="Select your deductibles"/>

            /* Add the converter to your item source */
            <Picker ItemsSource="{Binding Deductibles,Converter={StaticResource deductibleVisibilityConverter}}"
                    ItemDisplayBinding="{Binding DisplayName}"/>
        </StackLayout>
    </ContentPage.Content>
</ContentPage>

现在您可以隐藏任何不想在 UI 中显示的免赔额,但保留它们以供您计算!

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐


Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其他元素将获得点击?
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。)
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbcDriver发生异常。为什么?
这是用Java进行XML解析的最佳库。
Java的PriorityQueue的内置迭代器不会以任何特定顺序遍历数据结构。为什么?
如何在Java中聆听按键时移动图像。
Java“Program to an interface”。这是什么意思?