I have a ListView that displays all the days in a month as buttons and each button contains the day number. When I click one of the buttons I want it to take me to that days view. The buttons commands are bound to the ToDayView command. I dont want to make a bunch of different commands for each day that could possibly be in a month. How can I pass the day number through use of the command?
MonthView
<ListView ItemsSource="{Binding CurrentMonth.Days}" Grid.Row="1">
<ListView.ItemTemplate>
<DataTemplate>
<Button Content="{Binding DayNumber}" Grid.Row="1" Height="20" Width="100"
Command="{Binding ToDayViewCommand}"/>
</DataTemplate>
</ListView.ItemTemplate>
</ListView>
MonthViewModel
public class MonthViewModel : ViewModelBase
{
private readonly NavigationStore _navigationStore;
private Month _currentMonth;
public Month CurrentMonth
{
get { return _currentMonth; }
set
{
_currentMonth = value;
OnPropertyChanged("CurrenMonth");
}
}
public void ToDayView(object thing)
{
// use parameter as day number
int dayNumber = 25;
// find the Day object with that day number
for(int i = 0; i < CurrentMonth.Days.Count; i )
{
if(CurrentMonth.Days[i].DayNumber == dayNumber)
{
// give it to the view model to be displayed
_navigationStore.CurrentViewModel = new DayViewModel(CurrentMonth.Days[i], _navigationStore);
}
}
}
public BasicCommand ToDayViewCommand { get; set; }
public MonthViewModel(Month currentMonth, NavigationStore navigationStore)
{
CurrentMonth = currentMonth;
_navigationStore = navigationStore;
ToDayViewCommand = new BasicCommand(ToDayView);
}
}
BasicCommand
public class BasicCommand : CommandBase
{
readonly Action<object> _execute;
public BasicCommand(Action<object> execute)
{
_execute = execute;
}
public override bool CanExecute(object parameter) => true;
public override void Execute(object parameter)
{
_execute.Invoke(parameter);
}
}
CodePudding user response:
You can define the command parameter in your XAML code:
<Button Content="{Binding DayNumber}" Grid.Row="1" Height="20" Width="100"
Command="{Binding ToDayViewCommand}" CommandParameter="25" />
Note that CommandParameter
is a dependency property, hence you can also use a binding:
<Button Content="{Binding DayNumber}" Grid.Row="1" Height="20" Width="100"
Command="{Binding ToDayViewCommand}" CommandParameter="{Binding AmountDays}" />
In the method, that is invoked by your command, you have to cast the object to an int. Note that your parameter is a string, if you call it like in my first code snippet, hence you have to use int.Parse
:
public void ToDayView(object thing)
{
// use parameter as day number
int dayNumber = int.Parse(thing.ToString());
// find the Day object with that day number
for(int i = 0; i < CurrentMonth.Days.Count; i )
{
if(CurrentMonth.Days[i].DayNumber == dayNumber)
{
// give it to the view model to be displayed
_navigationStore.CurrentViewModel = new DayViewModel(CurrentMonth.Days[i], _navigationStore);
}
}
}