¿Cómo usar UIPanGestureRecognizer para mover objetos? iPhone/iPad
objective-c drag (6)
Encontré el tutorial Trabajando con UIGestureRecognizers , y creo que eso es lo que estoy buscando. Me ayudó a llegar a la siguiente solución:
-(IBAction) someMethod {
UIPanGestureRecognizer *panRecognizer = [[UIPanGestureRecognizer alloc] initWithTarget:self action:@selector(move:)];
[panRecognizer setMinimumNumberOfTouches:1];
[panRecognizer setMaximumNumberOfTouches:1];
[ViewMain addGestureRecognizer:panRecognizer];
[panRecognizer release];
}
-(void)move:(UIPanGestureRecognizer*)sender {
[self.view bringSubviewToFront:sender.view];
CGPoint translatedPoint = [sender translationInView:sender.view.superview];
if (sender.state == UIGestureRecognizerStateBegan) {
firstX = sender.view.center.x;
firstY = sender.view.center.y;
}
translatedPoint = CGPointMake(sender.view.center.x+translatedPoint.x, sender.view.center.y+translatedPoint.y);
[sender.view setCenter:translatedPoint];
[sender setTranslation:CGPointZero inView:sender.view];
if (sender.state == UIGestureRecognizerStateEnded) {
CGFloat velocityX = (0.2*[sender velocityInView:self.view].x);
CGFloat velocityY = (0.2*[sender velocityInView:self.view].y);
CGFloat finalX = translatedPoint.x + velocityX;
CGFloat finalY = translatedPoint.y + velocityY;// translatedPoint.y + (.35*[(UIPanGestureRecognizer*)sender velocityInView:self.view].y);
if (finalX < 0) {
finalX = 0;
} else if (finalX > self.view.frame.size.width) {
finalX = self.view.frame.size.width;
}
if (finalY < 50) { // to avoid status bar
finalY = 50;
} else if (finalY > self.view.frame.size.height) {
finalY = self.view.frame.size.height;
}
CGFloat animationDuration = (ABS(velocityX)*.0002)+.2;
NSLog(@"the duration is: %f", animationDuration);
[UIView beginAnimations:nil context:NULL];
[UIView setAnimationDuration:animationDuration];
[UIView setAnimationCurve:UIViewAnimationCurveEaseOut];
[UIView setAnimationDelegate:self];
[UIView setAnimationDidStopSelector:@selector(animationDidFinish)];
[[sender view] setCenter:CGPointMake(finalX, finalY)];
[UIView commitAnimations];
}
}
Hay varios ejemplos de la clase UIPanGestureRecognizer
. Por ejemplo, he leído this y todavía no puedo usarlo ...
En el archivo nib en el que estoy trabajando tengo un UIView
(rectángulo blanco en la imagen) que deseo arrastrar con esa clase:
y en mi archivo .m he colocado:
- (void)setTranslation:(CGPoint)translation inView:(UIView *)view
{
NSLog(@"Test to see if this method gets executed");
}
y ese método no se ejecuta cuando arrastro el mouse por UIView
. También he intentado colocar:
- (void)pan:(UIPanGestureRecognizer *)gesture
{
NSLog(@"testing");
}
Y ese método tampoco se ejecuta. Tal vez estoy equivocado, pero creo que estos métodos deberían funcionar como - (void) touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event
método de - (void) touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event
donde solo tengo que colocar ese método y se llamará cada vez que haya toques.
¿Qué estoy haciendo mal? ¿Tal vez tengo que establecer una conexión con ese método? Si es así, ¿cómo puedo hacer eso?
La versión de Swift 2:
// start detecting pan gesture
let panGestureRecognizer = UIPanGestureRecognizer(target: self, action: #selector(TTAltimeterDetailViewController.panGestureDetected(_:)))
panGestureRecognizer.minimumNumberOfTouches = 1
self.chartOverlayView.addGestureRecognizer(panGestureRecognizer)
func panGestureDetected(panGestureRecognizer: UIPanGestureRecognizer) {
print("pan gesture recognized")
}
versión rápida 2 de la respuesta de @MS AppTech
func handlePan(panGest : UIPanGestureRecognizer) {
let velocity : CGPoint = panGest.velocityInView(self.view);
let magnitude : CGFloat = CGFloat(sqrtf((Float(velocity.x) * Float(velocity.x)) + (Float(velocity.y) * Float(velocity.y))));
let slideMult :CGFloat = magnitude / 200;
//NSLog(@"magnitude: %f, slideMult: %f", magnitude, slideMult);
let slideFactor : CGFloat = 0.1 * slideMult; // Increase for more of a slide
var finalPoint : CGPoint = CGPointMake(panGest.view!.center.x + (velocity.x * slideFactor),
panGest.view!.center.y + (velocity.y * slideFactor));
finalPoint.x = min(max(finalPoint.x, 0), self.view.bounds.size.width);
finalPoint.y = min(max(finalPoint.y, 0), self.view.bounds.size.height);
UIView.animateWithDuration(Double(slideFactor*2), delay: 0, options: UIViewAnimationOptions.CurveEaseOut, animations: {
panGest.view!.center = finalPoint;
}, completion: nil)
}
-(IBAction)Method
{
UIPanGestureRecognizer *panRecognizer = [[UIPanGestureRecognizer alloc] initWithTarget:self action:@selector(handlePan:)];
[panRecognizer setMinimumNumberOfTouches:1];
[panRecognizer setMaximumNumberOfTouches:1];
[ViewMain addGestureRecognizer:panRecognizer];
[panRecognizer release];
}
- (Void)handlePan:(UIPanGestureRecognizer *)recognizer
{
CGPoint translation = [recognizer translationInView:self.view];
recognizer.view.center = CGPointMake(recognizer.view.center.x + translation.x,
recognizer.view.center.y + translation.y);
[recognizer setTranslation:CGPointMake(0, 0) inView:self.view];
if (recognizer.state == UIGestureRecognizerStateEnded) {
CGPoint velocity = [recognizer velocityInView:self.view];
CGFloat magnitude = sqrtf((velocity.x * velocity.x) + (velocity.y * velocity.y));
CGFloat slideMult = magnitude / 200;
NSLog(@"magnitude: %f, slideMult: %f", magnitude, slideMult);
float slideFactor = 0.1 * slideMult; // Increase for more of a slide
CGPoint finalPoint = CGPointMake(recognizer.view.center.x + (velocity.x * slideFactor),
recognizer.view.center.y + (velocity.y * slideFactor));
finalPoint.x = MIN(MAX(finalPoint.x, 0), self.view.bounds.size.width);
finalPoint.y = MIN(MAX(finalPoint.y, 0), self.view.bounds.size.height);
[UIView animateWithDuration:slideFactor*2 delay:0 options:UIViewAnimationOptionCurveEaseOut animations:^{
recognizer.view.center = finalPoint;
} completion:nil];
}
}
UIPanGestureRecognizer * pan1 = [[UIPanGestureRecognizer alloc]initWithTarget:self action:@selector(moveObject:)];
pan1.minimumNumberOfTouches = 1;
[image1 addGestureRecognizer:pan1];
-(void)moveObject:(UIPanGestureRecognizer *)pan;
{
image1.center = [pan locationInView:image1.superview];
}
if ([recognizer state] == UIGestureRecognizerStateChanged)
{
CGPoint translation1 = [recognizer translationInView:main_view];
img12.center=CGPointMake(img12.center.x+translation1.x, img12.center.y+ translation1.y);
[recognizer setTranslation:CGPointMake(0, 0) inView:main_view];
recognizer.view.center=CGPointMake(recognizer.view.center.x+translation1.x, recognizer.view.center.y+ translation1.y);
}
-(void)move:(UIPanGestureRecognizer*)recognizer
{
if ([recognizer state] == UIGestureRecognizerStateChanged)
{
CGPoint translation = [recognizer translationInView:self.view];
recognizer.view.center=CGPointMake(recognizer.view.center.x+translation.x, recognizer.view.center.y+ translation.y);
[recognizer setTranslation:CGPointMake(0, 0) inView:self.view];
}
}