Dharmendra Kumar
Dharmendra Kumar

Reputation: 408

Drop down Menu & right Click on list item in Xamarin.Forms UWP

I am struggling to show drop down menu on click of image and also right click and show menu on list view row. I managed to get something with the help of relative layout and frames but it is taking space and also not coming into correct position.

Here is what I have managed to get Current Screen

But I have to make it something like below. Space should be removed. The menu should come over stack layout. IS there any way to make it over stacklayout? something like below enter image description here

Also in the list shown below, I want to add right click and show menu option which also requires showing Frame or other layout over list view. See below image. Any help or example will help me a lot.

enter image description here

Upvotes: 0

Views: 1469

Answers (1)

Nico Zhu
Nico Zhu

Reputation: 32785

Drop down Menu & right Click on list item in Xamarin.Forms UWP

Xamarin ViewCell has ContextActions property that could use to response ListView item right click. Unfortunately, the MenuItem is hard to custom.

<ViewCell.ContextActions>
    <MenuItem Text="Add" Clicked="Add_Clicked"></MenuItem>
    <MenuItem Text="Delete" Clicked="Delete_Clicked"></MenuItem>
    <MenuItem Text="Edit" Clicked="Edit_Clicked"></MenuItem>
</ViewCell.ContextActions>

For your scenario, we suggest to custom ListViewRender, and listen ListViewItem right click event then call a popup. For more code please refer the following.

Forms client

public class CustomListView :ListView
{
    public event ItemRightTappedEventHandler ItemRightTapped;
    public void RaiseItemRightTapped(ItemRightTappedEventArgs e)
    {
        if (ItemRightTapped != null)
            this.ItemRightTapped(this, e);
    }

}
public delegate void ItemRightTappedEventHandler(object sender, ItemRightTappedEventArgs e);
public class ItemRightTappedEventArgs : EventArgs
{
    #region Fields

    private object itemData = null;

    private Point position;

    #endregion

    #region Constructor

    public ItemRightTappedEventArgs(object itemData, Point position)
    {
        this.itemData = itemData;
        this.position = position;
    }

    #endregion

    #region Property

    public object ItemData
    {
        get { return itemData; }
    }

    public Point Position
    {
        get { return position; }
    }

    #endregion
}

UWP Client

[assembly: ExportRenderer(typeof(CustomListView), typeof(CustomListViewRender))]

namespace DropDownMenuTest.UWP
{
    public class CustomListViewRender : ListViewRenderer
    {
        ListView listView;
        Xamarin.Forms.ITemplatedItemsView<Xamarin.Forms.Cell> TemplatedItemsView => Element;
        object clickItemdataContext;
        protected override void OnElementChanged(ElementChangedEventArgs<Xamarin.Forms.ListView> e)
        {
            base.OnElementChanged(e);
            listView = Control as ListView;
            if (Control != null)
            {
                listView.Loaded += ListView_Loaded;
            }

        }
        protected override void OnApplyTemplate()
        {
            base.OnApplyTemplate();
        }
        private void ListView_Loaded(object sender, Windows.UI.Xaml.RoutedEventArgs e)
        {

            listView.RightTapped += ListView_RightTapped;

        }

        private void ListView_RightTapped(object sender, Windows.UI.Xaml.Input.RightTappedRoutedEventArgs e)
        {
            var orig = e.OriginalSource as DependencyObject;
            int index = -1;


            // Work our way up the tree until we find the actual list item
            // the user tapped on

            while (orig != null && orig != List)
            {
                var lv = orig as ListViewItem;
                if (lv != null)
                {
                    index = TemplatedItemsView.TemplatedItems.GetGlobalIndexOfItem(lv.Content);
                    clickItemdataContext = listView.ItemFromContainer(lv);
                    break;
                }

                orig = VisualTreeHelper.GetParent(orig);
            }

            if (index > -1)
            {
                var point = e.GetPosition(listView);

                OnListItemClicked(clickItemdataContext, new Xamarin.Forms.Point(point.X, point.Y));
            }

        }

        void OnListItemClicked(object context, Xamarin.Forms.Point point)
        {
            var tappedEventArgs = new ItemRightTappedEventArgs(context, new Xamarin.Forms.Point(point.X, point.Y));
            var customListView = Element as CustomListView;
            customListView.RaiseItemRightTapped(tappedEventArgs);

        }
        protected override void OnElementPropertyChanged(object sender, PropertyChangedEventArgs e)
        {
            base.OnElementPropertyChanged(sender, e);
        }

    }
}

Usage

<local:CustomListView
    x:Name="MainListView"
    HasUnevenRows="True"
    ItemRightTapped="MainListView_ItemRightTapped"
    >
    <ListView.ItemTemplate>
        <DataTemplate>
            <ViewCell>
                <Grid>
                    <Label
                        FontSize="25"
                        Text="{Binding .}"
                        TextColor="Navy"
                        />
                </Grid>
            </ViewCell>
        </DataTemplate>
    </ListView.ItemTemplate>
</local:CustomListView>

private void MainListView_ItemRightTapped(object sender, ItemRightTappedEventArgs e)
{
// show popup view
}

Upvotes: 2

Related Questions