Unable to bind ViewModel to View - c#

I want to Display a list of pictures in a LongListSelector on Windows Phone 8.
That´s my Model:
public class LocationMediaModel : INotifyPropertyChanged
{
private string _id;
public string ID
{
get
{
return _id;
}
set
{
if (value != _id)
{
_id = value;
NotifyPropertyChanged("ID");
}
}
}
private string _mediatype;
public string MediaType
{
get
{
return _mediatype;
}
set
{
if (value != _mediatype)
{
_mediatype = value;
NotifyPropertyChanged("MediaType");
}
}
}
private string _url;
public string URL
{
get
{
return _url;
}
set
{
if (value != _url)
{
_url = value;
NotifyPropertyChanged("URL");
}
}
}
public event PropertyChangedEventHandler PropertyChanged;
private void NotifyPropertyChanged(String propertyName)
{
PropertyChangedEventHandler handler = PropertyChanged;
if (null != handler)
{
handler(this, new PropertyChangedEventArgs(propertyName));
}
}
}
Here´s my ViewModel:
public class LocationMediaViewModel : INotifyPropertyChanged
{
public LocationMediaViewModel()
{
this.MediaItems = new ObservableCollection<LocationMediaModel>();
}
public ObservableCollection<LocationMediaModel> MediaItems { get; private set; }
public event PropertyChangedEventHandler PropertyChanged;
private void NotifyPropertyChanged(String propertyName)
{
PropertyChangedEventHandler handler = PropertyChanged;
if (null != handler)
{
handler(this, new PropertyChangedEventArgs(propertyName));
}
}
// Properties vom Model <-> ViewModel:
private string _id;
public string ID
{
get
{
return _id;
}
set
{
if (value != _id)
{
_id = value;
NotifyPropertyChanged("ID");
}
}
}
private string _mediatype;
public string MediaType
{
get
{
return _mediatype;
}
set
{
if (value != _mediatype)
{
_mediatype = value;
NotifyPropertyChanged("MediaType");
}
}
}
private string _url;
public string URL
{
get
{
return _url;
}
set
{
if (value != _url)
{
_url = value;
NotifyPropertyChanged("URL");
}
}
}
public bool IsDataLoaded
{
get;
private set;
}
public void LoadData()
{
// Sample data; replace with real data
this.MediaItems.Add(new LocationMediaModel() { ID = "3e3b1e48-8463-424b-8256-15c569358dfb", MediaType = "jpg", URL = "http://media.contoso.com/thumbs/f3be161f-cffc-485e-8f1d-52cfcebc1c79.jpg" });
this.MediaItems.Add(new LocationMediaModel() { ID = "e5e7cb87-04bb-498a-ab57-83bd5c3425c4", MediaType = "jpg", URL = "http://media.contoso.com/thumbs/99FBBBB0-9C16-4E0A-B6E7-A1A709638D06.jpg" });
this.MediaItems.Add(new LocationMediaModel() { ID = "b45931bf-0778-45cc-9efa-fc1aa397ccd9", MediaType = "jpg", URL = "http://media.contoso.com/thumbs/dff96a4f-f22f-4c6d-af24-504a1c80b7c4.jpg" });
this.MediaItems.Add(new LocationMediaModel() { ID = "a23e31b1-9232-086c23fe2279ab1bb22dd0", MediaType = "jpg", URL = "http://media.contoso.com/thumbs/1d1315c7-3292-4e67-8189-5db5393ec801.jpg" });
this.MediaItems.Add(new LocationMediaModel() { ID = "22991670-32b2-45f6-be69-3892b9587865", MediaType = "jpg", URL = "http://media.contoso.com/thumbs/433EA3D7-B9BF-4F3E-96C8-EEC1B9B04896.jpg" });
this.IsDataLoaded = true;
}
}
And finaly my XAML view:
<phone:PhoneApplicationPage
x:Class="WhaGoO.LocationPage"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:phone="clr-namespace:Microsoft.Phone.Controls;assembly=Microsoft.Phone"
xmlns:shell="clr-namespace:Microsoft.Phone.Shell;assembly=Microsoft.Phone"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
d:DataContext="{d:DesignData DesignData/LocationDetailsSampleData.xaml}"
mc:Ignorable="d"
FontFamily="{StaticResource PhoneFontFamilyNormal}"
FontSize="{StaticResource PhoneFontSizeNormal}"
Foreground="{StaticResource PhoneForegroundBrush}"
SupportedOrientations="Portrait" Orientation="Portrait"
shell:SystemTray.IsVisible="True">
<Grid x:Name="LayoutRoot" Background="Transparent">
<phone:Pivot x:Name="pvtMainPivot" SelectionChanged="evt_PivotControl_SelectionChanged">
<!-- ++++++++++++++++++ Header -->
<phone:Pivot.Title>
<StackPanel HorizontalAlignment="Center">
<Image Stretch="None" HorizontalAlignment="Left" Margin="-5,0,0,0" MinWidth="50" MaxHeight="50" Source="/mAppData/logo.png"/>
</StackPanel>
</phone:Pivot.Title>
<!-- ++++++++++++++++++ EREIGNISSE -->
<phone:PivotItem x:Name="pivotitemFavoriten" Header="Ereignisse">
<StackPanel Margin="0,0,0,15" >
<Grid VerticalAlignment="Top" Margin="0,0,5,0">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="120" />
</Grid.ColumnDefinitions>
<TextBlock Grid.Column="0" TextTrimming="WordEllipsis" Text="LocationName" TextWrapping="NoWrap" Style="{StaticResource PhoneTextLargeStyle}" VerticalAlignment="Top" Margin="0,0,0,22" />
<Image Grid.Column="0" Width="138" Height="25" Source="/mAppData/stars-3.png" HorizontalAlignment="Left" VerticalAlignment="Bottom" Margin="0"/>
<TextBlock Grid.Column="1" Text="distance" TextWrapping="NoWrap" Style="{StaticResource PhoneTextSubtleStyle}" HorizontalAlignment="Right" Margin="0,0,-3,40" VerticalAlignment="Bottom"/>
<TextBlock Grid.Column="1" Text="lastupload" TextWrapping="NoWrap" Style="{StaticResource PhoneTextSubtleStyle}" HorizontalAlignment="Right" Margin="0,0,-3,20" VerticalAlignment="Bottom"/>
<TextBlock Grid.Column="1" Text="ratingscnt" TextWrapping="NoWrap" Style="{StaticResource PhoneTextSubtleStyle}" HorizontalAlignment="Right" Margin="0" VerticalAlignment="Bottom"/>
</Grid>
<TextBlock Grid.Column="1" Text="Marlene-Dietrich-Platz 1" TextWrapping="NoWrap" Style="{StaticResource PhoneTextSubtleStyle}" HorizontalAlignment="Left" Margin="0" VerticalAlignment="Bottom"/>
<TextBlock Grid.Column="1" Text="Berlin" TextWrapping="NoWrap" Style="{StaticResource PhoneTextSubtleStyle}" HorizontalAlignment="Left" Margin="0" VerticalAlignment="Bottom"/>
<phone:LongListSelector Name="lls_PhotoHub" Margin="0" IsGroupingEnabled="False" LayoutMode="Grid" DataContext="LocationMediaViewModel" ItemsSource="{Binding MediaItems}" GridCellSize="108,108" >
<phone:LongListSelector.ItemTemplate>
<DataTemplate>
<Image Width="100" Height="100" Source="{Binding URL}" />
</DataTemplate>
</phone:LongListSelector.ItemTemplate>
</phone:LongListSelector>
</StackPanel>
</phone:PivotItem>
<!-- ++++++++++++++++++ 2.PivotItem-->
<phone:PivotItem x:Name="pivotitemUmgebung" Header="Karte">
</phone:PivotItem>
</phone:Pivot>
</Grid>
</phone:PhoneApplicationPage>
But the binding seems not working -> no Images are displayed.
Can anyone help?

