简体   繁体   中英

Passing Datacontext as CommandParameter to Viewmodel in Windows 10

I am displaying the data in the gridview in a grouped style. I am already can create new items. Now I want to create a function that can delete the item that I create. Here is my viewmodel :

Viewmodel

public class VM : INotifyPropertyChanged
{
    public VM()
    {
        DeleteItem = new DelegateCommand(DeleteCurrentItem);
    }

    public ObservableCollection<Contact> ContList = new ObservableCollection<Contact>();

    private ObservableCollection<Category> _GroupedCollection;
    public ObservableCollection<Category> GroupedCollection
    {
        get
        {
            if (_GroupedCollection == null)
                _GroupedCollection = new ObservableCollection<Category>();
            return _GroupedCollection;
        }
        set
        {
            _GroupedCollection = value;
            if (PropertyChanged != null)
                PropertyChanged(this, new PropertyChangedEventArgs("GroupedCollection"));
        }
    }

    public void DeleteCurrentItem(object param)
    {
        var cont= param as Contact;
        // there is another class that declare another ObservableCollection that holds all the models.
        var category = GroupedCollection.FirstOrDefault(g => g.Key == cont.Account);
        if (category != null)
        {
            if (category.CredCategory.Contains(cont))
            {
                category.CredCategory.Remove(cont);
            }
        }
    }

    public DelegateCommand DeleteItem { get; set; }

    private string _Account;
    public string Account
    {
        get { return _Account; }
        set
        {
            _Account = value;
            if (PropertyChanged != null)
                PropertyChanged(this, new PropertyChangedEventArgs("Account"));
        }
    }


    public event PropertyChangedEventHandler PropertyChanged;
}

In my XAML, I have a flyout, which work as desired. I can hold the data displayed and the flyout will appear/open. But when I click "Delete", the 'gridview' does not delete it.

View (XAML)

<Page.DataContext>
    <data:VM/>
</Page.DataContext>
<Page.Resources>
    <CollectionViewSource x:Key="cvs" IsSourceGrouped="True" 
                          Source="{Binding GroupedCollection, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
                          ItemsPath="CredCategory"/>
</Page.Resources>
<Grid>
   <FlyoutBase.AttachedFlyout>
       <MenuFlyout x:Name="flyout">
            <MenuFlyoutItem Text="Delete" 
                            Command="{Binding DataContext.DeleteItem, ElementName=gridview}" 
                            CommandParameter="{Binding}"/>
        </MenuFlyout>
   </FlyoutBase.AttachedFlyout>
   <GridView x:Name="gridview" 
             ItemsSource="{Binding Source={StaticResource cvs}}"
        <GridView.ItemTemplate>
                <DataTemplate>
                 .  .  .  .
                <DataTemplate/>
        <GridView.ItemTemplate>
    <GridView/>
<Grid/>

I am showing the code-behind in case someone wants to see it.

View (Code-Behind)

public void cardstack_pass_Holding(object sender, HoldingRoutedEventArgs e)
    {
        //this is the event declared in the Datatemplate inside gridview
        flyout.ShowAt(sender as FrameworkElement);
        e.Handled = true;
    }

As I stated at the above, my problem is when I click the "Delete" on flyout , it should be deleting the data from the ObservableCollection right? Because as far as I know, the DataContext of the flyout is the DataContext of the data displayed, or am I wrong? How to fix this?

I mean, the gridview 's DataContext is the ObservableCollection, and the Stackpanels' DataContext inside gridview 's DataTemplate will be the Model Contact right? Since flyout was open at the item created, so the DataContext of flyout will inherit from the item's DataContext, and if the flyout 's CommandParameter = "{Binding}" , it should pass the Contact inside the item to the viewmodel, isn't it?

I might be missing something here but shouldn't the AttachedFlyout code go in the DataTemplate

Note Binding of Command to element name root (Page name) as we're inside the GridView eg

<Page x:Name="root">
    <Page.DataContext>
      <data:VM/>
    </Page.DataContext>
    <Page.Resources>
       <CollectionViewSource x:Key="cvs" IsSourceGrouped="True" 
                      Source="{Binding GroupedCollection, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
                      ItemsPath="CredCategory"/>
    </Page.Resources>
    <Grid>
      <GridView x:Name="gridview" 
          ItemsSource="{Binding Source={StaticResource cvs}}"
          <GridView.ItemTemplate>
             <DataTemplate>
                 <FlyoutBase.AttachedFlyout>
                   <MenuFlyout x:Name="flyout">
                      <MenuFlyoutItem Text="Delete" 
                           Command="{Binding DataContext.DeleteItem, ElementName=root}" 
                           CommandParameter="{Binding}"/>
                 </MenuFlyout>
              </FlyoutBase.AttachedFlyout>                 
            <DataTemplate/>
        <GridView.ItemTemplate>
     <GridView/>
  <Grid/>

This article shows how to use Behaviours which are available in UWP.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM