Почему привязка не обновляет выбранный элемент средства выбора

У меня есть Picker в моей форме Xamarin, привязанной к модели (код ниже).

Метод Load устанавливает SelectedVehicle, но средство выбора не показывает выбранный автомобиль. Когда страница загружается впервые, средство выбора показывает правильный элемент в списке. Но при перезагрузке страницы после изменения App.VehicleId средство выбора отображается пустым.

Даже если я явно установил SelectedIndex на сборщике во время OnAppearing, сборщик будет пустым, а SelectedIndex будет снова установлен на -1, когда я посмотрю позже.

Как правильно обновить выбор средства выбора при перезагрузке страницы?

Xaml:

<?xml version="1.0" encoding="utf-8" ?>
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
             xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
             xmlns:local="clr-namespace:DefectReport"
             x:Class="DefectReport.MainPage">
    <ContentPage.Content>
        <ScrollView>
            <StackLayout>
                <Label x:Name="Message" TextColor="Red" />
                <Label Text="Welcome to Vehicle Check" />
                <Label Text="Choose vehicle" />
                <Picker ItemsSource="{Binding Vehicles}" ItemDisplayBinding="{Binding RegistrationNumber}" SelectedItem="{Binding SelectedVehicle}" SelectedIndexChanged="Picker_SelectedIndexChanged" />
                <Label Text="{Binding SelectedVehicle.Description}" />
                <Button Text="Add vehicle not in list" Clicked="SelectVehicle_Clicked" />
                <Button Text="Check vehicle" Clicked="CheckVehicle_Clicked" />
                <Button Text="Log out" Clicked="LogOut_Clicked" />
            </StackLayout>
        </ScrollView>
    </ContentPage.Content>
</ContentPage>

Код позади:

public partial class MainPage : ContentPage {
    public class VehicleInfo : Model {
        public async void Load() {
            Vehicles = new ObservableCollection<Vehicle>(await App.Database.ReadAsync<Vehicle>().ToListAsync());
            SelectedVehicle = Vehicles.FirstOrDefault(v => v.DeviceRecordId == App.VehicleId) ?? Vehicles.FirstOrDefault();
            System.Diagnostics.Debug.WriteLine("App.VehicleId = " + App.VehicleId);
            System.Diagnostics.Debug.WriteLine("SelectedVehicle.Id = " + selectedVehicle.DeviceRecordId);
        }

        private Vehicle selectedVehicle;

        public Vehicle SelectedVehicle {
            get { return selectedVehicle; }
            set {
                if (selectedVehicle != value) {
                    selectedVehicle = value;
                    OnPropertyChanged("SelectedVehicle");
                }
            }
        }

        private ObservableCollection<Vehicle> vehicles;

        public ObservableCollection<Vehicle> Vehicles {
            get { return vehicles; }
            set {
                if (vehicles != value) {
                    vehicles = value;
                    OnPropertyChanged("Vehicles");
                }
            }
        }

    }
    VehicleInfo data;
    public MainPage() {
        data = new VehicleInfo();
        BindingContext = data;
        InitializeComponent();
    }

    protected override void OnAppearing() {
        base.OnAppearing();
        data.Load();
    }

Model - это простой класс, реализующий INotifyPropertyChanged:

public class Model : System.ComponentModel.INotifyPropertyChanged {
    public void OnPropertyChanged(string name) {
        if (PropertyChanged != null)
            PropertyChanged(this, new PropertyChangedEventArgs(name));
    }

    public event PropertyChangedEventHandler PropertyChanged;
}

person Nikki Locke    schedule 20.10.2017    source источник


Ответы (1)


Оказывается, проблема заключалась в создании нового ObservableCollection. Я изменил код

Vehicles = new ObservableCollection<Vehicle>(await App.Database.ReadAsync<Vehicle>().ToListAsync());

и вместо этого очистил существующую коллекцию и добавил в нее новые записи.

person Nikki Locke    schedule 20.10.2017