In MainWindow the commandbinding works fine. In UserControl1 it doesnt work. Note the datacontext is set correctly as is evidenced by the content of the button which is the result of a binding.
I am not trying to bind the command in the usercontrol to a command in mainwindow or any other such trickery. I am just trying to replicate what I did in MainWindow in UserControl1.
MainWindow XAML
<StackPanel>
<Button Content="Click Here" Command="{Binding ClickHereCommand}" Height="25" Width="90"></Button>
<local:UserControl1></local:UserControl1>
</StackPanel>
MainWindow Code Behind
public partial class MainWindow : Window
{
public static RoutedCommand ClickHereCommand { get; set; }
public MainWindow()
{
InitializeComponent();
this.DataContext = this;
ClickHereCommand = new RoutedCommand();
CommandBindings.Add(new CommandBinding(ClickHereCommand, ClickHereExecuted));
}
public void ClickHereExecuted(object sender, ExecutedRoutedEventArgs e)
{
System.Windows.MessageBox.Show("hello");
}
}
UserControl XAML
<UserControl x:Class="CommandBindingTest.UserControl1"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
mc:Ignorable="d"
d:DesignHeight="300" d:DesignWidth="300" x:Name="root">
<Grid DataContext="{Binding ElementName=root}" >
<Button Content="{Binding ButtonContent}" Command="{Binding ClickHereCommand}" Height="25" Width="90"></Button>
</Grid>
</UserControl>
UserControl Code Behind
public partial class UserControl1 : UserControl, INotifyPropertyChanged
{
private string _ButtonContent;
public string ButtonContent
{
get { return _ButtonContent; }
set
{
if (_ButtonContent != value)
{
_ButtonContent = value;
OnPropertyChanged("ButtonContent");
}
}
}
public static RoutedCommand ClickHereCommand { get; set; }
public UserControl1()
{
InitializeComponent();
ClickHereCommand = new RoutedCommand();
CommandBindings.Add(new CommandBinding(ClickHereCommand, ClickHereExecuted));
ButtonContent = "Click Here";
}
public void ClickHereExecuted(object sender, ExecutedRoutedEventArgs e)
{
System.Windows.MessageBox.Show("hello from UserControl1");
}
#region INotifyPropertyChanged Members
public event PropertyChangedEventHandler PropertyChanged;
public void OnPropertyChanged(string name)
{
if (PropertyChanged != null)
{
PropertyChanged(this, new PropertyChangedEventArgs(name));
}
}
#endregion
}
It's the best solution:
<Grid DataContext="{Binding RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type UserControl}}}" >
<Button Content="{Binding ButtonContent}" Command="{Binding ClickHereCommand}" Height="25" Width="90"></Button>
</Grid>
Other solutions:
You forgot set DataContext to UserControl1.
public UserControl1()
{
InitializeComponent();
ClickHereCommand = new RoutedCommand();
CommandBindings.Add(new CommandBinding(ClickHereCommand, ClickHereExecuted));
ButtonContent = "Click Here";
this.DataContext = this;
}
And after this you must delete in UserControl1 DataContext in Grid.
This:
<Grid DataContext="{Binding ElementName=root}" >
<Button Content="{Binding ButtonContent}" Command="{Binding ClickHereCommand}" Height="25" Width="90"></Button>
</Grid>
you must change to this:
<Grid>
<Button Content="{Binding ButtonContent}" Command="{Binding ClickHereCommand}" Height="25" Width="90"></Button>
</Grid>
Solution without set DataContext in UserControl:
You must change ButtonContent and ClickHereCommand to DependencyProperty.
public string ButtonContent
{
get { return (string)GetValue(ButtonContentProperty); }
set { SetValue(ButtonContentProperty, value); }
}
public static readonly DependencyProperty ButtonContentProperty =
DependencyProperty.Register("ButtonContent", typeof(string), typeof(UserControl1), new UIPropertyMetadata(string.Empty));
public RoutedCommand ClickHereCommand
{
get { return (RoutedCommand)GetValue(ClickHereCommandProperty); }
set { SetValue(ClickHereCommandProperty, value); }
}
public static readonly DependencyProperty ClickHereCommandProperty =
DependencyProperty.Register("ClickHereCommand", typeof(RoutedCommand), typeof(UserControl1), new UIPropertyMetadata(null));
And in ctor of UserControl1
:
public UserControl1()
{
InitializeComponent();
ClickHereCommand = new RoutedCommand();
CommandBindings.Add(new CommandBinding(ClickHereCommand, ClickHereExecuted));
ButtonContent = "Click Here";
//this.DataContext = this;
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With