I have three view controllers that are part of a UIScrollView. I want to be able to swipe between the three, although one of the view controllers has a UIPanGestureRecognizer. I use this pan gesture recognizer to allow the user to drag their finger up and down to increase and decrease the height of a rectangular UIView. Therefore, this UIPanGestureRecognizer only really needs to know about the upwards/downwards panning, and the scroll view can use the horizontal panning.
An example of this, is like the home screen; you can swipe left or right, but also swipe down to get spotlight. I want this kind of mechanism.
This is my code for the pan:
- (void)pan:(UIPanGestureRecognizer *)aPan; // When pan guesture is recognised
{
CGPoint location = [aPan locationInView:self.view]; // Location of finger on screen
CGRect secondRect = CGRectMake(210.0, 45.0, 70.0, 325.0); // Rectangles of maximimum bar area
CGRect minuteRect = CGRectMake(125.0, 45.0, 70.0, 325.0);
CGRect hourRect = CGRectMake(41.0, 45.0, 70.0, 325.0);
if (CGRectContainsPoint(secondRect, location)) { // If finger is inside the 'second' rectangle
CGPoint currentPoint = [aPan locationInView:self.view];
currentPoint.y -= 80; // Make sure animation doesn't go outside the bars' rectangle
if (currentPoint.y < 0) {
currentPoint.y = 0;
}
else if (currentPoint.y > 239) {
currentPoint.y = 239;
}
currentPoint.y = 239.0 - currentPoint.y;
CGFloat pointy = currentPoint.y - fmod(currentPoint.y, 4.0);
[UIView animateWithDuration:0.01f // Animate the bars to rise as the finger moves up and down
animations:^{
CGRect oldFrame = secondBar.frame;
secondBar.frame = CGRectMake(oldFrame.origin.x, (oldFrame.origin.y - (pointy - secondBar.frame.size.height)), oldFrame.size.width, (pointy));
}];
CGFloat result = secondBar.frame.size.height - fmod(secondBar.frame.size.height, 4.0);
secondInt = (result / 4.0); // Update labels with new time
self->secondLabel.text = [NSString stringWithFormat:@"%02d", secondInt];
}
The code is basically repeated for three separate rectangular UIViews.
If anyone can tell me how to get the homescreen-style panning/swiping into my app, that would be great!!
Alright, here is the short answer:
You have to use
UIGestureRecognizer
's method-requireGestureRecognizerToFail:
.And here is the long answer:
You have to make the pan gesture recognizer of your scroll view to succeed only if the pan gesture recognizer of
TimerViewController
fails. However that gesture (TimerViewController
's gesture) should only succeed if the initial movement is vertical. If it is horizontal it should fail. To accomplish this we have to subclassUIPanGestureRecognizer
and modify it to fit those needs. Here is what you have to do:VerticalPanGestureRecognizer
to your project.TimerViewController
as shown.ScrollViewController
as shown.VerticalPanGestureRecognizer.h
VerticalPanGestureRecognizer.m
TimerViewController.h
TimerViewController.m
ScrollViewController.m
This new approach works perfectly. I tested it. Let me know if you have more questions.
Cheers!
UPDATE
To answer the question you posted on the comments, here is what you have to do:
Again, I tested it and it's working. You just have to add the gesture recognizer for the bars