You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C# Xamarin.Forms中如何将ViewModel层异步等待数据传递到View层

问题根因

  1. locations是公共字段,XAML数据绑定仅支持绑定公共属性,不支持字段
  2. 未实现属性变更通知,异步赋值完成后UI无法收到变更通知
  3. 绑定数据源类型不匹配:LocationsList是包装类,实际可渲染的列表数据是其内部的Locations属性,直接绑定包装类无法正常渲染列表

修改方案

1. 调整LocationsViewModel属性定义

你继承的BaseViewModel默认已封装INotifyPropertyChanged相关逻辑,直接使用其提供的属性变更通知方法即可:

class LocationsViewModel : BaseViewModel
{
    private Location deviceLocation;
    // 替换原有public LocationsList locations;字段
    private LocationsList _locations;
    public LocationsList Locations
    {
        get => _locations;
        set
        {
            _locations = value;
            OnPropertyChanged(); // 方法名与BaseViewModel保持一致,部分模板可能叫NotifyPropertyChanged
            // 同步通知列表属性变更
            OnPropertyChanged(nameof(LocationItems));
        }
    }
    // 暴露给ListView绑定的实际列表属性
    public List<LocationItem> LocationItems => Locations?.Locations;
    // 若后续需要动态增删列表项,将List替换为ObservableCollection<LocationItem>即可

    public LocationsViewModel()
    {
        Title = "Lokacije";
        // 建议将此处调用移到Page的OnAppearing中,避免构造函数异步逻辑吞异常
        // RunAsyncMethods();
    }

    // 改返回值为Task,避免async void丢异常
    public async Task RunAsyncMethods()
    {
        Locations = await FetchLocationsJson();
        deviceLocation = await FetchDeviceLocation();
        Locations = await SortLocationsByProximity(deviceLocation, Locations);
    }
}

2. 修改XAML绑定路径

将ListView的ItemsSource绑定到新增的列表属性:

<ListView Grid.Row="1"
          x:Name="LocationsListView"
          ItemsSource="{Binding LocationItems}"
          ...>

3. 可选:优化异步逻辑触发时机

在LocationsPage.xaml.cs中添加页面生命周期触发逻辑,避免构造函数异步异常:

protected override async void OnAppearing()
{
    base.OnAppearing();
    if (BindingContext is LocationsViewModel vm && vm.Locations == null)
    {
        await vm.RunAsyncMethods();
    }
}

补充说明

如果后续修改LocationItem的属性(比如Proximity)需要同步更新UI,需要让LocationItem也继承BaseViewModel,给每个属性加上变更通知逻辑即可。

内容的提问来源于stack exchange,提问作者s3c

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.07 05:09:02