我有一个场景,我需要获取所选 TextCell 的值并使用它来更新 ListView 之外的标签。我注意到 ListView 有一个 SelectedItem 属性,而 TextCell 有一个 Command 属性。这些有什么区别?
作为一个更一般的设计问题(我正在使用 Xamarin MVVM),我应该如何进行更新?目前我正在考虑使用 ListView SelectedItem 属性并将其(双向)与我的 VM 绑定(bind)。然后在 Setter 中,我将更新标签绑定(bind)到的 VM 属性.... 问题是我有一个需要执行的异步任务,因为它将 TextCell 值转换为我需要的 Label 值。 ...我该怎么做?
我见过提到行为,但这似乎更多地用于 UI(而不是逻辑)。我也尝试过使用 Task.Run 来解决 setter 中的异步问题,但很明显异步项不适合 setter。我还考虑过使用 MessagingCenter,但这似乎是针对 VM -> VM 的。 TextCell 命令似乎合适,但已阅读改为使用 SelectedItems。
看法:
<ListView x:Name="ResultsList"
SelectedItem="{Binding SelectedDestinationItem,
Mode=TwoWay}">
<ListView.ItemTemplate>
<DataTemplate>
<TextCell Text="{Binding Description}" Detail="{Binding Place_ID}"/>
</DataTemplate>
</ListView.ItemTemplate>
</ListView>
<Label Text="{Binding Current.Destination}"/>
对于虚拟机:
public AutoCompletePrediction SelectedDestinationItem
{
get => _selectedDestinationItem;
set
{
SetProperty(ref _selectedDestinationItem, value, "SelectedDestinationItem");
if (_selectedDestinationItem == null) return;
//not valid
var place = await Places.GetPlace(_selectedDestinationItem.Place_ID, Constants.PlacesApiKey);
Current.Destination = place;
SelectedDestinationItem = null;
}
}
private AutoCompletePrediction _selectedDestinationItem;
最佳答案
示例虚拟机:
public class MyViewModel : ViewModelBase {
private string _text;
public string Text {
get => _text;
set {
_text = value;
OnPropertyChanged();
}
}
private YourItemType _selectedItem;
public YourItemType SelectedItem {
get => _selectedItem;
set {
_selectedItem = value;
Task.Run(() => GetValue(value));
OnPropertyChanged();
}
}
private readonly object _lockObject = new object();
private void GetValue(YourItemType item){
if(item == null) {
Text = "invalid";
return;
}
//avoid entering twice here
lock(_lockObject) {
//Do your work here - it's in the background already
Text = resultOfWork;
}
}
}
OnPropertyChanged() 是 INotifyPropertyChanged 的实现。就像是:
public class ViewModelBase : INotifyPropertyChanged {
public event PropertyChangedEventHandler PropertyChanged;
[NotifyPropertyChangedInvocator]
protected virtual void OnPropertyChanged([CallerMemberName] string propertyName = null) {
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
}
protected virtual void OnPropertyChangedByName(string propertyName) {
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
}
public void RefreshView() {
foreach (var propertyInfo in GetType().GetRuntimeProperties()) {
OnPropertyChangedByName(propertyInfo.Name);
}
}
}
关于c# - 与 ListView SelectedItem 与 TextCell 命令绑定(bind),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48977929/