As Florent Gz pointed out, I don't see any DataContext initialization either.
In your PhoneApplicationPage code behind, in the constructor, add this:
this.DataContext = new LocationMediaViewModel();

Related

How to update data in a new non-modal window after changing the selection to ListView?

I have a user list in MainWindow. After pressing the preview button, a non-modal window for data editing opens. Updated data are changed in real time in the main window. The question is how to bind the windows so that because the user changes from the list in the main window, he changes in real time in an already open non-modal window.
WPF does not recommend coding business logic directly in xaml.cs
files.
It is recommended that you write code using the MVVM pattern
ViewModel
public class podgladUzytkownika : INotifyPropertyChanged
{
private string imie;
private string nazwisko;
private string mail;
public string Mail
{
get => mail;
set => this.SetValue(ref mail, value);
}
public string Nazwisko
{
get => nazwisko;
set => this.SetValue(ref nazwisko, value);
}
public string Imie
{
get => imie;
set => this.SetValue(ref imie, value);
}
public event PropertyChangedEventHandler PropertyChanged;
protected void SetValue<T>(ref T oldValue, T newValue, [CallerMemberName] string propertyName = null)
{
oldValue = newValue;
OnPropertyChanged(propertyName);
}
[NotifyPropertyChangedInvocator]
protected virtual void OnPropertyChanged([CallerMemberName] string propertyName = null)
{
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
}
}
public class MainWindowViewModel
{
private int refreshCount;
public ICommand RefreshCommand { get; }
public ICommand PodgladUzytkownikaShow { get; }
public podgladUzytkownika data { get; }
public MainWindowViewModel()
{
data = new podgladUzytkownika();
PodgladUzytkownikaShow = new Command(PodgladUzytkownikaShowExecute);
RefreshCommand = new Command(RefreshCommandExecute);
}
private void PodgladUzytkownikaShowExecute(object obj)
{
var window = new Window();
window.DataContext = data;
window.Show();
}
private void RefreshCommandExecute(object obj)
{
// Data updates are passed to the view
refreshCount++;
data.Imie = nameof(data.Imie) + refreshCount;
data.Nazwisko = nameof(data.Nazwisko) + refreshCount;
data.Mail = nameof(data.Mail) + refreshCount;
}
}
View
// MainWindow.xaml
<StackPanel x:Name="StackPanel1">
<Button Content="PodgladUzytkownika" Command="{Binding Path=PodgladUzytkownikaShow}"/>
<Button Content="Refresh" Command="{Binding Path=RefreshCommand}"/>
</StackPanel>
// window.xaml
<StackPanel >
<TextBlock Text="{Binding Path=Imie }"/>
<TextBlock Text="{Binding Path=Nazwisko }"/>
<TextBlock Text="{Binding Path=Mail }"/>
</StackPanel>
Demo
this.MainWindow.DataContext =new MainWindowViewModel();
After chasing one problem after another with your comments, the problem is your code is not well-designed. Using data bindings (one of the prime benefits of WPF), you can stop chasing your tail with trying to figure out how to update one UI when data changes. Here is a simplified version of your code that will always ensure the UI matches the data you wish to manipulate.
MainWindow.xaml
<Grid Margin="3">
<Grid.RowDefinitions>
<RowDefinition Height="auto"/>
<RowDefinition/>
<RowDefinition Height="auto"/>
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition />
<ColumnDefinition Width="auto"/>
<ColumnDefinition Width="auto"/>
</Grid.ColumnDefinitions>
<Label Margin="3" Grid.ColumnSpan="3">Lista użytkowników</Label>
<Button Margin="3" Padding="3" Grid.Row="2" Grid.ColumnSpan="3" Click="Zamknij_Click">Zamknij</Button>
<StackPanel Margin="3" Grid.Column="2" Grid.Row="1">
<!--<Button Name="Dodaj" Click="Dodaj_Click" Margin="3" Padding="10,3" >Dodaj...</Button>-->
<!--<Button Name="Usun" IsEnabled="False" Click="Usun_Click" Margin="3" Padding="10,3" >Usuń</Button>-->
<!--<Button Name="Edytuj" IsEnabled="False" Click="Edytuj_Click" Margin="3" Padding="10,3" >Edytuj...</Button>-->
<Button Name="Podglad" IsEnabled="False" Click="Podglad_Click" Margin="3" Padding="10,3" >Podgląd...</Button>
</StackPanel>
<ListView SelectionMode="Single" SelectionChanged="Selection_Changed" Name="lv_uzytkownicy" Margin="3" Grid.Row="1">
<ListView.View>
<GridView>
<GridView.Columns>
<GridViewColumn Header="Imię"
DisplayMemberBinding="{Binding Imie}"/>
<GridViewColumn Header="Nazwisko"
DisplayMemberBinding="{Binding Nazwisko}" />
<GridViewColumn Header="Mail"
DisplayMemberBinding="{Binding Mail}"/>
</GridView.Columns>
</GridView>
</ListView.View>
</ListView>
<GridSplitter Grid.Column="1" Grid.Row="1" Width="5" ResizeDirection="Columns" HorizontalAlignment="Center"/>
</Grid>
MainWindow.xaml.cs
using System.Collections.ObjectModel;
public partial class MainWindow : Window
{
public ObservableCollection<Uzytkownik> listaUzytkownikow = new ObservableCollection<Uzytkownik>();
Podglad_Uzytkownika podgladUzytkownika;
public MainWindow()
{
InitializeComponent();
lv_uzytkownicy.ItemsSource = listaUzytkownikow;
listaUzytkownikow.Add(new Uzytkownik("Mietek", "Żul", "sikalafa#wp.pl"));
listaUzytkownikow.Add(new Uzytkownik("Franek", "Alpinista", "halo#gmail.pl"));
listaUzytkownikow.Add(new Uzytkownik("Stefan", "Ulążka", "mam.to#o2.pl"));
this.DataContext = this;
}
private void Podglad_Click(object sender, RoutedEventArgs e)
{
podgladUzytkownika = new Podglad_Uzytkownika();
podgladUzytkownika.DataContext = lv_uzytkownicy.SelectedItem;
podgladUzytkownika.Show();
}
private void Zamknij_Click(object sender, RoutedEventArgs e)
{
Close();
}
private void Selection_Changed(object sender, SelectionChangedEventArgs e)
{
if (lv_uzytkownicy.SelectedItems.Count > 0) Podglad.IsEnabled = true;
else Podglad.IsEnabled = false;
if (podgladUzytkownika != null && podgladUzytkownika.IsVisible)
{
podgladUzytkownika.DataContext = lv_uzytkownicy.SelectedItem;
}
}
}
Podglad_Uzytkownika.xaml
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="auto"/>
<RowDefinition Height="auto"/>
<RowDefinition Height="auto"/>
<RowDefinition Height="auto"/>
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="auto"/>
<ColumnDefinition/>
</Grid.ColumnDefinitions>
<Label Margin="3">Imię</Label>
<Label Margin="3" Grid.Row="1">Nazwisko</Label>
<Label Margin="3" Grid.Row="2">Email</Label>
<TextBox Name="imieTextBox" Text="{Binding Imie, UpdateSourceTrigger=PropertyChanged}" Margin="3" Grid.Column="1"/>
<TextBox Name="nazwiskoTextBox" Text="{Binding Nazwisko, UpdateSourceTrigger=PropertyChanged}" Margin="3" Grid.Column="1" Grid.Row="1"/>
<TextBox Name="mailTextBox" Text="{Binding Mail, UpdateSourceTrigger=PropertyChanged}" Margin="3" Grid.Column="1" Grid.Row="2"/>
<Grid HorizontalAlignment="Center" Grid.ColumnSpan="2" Grid.Row="3" Grid.IsSharedSizeScope="True">
<Grid.ColumnDefinitions>
<ColumnDefinition SharedSizeGroup="pierwsza" />
</Grid.ColumnDefinitions>
<Button Margin="3" Padding="20, 5" Name="Podglad" Click="Podglad_Click" IsDefault="True">Zamknij</Button>
</Grid>
</Grid>
Podglad_Uzytkownika.xaml.cs
public partial class Podglad_Uzytkownika : Window
{
public Podglad_Uzytkownika()
{
InitializeComponent();
}
private void Podglad_Click(object sender, RoutedEventArgs e)
{
Close();
}
}
Uzytkownik.cs
public class Uzytkownik : INotifyPropertyChanged
{
private string imie;
private string nazwisko;
private string mail;
public Uzytkownik(string imie, string nazwisko, string mail)
{
this.Imie = imie;
this.Nazwisko = nazwisko;
this.Mail = mail;
}
public string Imie { get => this.imie; set { this.imie = value; OnPropertyChanged(); } }
public string Nazwisko { get => this.nazwisko; set { this.nazwisko = value; OnPropertyChanged(); } }
public string Mail { get => this.mail; set { this.mail = value; OnPropertyChanged(); } }
public event PropertyChangedEventHandler PropertyChanged;
public void OnPropertyChanged([CallerMemberName] string propertyName = null)
{
this.PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
}
}

