Triggering commands from DataGridTemplateColumn in Silverlight

Topics: Prism v4 - Silverlight 4
Feb 18, 2011 at 2:36 PM

I am trying to fire a command from a DataGridTemplateColumn in a Silverlight datagrid. This used to work very well in WPF but does not work in Silverlight. I have read about several approaches to solve this issue (adding behaviors, using static resources on the view, etc.) but wanted to know what is the recommended approach in light of Prism 4. Here's what I have right now that doesn't work (I am binding the command to the current view using ElementName):

<sdk:DataGridTemplateColumn Header="Name">
    <sdk:DataGridTemplateColumn.CellTemplate>
        <DataTemplate>
            <HyperlinkButton
                Content="{Binding Path=Name}"
                Command="{Binding ElementName=ThisView, Path=DataContext.SelectAccountCommand}"
                CommandParameter="{Binding}" />
        </DataTemplate>
    </sdk:DataGridTemplateColumn.CellTemplate>
</sdk:DataGridTemplateColumn>

Developer
Feb 18, 2011 at 2:47 PM
Edited Feb 18, 2011 at 2:47 PM

Hi,

There is no recommended approach per se in prism. However, you might find the following thread useful, as a similar problem is dealt with:

command in datagrid not work

I hope you find this helpful.

Guido Leandro Maliandi
http://blogs.southworks.net/gmaliandi

Feb 18, 2011 at 4:18 PM

Thanks Guido. I tried the solution suggested in that thread, but could not code exactly like that. That thread suggests:

        [ImportingConstructor]
        public ProductList(ProductListViewModel viewModel)
        {            
            this.DataContext = viewModel;
            this.Resources.Add("ViewModel", viewModel);
            InitializeComponent();
        }

Since I am not using an ImportingConstructor, I added the resource in the [Import] of the ViewModel. However this did not work. Any thoughts why?

    [ViewExport(RegionName = "LoggedInUserRegion")]
    [PartCreationPolicy(CreationPolicy.NonShared)]
    public partial class AccountsView : UserControl
    {
        public AccountsView()
        {
            Debug.WriteLine("[Debug] AccountsView.AccountsView()");
            InitializeComponent();
        }

        [Import]
        public IAccountsViewModel ViewModel
        {
            set
            {
                this.DataContext = value;
                this.Resources.Add("ViewModel", value);
            }
        }
    }

Developer
Feb 18, 2011 at 4:35 PM

Hi,

The approach you've followed might not be working because you need to add the resource before calling the InitializeComponent method. You could, for example, declare the import, and call the InitializeComponent method inside the setter. Another possibility would be to implement the IPartImportsSatisfiedNotification interface and call the InitializeComponent method in the OnImportsSatisfied method.

I hope you find this helpful.

Guido Leandro Maliandi
http://blogs.southworks.net/gmaliandi

Feb 18, 2011 at 7:42 PM

I followed the example in the other post and changed the constructor to an [ImportingConstructor] with viewModel passed in as a parameter. Everything is working now. I personally try to avoid parameterized constructors for Views because they have caused problems for me when working inside Visual Studio (don't know if that's a valid concern). However in this case it seems to be the cleanest way to trigger the command.

Guido, thanks so much for your help.