Xamarin Forms TapGestureRecognizer 未发出命令

问题描述

所以我有一个 xamarin 表单应用程序,目前只为 android 实现。我正在尝试实现点击事件。当点击时,这永远不会命中 viewmodel 中的命令。我不确定我的代码是否有问题,或者我只是执行错误

视图模型代码

    private RelayCommand<object> _OnClickableLabel;

    public RelayCommand<object> OnClickableLabel
    {
        get { return _OnClickableLabel ?? (_OnClickableLabel = new RelayCommand<object>((currentObject) => Test(currentObject))); }
    }

    private void Test(object currentObject)
    {
        Application.Current.MainPage.displayAlert("Alert","were going down cap","OK");
    }

页面 Xaml:

  <ListView Grid.Row="1" ItemsSource="{Binding Notifications}" RowHeight="100">
    <ListView.ItemTemplate>
        <DataTemplate>
            <ViewCell>
                <StackLayout Orientation="Vertical"  BackgroundColor="{Binding BackgroundColor}">
                    <StackLayout.GestureRecognizers>
                        <TapGestureRecognizer Command="{Binding OnClickableLabel }" />
                    </StackLayout.GestureRecognizers>
                    <Label FontSize="Large" Text="{Binding Title}"></Label>
                    <Label FontSize="Small" Text="{Binding Text}"></Label>
                </StackLayout>
            </ViewCell>
        </DataTemplate>
    </ListView.ItemTemplate>
</ListView>

我已经使用页面的 cs 代码中的方法对其进行了测试,效果很好,但它必须在 viewmodel 中实现,因为它会影响该数据。

解决方法

根据您的描述,您想在 ListView 中add a tap gesture recognizer,并且想将 ListView 当前行数据传递给 TapGestureRecognizer 事件,对吗?

如果是的话,按照Jason的意见,你需要先看看Xamarin.Forms Relative Bindings,把ListView命名为listview1,然后看看下面的代码:

<ListView
            x:Name="listview1"
            Grid.Row="1"
            ItemsSource="{Binding Notifications}"
            RowHeight="100">
            <ListView.ItemTemplate>
                <DataTemplate>
                    <ViewCell>
                        <StackLayout BackgroundColor="{Binding BackgroundColor}" Orientation="Vertical">
                            <StackLayout.GestureRecognizers>
                                <TapGestureRecognizer Command="{Binding BindingContext.OnClickableLabel,Source={x:Reference listview1}}" CommandParameter="{Binding .}" />
                            </StackLayout.GestureRecognizers>
                            <Label FontSize="Large" Text="{Binding Title}" />
                            <Label FontSize="Small" Text="{Binding Text}" />
                        </StackLayout>
                    </ViewCell>
                </DataTemplate>
            </ListView.ItemTemplate>
        </ListView>

public partial class Page16 : ContentPage
{
    public ObservableCollection<Notclass> Notifications { get; set; }
    public ICommand OnClickableLabel { get; set; }
    public Page16()
    {
        InitializeComponent();
        Notifications = new ObservableCollection<Notclass>()
        {
            new Notclass(){Title="title 1",Text="notification 1"},new Notclass(){Title="title 2",Text="notification 2"},new Notclass(){Title="title 3",Text="notification 3"},new Notclass(){Title="title 4",Text="notification 4"},new Notclass(){Title="title 5",Text="notification 5"}

        };
        OnClickableLabel = new Command(n=> {
            var vm = (Notclass)n;
            Application.Current.MainPage.DisplayAlert("Alert",vm.Title,"OK"); 
        });

        this.BindingContext = this;
    }
}

public class Notclass
{
    public string Title { get; set; }
    public string Text { get; set; }
    public Color BackgroundColor { get; set; } = Color.White;
}