1

我尝试实现我的第一个 MVVM 项目。首先,我创建了名为“person.cs”的模型。然后我创建了一个模型视图“AddPerson.cs”,它应该动态创建存储在 person.cs 中的数据。在我看来(完全用 xaml 创建)我有一个按钮,它应该从我的“AddPerson.cs”调用方法“CreatePerson()”。我喜欢绑定方法。

此外,我创建了一个标签,它应该绑定到类“person.cs”,例如绑定到公共字符串“Name”。

如何将 Button 的 BindingContext 设置为“AddPerson.cs”-class,将 Label 的 BindingContext 设置为“person.cs”-class?

4

2 回答 2

1

您缺少一些基本概念,导致您的请求很奇怪。

您不会将数据绑定到类定义,而是绑定到类的实例。由于一个 ViewModel 是一个类,它可能包含您数据绑定到的其他类的实例,除此之外的所有内容在 99% 的情况下都是错误的做法,而您的示例不是这 1% 的情况之一。

所以基本上你的 ViewModel 应该是这样的:

public class PersonViewModel
{
   public Person Person {get; set}
   public ICommand AddPersonCommand {get; set}
}

然后,您的 BindingContext 是 PersonViewModel 的一个实例,然后在 Label 上您绑定到 Person,而在按钮上您将绑定到 AddPersonCommand。

于 2019-01-07T21:58:19.460 回答
1

是的,这是可能的。大多数元素继承BindablObject. 每个BindableObjaect都有一个BindingContext属性。请参阅:https ://docs.microsoft.com/en-us/xamarin/xamarin-forms/xaml/xaml-basics/data-binding-basics

主视图模型

整个页面的视图模型,它包含每个子视图模型。

public class MainViewModel
{
    public AddPersonViewModel AddPersonViewModel { get; }
    public PersonViewModel PersonViewModel { get; }

    public MainViewModel()
    {
        // the passed action is just a fake action to simulate adding a person
        AddPersonViewModel = new AddPersonViewModel(value => PersonViewModel.Name = value);
        PersonViewModel = new PersonViewModel();
    }
}

添加人员视图模型

包含您的添加逻辑。

public class AddPersonViewModel : INotifyPropertyChanged
{ 
    public AddPersonViewModel(Action<string> onAction)
    {
        AddPerson = new Command(() => 
        {
            onAction(NewName); // call your update logic
            NewName = ""; // reset name
        });
    }

    public Command AddPerson { get; }
    private string _name;

    public string NewName
    {
        get => _name;
        set
        {
            _name = value;
            PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(nameof(NewName)));
        }
    }
    public event PropertyChangedEventHandler PropertyChanged;
}

人视图模型

包含你的“新”人。

public class PersonViewModel : INotifyPropertyChanged
{
    private string _name;

    public string Name
    {
        get => _name;
        set
        {
            _name = value;
            PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(nameof(Name)));
        }
    }

    public event PropertyChangedEventHandler PropertyChanged;
}

主页

创建并设置您的 MainViewModel。

public partial class MainPage : ContentPage
{
    public MainPage()
    {
        InitializeComponent();
        BindingContext = new MainViewModel();
    }
}

主页.xaml

在这里,我们将BindingContextofEntry和绑定Button到 我们which的AddPersonViewModel属性上。然后我们绑定本地的和属性_ContentPage's BindingContextMainViewModelTextLabelCommandButtonNewNameAddPersonBindingContextAddPersonViewModel

对于Label.

<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
             xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
             xmlns:local="clr-namespace:App5"
             x:Class="App5.MainPage">

    <StackLayout>
        <Entry BindingContext="{Binding AddPersonViewModel}" Text="{Binding NewName}" 
           HorizontalOptions="FillAndExpand" />
        <Button BindingContext="{Binding AddPersonViewModel}" Text="Click me!" Command="{Binding AddPerson}" 
           HorizontalOptions="Center" />
        <Label Text="Added Person:" FontAttributes="Bold" 
           HorizontalOptions="Center"/>
        <Label BindingContext="{Binding PersonViewModel}" Text="{Binding Name}" 
           HorizontalOptions="Center"/>
    </StackLayout>

</ContentPage>

这个例子很老套,但我想你明白了。关键是已经提到的属性BindingContext

于 2019-01-07T21:36:07.787 回答