为自定义用户控件

时间:2015-07-18 14:44:41

标签: xamarin xamarin.forms

我正在尝试创建名为Xamarin.Forms的第一个LocationSelector自定义用户控件。它有一个Entry,当用户输入内容时,会显示一个包含可选位置的列表(类似于Google地图中的选择)。

所选位置是控件的重要“返回值”。 我的计划是捕获列表的ItemSelected事件并设置SelectedLocation属性。 LocationSelector被设计为MVVM,因为到目前为止一切正常,只是Code-Behind(我认为足以描述问题):

public partial class LocationSelector : StackLayout
{
    public static readonly BindableProperty SelectedLocationProperty =
      BindableProperty.Create<LocationSelector, LocationModel>(s => s.SelectedLocation, new LocationModel(), BindingMode.TwoWay);

    public LocationSelector()
    {
        InitializeComponent();
        var model = new LocationSelectorModel();
        BindingContext = model;

        _listView.ItemSelected += (sender, args) =>
        {
            SelectedLocation = model.SelectedLocation;
        };
    }

    public LocationModel SelectedLocation
    {
        get { return (LocationModel)GetValue(SelectedLocationProperty); }
        set { SetValue(SelectedLocationProperty, value); }
    }
}

现在我想在BindingContext设置为SearchViewModel的搜索视图中使用此控件:

<ContentPage x:Class="Application.App.Views.SearchView" ...>
    <c:LocationSelector SelectedLocation="{Binding Location}"/>
</ContentPage>

public class SearchViewModel : ViewModel
{
    private LocationModel _location;
    public LocationModel Location
    {
        get { return _location; }
        set { SetProperty(ref _location, value); }
    }       
}

不幸的是,这不起作用。输出抛出一个绑定警告:

  

绑定:'Application.App.CustomControls.LocationSelectorModel'找​​不到'Location'属性,target属性:'Application.App.CustomControls.LocationSelector.SelectedLocation'

为什么将绑定指向ViewModel中的属性,该属性在我的自定义控件中使用,而不是在视图的BindingContext中使用?

1 个答案:

答案 0 :(得分:3)

问题是将BindingContext设置为用户控件的视图模型:

public LocationSelector()
{
    var model = new LocationSelectorModel();
    BindingContext = model; // this causes the problem
    // ...
}

this帖子中,我找到了解决方案。将BindingContext设置为每个子元素而不是整个用户控件正在执行此任务:

public LocationSelector()
{
    var model = new LocationSelectorModel();
    foreach (var child in Children)
    {
        child.BindingContext = model;
    }
}