WPF: binding commands in styles and / or data templates (MVVM)?

Here is a very quick and simplified explanation of my situation. I have defined the style for the Hyperlink controls and they have the Command property associated with the command defined in the ViewModel class (simplified):

 <Window.Resources> ... <Style x:Key="hyperlinkStyle" TargetType="Hyperlink"> ... <Setter Property="Command" Value="{Binding Path=OpenHyperlinkCommand}" /> ... </Style> ... </Window.Resources> 

Then I created a content control in the window that I am designing. It has a data template defined in window resources. Inside this data template, I added some hyperlinks, and I set these hyperlinks to use a previously defined style.

The window looks like this (simplified):

 <Window> ... <ContentControl ... ContentTemplate="{StaticResource myDataTemplate}" /> ... </Window> 

The data template looks like this (simplified):

 <Window.Resources> ... <DataTemplate x:Key="myDataTemplate DataType="{x:Type my:MyType}"> ... <TextBlock> <Hyperlink Style="{StaticResource hyperlinkStyle}" CommandParameter="{Binding Path=Uri1}"> <TextBlock Text="{Binding Path=Uri1}" /> </Hyperlink> </TextBlock> ... <TextBlock> <Hyperlink Style="{StaticResource hyperlinkStyle}" CommandParameter="{Binding Path=Uri2}"> <TextBlock Text="{Binding Path=Uri2}" /> </Hyperlink> </TextBlock> ... </DataTemplate> ... </Window.Resources> 

Binding to the OpenHyperlinkCommand in style does not work, because the ViewModel window associated with it contains this command, but the DataTemplate bound to MyType objects that do not contain this command (and should not).

How do I make this binding? Two questions:

  • Here is my suggestion: I named my window x:Name="myWindow" and changed the binding command inside the style:

     <Setter Property="Command" Value="{Binding ElementName=myWindow Path=DataContext.OpenHyperlinkCommand}" /> 

    It works, but it looks so dirty. Am I doing it wrong? Is there a better way, more MVVM-like? This is fragile because I set a specific element name inside the style!

  • Is it good practice to write team bindings inside a style in the first place? If not, what is the alternative? What if I developed a sophisticated UserControl , how would I issue commands to components somewhere deep inside its logical tree?

Thanks for the help!

+6
source share
1 answer
  • Alternative syntax will use RelativeSource

    <Setter Property="Command" Value="{Binding DataContext.OpenHyperlinkCommand, RelativeSource={Relative Source AncestorType={x:Type Window}}}">

  • I see nothing wrong with writing style bindings for commands

+17
source

Source: https://habr.com/ru/post/885769/


All Articles