Я пытаюсь реализовать ContentVage MVVM с ListView, который должен быть привязан к заполненному универсальному списку объектов модели XML в ViewModel, но привязка не удалась.Показанный код вызывает API, который возвращает действительный список данных XML.Тот же код прекрасно работает, когда привязка выполняется непосредственно в коде за страницей содержимого XAML Xamarin, устанавливая ItemSource в codebehind.Как уже было сказано, проблема возникает только при попытке передать ListView через ViewModel, назначенную на страницу содержимого.Я прошел через код в ViewModel и ListView успешно заполнен, но привязка просто не работает.У меня есть другие элементы управления на странице, для которых работает привязка модели, но единственный неработающий элемент управления - это ListView.Код показан ниже:
ViewModel:
using RestDemo.Model;
using RestDemo.Views;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Net.Http;
using System.Text;
using System.Threading.Tasks;
using System.Xml.Linq;
using Xamarin.Forms;
using Xamarin.Forms.Xaml;
using System.ComponentModel;
using System.Windows.Input;
using System.Collections.ObjectModel;
namespace RestDemo.ViewModel
{
public class ViewModel : INotifyPropertyChanged
{
public event PropertyChangedEventHandler PropertyChanged;
public ViewModel ()
{
GetRequest();
}
List<XmlPizzaDetails> _objPizzaList;
string _selectedDescription = "Descriptions: ";
bool _progress;
string _cusButtonText = "Hello";
public bool Progress
{
get { return _progress; }
set { _progress = value; }
}
public string CusButtonText
{
get { return _cusButtonText; }
set { _cusButtonText = value; }
}
public string SelectedDescription
{
get { return _selectedDescription; }
set { _selectedDescription = value; }
}
public List<XmlPizzaDetails> ObjPizzaList
{
get { return _objPizzaList; }
set
{
if (_objPizzaList != value)
{
_objPizzaList = value;
OnPropertyChanged("ObjPizzaList");
}
}
}
public string Description
{
get { return _selectedDescription; }
set { _selectedDescription = value; }
}
public ICommand SelectedCommand => new Command(() =>
{
CusButtonText = "Goodby";
});
event PropertyChangedEventHandler INotifyPropertyChanged.PropertyChanged
{
add
{
}
remove
{
}
}
public async void GetRequest()
{
if (NetworkCheck.IsInternet())
{
Uri geturi = new Uri("http://api.androidhive.info/pizza/?format=xml"); //replace your xml url
HttpClient client = new HttpClient();
HttpResponseMessage responseGet = await client.GetAsync(geturi);
string response = await responseGet.Content.ReadAsStringAsync();
//Xml Parsing
ObjPizzaList = new List<XmlPizzaDetails>();
XDocument doc = XDocument.Parse(response);
foreach (var item in doc.Descendants("item"))
{
XmlPizzaDetails ObjPizzaItem = new XmlPizzaDetails();
ObjPizzaItem.ID = item.Element("id").Value.ToString();
ObjPizzaItem.Name = item.Element("name").Value.ToString();
ObjPizzaItem.Cost = item.Element("cost").Value.ToString();
ObjPizzaItem.Description = item.Element("description").Value.ToString();
ObjPizzaList.Add(ObjPizzaItem);
}
Progress = false;
}
}
protected virtual void OnPropertyChanged(string propertyName)
{
if (PropertyChanged != null)
{
PropertyChanged(this,
new PropertyChangedEventArgs(propertyName));
}
}
}
}
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:xlocal="clr-namespace:RestDemo.ViewModel"
xmlns:local="clr-namespace:RestDemo"
xmlns:Views="clr-namespace:RestDemo.Views"
x:Class="RestDemo.XmlParsingPageBehavior">
<ContentPage.BindingContext>
<xlocal:ViewModel />
</ContentPage.BindingContext>
<Grid>
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="*"/>
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<Grid Grid.Row="0" Grid.Column="0" Grid.ColumnSpan="2">
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="*" />
<ColumnDefinition Width="*" />
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<Views:CustomButton Grid.Row="0" Grid.Column="0" Text="HOME" />
<Views:CustomButton Grid.Row="0" Grid.Column="1" Text="Administrative Maintence" />
<Views:CustomButton Grid.Row="0" Grid.Column="2" Text="User Maintence" />
<Views:CustomButton Grid.Row="0" Grid.Column="3" Text="About" />
</Grid>
<Grid Grid.Row="1" Grid.Column="0" Grid.ColumnSpan="2">
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="Auto" />
</Grid.ColumnDefinitions>
<Views:CustomButton Grid.Row="0" Grid.Column="0" Text="{Binding CusButtonText, Mode=TwoWay}">
<Views:CustomButton.Behaviors>
<local:ItemSelectedToCommandBehavior />
</Views:CustomButton.Behaviors>
</Views:CustomButton>
</Grid>
<Frame Margin="5, 5, 5, 5" Grid.Row="2" Grid.Column="1" BackgroundColor = "Cyan">
<ListView x:Name="PizzaListView" ItemsSource="{Binding ObjPizzaList}" Margin="5, 0, 5, 0" Grid.Row="2" Grid.Column="1" HorizontalOptions="FillAndExpand" HasUnevenRows="True">
<ListView.ItemTemplate>
<DataTemplate>
<ViewCell>
<Grid HorizontalOptions="FillAndExpand" Margin="0,0,0,0" Padding="20">
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<Label Text="{Binding Name}" HorizontalOptions="StartAndExpand" Grid.Row="0" TextColor="Blue" FontAttributes="Bold"/>
<Label Text="{Binding Cost}" HorizontalOptions="StartAndExpand" Grid.Row="1" TextColor="Orange" FontAttributes="Bold"/>
<Label Text="{Binding Description}" HorizontalOptions="StartAndExpand" Grid.Row="2" TextColor="Gray" FontAttributes="Bold"/>
<BoxView HeightRequest="2" Margin="0,10,10,0" BackgroundColor="Gray" Grid.Row="3" HorizontalOptions="Fill" />
</Grid>
</ViewCell>
</DataTemplate>
</ListView.ItemTemplate>
</ListView>
</Frame>
</Grid>
<ActivityIndicator x:Name="ProgressLoader" IsVisible="{Binding Progress}" IsRunning="True"/>
</Grid>
</ContentPage>