2011-01-27 9 views
5

Tengo una subclase UIView que quiero mover dentro de su superview. Cuando el usuario toca el UIView en algún lugar fuera del self.center, pero dentro de self.bounds "salta" porque agrego la nueva ubicación al self.center para lograr el movimiento real. Para evitar este comportamiento, intento establecer un punto de anclaje que permita al usuario tomar y arrastrar la vista a cualquier lugar dentro de sus límites.Configuración del punto de anclaje para la capa UIView

Mi problema es que cuando calculo el nuevo punto de anclaje (como se muestra en el siguiente código) no ocurre nada, la vista no cambia de posición en absoluto. Por otro lado, si configuro el punto de anclaje en un punto precalculado, puedo mover la vista (pero luego, por supuesto, "salta" al punto precalculado). ¿Cómo es que esto no funciona como se esperaba?

Gracias.

- (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event 
{ 
    // Only support single touches, anyObject retrieves only one touch 
    UITouch *touch = [touches anyObject]; 
    CGPoint locationInView = [touch locationInView:self]; 

    // New location is somewhere within the superview 
    CGPoint locationInSuperview = [touch locationInView:self.superview]; 

    // Set an anchorpoint that acts as starting point for the move 
    // Doesn't work! 
    self.layer.anchorPoint = CGPointMake(locationInView.x/self.bounds.size.width, locationInView.y/self.bounds.size.height); 
    // Does work! 
    self.layer.anchorPoint = CGPointMake(0.01, 0.0181818); 

    // Move to new location 
    self.center = locationInSuperview; 
} 
+1

asegúrate de tener una comprensión completa de anchorPoint: http://stackoverflow.com/a/22188420/550393 – 2cupsOfTech

Respuesta

12

Como Kris Van Bael señaló, necesitará hacer los cálculos del punto de anclaje en el método touchsBegan:withEvent: para no anular el movimiento. Además, como el cambio de la capa anchorPoint moverá la posición inicial de la vista, debe agregar un desplazamiento al punto center de la vista para evitar un 'salto' después del primer toque.

Usted puede hacer esto mediante el cálculo (y añadiendo a punto center de su punto de vista) la compensación en base a la diferencia entre los puntos de anclaje inicial y final (multiplicado por su visión ancho/alto) o se puede configurar de center la vista a la inicial punto de contacto.

Algo como esto quizá:

- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event { 

    UITouch *touch = [touches anyObject]; 
    CGPoint locationInView = [touch locationInView:self]; 
    CGPoint locationInSuperview = [touch locationInView:self.superview]; 

    self.layer.anchorPoint = CGPointMake(locationInView.x/self.frame.size.width, locationInView.y/self.frame.size.height); 
    self.center = locationInSuperview; 
} 

- (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event { 

    UITouch *touch = [touches anyObject]; 
    CGPoint locationInSuperview = [touch locationInView:self.superview]; 

    self.center = locationInSuperview; 
} 

Más información sobre anchorPoint 's de documentos de manzana y here una pregunta similar SO hice referencia here.

0

Debe actualizar el punto de anclaje solo en TouchBeinge. Si lo vuelve a calcular todo el tiempo (TouchMoved), es lógico que la subvista no se mueva.

+0

Gracias, por supuesto, ¡tienes razón! Además, obviamente no tiene sentido volver a calcular el punto de anclaje, ya que el usuario no moverá el dedo dentro de los límites cuando comience el movimiento real. Cambiar la actualización de anchorPoint a touhesBegan sin embargo surgió un problema de compensación como Sam destaca en su respuesta. – Oskar

Cuestiones relacionadas