Xamarin使用xct TouchEffect长按ListView时MessagingCenter订阅失败问题求助
问题根因及修复方案
- 构造函数逻辑缺失导致Command未初始化
你当前的Item类中,LongPressItemCommand仅在无参构造函数中完成初始化,如果你在ItemViewModel中填充Items集合时,使用的是new Item("物品名", "描述")这个带参构造函数创建实例,那么生成的Item对象的LongPressItemCommand为null,长按事件不会触发任何逻辑,自然不会发送消息。
修复方法:修改带参构造函数,让它调用无参构造,保证所有实例都会初始化Command:
public Item(string itemName, string itemDescription) : this() { ItemName = itemName; ItemDescription = itemDescription; }
- 可选优化:调整Command绑定位置,符合MVVM规范
你现在把业务逻辑相关的Command放在Model层属于不合理的设计,完全可以把长按Command放到ItemViewModel中,不需要用MessagingCenter中转,实现更简单:
- 首先在
ItemViewModel中添加Command定义:
public ICommand LongPressItemCommand { get; } // ViewModel构造函数中初始化 public ItemViewModel() { LongPressItemCommand = new Command<Guid>(async itemId => { // 这里直接处理长按逻辑,需要弹框的话也可以直接调用依赖服务,或者通知页面处理 await App.Current.MainPage.DisplayActionSheet("Test", "Test", "OK"); }); }
- 修改XAML中的绑定逻辑,通过父控件引用绑定到ViewModel的Command:
<Grid Padding="0,0,8,0" Margin="4,0,4,0" xct:TouchEffect.LongPressCommand="{Binding BindingContext.LongPressItemCommand, Source={x:Reference lstView}}" xct:TouchEffect.CommandParameter="{Binding ItemId}">
- 小问题修复
你当前Main_PopupMenu方法中的DisplayActionSheet是异步方法,需要加await关键字才能正常弹出:
public async void Main_PopupMenu(Guid itemId) { await DisplayActionSheet("Test", "Test", "OK"); }
另外使用MessagingCenter要记得在页面销毁时取消订阅,避免内存泄漏:
protected override void OnDisappearing() { base.OnDisappearing(); MessagingCenter.Unsubscribe<Item, Guid>(this, "PopupMenuItemMsg"); }
内容的提问来源于stack exchange,提问作者Noah
相关产品推荐
相关产品推荐

