How to add a vertical swipe gesture to iPhone app for all screens? - iphone-sdk-3.0

I'd like to add a gesture to my app so when the user swipes vertically it triggers a method to do something. The swipe can be up or down. I've never done anything with gestures so this is my first use of a gesture other than what is included in a UITableView for deleting rows.
The other problem is that most of my screens are UITableViews so the user could be simply scrolling the UITableView. So I am wondering if I could use a two finger swipe (vertical) to detect the gesture to run the code vs. a single finger swipe to scroll the UITableView?
Thank you in advance.
Neal

This goes in ApplicationDidLaunch:
UISwipeGestureRecognizer *swipeGesture = [[[UISwipeGestureRecognizer alloc] initWithTarget:self action:#selector(swipedScreen:)] autorelease];
swipeGesture.numberOfTouchesRequired = 2;
swipeGesture.direction = (UISwipeGestureRecognizerDirectionUp|UISwipeGestureRecognizerDirectionDown);
[window addGestureRecognizer:swipeGesture];
then implement
- (void) swipedScreen:(UISwipeGestureRecognizer*)swipeGesture {
// do stuff
}
Use the documentation for UIGestureRecognizer and UISwipeGestureRecognizer.
Also if you wish to detect the direction of the swipe you will have to setup two separate gesture recognizers. You can not get the direction of a swipe from a swipe gesture recognizer, only the directions it is registered to recognize.

In swift 4.0, that goes on the method didFinishLaunchingWithOptions of the AppDelegate:
let swipeGesture = UISwipeGestureRecognizer(target: self, action: #selector(self.swipedScreen(swipeGesture:)))
swipeGesture.numberOfTouchesRequired = 2
swipeGesture.direction = [UISwipeGestureRecognizerDirection.up, UISwipeGestureRecognizerDirection.down]
window?.addGestureRecognizer(swipeGesture)
And the action:
#objc func swipedScreen(swipeGesture: UISwipeGestureRecognizer){
Swift.print("hy")
}

Related

Transparent UIView on top detecting touches

I have an iPad project structured with a UISplitViewController:
RootViewController
DetailviewController
Both of them are detecting touches with Gesture Recognizer inside their own Class.
I would like to create a transparent UIView on top of all the Classes to detect ONLY a Diagonal Swipe (from the left bottom corner to the right top corner).
So, when the swipe will be detected I will launch a function otherwise nothing appended and the touch should be passed on the low level view.
I tried these two solutions:
Add a GestureRecognizer on this top transparent view but this will hide all touches to the lower hierarchy views.( with userInteraction enabled: YES ofcourse);
The other solution is to make the init like this
-(id)initWithFrame:(CGRect)frame
{
self = [super initWithFrame:frame];
if (self) {
// Initialization code
[self setBackgroundColor:[UIColor colorWithWhite:1 alpha:0.01]];
[self setUserInteractionEnabled:NO];
}
return self;
}
and try to detect the swipe with
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event
But at this point all the touches are not detected.
Anybody have a nice solution?
I will not create a transparent UIView like you are mentioning. I will add a UISwipeGestureRecognizer to the UISplitViewController's view this is already the view that contains all your subviews. You can have access to the view within the app delegate:
UISplitViewController *splitViewController = (UISplitViewController *)self.window.rootViewController;
// attach the swipe gesture to the view that embeds the rootView and the detailView
UISwipeGestureRecognizer* swipeGesture = [[UISwipeGestureRecognizer alloc] initWithTarget:splitViewController.view action:#selector(swipeUpdated:)];
Can't you just add a gesture recognizer to the UISplitViewController's view?
You should look into Container Controllers. You can make your own SplitViewController and make a third view on top of the controller that detects the swipe. Custom container controllers are pretty straight forward and gives you a lot of flexibility.

UIGestureRecognizer blocking tableview scrolling

I have a table with static cells. One of these cells has a view in it with a pan gesture recogniser on it.
When I am scrolling down my tableview, when I get to the cell with the view with pan gesture recogniser, scrolling doesn't seem to work. If I touch outside the view (to the side or top or bottom) it works and I can scroll. I have an if statement in my gesturerecognizer that tests whether a certain area has been touched, and if so performs an action.
I have looked at this issue (http://stackoverflow.com/questions/3295239/uigesturerecognizer-blocking-table-view-scrolling) but setting cancelsTouchesInView to NO didn't work, I don't have anywhere setting the state property and using the method - (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldRecognizeSimultaneouslyWithGestureRecognizer:(UIGestureRecognizer *)otherGestureRecognizer
I don't know where to get the 'otherGestureRecognizer' from or what object to call that method on.
I'm assuming I wan't to put my gesture recogniser as the first argument, and the tableview's scroll gesture recogniser as the otherGestureRecogniser, is that correct? If so, how do I get that?
UIPanGestureRecognizer *windPanGesture = [[UIPanGestureRecognizer alloc] initWithTarget:self action:#selector(moveWindHandle:)];
[self.windRangeView addGestureRecognizer:windPanGesture];
Then in my moveWindHandle:
-(void)moveWindHandle:(UIPanGestureRecognizer *)gesture
{
gesture.cancelsTouchesInView = NO;
isMovingHandle = [self isPoint:startedTouchAt insideHandle:_toHandleWindImageView];
if(isMovingHandle) {
if(gesture.state == UIGestureRecognizerStateBegan) {
//do stuff
}
}
else
{
//i want it to ignore this gesture and just scroll like normal if that is what hte user did
}
}
I have set the tableviewcontroller as a UIGestureRecognizerDelegate, but I don't know what to do with that.
You would not be the one calling -gestureRecognizer:shouldRecognizeSimultaneouslyWithGestureRecognizer:. That method is called by the system. You need to set your table view controller as the delegate for your window pan gesture.
windPanGesture.delegate = self;
At that point, when you do the pan, the system will call the delegate method -gestureRecognizer:shouldRecognizeSimultaneouslyWithGestureRecognizer: with your gesture recognizer as one argument and the scroll view's gesture recognizer as the other.
Update
You may also want to implement the -gestureRecognizerShouldBegin: method and return NO if you are not in one of the certain areas.

Adding UITapGestureRecognizer to UINavigationBar overrides ability to use ScrollToTop

So Ive added a TapGestureRecognizer to the navigation bar in order to "pull down" another view, thus its a UIPanGesture Recognizer. The problem is when this gesture is added the UITableView scrollToTop method no longer works, even if enabled before or after the addition of the gesture recognizer.
Has anyone ever experienced or can think of an easy solution?
Thanks!
Heres My Code:
if (!pan) {
_pan = [[UIPanGestureRecognizer alloc] initWithTarget:self action:#selector(panaction:)];
[_pan setMaximumNumberOfTouches:1];
}
_pan.delegate = self;
[self.navigationController.navigationBar addGestureRecognizer:_pan];
EDIT:
Ok, the problem seems to be adding a UIView as a subview in order to drag down from the UINavigation bar, when I dont add the subview the scrollToTop works fine, once its added it must be intercepting the touch event underneath the status bar..

iOS - Gesture and uislider

I'm developing an app for iOS with a menu like Facebook with ECSlidingViewController, a nice project to manage the horizontal gesture on the app.
The problems borns when I put into the view an UISlider... I can't touch it nice because the sliding motion of the sliders is being mistaken as a swipe left/right.
This is the header file of che class with all the methods and this is the code to put in the main view:
if (![self.slidingViewController.underLeftViewController isKindOfClass:[MenuViewController class]]) {
self.slidingViewController.underLeftViewController = [self.storyboard instantiateViewControllerWithIdentifier:#"Menu"];
}
if (![self.slidingViewController.underRightViewController isKindOfClass:[UnderRightViewController class]]) {
self.slidingViewController.underRightViewController = [self.storyboard instantiateViewControllerWithIdentifier:#"UnderRight"];
}
[self.view addGestureRecognizer:self.slidingViewController.panGesture];
This last line is the code that integrate the gesture on the app.
Is there a method to disable the gesture only on the uislider?
Thanks at all.
You can add a delegate to self.slidingViewController.panGesture and have it ignore touches that are on a UISlider view. The following question and answer have all the information you need: Pan gesture interferes with UISlider.

How to detect a tap gesture in subviews

Quick question: how do i detect if a tap gesture recognizer is within a subview of the view it is added to? Eg. if i click on an object such as a square that has been added as a subview to a background which a tap gesture recognizer has been added to, how do I detect that it has been tapped?
You can grab the point of the tap off the gesture recognizer when your handler method is called respective to any view you wish using -locationInView:. Then, use the following method on UIView: - (UIView *)hitTest:(CGPoint)point withEvent:(UIEvent *)event to get a reference to the actual sub view that was tapped remembering that the point you pass in is in the same coordinate space as the view.
Some code to get you started:
CGPoint point = [tapGestureRecognizer locationInView:parentView];
UIView *tappedView = [parentView hitTest:point withEvent:nil];
For hit testing to work the view needs to have the userInteractionEnabled property set to YES. Many views, such as UILabels have this set to NO by default. So prior to the above:
self.subviewOfInterest.userInteractionEnabled = YES;
maybe you should set as:
subviews.userInteractionEnabled = YES;
good luck!
you can use the requireGestureRecognizerToFail: to recognize the tap on subview please refer this code