В настоящее время я вращаю UIImageView, касаясь, перетаскивая и отпуская. Я вращаю объект по функции:
-(void)rotateForTime:(CGFloat)time distance:(CGFloat)distance
{
CABasicAnimation* rotationAnimation;
rotationAnimation = [CABasicAnimation animationWithKeyPath:@"transform.rotation.z"];
rotationAnimation.toValue = [NSNumber numberWithFloat:distance];
rotationAnimation.removedOnCompletion = NO;
rotationAnimation.fillMode = kCAFillModeForwards;
rotationAnimation.duration = time;
rotationAnimation.repeatCount = 1.0;
rotationAnimation.timingFunction = [CAMediaTimingFunctionfunctionWithName:
kCAMediaTimingFunctionEaseOut];
rotationAnimation.delegate = self;
[bottle.layer addAnimation:rotationAnimation forKey:@"rotationAnimation"];
}
Поскольку после поворота границы прямоугольного изображения меняются, чтобы определить, касается ли пользователь внутреннего изображения или нет, я отслеживаю углы изображения, поворачивая их на то же расстояние, на которое я поворачиваю изображение и затем используйте методы определения вектора-> пересечения ребер, чтобы проверить, коснулся ли пользователь границ прямоугольника, сделанного углами. Я использую эту функцию для поворота углов:
-(void) rotateImageBounds:(CGFloat) angle
{
// Translate the center and the corners of the image to the origin and their respective positions.
corner1.x = corner1.x - bottle.center.x;
corner1.y = corner1.y - bottle.center.y;
corner2.x = corner2.x - bottle.center.x;
corner2.y = corner2.y - bottle.center.y;
corner3.x = corner3.x - bottle.center.x;
corner3.y = corner3.y - bottle.center.y;
corner4.x = corner4.x - bottle.center.x;
corner4.y = corner4.y - bottle.center.y;
// Rotates the point around the origin/center.
// x = x1cos(angle) - x1sin(angle)
// y = x1sin(angle) + y1cos(angle)
CGFloat tempX;
tempX = (corner1.x*cos(angle)) - (corner1.y*sin(angle));
corner1.y = (corner1.x*sin(angle)) + (corner1.y*cos(angle));
corner1.x = tempX;
tempX = (corner2.x*cos(angle)) - (corner2.y*sin(angle));
corner2.y = (corner2.x*sin(angle)) + (corner2.y*cos(angle));
corner2.x = tempX;
tempX = (corner3.x*cos(angle)) - (corner3.y*sin(angle));
corner3.y = (corner3.x*sin(angle)) + (corner3.y*cos(angle));
corner3.x = tempX;
tempX = (corner4.x*cos(angle)) - (corner4.y*sin(angle));
corner4.y = (corner4.x*sin(angle)) + (corner4.y*cos(angle));
corner4.x = tempX;
// Translates the points back to the original center of the image.
corner1.x = corner1.x + bottle.center.x;
corner1.y = corner1.y + bottle.center.y;
corner2.x = corner2.x + bottle.center.x;
corner2.y = corner2.y + bottle.center.y;
corner3.x = corner3.x + bottle.center.x;
corner3.y = corner3.y + bottle.center.y;
corner4.x = corner4.x + bottle.center.x;
corner4.y = corner4.y + bottle.center.y;
}
Это прекрасно работает после первого поворота, углы выглядят так, как будто все еще находятся в углах изображения. Однако после дополнительных поворотов изображение и углы больше не совпадают. Насколько я знаю, метод вращения точен, и математика для углов правильна. Я пытался разобраться с этой проблемой уже несколько дней. Любая помощь будет принята с благодарностью.
РЕДАКТИРОВАТЬ * Проблема решена:
В итоге я позволил анимации удалить себя, когда она была сделана, и просто повернул изображение в правильное положение, когда я закончил (это было проще, потому что мне также нужно поворачивать изображение во время движения мыши).
Для функции поворота: (угол - это угол, под которым в данный момент находилась мышь (или касание), полученный с помощью atan2 (dy, dx), где dy - высота между касанием и центром, а dx - ширина. нужно вращать.
-(void)rotateForTime:(CGFloat)time distance:(CGFloat)distance
{
animating = TRUE;
CABasicAnimation* rotationAnimation;
rotationAnimation = [CABasicAnimation animationWithKeyPath:@"transform.rotation.z"];
rotationAnimation.fromValue = [NSNumber numberWithFloat:angle];
rotationAnimation.toValue = [NSNumber numberWithFloat:distance + angle];
rotationAnimation.removedOnCompletion = YES;
rotationAnimation.fillMode = kCAFillModeForwards;
rotationAnimation.duration = time;
rotationAnimation.repeatCount = 1.0;
rotationAnimation.timingFunction = [CAMediaTimingFunction
functionWithName:kCAMediaTimingFunctionEaseOut];
rotationAnimation.delegate = self;
[bottle.layer addAnimation:rotationAnimation forKey:@"rotationAnimation"];
}
А затем в конце анимации:
-(void)animationDidStop:(CAAnimation *)theAnimation finished:(BOOL)flag
{
animating = FALSE;
// Rotates the image to the last spot that the animation rotated to.
[bottle.layer setValue:[NSNumber numberWithFloat:angle + distance]
forKeyPath:@"transform.rotation.z"];
// Gives the corners of the image after rotation (Thanks to mustISignUp) check to make sure
// that the touch is within these bounds (I use a ray line intersection algorithm in another part of my code)
ptInLayerCoords1 = [[bottle.layer presentationLayer] convertPoint:corner1 toLayer:self.view.layer];
ptInLayerCoords2 = [[bottle.layer presentationLayer] convertPoint:corner2 toLayer:self.view.layer];
ptInLayerCoords3 = [[bottle.layer presentationLayer] convertPoint:corner3 toLayer:self.view.layer];
ptInLayerCoords4 = [[bottle.layer presentationLayer] convertPoint:corner4 toLayer:self.view.layer];
}