Brian Mains
Brian Mains

Reputation: 50728

Command Is Not Firing From VIew

I have a windows store app using XAML, where I have a binding that is of type:

DelegateCommand<DomainObject>

I'm trying to bind a list of DomainObject's like the following. Note the button in the item template, fires the StartCommand:

<ItemsControl
    x:Name="MyList"
    ItemsSource="{Binding Path=Items}">
    <ItemsControl.ItemTemplate>
        <DataTemplate>
            <StackPanel Orientation="Horizontal" Style="{StaticResource Para}">
                <Image>
                    <Image.Source>
                        <BitmapImage UriSource="{Binding Path=Image}" />
                    </Image.Source>
                </Image>

                <TextBlock Text="{Binding Path=Name}" Width="300" />

                <Button Content="Start"
                    Command="{Binding Path=StartCommand}"
                    CommandParameter="{Binding}"/>
            </StackPanel>
        </DataTemplate>
    </ItemsControl.ItemTemplate>
</ItemsControl>

In the view model, I have the following:

public DelegateCommand<DomainObject> StartCommand
{
    get { return _startCommand; }
    set
    {
        _startCommand = value;
                //method I use to fire the property changed event
        this.NotifyPropertyChanged("StartCommand");
    }
}

I instantiate an instance of the command via:

StartCommand = new DelegateCommand<DomainObject>(StartSession);

However, when the button is clicked, it never fires the command... my breakpoint in StartSession is not hit. Where have I gone wrong? Is it how I setup the command or parameter? I can't figure this out. Also note that the item in the ItemsControl is bound to an instance of DomainObject, so I want to pass that as the CommandParameter, which is why I think I messed it up...

Upvotes: 0

Views: 145

Answers (1)

Simon Belanger
Simon Belanger

Reputation: 14870

The reason this is not working is because of the DataContext inside an ItemTemplate. The line:

<Button Content="Start"
        Command="{Binding Path=StartCommand}"
        CommandParameter="{Binding}"/>

Will bind to the StartCommand property in the DomainObject class, not your View Model. Do bind to the correct DataContext (the one your ItemsControl, not your ItemContainer is bound to) a small adjustment is required:

<Button Content="Start"
        Command="{Binding Path=DataContext.StartCommand, 
                          RelativeSource={RelativeSource AncestorType={x:Type ItemsControl}}}"
        CommandParameter="{Binding}"/>

This way, the WPF binding will find the ancestor of type ItemsControl and bind to the DataContext.StartCommand property (assuming the DataContext is your View Model).

Upvotes: 3

Related Questions