Binding the background color in a long list selector

i am trying to bind the background color with the item template containing a grid in it. I want that depending upon the status the background color of each item in a list should be highlighted automatically. So i am doing it but no color is shown on the respective item.so how to bind the grid background such that color is changed. Xaml code :
<phone:LongListSelector x:Name="ResultListBox"
Margin="35,10,35,-25"
ItemsSource="{Binding Country}"
ItemTemplate="{StaticResource CustomList}"
Height="436" SelectionChanged="ResultListBox_SelectionChanged" Loaded="Listbox_loaded">
<UserControl.Resources>
<DataTemplate x:Key="CustomList">
<Grid Margin="5,0,10,5" Tag="{Binding Name}" x:Name="CountryGrid" Tap="BorderColor" >
<Grid.Background>
<SolidColorBrush Color="{Binding HighlightBackgroundColor}" />
</Grid.Background>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="450"/>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="45"></RowDefinition>
</Grid.RowDefinitions>
<Border VerticalAlignment="Center" x:Name="HighlightBG" HorizontalAlignment="Left" Grid.Column="0" Margin="0,5,0,0" Height="70" CornerRadius="0,10,10,0" Grid.Row="0" >
<StackPanel Orientation="Vertical" Margin="0,5,0,0" HorizontalAlignment="Center" >
<TextBlock Text="{Binding Name}" x:Name="nametextblock" VerticalAlignment="Top" TextWrapping="Wrap" Foreground="White" FontSize="30" HorizontalAlignment="Center" ></TextBlock>
</StackPanel>
</Border>
</Grid>
</DataTemplate>
</UserControl.Resources>
c# code snippet:
public partial class ListPopup : UserControl,INotifyPropertyChanged
{
public ListPopup()
{
InitializeComponent();
this.Loaded += ListPopup_Loaded;
this.IsSelected = false;
//, INotifyPropertyChanged
this.NonHighlightColor = new SolidColorBrush(Colors.Transparent);
this.HighLightColor = new SolidColorBrush(Colors.Red);
}
public event PropertyChangedEventHandler PropertyChanged;
protected void OnPropertyChanged(string name)
{
PropertyChangedEventHandler handler = PropertyChanged;
if (handler != null)
{
handler(this, new PropertyChangedEventArgs(name));
}
}
////////////
private bool _is_selected;
public bool IsSelected
{
get { return _is_selected; }
set
{
_is_selected = value;
OnPropertyChanged("HighlightBackgroundColor");
}
}
public SolidColorBrush HighlightBackgroundColor
{
get { if (IsSelected) return HighLightColor; else return NonHighlightColor; }
}
private SolidColorBrush HighLightColor { get; set; }
private SolidColorBrush NonHighlightColor { get; set; }
}
You're exposing a Brush but binding it as a Color. Just change your XAML:
<Grid Margin="5,0,10,5" Background="{Binding HighlightBackgroundColor}" Tag="{Binding Name}" x:Name="CountryGrid" Tap="BorderColor" >

