Hi I am Building a Xamarin App using a firebase realtime db that looks like this:
-->PetProfile
---->Node
->UserEmail
->PetName
->Breed
---->Node
->UserEmail
->PetName
->Breed
I have managed to make a collection view showing all the pets of the user by using the useremail as a key. However I am having a problem. If I add a new pet in the database on the addPetPage and navigate back to the page with the collectionView it doesn't update the collectionView unless I reload the App. Why would that be?
here is my code for the the ViewModel:
class MyIDPageViewModel : INotifyPropertyChanged
{
FirebaseHelper firebaseHelper = new FirebaseHelper();
public Command AddAPetCommand { get; set; }
private string _petName;
private string _breed;
private string _dob;
private string _gender;
private string _weight;
private string _petCareInfo;
public string PetName { get => _petName;set {_petName = value; }}
public string Breed { get => _breed;set { _breed = value;}}
public string DOB {get => _dob; set { _dob = value;}}
public string Gender{get => _gender; set{ _gender = value;}}
public string Weight{get => _weight; set{_weight = value;}}
public string PetCareInfo {get => _petCareInfo; set{ _petCareInfo = value; }}
public IList<PetProfile> source;
public ObservableCollection<PetProfile> PetInfo { get; private set; }
public IList<PetProfile> EmptyPetInfo
{
get => source;
private set
{
if (value != source)
{
source = value;
OnPropertyChanged(nameof(EmptyPetInfo));
}
}
}
public MyIDPageViewModel()
{
source = new ObservableCollection<PetProfile>();
AddAPetCommand = new Command( () => PerformAddAPetCommand());
CreatePetProfileCollection();
}
private async void PerformAddAPetCommand()
{
await firebaseHelper.AddPetInfo(_petName, _breed, _dob, _weight, _gender, _petCareInfo);
var petProfiles = await firebaseHelper.GetAllUserPetInfos();
if (petProfiles != null)
{
EmptyPetInfo = new ObservableCollection<PetProfile>();
foreach (var groupitems in petProfiles)
{
EmptyPetInfo.Add(new PetProfile() { PetName = groupitems.PetName, UserEmail = groupitems.UserEmail, Breed = groupitems.Breed, DOB = groupitems.DOB, Gender = groupitems.Gender, Weight = groupitems.Weight, CareInformation = groupitems.CareInformation });
}
OnPropertyChanged();
}
}
public async void CreatePetProfileCollection()
{
var petProfiles = await firebaseHelper.GetAllUserPetInfos();
if (petProfiles != null)
{
EmptyPetInfo = new ObservableCollection<PetProfile>();
foreach (var groupitems in petProfiles)
{
EmptyPetInfo.Add(new PetProfile() { PetName = groupitems.PetName, UserEmail = groupitems.UserEmail, Breed = groupitems.Breed, DOB = groupitems.DOB, Gender = groupitems.Gender, Weight = groupitems.Weight, CareInformation = groupitems.CareInformation });
}
}
}
#region INotifyPropertyChanged
public event PropertyChangedEventHandler PropertyChanged;
void OnPropertyChanged([CallerMemberName] string propertyName = null)
{
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
}
#endregion
}
Here is the xaml page:
<ContentPage.Content>
<ScrollView>
<StackLayout>
<Label Text="Add a Pet:"
VerticalOptions="Start"
HorizontalOptions="Start"
Padding="15"
FontSize="Large"
FontAttributes="Bold"/>
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="360"/>
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*"/>
</Grid.ColumnDefinitions>
<Image Source="https://i.pinimg.com/564x/bf/99/57/bf9957520ad1e6145cadc9c1c2e08b0f.jpg"
Aspect="AspectFit"/>
<Image Source="https://cdn1.iconfinder.com/data/icons/rounded-black-basic-ui/139/Photo_Add-RoundedBlack-512.png"
Scale="0.25"/>
</Grid>
<Grid Margin="15" Padding="0" RowSpacing="0" ColumnSpacing="5">
<Grid.RowDefinitions>
<RowDefinition Height="60"/>
<RowDefinition Height="60"/>
<RowDefinition Height="60"/>
<RowDefinition Height="60"/>
<RowDefinition Height="60"/>
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*"/>
<ColumnDefinition Width="*"/>
</Grid.ColumnDefinitions>
<Label Text="Name:" Padding="0" FontAttributes="Bold" FontSize="20" Grid.Row="0" Grid.Column="0" VerticalOptions="End"/>
<Label Text="Breed:" Padding="0" FontAttributes="Bold" FontSize="20" Grid.Row="0" Grid.Column="1" VerticalOptions="End"/>
<Label Text="Age:" Padding="0" FontAttributes="Bold" FontSize="20" Grid.Row="2" Grid.Column="0" VerticalOptions="End"/>
<Label Text="Weight:" Padding="0" FontAttributes="Bold" FontSize="20" Grid.Row="2" Grid.Column="1" VerticalOptions="End"/>
<Label Text="Gender:" Padding="0" FontAttributes="Bold" FontSize="20" Grid.Row="4" Grid.Column="0" VerticalOptions="End"/>
<Entry x:Name="PetName" Text="{Binding PetName}" Grid.Row="1" Grid.Column="0" Background="white" PlaceholderColor="Black" VerticalOptions="Start"/>
<Entry x:Name="Breed" Text="{Binding Breed}" Grid.Row="1" Grid.Column="1" Background="white" PlaceholderColor="Black" VerticalOptions="Start"/>
<DatePicker x:Name="DOB" Date="{Binding DOB}" Grid.Row="3" Grid.Column="0" VerticalOptions="Start" Format="dd-MM-yyyy"/>
<Picker x:Name="gender" SelectedItem="{Binding Gender}" Title="Select a Gender" TitleColor="Black" Grid.Row="5" Grid.Column="0" VerticalOptions="Start">
<Picker.Items>
<x:String>Male</x:String>
<x:String>Female</x:String>
</Picker.Items>
</Picker>
<Picker x:Name="Weight" SelectedItem="{Binding Weight}" Title="Select a Weight" TitleColor="Black" Grid.Row="3" Grid.Column="1" VerticalOptions="Start">
<Picker.Items>
<x:String>S: 2 - 8 Kg</x:String>
<x:String>M: 9 - 20 Kg</x:String>
<x:String>L: 21 - 40 Kg</x:String>
<x:String>XL: 41+ Kg</x:String>
</Picker.Items>
</Picker>
</Grid>
<Label x:Name="CareInformation" Text="Care Information" FontSize="Large" FontAttributes="Bold" Margin="15"/>
<Editor x:Name="PetCareInfo" Text="{Binding PetCareInfo}" Placeholder="Help for our dogwalkers and sitters:" Margin="15"/>
<Button Text="Submit">
<Button.Behaviors>
<behaviors:EventToCommandBehavior EventName="Clicked" Command="{Binding AddAPetCommand}"/>
</Button.Behaviors>
</Button>
</StackLayout>
</ScrollView>
</ContentPage.Content>
The Page with the collection view:
<ContentPage.BindingContext>
<local:MyIDPageViewModel/>
</ContentPage.BindingContext>
<ContentPage.Content>
<StackLayout>
<Label
Text="My Id"
VerticalOptions="Start"
HorizontalOptions="Start"
Padding="15"
FontSize="Title"
FontAttributes="Bold"
TextColor="Black"/>
<Label Text="Name:" FontSize="Subtitle" Margin="15,0" FontAttributes="Bold"/>
<Label x:Name="UserName" FontSize="Medium" Margin="15,0"/>
<Label Text="Email Address:" FontSize="Subtitle" Margin="15,0" FontAttributes="Bold"/>
<Label x:Name="UserEmail" FontSize="Medium" Margin="15,0"/>
<Label Text="Phone Number:" FontSize="Subtitle" Margin="15,0" FontAttributes="Bold"/>
<Label x:Name="UserPhoneNumber" FontSize="Medium" Margin="15,0"/>
<Label Text="Address:" FontSize="Subtitle" Margin="15,0" FontAttributes="Bold"/>
<Label x:Name="UserAddress" FontSize="Medium" Margin="15,0"/>
<Label Text="My Pets:" FontSize="Large" Margin="15,0" FontAttributes="Bold"/>
<CollectionView ItemsSource="{Binding EmptyPetInfo}" >
<CollectionView.ItemTemplate>
<DataTemplate>
<Grid Padding="10">
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="Auto" />
</Grid.ColumnDefinitions>
<Label Grid.Column="0"
Grid.Row="0"
Text="{Binding PetName}"
FontAttributes="Bold" />
<Label Grid.Row="0"
Grid.Column="2"
Text="View Profile"
FontAttributes="Italic"
VerticalOptions="End" />
<Label Grid.Column="1"
Grid.Row="0"
Text="{Binding PetName}"
FontAttributes="Bold" />
<Label Grid.Row="0"
Grid.Column="2"
Text="View Profile"
FontAttributes="Italic"
VerticalOptions="End">
<Label.GestureRecognizers>
<TapGestureRecognizer Tapped="ViewPetProfile_Tapped"/>
</Label.GestureRecognizers>
</Label>
</Grid>
</DataTemplate>
</CollectionView.ItemTemplate>
</CollectionView>
<Label Text="+ Add pet" HorizontalOptions="Center" FontAttributes="Bold">
<Label.GestureRecognizers>
<TapGestureRecognizer Tapped="AddaPet_Tapped"/>
</Label.GestureRecognizers>
</Label>
<Button Text="Edit" HorizontalOptions="End" Margin="15" Clicked="Edit_Clicked"/>
</StackLayout>
</ContentPage.Content>
</ContentPage>