3

A Grid in my DataTemplate currently has this Flyout.

                    <Grid.ContextFlyout>
                        <MenuFlyout x:Name="AlbumFlyout">
                            <MenuFlyoutItem Icon="Shuffle" Text="Shuffle" />
                            <MenuFlyoutItem Icon="Delete" Text="Delete" />
                        </MenuFlyout>
                    </Grid.ContextFlyout>

And I also have a Flyout generated dynamically:

    public static MenuFlyout GetAddToPlaylistFlyout()
    {
        MenuFlyout flyout = new MenuFlyout();
        flyout.Items.Add(new MenuFlyoutItem()
        {
            Icon = new FontIcon() { Glyph = "\uEC4F" },
            Text = "Now Playing"
        });
        flyout.Items.Add(new MenuFlyoutSeparator());
        flyout.Items.Add(new MenuFlyoutItem()
        {
            Icon = new SymbolIcon(Symbol.Add),
            Text = "New Playlist"
        });
        foreach (var playlist in Settings.settings.Playlists)
        {
            var item = new MenuFlyoutItem()
            {
                Icon = new SymbolIcon(Symbol.Audio),
                Text = playlist.Name
            };
            flyout.Items.Add(item);
        }
        return flyout;
    }

It is dynamically generated because I need to reuse it a lot and some of its MenuFlyoutItem is generated from user's data.

How can I insert the code-generated Flyout right below the Shuffle above the Delete?

---Update---

This is part of my ListView definition.

<ListView
    x:Name="SongsListView"
    Grid.Row="1"
    AllowDrop="True"
    CanDrag="True"
    CanReorderItems="True"
    ContainerContentChanging="SongsListView_ContainerContentChanging"
    IsItemClickEnabled="True"
    ItemClick="SongsListView_ItemClick"
    ItemsSource="{Binding Songs, Mode=TwoWay}"
    ReorderMode="Enabled"
    SelectionMode="None">
    <ListView.ItemContainerStyle>
        <Style TargetType="ListViewItem">
            <Setter Property="HorizontalContentAlignment" Value="Stretch" />
            <Setter Property="ContextFlyout" Value="{StaticResource ListViewItemContextFlyout}" />
        </Style>
    </ListView.ItemContainerStyle>
</ListView>
Seaky Lone
  • 992
  • 1
  • 10
  • 29

1 Answers1

3

It looks like you have two fixed items, Shuffle and Delete.

You want to insert the newly generated MenuFlyout item between these two items. Try this code:

var newFlyout = GetAddToPlaylistFlyout();
foreach(var item in newFlyout.Items)
{
    AlbumFlyout.Items.Insert(AlbumFlyout.Items.Count - 1, item);
}

By the way, if your AlbumFlyout is in the DataTemplate and may not be available in Code-behind, you can try to put it in Page.Resources and then reference it with StaticResource.

Best regards.

Richard Zhang
  • 7,523
  • 1
  • 7
  • 13
  • Do you mean put the `DataTemplate` in the resources? – Seaky Lone Sep 03 '19 at 05:32
  • 1
    It is not required to put the DataTemplate in the Resource, but if your `MenuFlyout` is a child of the DataTemplate, you can consider putting the MenuFlyout in the Resource in order to get it. – Richard Zhang Sep 03 '19 at 07:01
  • I have now put the `MenuFlyout` in the `Resource` and assign the `MenuFlyout ` using `ListView.ItemContainerStyle` but now I have another problem. I used to be able access the data bound to the DataTemplate by doing `(sender as MenuFlyoutItem).DataContext`. Now it's returning `null`. How can I get the data? – Seaky Lone Sep 03 '19 at 12:52
  • Try using ContextFlyout="{StaticResource your_flyout}" so that MenuFlyout can share the DataContext – Richard Zhang Sep 03 '19 at 13:30
  • Yes this is what I did: `` but I still get null. I put it in the Style of `ListView.ItemContainerStyle`. – Seaky Lone Sep 03 '19 at 13:38
  • Please do not write ContextFlyout to Style, complete resource link in DataTemplate. – Richard Zhang Sep 03 '19 at 13:45
  • I have actually also has a question with that. For example, my `DataTemplate` has a `Grid` as it content. And should I register the `MenuFlyout` to `Grid.ContextFlyout`? But the problem with that is the right click only triggers the flyout when I click on the place with UI element on the `ListViewItem`. Adding it to the `ListView.ItemContainerStyle` makes it work everywhere. – Seaky Lone Sep 03 '19 at 13:59
  • You can create a highly transparent color as the Grid background so that the mouse doesn't penetrate the Grid, and you can also set the ListViewItem's `HorizontalContentAlignment` property to **Stretch** to ensure that the Grid can fill the entire element. – Richard Zhang Sep 03 '19 at 14:04
  • Sorry for so many questions but can you take a look at my code [here](https://github.com/SeakyLuo/SMPlayer/blob/master/SMPlayer/Controls/PlaylistControl.xaml) why right click doesn't trigger the `MenuFlyout`? – Seaky Lone Sep 03 '19 at 14:40
  • 1
    When right-clicking on an actual element (such as a TextBlock), will MenuFlyout appear? If so, the problem is that on your transparent background, you have not set the Background for the Grid, which means that when you right click on the blank, the pointer actually penetrates the Grid, and there is no actual trigger, you can try to give the Grid set the Background and observe the trigger. – Richard Zhang Sep 03 '19 at 14:48
  • Do you mean I need to create an transparent element to be the background or just set it to be transparent? – Seaky Lone Sep 03 '19 at 15:07
  • Please set the background color of the Grid, do not be transparent. You can create a SolidColorBrush resource and set Opacity to 0.1, but don't be transparent. – Richard Zhang Sep 03 '19 at 15:10