XMLA, data-binding does not working

<Window x:Class="RMT_MMO.Starter.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="MainWindow" Height="304" Width="472"
ResizeMode="NoResize">
<Grid Margin="10">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="100*"/>
<ColumnDefinition Width="200*"/>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="50*"/>
<RowDefinition Height="10*"/>
<RowDefinition Height="40*"/>
<RowDefinition Height="40*"/>
<RowDefinition Height="80*"/>
</Grid.RowDefinitions>
<ProgressBar Grid.ColumnSpan="2" Maximum="100" Value="{Binding Percent}"/>
<Label Grid.ColumnSpan="2" Content="{Binding Status }" HorizontalContentAlignment="Center" VerticalContentAlignment="Center" FontSize="14" FontWeight="Bold" Margin="0,0,0,10"/>
<Label Grid.Row="2" Content="Username" HorizontalContentAlignment="Right" VerticalContentAlignment="Center" FontSize="14" FontWeight="Bold"/>
<TextBox IsEnabled="{Binding CanLogin}" Grid.Row="2" Grid.Column="1" Margin="5" Text="{Binding Username}" HorizontalContentAlignment="Center" VerticalContentAlignment="Center"/>
<Label Grid.Row="3" Content="Password" HorizontalContentAlignment="Right" VerticalContentAlignment="Center" FontSize="14" FontWeight="Bold"/>
<PasswordBox IsEnabled="{Binding CanLogin}" Grid.Row="3" Grid.Column="1" Margin="5" x:Name="Password" HorizontalContentAlignment="Center" VerticalContentAlignment="Center" />
<Button Click="Login" IsDefault="True" IsEnabled="{Binding CanLogin}" Content="asdasd" Grid.Row="4" HorizontalAlignment="Left" Padding="10" Margin="10,25,0,19" RenderTransformOrigin="7.273,0.484" Width="247" Grid.Column="1"/>
</Grid>
</Window>
So here how MainWindow look, when I click to button this code execute
using System.Windows;
namespace RMT_MMO.Starter
{
public partial class MainWindow
{
private readonly MainWindowViewModel _viewModel;
public MainWindow()
{
InitializeComponent();
_viewModel = new MainWindowViewModel();
DataContext = _viewModel;
_viewModel.CanLogin = true;
}
public void Login(object sender,RoutedEventArgs e)
{
// MessageBox.Show(_viewModel.Percent.ToString());
_viewModel.CanLogin = false;
_viewModel.Percent =50;
// _viewModel.Status = "Stuff happened";
}
}
}
And MainWindowViewModel class looks like this:
using System.ComponentModel;
using System.Runtime.CompilerServices;
namespace RMT_MMO.Starter
{
public class MainWindowViewModel:INotifyPropertyChanging
{
private bool _canLogin;
private string _status;
private double _percent;
private string _username;
public event PropertyChangingEventHandler PropertyChanging;
public bool CanLogin
{
get { return _canLogin; }
set
{
_canLogin = value;
OnPropertyChanged();
}
}
public string Status
{
get { return _status; }
set
{
_status = value;
OnPropertyChanged();
}
}
public double Percent
{
get { return _percent; }
set
{
_percent = value;
OnPropertyChanged();
}
}
public string Username
{
get { return _username; }
set
{
_username = value;
OnPropertyChanged();
}
}
private void OnPropertyChanged([CallerMemberName] string propertyName = null)
{
var handler = PropertyChanging;
if (handler != null)
handler(this, new PropertyChangingEventArgs(propertyName));
}
}
}
What I am trying to do is to bind xmla and this code, when I hit button binding is not performed.
I know it it is trivial mistake but I simple can't fined it, I tried searching online but I failed. All help is welcome.
It could be because you are using INotifyPropertyChanging when you should be using INotifyPropertyChanged interface.

