Search code examples
iosobjective-cecslidingviewcontroller

ECSlidingViewController passing UILongPressGestureRecognizer


I have looked around for solutions but none of them answer my question. Therefore, I took a step back from my project to try to work out this feature. I am using AppDelegate to help me see code clearer.

I want the menu to slide out when users touch and hold the screen. It should slide back when users release their touch.

However, I am unable to send gesture parameters.

AppDelegate.m

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
    self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
    UIStoryboard *mainStoryboard = [UIStoryboard storyboardWithName:@"Main"
                                                         bundle: nil];
    ScrollViewController *topViewController = [mainStoryboard instantiateViewControllerWithIdentifier:@"Scroll"];
    MenuViewController *underLeftViewController = (MenuViewController *)[mainStoryboard instantiateViewControllerWithIdentifier:@"Menu"];

    ECSlidingViewController *slidingViewController = [[ECSlidingViewController alloc] initWithTopViewController:topViewController];
    slidingViewController.underLeftViewController = underLeftViewController;

    [slidingViewController.view addGestureRecognizer:slidingViewController.panGesture];
    self.window.rootViewController = slidingViewController;

    // HOW DO I PASS GESTURE DATA?

    UILongPressGestureRecognizer *revealMenuRecognizer = [[UILongPressGestureRecognizer alloc] initWithTarget:slidingViewController.underLeftViewController action:@selector(revealMenu:  GESTURE PARAMETERS?  )];

    [topViewController.view addGestureRecognizer:revealMenuRecognizer];
    return YES;
}

MenuViewController.m

- (void)revealMenu:(UILongPressGestureRecognizer *)longPressRecognizer {
    if (longPressRecognizer.state == UIGestureRecognizerStateBegan) {
        [self.slidingViewController anchorTopViewToRightAnimated:YES];
    } else {
        if (longPressRecognizer.state == UIGestureRecognizerStateCancelled
            || longPressRecognizer.state == UIGestureRecognizerStateFailed
            || longPressRecognizer.state == UIGestureRecognizerStateEnded)
        {
            [self.slidingViewController resetTopViewAnimated:YES];
        }
    }
}

Solution

  • should be action:@selector(revealMenu:)]; Placing a colon is enough to let the gesture recognizer to pass the UIGestureRecognizer object to the action. Reading from the UIGestureRecognizer reference guide

    The action methods invoked must conform to one of the following signatures:

    • (void)handleGesture;
    • (void)handleGesture:(UIGestureRecognizer *)gestureRecognizer;

    Methods conforming to the latter signature permit the target in some cases to query the gesture recognizer sending the message for additional information. For example, the target could ask a UIRotationGestureRecognizer object for the angle of rotation (in radians) since the last invocation of the action method for this gesture.

    Leave the colon off if you don't care about the object include it if you need data from it. You want the latter.