Search code examples
c#uwpxamarin.formsuipangesturerecognizer

Xamarin.Forms using PanGestureRecognizer - move outside of Window area on UWP does not trigger Status Canceled or Completed


My question is regarding the PanGestureRecognizer on Xamarin.Forms, specifically on UWP. The pan gesture works great and the menu slides in and out but if you move the mouse cursor outside of the application window it does not trigger GestureStatus.Canceled, or GestureStatus.Completed. I've simplified the code below because it is not important. The pan gesture is working correctly and the menu is sliding in and out with the pan. The issue is it is not triggering anything if you move the cursor outside of the app window.

Code below:

panContainer is a simple ContentView.

var panGesture = new PanGestureRecognizer();
panGesture.PanUpdated += PanUpdated;
panContainer.GestureRecognizers.Add(panGesture);

private void PanUpdated(object sender,PanUpdatedEventArgs e) {
        switch(e.StatusType) {
            case GestureStatus.Started:
                break;
            case GestureStatus.Running:
                menuLayout.TranslationX = (float)e.TotalX;
                break;
            case GestureStatus.Completed:
            case GestureStatus.Canceled:  //I assumed this would be called!
                if(menuLayout.TranslationX < 100) {
                    Close();
                } else {
                    Open();
                }
                break;
        }
    }

Thanks in advance!


Solution

  • if you move the mouse cursor outside of the application window it does not trigger GestureStatus.Canceled, or GestureStatus.Completed. I've simplified the code below because it is not important. The pan gesture is working correctly and the menu is sliding in and out with the pan. The issue is it is not triggering anything if you move the cursor outside of the app window.

    I have tested your code and reproduce the issue. I tried to find the cause of the problem in the source code. I found the following code.

    void OnPointerCanceled(object sender, PointerRoutedEventArgs e)
    {
        uint id = e.Pointer.PointerId;
        if (_fingers.Contains(id))
            _fingers.Remove(id);
    
        PinchComplete(false);
        PanComplete(false);
    }
    
    void OnPointerExited(object sender, PointerRoutedEventArgs e)
    {
        uint id = e.Pointer.PointerId;
        if (_fingers.Contains(id))
            _fingers.Remove(id);
    
        PinchComplete(true);
        PanComplete(true);
    }
    
    void OnPointerPressed(object sender, PointerRoutedEventArgs e)
    {
        uint id = e.Pointer.PointerId;
        if (!_fingers.Contains(id))
            _fingers.Add(id);
    }
    
    void OnPointerReleased(object sender, PointerRoutedEventArgs e)
    {
        uint id = e.Pointer.PointerId;
        if (_fingers.Contains(id))
            _fingers.Remove(id);
    
        PinchComplete(true);
        PanComplete(true);
    }
    

    The PanComplete method will be invoked when you PointerExited,ManipulationCompleted etc. But it has not been invoked when the pointer exited. And then I tried to test PointerExited and ManipulationCompleted event in uwp native project. Both are working properly.

    <Border Width="200" Height="200"  Background="Red" PointerEntered="Border_PointerEntered" PointerExited="Border_PointerExited" ManipulationCompleted="Border_ManipulationCompleted"/>
    

    So,there may be some issues with xamarin.