How to delete item from collection?

So im creating an app which allows users to make habit list. It works fine when I try to make new habits. but Im stuck at how to delete them.
this is the XAML for the binding
<PivotItem
Header="HABIT LIST"
Margin="10,10,0,0">
<ScrollViewer>
<!--Habit item template-->
<Grid Margin="0,0,10,0">
<Grid.Resources>
<DataTemplate x:Name="dataTemplate">
<Grid Margin="0,0,0,0"
Holding="ListViewItem_Holding">
<!--ContextMenu-->
<FlyoutBase.AttachedFlyout>
<MenuFlyout>
<MenuFlyoutItem
x:Name="deletehabit"
Text="Delete"
Click="deletehabit_Click"
RequestedTheme="Dark"
/>
</MenuFlyout>
</FlyoutBase.AttachedFlyout>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="105" />
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<!--ProgressBar-->
<StackPanel
Grid.Column="0"
CommonNavigationTransitionInfo.IsStaggerElement="True">
<ProgressBar
x:Name="habitbar"
Grid.Column="0"
Margin="0,105,-10,-105"
Value="{Binding Dates, Converter={StaticResource CompletedDatesToIntegerConverter}}"
Maximum="21"
Minimum="0"
Foreground="#FF32CE79"
Width="100"
Height="50"
HorizontalAlignment="Stretch"
VerticalAlignment="Top"
RenderTransformOrigin="0,0"
Pivot.SlideInAnimationGroup="GroupOne"
FontFamily="Global User Interface"
>
<ProgressBar.RenderTransform>
<CompositeTransform Rotation="270"/>
</ProgressBar.RenderTransform>
</ProgressBar>
</StackPanel>
<!--Details-->
<StackPanel
x:Name="habitdetail"
Grid.Column="1"
Margin="-30,0,0,0" >
<TextBlock
Text="{Binding Name}"
FontSize="24"
Foreground= "#FF3274CE"
FontWeight="Thin"
HorizontalAlignment="Left"
VerticalAlignment="Top"
FontFamily="Global User Interface"
Pivot.SlideInAnimationGroup="GroupTwo"/>
<TextBlock
Text="{Binding Description}"
FontSize="18"
FontWeight="Thin"
HorizontalAlignment="Left"
VerticalAlignment="Top"
FontFamily="Global User Interface"
LineHeight="10"
Pivot.SlideInAnimationGroup="GroupTwo"/>
<!--Button-->
<Button
x:Name="CompletedButton"
Content="!"
Command="{Binding CompletedCommand}"
CommandParameter="{Binding}"
IsEnabled="{Binding Dates, Converter={StaticResource IsCompleteToBooleanConverter}}"
HorizontalAlignment="Stretch"
VerticalAlignment="Stretch"
Margin="0,5,0,0"
Background="#FFCE3232"
Foreground="White"
Height="21"
BorderBrush="#FFCE3232"
FontFamily="Global User Interface"
ClickMode="Release"
Pivot.SlideInAnimationGroup="GroupThree"
Width="280"/>
</StackPanel>
</Grid>
</DataTemplate>
</Grid.Resources>
<ListView
x:Name="habitlist"
ItemsSource="{Binding}"
ItemTemplate="{StaticResource dataTemplate}"
Background="{x:Null}"
/>
</Grid>
</ScrollViewer>
</PivotItem>
this is the code behind for deleting the habit which I don't know what to type
private void ListViewItem_Holding(object sender, HoldingRoutedEventArgs e)
{
FrameworkElement senderElement = sender as FrameworkElement;
FlyoutBase flyoutBase = FlyoutBase.GetAttachedFlyout(senderElement);
flyoutBase.ShowAt(senderElement);
}
private void deletehabit_Click(object sender, RoutedEventArgs e)
{
//TODO
}
and heres the datamodel
public class Habit : INotifyPropertyChanged
{
public int ID { get; set; }
public string Name { get; set; }
public string Description { get; set; }
public ObservableCollection<DateTime> Dates { get; set; }
[IgnoreDataMember]
public ICommand CompletedCommand { get; set; }
public Habit()
{
CompletedCommand = new CompletedButtonClick();
Dates = new ObservableCollection<DateTime>();
}
public void AddDate()
{
Dates.Add(DateTime.Today);
NotifyPropertyChanged("Dates");
}
public event PropertyChangedEventHandler PropertyChanged;
private void NotifyPropertyChanged(string propertyName)
{
if (PropertyChanged != null)
{
PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
}
}
}
public class DataSource
{
private ObservableCollection<Habit> _habits;
const string fileName = "habits.json";
public DataSource()
{
_habits = new ObservableCollection<Habit>();
}
public async Task<ObservableCollection<Habit>> GetHabits()
{
await ensureDataLoaded();
return _habits;
}
private async Task ensureDataLoaded()
{
if (_habits.Count == 0)
await getHabitDataAsync();
return;
}
private async Task getHabitDataAsync()
{
if (_habits.Count != 0)
return;
var jsonSerializer = new DataContractJsonSerializer(typeof(ObservableCollection<Habit>));
try
{
// Add a using System.IO;
using (var stream = await ApplicationData.Current.LocalFolder.OpenStreamForReadAsync(fileName))
{
_habits = (ObservableCollection<Habit>)jsonSerializer.ReadObject(stream);
}
}
catch
{
_habits = new ObservableCollection<Habit>();
}
}
public async void AddHabit(string name, string description)
{
var habit = new Habit();
habit.Name = name;
habit.Description = description;
habit.Dates = new ObservableCollection<DateTime>();
_habits.Add(habit);
await saveHabitDataAsync();
}
private async Task saveHabitDataAsync()
{
var jsonSerializer = new DataContractJsonSerializer(typeof(ObservableCollection<Habit>));
using (var stream = await ApplicationData.Current.LocalFolder.OpenStreamForWriteAsync(fileName,
CreationCollisionOption.ReplaceExisting))
{
jsonSerializer.WriteObject(stream, _habits);
}
}
public async void CompleteHabitToday(Habit habit)
{
int index = _habits.IndexOf(habit);
_habits[index].AddDate();
await saveHabitDataAsync();
}
}
im very new to programming
thanks
If I understand the question correctly, just call the
NameOfCollectionGoesHere.Remove()
Method.
You can also clear the entire collection with
.Clear()
Is that what you are asking for?

