MR.Gestures handles ALL touch gestures

14567810»

Posts

  • Umar3xUmar3x FRMember ✭✭

    Hello all,

    I need to create my own button class for custom rendering needs. But it seems then that command binding is not triggered anymore.

    My class is simple :

    public class ButtonComponent : MR.Gestures.Button
    {

    }
    

    _validateButton.SetBinding(MR.Gestures.TappedCommandProperty,
    "ValidateAddingPinCommand");

    I put ButtonComponent.TappedCommandProperty to test if it would work with but same issue, nothing triggered.

    If you know why it does such a behavior or if I could find a workaround if inheritance is causing the issue, which could be a future problem for me for other controls :/

    Thanks for your response,

    Regards,

  • MichaelRumplerMichaelRumpler ATMember ✭✭✭✭✭

    @RyanMorris I try to keep all other gesture event handlers on the controls working in order not to break any native functionality. This includes dragging a map around.

    @aj-ja UWP doesn't check if there are multiple elements above each other and it triggers all elements which are at the touch coordinates. I don't know, which elements are on top and as I wrote above, I don't want to break any native functionality by suppressing any touch gestures.

    @Umar3x I don't understand what you're trying to do and how. Please send me a repro project.

  • Umar3xUmar3x FRMember ✭✭
    edited September 22

    Hello Michael ... I don't try to achieve anything. I'm just having a button class extending MR.Gestures.Button class ... and since I extend it this line do not work anymore, seems that as I extend it, the MR.Gestures.Button.TappedCommandProperty do not work anymore.

    public class ButtonComponent : MR.Gestures.Button
    {
    
    }
    

    private ButtonComponent _validateButton;

    _validateButton.SetBinding(MR.Gestures.Button.TappedCommandProperty, "ValidateAddingPinCommand");

    What I'm saying is that extending the class causes binding not to work.

    Thanks.

  • MichaelRumplerMichaelRumpler ATMember ✭✭✭✭✭

    The commands should also work in subclasses.
    Do you have a custom renderer for your ButtonComponent? Then the renderer must inherit from MR.Gestures.platform.Renderers.ButtonRenderer.

  • Umar3xUmar3x FRMember ✭✭

    Well it seems that it does not work with the subclass. I don't use a buttonRenderer. The command is simply not triggered.

  • Umar3xUmar3x FRMember ✭✭
    edited October 25

    Hi @MichaelRumpler,

    Still got the prob. When simply extending MR.Gestures.Button (w/o any renderer, nothing) the tappedcommand is not triggered anymore.
    So with only that code :

    public class ButtonComponent : MR.Gestures.Button
        {
    
        }
    

    Thanks.

  • MichaelRumplerMichaelRumpler ATMember ✭✭✭✭✭
    edited October 27

    I just released MR.Gestures 1.5.0.

    This version includes support for MacOS and .NET Standard 1.0.

    Of course Apple managed to make MacOS and iOS very different when it comes to gestures. So this was much more effort than I thought. There are also still some bugs in Xamarin.Forms.MacOS.

    Apple still has no multi touch displays for MacOS, so I made the touch gestures on the Mac to work as I would expect them to. If you think anything is awkward or doesn't behave as you would expect, please let me know.

    Down, Up, Tapping, Tapped, DoubleTapped, LongPressing, LongPressed, Panning, Panned and Swiped can be triggered with the mouse.
    For Pinching, Pinched, Rotating and Rotated you need a Trackpad and two or more fingers.
    Panning, Panned and Swiped can also be triggered with the Trackpad with two or more fingers.

    As the Trackpad has coordinates of its own which are not related to the touched view at all, the Points in Touches work a bit different then on the other platforms / using the mouse. Apple recommends to use [NSTouch](https://developer.apple.com/documentation/appkit/nstouch "NSTouch").normalizedPosition * deviceSize as coordinates but this is still very small if you drag and drop an element. So I added MR.Gestures.MacOS.Settings.TrackpadCoordinateRatio and multiply all coordinates by that setting. The default is 5/5, but you can change it however you want to get bigger or smaller values for the Touches.

    Apple also doesn't use the same coordinate system in MacOS as every other computer on earth. They have the 0/0 point at the LOWER left. So keep this in mind when you work with the view, touch or other coordinates.
    Most likely you'll have to do some different logic on the Mac than on the other platforms. Fortunately this is consistent with Xamarin.Forms.VisualElement.TranslationY and other Y coordinates.
    This also means that angles are counter clock wise instead of clock wise on every other platform.

    There's also a bug in Xamarin.Forms.MacOS. Their PageRenderer and ScrollViewRenderer don't have virtual methods OnElementChanged and OnElementPropertyChanged to override. Therefore I cannot hook into those elements' touch handlers. I already submitted a PR to Xamarin and they already merged it into master, but it is not yet included in XF 2.4.0.18342.

    Some elements don't work in the GestureSample. The touch gestures work completely, but the native functionality of the element does not work anymore. I'm still working on that.

    The Cell renderers don't have Touches*WithEvent methods to override, so there multitouch gestures with the Trackpad don't work. But you can still add a ContentView or similar to handle them there.

    More info can be found in my Compatibility section.

  • MichaelRumplerMichaelRumpler ATMember ✭✭✭✭✭
    edited October 27

    Initially I wanted to use the very cheap price of EUR 10,- just for the first few weeks. Those weeks now extended to 2.5 years. It's far overdue that I raise it. The effort for MacOS and general support is too high. Some people also seem to think that I could fix all their bugs if they buy a product for €10,-. Well, sorry, I can't do that.

    MR.Gestures now costs EUR 40,-. This is the price for around 30 minutes when you hire me as consultant.

    @Umar3x As you were not able to send me a repro project, I made one for you. I added a test page to the GestureSample in Tests / Custom Button. This uses a CustomButton which inherits from the MR.Gestures.Button. It works just fine.

  • JohnBairdJohnBaird USMember ✭✭

    Thanks so much for version 1.5 which supports .net standard... works like a charm...

  • BrianLimkemannBrianLimkemann USMember

    I have a similar issue on UWP where anything below an Action Sheet is fired as well.

  • RBanseRBanse DEMember

    First of all I'd like to thank you, Michael Rumpler. Your plugin saved me a lot of time.

    Now my problem: My app uses a Master-Detail-Page with 4 detail pages. One of these pages contains a TableView with a MR.Gestures.ViewCell. When this page is opened the first time, everything works fine, but switching to another page and back again crashes the app. I receive a NullReferenceException caused by the renderer in iOS.

    System.NullReferenceException: Object reference not set to an instance of an object
    at MR.Gestures.iOS.iOSGestureHandler.removeGestureRecognizers () [0x0001d] in <1b0efa77a4694803aaf75c99d82a8b9c>:0
    at MR.Gestures.iOS.iOSGestureHandler.AddGestureRecognizers (MR.Gestures.IGestureAwareControl element, UIKit.UIView view) [0x0000f] in <1b0efa77a4694803aaf75c99d82a8b9c>:0
    at MR.Gestures.iOS.Renderers.ViewCellRenderer.GetCell (Xamarin.Forms.Cell item, UIKit.UITableViewCell reusableCell, UIKit.UITableView tv) [0x0000a] in <1b0efa77a4694803aaf75c99d82a8b9c>:0
    at Xamarin.Forms.Platform.iOS.CellTableViewCell.GetNativeCell (UIKit.UITableView tableView, Xamarin.Forms.Cell cell, System.Boolean recycleCells, System.String templateId) [0x00080] in <9a5948fff8254b13a3d593c76c73b9b1>:0
    at Xamarin.Forms.Platform.iOS.TableViewModelRenderer.GetCell (UIKit.UITableView tableView, Foundation.NSIndexPath indexPath) [0x0001d] in <9a5948fff8254b13a3d593c76c73b9b1>:0
    at at (wrapper managed-to-native) UIKit.UIApplication:UIApplicationMain (int,string[],intptr,intptr)
    at UIKit.UIApplication.Main (System.String[] args, System.IntPtr principal, System.IntPtr delegate) [0x00005] in /Users/builder/data/lanes/5520/51128b8c/source/xamarin-macios/src/UIKit/UIApplication.cs:79
    at UIKit.UIApplication.Main (System.String[] args, System.String principalClassName, System.String delegateClassName) [0x00038] in /Users/builder/data/lanes/5520/51128b8c/source/xamarin-macios/src/UIKit/UIApplication.cs:63
    at MobilePos.Services.iOS.Application.Main (System.String[] args) [0x00001] in /Users/secret/project/name/iOS/Main.cs:17

    The related xaml is just that simple (sorry, I have to be here for a bit longer, before I can post links...):

    <?xml version="1.0" encoding="UTF-8"?>
    <ContentPage 
       xmlns="..." 
       xmlns:x="..."
       xmlns:i18n="clr-namespace:MobilePos.Localization"
       xmlns:util="clr-namespace:MobilePos.Helpers"
       xmlns:statics="clr-namespace:MobilePos.Statics"
       xmlns:mr="clr-namespace:MR.Gestures;assembly=MR.Gestures"
       x:Class="MobilePos.Pages.InfoPage"
       Title="{i18n:Translate Nav_Info}">
    
       <ContentPage.Resources>
          <ResourceDictionary>
             <util:SendTaskQueueCountNameConverter x:Key="ISendTaskQueueCountNameConverter"/>
          </ResourceDictionary>
       </ContentPage.Resources>
    
        <ContentPage.Content>
          <TableView Intent="Form">
             <TableView.Root>           
                <TableSection Title="{i18n:Translate TableSection_CloudConnection}">
                   <mr:ViewCell TappedCommand="{Binding ShowSendTaskQueueCommand}">
                      <Label Margin="15" Text="{Binding SendTaskQueueCount, Converter={StaticResource ISendTaskQueueCountNameConverter}}" VerticalOptions="CenterAndExpand" />
                   </mr:ViewCell>  
                </TableSection>            
             </TableView.Root>
          </TableView>
        </ContentPage.Content>
    </ContentPage>
    
  • RBanseRBanse DEMember

    First of all I'd like to thank you, Michael Rumpler. Your plugin saved me a lot of time.

    Now my problem: My app uses a Master-Detail-Page with 4 detail pages. One of these pages contains a TableView with a MR.Gestures.ViewCell. When this page is opened the first time, everything works fine, but switching to another page and back again crashes the app. I receive a NullReferenceException caused by the renderer in iOS.

    System.NullReferenceException: Object reference not set to an instance of an object
    at MR.Gestures.iOS.iOSGestureHandler.removeGestureRecognizers () [0x0001d] in <1b0efa77a4694803aaf75c99d82a8b9c>:0
    at MR.Gestures.iOS.iOSGestureHandler.AddGestureRecognizers (MR.Gestures.IGestureAwareControl element, UIKit.UIView view) [0x0000f] in <1b0efa77a4694803aaf75c99d82a8b9c>:0
    at MR.Gestures.iOS.Renderers.ViewCellRenderer.GetCell (Xamarin.Forms.Cell item, UIKit.UITableViewCell reusableCell, UIKit.UITableView tv) [0x0000a] in <1b0efa77a4694803aaf75c99d82a8b9c>:0
    at Xamarin.Forms.Platform.iOS.CellTableViewCell.GetNativeCell (UIKit.UITableView tableView, Xamarin.Forms.Cell cell, System.Boolean recycleCells, System.String templateId) [0x00080] in <9a5948fff8254b13a3d593c76c73b9b1>:0
    at Xamarin.Forms.Platform.iOS.TableViewModelRenderer.GetCell (UIKit.UITableView tableView, Foundation.NSIndexPath indexPath) [0x0001d] in <9a5948fff8254b13a3d593c76c73b9b1>:0
    at at (wrapper managed-to-native) UIKit.UIApplication:UIApplicationMain (int,string[],intptr,intptr)
    at UIKit.UIApplication.Main (System.String[] args, System.IntPtr principal, System.IntPtr delegate) [0x00005] in /Users/builder/data/lanes/5520/51128b8c/source/xamarin-macios/src/UIKit/UIApplication.cs:79
    at UIKit.UIApplication.Main (System.String[] args, System.String principalClassName, System.String delegateClassName) [0x00038] in /Users/builder/data/lanes/5520/51128b8c/source/xamarin-macios/src/UIKit/UIApplication.cs:63
    at MobilePos.Services.iOS.Application.Main (System.String[] args) [0x00001] in /Users/secret/project/name/iOS/Main.cs:17

    The related xaml is just that simple (sorry, I cannot post links right now, so I had to remove some xmlns):

    <?xml version="1.0" encoding="UTF-8"?>
    <ContentPage 
       xmlns="..." 
       xmlns:x="..."
       xmlns:i18n="clr-namespace:MobilePos.Localization"
       xmlns:util="clr-namespace:MobilePos.Helpers"
       xmlns:statics="clr-namespace:MobilePos.Statics"
       xmlns:mr="clr-namespace:MR.Gestures;assembly=MR.Gestures"
       x:Class="MobilePos.Pages.InfoPage"
       Title="{i18n:Translate Nav_Info}">
    
       <ContentPage.Resources>
          <ResourceDictionary>
             <util:SendTaskQueueCountNameConverter x:Key="ISendTaskQueueCountNameConverter"/>
          </ResourceDictionary>
       </ContentPage.Resources>
    
        <ContentPage.Content>
          <TableView Intent="Form">
             <TableView.Root>           
                <TableSection Title="{i18n:Translate TableSection_CloudConnection}">
                   <mr:ViewCell TappedCommand="{Binding ShowSendTaskQueueCommand}">
                      <Label Margin="15" Text="{Binding SendTaskQueueCount, Converter={StaticResource ISendTaskQueueCountNameConverter}}" VerticalOptions="CenterAndExpand" />
                   </mr:ViewCell>  
                </TableSection>            
             </TableView.Root>
          </TableView>
        </ContentPage.Content>
    </ContentPage>
    
  • RBanseRBanse DEMember

    First of all I'd like to thank you, Michael Rumpler. Your plugin saved me a lot of time.

    Now my problem: My app uses a Master-Detail-Page with 4 detail pages. One of these pages contains a TableView with a MR.Gestures.ViewCell. When this page is opened the first time, everything works fine, but switching to another page and back again crashes the app. I receive a NullReferenceException caused by the renderer in iOS.

    System.NullReferenceException: Object reference not set to an instance of an object
    at MR.Gestures.iOS.iOSGestureHandler.removeGestureRecognizers () [0x0001d] in <1b0efa77a4694803aaf75c99d82a8b9c>:0
    at MR.Gestures.iOS.iOSGestureHandler.AddGestureRecognizers (MR.Gestures.IGestureAwareControl element, UIKit.UIView view) [0x0000f] in <1b0efa77a4694803aaf75c99d82a8b9c>:0
    at MR.Gestures.iOS.Renderers.ViewCellRenderer.GetCell (Xamarin.Forms.Cell item, UIKit.UITableViewCell reusableCell, UIKit.UITableView tv) [0x0000a] in <1b0efa77a4694803aaf75c99d82a8b9c>:0
    at Xamarin.Forms.Platform.iOS.CellTableViewCell.GetNativeCell (UIKit.UITableView tableView, Xamarin.Forms.Cell cell, System.Boolean recycleCells, System.String templateId) [0x00080] in <9a5948fff8254b13a3d593c76c73b9b1>:0
    at Xamarin.Forms.Platform.iOS.TableViewModelRenderer.GetCell (UIKit.UITableView tableView, Foundation.NSIndexPath indexPath) [0x0001d] in <9a5948fff8254b13a3d593c76c73b9b1>:0
    at at (wrapper managed-to-native) UIKit.UIApplication:UIApplicationMain (int,string[],intptr,intptr)
    at UIKit.UIApplication.Main (System.String[] args, System.IntPtr principal, System.IntPtr delegate) [0x00005] in /Users/builder/data/lanes/5520/51128b8c/source/xamarin-macios/src/UIKit/UIApplication.cs:79
    at UIKit.UIApplication.Main (System.String[] args, System.String principalClassName, System.String delegateClassName) [0x00038] in /Users/builder/data/lanes/5520/51128b8c/source/xamarin-macios/src/UIKit/UIApplication.cs:63
    at MobilePos.Services.iOS.Application.Main (System.String[] args) [0x00001] in /Users/secret/project/name/iOS/Main.cs:17

    The related xaml is just that simple (sorry, I cannot post links right now, so I had to remove some xmlns):

    <?xml version="1.0" encoding="UTF-8"?>
    <ContentPage 
       xmlns="..." 
       xmlns:x="..."
       xmlns:i18n="clr-namespace:MobilePos.Localization"
       xmlns:util="clr-namespace:MobilePos.Helpers"
       xmlns:statics="clr-namespace:MobilePos.Statics"
       xmlns:mr="clr-namespace:MR.Gestures;assembly=MR.Gestures"
       x:Class="MobilePos.Pages.InfoPage"
       Title="{i18n:Translate Nav_Info}">
    
       <ContentPage.Resources>
          <ResourceDictionary>
             <util:SendTaskQueueCountNameConverter x:Key="ISendTaskQueueCountNameConverter"/>
          </ResourceDictionary>
       </ContentPage.Resources>
    
        <ContentPage.Content>
          <TableView Intent="Form">
             <TableView.Root>           
                <TableSection Title="{i18n:Translate TableSection_CloudConnection}">
                   <mr:ViewCell TappedCommand="{Binding ShowSendTaskQueueCommand}">
                      <Label Margin="15" Text="{Binding SendTaskQueueCount, Converter={StaticResource ISendTaskQueueCountNameConverter}}" VerticalOptions="CenterAndExpand" />
                   </mr:ViewCell>  
                </TableSection>            
             </TableView.Root>
          </TableView>
        </ContentPage.Content>
    </ContentPage>
    
  • JonathanDibbleJonathanDibble GBMember ✭✭

    I have been checking out your Nuget package prior to purchase and I have been using it in demo mode with the app name set at "GestureSample" and the licence key setup like this :

    MR.Gestures.iOS.Settings.LicenseKey = "ALZ9-BPVU-XQ35-CEBG-5ZRR-URJQ-ED5U-TSY8-6THP-3GVU-JW8Z-RZGE-CQW6"; // key for GestureSample

    I am having problems with the LongPressedCommand on iOS firing erratically before I have lifted my finger. It works fine on my android device, but fails on iPhone and the simulator. There are no Xamarin.Forms based gesture recognizers in the page, just ones from this package.

    This is the section of my xaml
    <Frame Grid.Row="2" Grid.Column="{Binding ButtonColumnOnUi}" Padding="2" BackgroundColor="{StaticResource WhiteSmoke}" CornerRadius="6" WidthRequest="48" HeightRequest="48" VerticalOptions="Center" HorizontalOptions="Center" HasShadow="false" > <mr:Image x:Name="ButtonRewind" Source="rewindfilled" BackgroundColor="{StaticResource WhiteSmoke}" VerticalOptions="Center" HorizontalOptions="Center" LongPressingCommand="{Binding RewindCommand}" LongPressedCommand="{Binding RewindFinishedCommand}" /> </Frame>

    Is this something that is not supported in the "demo mode" or is there something else I need to do to achieve this in iOS

  • MichaelRumplerMichaelRumpler ATMember ✭✭✭✭✭

    @JonathanDibble That should work. Please send me a repro project so I can have a look.

  • JonathanDibbleJonathanDibble GBMember ✭✭

    @MichaelRumpler That's good to hear it should work. I must be doing something strange in the background with my iOS project. I am not really able to pass on the project without permission from my client ( isn't my intellectual property). I will let you know how I progress. Thanks

  • JonathanDibbleJonathanDibble GBMember ✭✭

    @MichaelMuegel I've got to the bottom of the problem.

    The LongPressingCommand starts a 125ms timer that moves a slider backward to simulate an audio rewind process.

    In the Elapsed event on the timer the code writes a value to the property that is bound to the Value property of the Slider. This seems to cause the LongPressedCommand to be executed, but in iOS only.

    When LongPressedCommand executes the timer is stopped.

    It seems I will need to think of another way to achieve the functionality, so that I can continue to use the MR.Gestures package

  • JonathanDibbleJonathanDibble GBMember ✭✭
    edited November 29

    @MichaelRumpler I've got to the bottom of the problem.

    The LongPressingCommand starts a 125ms timer that moves a slider backward to simulate an audio rewind process.

    In the Elapsed event on the timer the code writes a value to the property that is bound to the Value property of the Slider. This seems to cause the LongPressedCommand to be executed, but in iOS only. Could you explain how writing to this bound property causes the LongPressedCommand to be executed?

    When LongPressedCommand executes the timer is stopped.

    It seems I will need to think of another way to achieve the functionality, so that I can continue to use the MR.Gestures package

14567810»
Sign In or Register to comment.