How to center superview along with view when using UIPanGestureRecognizer? - ios

I Created a sample application, when we click on a button another view(ResizingViewController) view shows up.
when i drag ResizingViewController it is moving correctly but i can see another view behind it.I think it is super view (as show in in this image, but not able to make both move at same time).
please help me to fix it?(if i drag view then both should move to same position)
my code is as below
- (IBAction)click_Action:(id)sender {
if (!resizingViewController) {
return;
}
//Creating Right Button, asigning a method to it.
UIBarButtonItem *rightButton = [[UIBarButtonItem alloc] initWithTitle:#"Close"
style:UIBarButtonItemStylePlain target:self action:#selector(done)];
[resizingViewController.navigationItem setRightBarButtonItem:rightButton];
theNavigationController = [[UINavigationController alloc]
initWithRootViewController:resizingViewController];
[theNavigationController.navigationBar setTintColor:[UIColor blueColor]];
if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad) {
theNavigationController.modalPresentationStyle
=UIModalPresentationFormSheet;
}
[self presentViewController:theNavigationController animated:YES completion:nil];
CGRect r = CGRectMake(100, 100, 300, 400);
r = [self.view convertRect:r toView:self.view];
theNavigationController.view.superview.frame = r;
//Adding gesture reconizer to resizingviewcontroller
UIPanGestureRecognizer *panGestureRecognizer = [[UIPanGestureRecognizer alloc]
initWithTarget:self action:#selector(handlePanFrom:)];
[theNavigationController.view addGestureRecognizer:panGestureRecognizer];
}
-(void)handlePanFrom:(UIPanGestureRecognizer *) recognizer
{
CGPoint translation = [recognizer translationInView:recognizer.view];
//Changing Center of the the view as soon as user selects the view and drags
recognizer.view.center = CGPointMake(recognizer.view.center.x + translation.x,
recognizer.view.center.y + translation.y);
CGPoint r = CGPointMake(recognizer.view.center.x+100,
recognizer.view.center.y+100);
r = [self.view convertPoint:r toView:self.view];
recognizer.view.superview.center = r;
//Should not forget to give below code, else view goes out of bounds.
[recognizer setTranslation:CGPointZero inView:self.view];
}

OK i fixed this.(marking this as answer so that if any one have same problem can use this)
-(void)handlePanFrom:(UIPanGestureRecognizer *) recognizer
{
CGPoint translation = [recognizer translationInView:recognizer.view.superview];
recognizer.view.superview.center =
CGPointMake(recognizer.view.superview.center.x+translation.x,
recognizer.view.superview.center.y+translation.y);
[recognizer setTranslation:CGPointZero inView:self.view];
}

Related

Setting frame to view during UIPanGesture recognition

I'm trying to update frames for two labels during UIPanGesture recognition of a UIView (centre grey color).
Functionality
I need to choose a language between English and Arabic. There is a slider button in middle (grey view) and I have applied UIPanGesture to that. So while swiping towards Arabic the language English should move to centre and assumes that its selected and vice versa.
I tried my level best but I can only make upto this. Frames are not setting properly and I don't know is there any other easy way to do this.
Code
- (void)viewDidLoad {
[super viewDidLoad];
UIPanGestureRecognizer *gesture = [[UIPanGestureRecognizer alloc] initWithTarget:self action:#selector(handleGesture:)];
[dragview addGestureRecognizer:gesture];
}
- (void)handleGesture:(UIPanGestureRecognizer *)gestureRecognizer
{
CGPoint velocity = [gestureRecognizer velocityInView: gestureRecognizer.view];
CGPoint location = [gestureRecognizer locationInView: gestureRecognizer.view];
if(velocity.x > 0)
{
NSLog(#"gesture went right");
if (dragview.frame.origin.x + dragview.frame.size.width >= dragV.frame.size.width) {
[dragview setFrame:CGRectMake(dragV.frame.size.width - dragview.frame.size.width, dragview.frame.origin.y, dragview.frame.size.width, dragview.frame.size.height)];
english.center = CGPointMake(dragV.frame.size.width / 2,
dragV.frame.size.height / 2);
} else {
float dX = location.x-panCoord.x;
gestureRecognizer.view.frame = CGRectMake(gestureRecognizer.view.frame.origin.x+dX, 0, gestureRecognizer.view.frame.size.width, gestureRecognizer.view.frame.size.height);
[english setFrame:CGRectMake(english.frame.origin.x + 1.0f, english.frame.origin.y, english.frame.size.width, english.frame.size.height)];
[arabic setFrame:CGRectMake(arabic.frame.origin.x + 1.0f, arabic.frame.origin.y, arabic.frame.size.width, arabic.frame.size.height)];
}
}
else
{
NSLog(#"gesture went left");
if (dragview.frame.origin.x <= 0) {
[dragview setFrame:CGRectMake(0, dragview.frame.origin.y, dragview.frame.size.width, dragview.frame.size.height)];
arabic.center = CGPointMake(dragV.frame.size.width / 2,
dragV.frame.size.height / 2);
} else {
float dX = location.x+panCoord.x;
gestureRecognizer.view.frame = CGRectMake(gestureRecognizer.view.frame.origin.x+dX, 0, gestureRecognizer.view.frame.size.width, gestureRecognizer.view.frame.size.height);
[english setFrame:CGRectMake(english.frame.origin.x - 1.0f, english.frame.origin.y, english.frame.size.width, english.frame.size.height)];
[arabic setFrame:CGRectMake(arabic.frame.origin.x - 1.0f, arabic.frame.origin.y, arabic.frame.size.width, arabic.frame.size.height)];
}
}
}
Screenshots
Initially it looks like this,
While dragging towards arabic,
While dragging towards english,
Answers are appreciated!!
I got output.I tried your code and I used SwipeGestureRecognizer code.It works fine now.
I tried with 2 optins
OPTION 1:SwipeGestureRecognizer
- (void)viewDidLoad
{
[super viewDidLoad];
// Swipe Left
UISwipeGestureRecognizer *swipeLeft = [[UISwipeGestureRecognizer alloc] initWithTarget:self action:#selector(handleSwipeLeft:)];
swipeLeft.direction = UISwipeGestureRecognizerDirectionLeft;
[arabicView addGestureRecognizer:swipeLeft];
// Swipe Right
UISwipeGestureRecognizer *swipeRight = [[UISwipeGestureRecognizer alloc] initWithTarget:self action:#selector(handleSwipeRight:)];
swipeRight.direction = UISwipeGestureRecognizerDirectionRight;
[englishView addGestureRecognizer:swipeRight];
}
- (void)handleSwipeLeft:(UISwipeGestureRecognizer *)recognizer
{
[self performSelector:#selector(moveAtRight) withObject:nil afterDelay:0.01f];
}
- (void)handleSwipeRight:(UISwipeGestureRecognizer *)recognizer
{
[self performSelector:#selector(moveAtLeft) withObject:nil afterDelay:0.01f];
}
-(void)moveAtRight
{
englishView.frame = CGRectMake(0, 0, 53, 53);
englishView.backgroundColor = [UIColor lightGrayColor];
arabicView.frame = CGRectMake(53, 0, 205, 53);
english.text = #"English";
arabic.text = #"Arabic";
arabicView.backgroundColor = [UIColor blueColor];
[dragview removeFromSuperview];
}
-(void)moveAtLeft
{
englishView.frame = CGRectMake(0, 0, 205, 53);
arabicView.frame = CGRectMake(205, 0, 53, 53);
arabicView.backgroundColor = [UIColor lightGrayColor];
englishView.backgroundColor = [UIColor blueColor];
english.text = #"English";
arabic.text = #"Arabic";
[dragview removeFromSuperview];
}
In above code I set background color to blue.If you want to any other color change.
At Initial
When I swipe towards Arabic
When I swipe towards English
Above these are output.
OPTION 2:PanGestureRecognizer
Now I tried with your PanGestureRecognizer Code.I set frame and background color for englishView and arabicView separately.Now it works fine.
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.
_drawPath = [UIBezierPath
bezierPathWithRoundedRect:CGRectMake(0, 0, 140, 35)
byRoundingCorners:(UIRectCornerBottomLeft | UIRectCornerBottomRight | UIRectCornerTopLeft | UIRectCornerTopRight)
cornerRadii:CGSizeMake(4, 4)
];
_rectLayer = [[CAShapeLayer alloc] init];
_rectLayer.path = _drawPath.CGPath;
_rectLayer.strokeColor = [UIColor blackColor].CGColor;
_rectLayer.lineWidth = 2.0f;
_rectLayer.fillColor = [UIColor clearColor].CGColor;
_rectLayer.strokeEnd = 0.f;
[vi.layer addSublayer:_rectLayer];
[self drawRectangle:nil];
UIPanGestureRecognizer *gesture = [[UIPanGestureRecognizer alloc] initWithTarget:self action:#selector(handleGesture:)];
[gesture setMinimumNumberOfTouches:1];
[gesture setMaximumNumberOfTouches:1];
[englishView addGestureRecognizer:gesture];
UIPanGestureRecognizer *gesture1 = [[UIPanGestureRecognizer alloc] initWithTarget:self action:#selector(handleGesture:)];
[gesture1 setMinimumNumberOfTouches:1];
[gesture1 setMaximumNumberOfTouches:1];
[arabicView addGestureRecognizer:gesture1];
}
- (void)handleGesture:(UIPanGestureRecognizer *)gestureRecognizer
{
if (gestureRecognizer.state == UIGestureRecognizerStateChanged)
{
NSLog(#"Changed");
CGPoint velocity = [gestureRecognizer velocityInView:gestureRecognizer.view];
CGPoint translation = [gestureRecognizer translationInView:gestureRecognizer.view];
if(velocity.x > 0)
{
NSLog(#"gesture went right");
gestureRecognizer.view.frame = CGRectMake(gestureRecognizer.view.frame.origin.x + translation.x, 0, gestureRecognizer.view.frame.size.width, gestureRecognizer.view.frame.size.height);
NSLog(#"The gestureRecognizer frame is - %#",NSStringFromCGRect(gestureRecognizer.view.frame));
[englishView setFrame:CGRectMake(0, englishView.frame.origin.y, 205, englishView.frame.size.height)];
[englishView setBackgroundColor:[UIColor colorWithRed:(15/255.0f) green:(97/255.0f) blue:(163/255.0f) alpha:1.0f]];
[arabicView setFrame:CGRectMake(205, arabicView.frame.origin.y, 53, arabicView.frame.size.height)];
[arabicView setBackgroundColor:[UIColor lightGrayColor]];
[gestureRecognizer setTranslation:CGPointMake(0, 0) inView:dragV];
[dragview removeFromSuperview];
}
else
{
NSLog(#"gesture went left");
gestureRecognizer.view.frame = CGRectMake(gestureRecognizer.view.frame.origin.x + translation.x, 0, gestureRecognizer.view.frame.size.width, gestureRecognizer.view.frame.size.height);
[arabicView setFrame:CGRectMake(53, arabicView.frame.origin.y, 205, arabicView.frame.size.height)];
[englishView setFrame:CGRectMake(0, englishView.frame.origin.y,53,englishView.frame.size.height)];
[arabicView setBackgroundColor:[UIColor colorWithRed:(15/255.0f) green:(97/255.0f) blue:(163/255.0f) alpha:1.0f]];
[englishView setBackgroundColor:[UIColor lightGrayColor]];
[gestureRecognizer setTranslation:CGPointMake(0, 0) inView:dragV];
[dragview removeFromSuperview];
}
}
}
At First once I run the app
Middle Finger towards Arabic View
Middle Finger towards English View

UIPanGestureRecognizer always move from location (0, 0)

I'd like to drag customView.
But, when I drag the customView, it always move from location (0, 0).
Please look at following image.
the red parts is the customView, and when I drag it, it move to the location.
How do I fix it to make move customView correctly?
I have this code.
labelview is the customView(subclass of UIView).
- (void)viewDidLoad
{
[super viewDidLoad];
_labelView = [[LabelView alloc]initWithFrame:CGRectMake(20, 60, 200, 100)];
UIPanGestureRecognizer* pan = [[UIPanGestureRecognizer alloc]initWithTarget:self action:#selector(panAction:)];
[_labelView addGestureRecognizer:pan];
[self.view addSubview:_labelView];
}
- (void)panAction:(UIPanGestureRecognizer *)sender
{
CGPoint p = [sender translationInView:self.view];
CGPoint movedPoint = CGPointMake(_labelView.center.x + p.x, _labelView.center.y + p.y);
sender.view.center = movedPoint;
[sender setTranslation:movedPoint inView:self.view];
}
While the other two answers are technically correct, they are not ideal solutions because when you add a gesture recognizer to self.view then anytime you drag anywhere in self.view you will drag your LabelView, but I imagine you only want to drag it when you actually have your finger on the LabelView itself.
So, just keep what you have, but change this one line:
[sender setTranslation:movedPoint inView:self.view];
to
[sender setTranslation:CGPointZero inView:self.view];
You have implemented the logic upside down. It has to be exactly other way around. Set the ´UIPanGestureRecognizer´ to UIViewController's view and set the center of your custom view.
- (void)viewDidLoad
{
[super viewDidLoad];
_labelView = [[LabelView alloc]initWithFrame:CGRectMake(20, 60, 200, 100)];
UIPanGestureRecognizer* pan = [[UIPanGestureRecognizer alloc]initWithTarget:self action:#selector(panAction:)];
// [_labelView addGestureRecognizer:pan]; must be removed
[self.view addGestureRecognizer:pan]; // must be added
[self.view addSubview:_labelView];
}
- (void)panAction:(UIPanGestureRecognizer *)sender
{
CGPoint p = [sender translationInView:self.view];
CGPoint movedPoint = CGPointMake(_labelView.center.x + p.x, _labelView.center.y + p.y);
[_labelView setCenter:movedPoint];
}
I solved by writing following code.
Thank you for answers.
- (void)viewDidLoad
{
[super viewDidLoad];
_labelView = [[LabelView alloc]initWithFrame:CGRectMake(20, 60, 200, 100)];
UIPanGestureRecognizer* pan = [[UIPanGestureRecognizer alloc]initWithTarget:self action:#selector(panAction:)];
[_labelView addGestureRecognizer:pan];
[self.view addSubview:_labelView];
}
- (void)panAction:(UIPanGestureRecognizer *)sender
{
CGPoint p = [sender translationInView:sender.view];
CGPoint movedPoint = CGPointMake(sender.view.center.x + p.x, sender.view.center.y + p.y);
sender.view.center = movedPoint;
[sender setTranslation:CGPointZero inView:sender.view];
}

Changing the text of a uilabel then add new uilabel

I want to change the text of a label, then have the user move it to where they want it on the screen (which is currently working) (the user hits - "Add text").
Once they place it where they would like. I want the "Add text" button to create a new label that the user can move. I'm not sure how to create these on the fly an to make sure that the gesture recognizers function with the new label. Thanks for suggestions.
This is what I have now,,, doesn't work quite yet.
-(IBAction)addText:(id)sender
{
textView.hidden=YES;
labelShirt.text= textField.text;
[textField resignFirstResponder];
[self addTextButtonPressed];
}
-(void)addTextButtonPressed
{
// CGRect *textFrame =
// myInitialFrame is a CGRect you choose to place your label
UILabel *myNewLabel = [[UILabel alloc] initWithFrame:CGRectMake(50,50,100,100)];
UIPanGestureRecognizer *panGestureRecognizer = [[UIPanGestureRecognizer alloc] initWithTarget:self
action:#selector(labelMoved:)];
myNewLabel.text =textField.text;
[self.view addSubview:myNewLabel];
}
-(void)labelMoved:(UIPanGestureRecognizer *)sender
{
CGPoint translation = [sender translationInView:self.view];
sender.view.frame = CGRectOffset(sender.view.frame, translation.x, translation.y);
}
// The action that is added to your add text button
-(void)addTextButtonPressed
{
// myInitialFrame is a CGRect you choose to place your label
UILabel *myNewLabel = [[UILabel alloc] initWithFrame:myInitialFrame];
UIPanGestureRecognizer *panGestureRecognizer = [[UIPanGestureRecognizer alloc] initWithTarget:self
action:#selector(labelMoved:)];
myNewLabel.text = #"My initial text";
// EDIT
[self.view addSubview:myNewLabel];
[myNewLabel addGestureRecognizer:panGestureRecognizer];
}
-(void)labelMoved:(UIPanGestureRecognizer *)sender
{
CGPoint translation = [sender translationInView:self.view];
sender.view.frame = CGRectOffset(sender.view.frame, translation.x, translation.y);
}
I don't know if that's enough to solve your problem, just comment if you still need more explanation.

UIGestureRecognizer not recognizing

I was trying to create a label that should be draggable. But the dragged event is not firing (checked with break point). Below is the code.
- (IBAction)InsertText:(UIBarButtonItem *)sender {
UILabel *lblWatermark = [[UILabel alloc] initWithFrame:currentImage.frame];
lblWatermark.text = #"Copyright";
lblWatermark.userInteractionEnabled = YES;
[lblWatermark sizeToFit];
UIPanGestureRecognizer *gesture = [[UIPanGestureRecognizer alloc]
initWithTarget:self
action:#selector(labelDragged:)];
[lblWatermark addGestureRecognizer:gesture];
[currentImage addSubview:lblWatermark];
}
- (void)labelDragged:(UIPanGestureRecognizer *)gesture
{
UILabel *label = (UILabel *)gesture.view;
CGPoint translation = [gesture translationInView:label];
// move label
label.center = CGPointMake(label.center.x + translation.x,
label.center.y + translation.y);
[gesture setTranslation:CGPointZero inView:label];
}
Thank you in advance,
Spotted the error. Actually I had also to make
userInteractionEnabled = YES
Not only for the label But also for the Imageview in which I am adding the label.
Make sure your ViewController is the delegate for UIGestureRecognizer with (.h file):
#interface View : UIView <UIGestureRecognizerDelegate>
And then set:
gesture.delegate = self;

Drag and drop an image from UIPopoverController to UIViewController

I'm showing a UIPopoverController in a ViewController, and I want to drag one image from the popover to the ViewController.
I know that to do it, I need to use a UIGestureRecognizer, but I don't know how. I can move the image around the popover, but I can't drag and drop it to the ViewController.
My code:
-(void)viewDidLoad
{
UIPanGestureRecognizer *panGesture = [[UIPanGestureRecognizer alloc] initWithTarget:self action:#selector(moveImage:)];
[panGesture setMinimumNumberOfTouches:1];
[panGesture setMaximumNumberOfTouches:1];
[self.view addGestureRecognizer:panGesture];
}
- (void)moveImage:(UIPanGestureRecognizer *)recognizer
{
CGPoint newCenter = [recognizer translationInView:self.view];
if([recognizer state] == UIGestureRecognizerStateBegan) {
beginX = ball.center.x;
beginY = ball.center.y;
}
newCenter = CGPointMake(beginX + newCenter.x, beginY + newCenter.y);
[ball setCenter:newCenter];
}

Resources