我试图设置一个项目表(UITableView),每个单元格中都有一个按钮,导航到其项目的详细配置文件。
但我不确定在MvvmCross中正确处理这个问题的方法是什么。我的一些想法:
ItemCellView
的按钮插座公开并将其绑定在GetOrCreateCellFor
ShowItemDetailsCommand
传递到每个ItemCellView
并将其绑定到ItemCellView
到ItemsView
的简单回调,而不是绑定MvxViewModel
并从那里调用导航服务public class Item
{
public string Name { get; set; }
}
public class ItemsViewModel : MvxViewModel
{
public List<Item> Items { get; }
public MvxCommand ShowItemDetailsCommand { get; }
readonly IMvxNavigationService _navigationService;
readonly IDatabaseService _databaseService;
public ItemsViewModel(IMvxNavigationService navigationService, IDatabaseService databaseService)
{
ShowItemDetailsCommand = new MvxCommand(ShowItemDetails);
_navigationService = navigationService;
_databaseService = databaseService;
Items = _databaseService.SelectItems();
}
void ShowItemDetails()
{
// not sure how "item" gets here so far
_navigationService.Navigate<ItemDetailsViewModel, Item>(item);
}
}
public partial class ItemsView : MvxTableViewController<ItemsViewModel>
{
public ItemsView() : base("ItemsView", null) {}
public override void ViewDidLoad()
{
base.ViewDidLoad();
TableView = View as UITableView;
var source = new TableViewSource(TableView);
var bindings = this.CreateBindingSet<ItemsView, ItemsViewModel>();
bindings.Bind(source).To(vm => vm.Items);
bindings.Apply();
TableView.Source = source;
TableView.ReloadData();
}
public class TableViewSource : MvxTableViewSource
{
public TableViewSource(UITableView tableView) : base(tableView)
{
TableView.RegisterNibForCellReuse(UINib.FromName("ItemCellView", NSBundle.MainBundle), ItemCellView.kCellId);
}
protected override UITableViewCell GetOrCreateCellFor(UITableView tableView, NSIndexPath indexPath, object item)
{
return TableView.DequeueReusableCell(ItemCellView.kCellId, indexPath) as ItemCellView;
}
}
}
public partial class ItemCellView : MvxTableViewCell
{
public const string kCellId = "item_cell";
// also has an [Outlet] UIButton in the .designer.cs part
public ItemCellView(IntPtr handle) : base(handle)
{
this.DelayBind(() =>
{
var bindings = this.CreateBindingSet<ItemCellView, Item>();
bindings.Bind(Name).To(i => i.Name);
bindings.Apply();
});
}
}
答案 0 :(得分:2)
您应该在单元格的构造方法中绑定ItemCellView
的按钮:
// MyBtn is my Cell's button outlet
protected ItemCellView(IntPtr handle) : base(handle)
{
this.DelayBind(() =>
{
var bindings = this.CreateBindingSet<MyTableViewCell, Item>();
// Use this bind to set your button's title
bindings.Bind(MyBtn).For("Title").To(item => item.Name);
// This bind is used for binding a command in the Item model
// CommandParameter can pass your parameter
bindings.Bind(MyBtn).To(item => item.ShowItemDetailsCommand).CommandParameter(DataContext);
bindings.Apply();
});
}
由于在Cell中DataContext已更改为Item
模型,因此应在模型类中配置绑定命令:
public class Item
{
private readonly Lazy<IMvxNavigationService> _navigationService = new Lazy<IMvxNavigationService>(Mvx.Resolve<IMvxNavigationService>);
public string Name { set; get; }
private ICommand showItemDetailsCommand;
public ICommand ShowItemDetailsCommand
{
get
{
return showItemDetailsCommand ?? (showItemDetailsCommand = new MvxCommand<Item>(ShowItemDetails));
}
}
async void ShowItemDetails(Item item)
{
await _navigationService.Value.Navigate<SecondViewModel, Item>(item);
}
}
最后,您要推送的SecondViewModel将通过事件Prepare()
接收此参数:
public class SecondViewModel : MvxViewModel<Item>
{
public override void Prepare(Item parameter)
{
}
}