Metro 8 - Binding ListView causes System.ArgumentException "Value does not fall within the expected range"

Am not sure what just happened why this morning, I ran my project and it started causing an System.ArgumentException error. Maybe I changed something last night and I was half-asleep again.
I tried searching for an answer and it gave me an idea about having the same name in property?
I scanned my codes and it looks like it's the same the last it successfully ran .. weird..
Maybe you can help me hunt for the error and enlighten me with it.
Basically the error is causing in this code
lvSubmeters.ItemsSource = this.store
in this code
public MainPage()
{
this.InitializeComponent();
this.InitializeControlEvents();
this.InitializeControls();
}
void InitializeControls()
{
store = new DataStore();
store.AllItems = new System.Collections.ObjectModel.ObservableCollection<ItemFields>();
PopulateTempData();
lvSubmeters.ItemsSource = this.store;
}
this is my PopulateTempData
void PopulateTempData()
{
txCurrentBill.Text = "5308.07";
txKwHUsed.Text = "710";
txTotalAdditonalCharges.Text = "249.1";
ComputeKwhPerSubmeter(txTotalAdditonalCharges, null);
RefreshListView(new ItemFields()
{
MeterID = "1234",
Fullname = "XOP",
LastReading = 22980,
NewReading = 23107,
KwhPerSubmeter = Convert.ToDouble(txKwHPerSub.Tag),
AdditionalCharges = Convert.ToDouble(txChargeForEachSubmeters.Tag)
});
RefreshListView(new ItemFields()
{
MeterID = "2345",
Fullname = "Bigasan",
LastReading = 0,
NewReading = 0,
KwhPerSubmeter = Convert.ToDouble(txKwHPerSub.Tag),
AdditionalCharges = Convert.ToDouble(txChargeForEachSubmeters.Tag)
});
RefreshListView(new ItemFields()
{
MeterID = "3456",
Fullname = "Store",
LastReading = 0,
NewReading = 0,
KwhPerSubmeter = Convert.ToDouble(txKwHPerSub.Tag),
AdditionalCharges = Convert.ToDouble(txChargeForEachSubmeters.Tag)
});
RefreshListView(new ItemFields()
{
MeterID = "4567",
Fullname = "Social & Play",
LastReading = 7056,
NewReading = 7511,
KwhPerSubmeter = Convert.ToDouble(txKwHPerSub.Tag),
AdditionalCharges = Convert.ToDouble(txChargeForEachSubmeters.Tag)
});
RefreshListView(new ItemFields()
{
MeterID = "5678",
Fullname = "Parlor",
LastReading = 8277,
NewReading = 8365,
KwhPerSubmeter = Convert.ToDouble(txKwHPerSub.Tag),
AdditionalCharges = Convert.ToDouble(txChargeForEachSubmeters.Tag)
});
}
this is ItemFields Model
using System;
namespace ElectricSubmeterBillComputation.Models
{
using System.ComponentModel;
public class ItemFields : System.ComponentModel.INotifyPropertyChanged
{
string _meter_id = string.Empty;
public string MeterID
{
get { return this._meter_id; }
set
{
if (_meter_id != value)
{
_meter_id = value;
NotifyPropertyChanged("MeterID");
}
}
}
string _fullname = string.Empty;
public string Fullname
{
get { return this._fullname; }
set
{
if (this._fullname != value)
{
this._fullname = value;
NotifyPropertyChanged("Fullname");
}
}
}
int _lastreading = 0;
public int LastReading
{
get { return this._lastreading; }
set
{
if (this._lastreading != value)
{
this._lastreading = value;
NotifyPropertyChanged("LastReading");
}
}
}
int _newreading = 0;
public int NewReading
{
get { return this._newreading; }
set
{
if (this._newreading != value)
{
this._newreading = value;
NotifyPropertyChanged("NewReading");
}
}
}
int _kwhused = 0;
public int KwHUsed
{
get { return this._kwhused; }
set
{
if (this._kwhused != value)
{
this._kwhused = value;
NotifyPropertyChanged("KwHUsed");
}
}
}
double _KwHPerSubmeter = 0.0;
public double KwhPerSubmeter
{
get { return this._KwHPerSubmeter; }
set
{
if (this._KwHPerSubmeter != value)
{
this._KwHPerSubmeter = value;
NotifyPropertyChanged("KwhPerSubmeter");
}
}
}
double _kwhamount = 0.0;
public double KwhUsedAmount
{
get { return this._kwhamount; }
set
{
if (this._kwhamount != value)
{
this._kwhamount = value;
NotifyPropertyChanged("KwhUsedAmount");
}
}
}
double _add_charge = 0.0;
public double AdditionalCharges
{
get { return this._add_charge; }
set
{
if (this._add_charge != value)
{
this._add_charge = value;
NotifyPropertyChanged("AdditionalCharges");
}
}
}
double _total_amount = 0.0;
public double TotalAmount
{
get { return this._total_amount; }
set
{
if (this._total_amount != value)
{
this._total_amount = value;
NotifyPropertyChanged("TotalAmount");
}
}
}
public void Update()
{
KwHUsed = NewReading - LastReading;
KwhUsedAmount = KwHUsed * KwhPerSubmeter;
TotalAmount = KwhUsedAmount + AdditionalCharges;
}
#region INotifyPropertyChanged
public event PropertyChangedEventHandler PropertyChanged;
private void NotifyPropertyChanged(String info)
{
if (PropertyChanged != null)
{
PropertyChanged(this, new PropertyChangedEventArgs(info));
}
}
#endregion
}
}
and this is the DataStore Model
using System;
using System.Collections.ObjectModel;
namespace ElectricSubmeterBillComputation.Models
{
using System.ComponentModel;
public class DataStore : INotifyPropertyChanged
{
ObservableCollection<ItemFields> _allItems;
public ObservableCollection<ItemFields> AllItems
{
get { return this._allItems; }
set
{
_allItems = value;
NotifyPropertyChanged("AllItems");
}
}
public void UpdateAllAmounts(double AdditionalChargersPerSubmeter)
{
foreach (ItemFields item in _allItems)
{
item.AdditionalCharges = AdditionalChargersPerSubmeter;
item.Update();
}
}
#region INotifyPropertyChanged
public event PropertyChangedEventHandler PropertyChanged;
private void NotifyPropertyChanged(String info)
{
if (PropertyChanged != null)
{
PropertyChanged(this, new PropertyChangedEventArgs(info));
}
}
#endregion
}
}
and lastly, my listview
<ListView Grid.Row="3" x:Name="lvSubmeters" ItemTemplate="{StaticResource SubmeterItems}" VerticalAlignment="Top" HorizontalAlignment="Stretch" SelectionChanged="lvSubmeters_SelectionChanged">
<ListView.ItemContainerStyle>
<Style TargetType="ListViewItem">
<Setter Property="HorizontalContentAlignment" Value="Stretch" />
</Style>
</ListView.ItemContainerStyle>
</ListView>
and SubmeterItems template
<DataTemplate x:Name="SubmeterItems">
<Grid VerticalAlignment="Top" HorizontalAlignment="Stretch" Margin="5,5,5,5">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="166"/>
<ColumnDefinition Width="100*"/>
<ColumnDefinition Width="200"/>
</Grid.ColumnDefinitions>
<StackPanel Grid.Column="0" VerticalAlignment="Top">
<TextBlock HorizontalAlignment="Stretch" VerticalAlignment="Top" Text="{Binding MeterID}" FontSize="24" FontWeight="Bold" Foreground="#FF429AA3" />
<TextBlock HorizontalAlignment="Stretch" VerticalAlignment="Top" Text="{Binding Fullname}" FontSize="16" />
</StackPanel>
<StackPanel Grid.Column="1" VerticalAlignment="Top" Height="95">
<TextBlock HorizontalAlignment="Stretch" VerticalAlignment="Top" Text=" " FontSize="24" FontWeight="Bold" Foreground="#FF429AA3" />
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="100"/>
<ColumnDefinition Width="29*"/>
</Grid.ColumnDefinitions>
<StackPanel Grid.Column="0">
<TextBlock Grid.Column="0" VerticalAlignment="Top" Text="Last Reading:" FontSize="14" Margin="0,0,5,5" />
<TextBlock Grid.Column="0" VerticalAlignment="Top" Text="New Reading:" FontSize="14" Margin="0,0,5,5" />
<TextBlock Grid.Column="0" VerticalAlignment="Top" Text="KW/H Used:" FontSize="14" Margin="0,0,5,5" />
</StackPanel>
<StackPanel Grid.Column="1">
<TextBlock Grid.Column="1" VerticalAlignment="Top" Text="{Binding LastReading}" FontSize="14" Margin="0,0,5,5" FontWeight="Bold" />
<TextBlock Grid.Column="1" VerticalAlignment="Top" Text="{Binding NewReading}" FontSize="14" Margin="0,0,5,5" FontWeight="Bold" />
<TextBlock Grid.Column="1" VerticalAlignment="Top" Text="{Binding KwHUsed}" FontSize="14" Margin="0,0,5,5" FontWeight="Bold" />
</StackPanel>
</Grid>
</StackPanel>
<StackPanel Grid.Column="2" VerticalAlignment="Bottom" HorizontalAlignment="Stretch" Background="Black">
<TextBlock HorizontalAlignment="Stretch" VerticalAlignment="Top" Text="{Binding KwhUsedAmount}" FontSize="20" FontWeight="Bold" Foreground="Red" TextAlignment="Right" Margin="0,0,5,0" />
<StackPanel Orientation="Horizontal" HorizontalAlignment="Right">
<TextBlock HorizontalAlignment="Stretch" VerticalAlignment="Top" Text="+" FontSize="20" Foreground="#99FF0000" TextAlignment="Right" Margin="0,0,5,0"/>
<TextBlock HorizontalAlignment="Stretch" VerticalAlignment="Top" Text="{Binding AdditionalCharges}" FontSize="20" Foreground="#99FF0000" TextAlignment="Right" Margin="0,0,5,0"/>
</StackPanel>
<TextBlock HorizontalAlignment="Stretch" VerticalAlignment="Top" Text="{Binding TotalAmount}" FontSize="34" FontWeight="Bold" Foreground="Green" TextAlignment="Right" Margin="0,0,5,0" />
</StackPanel>
</Grid>
</DataTemplate>
and finally the stack trace
at Windows.UI.Xaml.Controls.ItemsControl.put_ItemsSource(Object value)
at ElectricSubmeterBillComputation.MainPage.InitializeControls() in d:\Codes\WindowsMetro\ElectricSubmeterBillComputation\ElectricSubmeterBillComputation\MainPage.xaml.cs:line 43
at ElectricSubmeterBillComputation.MainPage..ctor() in d:\Codes\WindowsMetro\ElectricSubmeterBillComputation\ElectricSubmeterBillComputation\MainPage.xaml.cs:line 33
at ElectricSubmeterBillComputation.ElectricSubmeterBillComputation_XamlTypeInfo.XamlTypeInfoProvider.Activate_1_MainPage() in d:\Codes\WindowsMetro\ElectricSubmeterBillComputation\ElectricSubmeterBillComputation\obj\Debug\XamlTypeInfo.g.cs:line 121
at ElectricSubmeterBillComputation.ElectricSubmeterBillComputation_XamlTypeInfo.XamlUserType.ActivateInstance() in d:\Codes\WindowsMetro\ElectricSubmeterBillComputation\ElectricSubmeterBillComputation\obj\Debug\XamlTypeInfo.g.cs:line 277
Solved it ..
lvSubmeters.ItemsSource = this.store;
it should be
lvSubmeters.ItemsSource = this.store.AllItems;
so in order to make the first code above
lvSubmeters.DataContext = this.store;
ListView should have
ItemsSource="{Binding AllItems}"

Categories

Resources