我们如何在 3D 空间中同时旋转 2 个 UIView 平面
Posted
技术标签:
【中文标题】我们如何在 3D 空间中同时旋转 2 个 UIView 平面【英文标题】:How do we rotate 2 UIView planes simultaneously in 3D space 【发布时间】:2014-04-21 15:34:51 【问题描述】:由于项目限制,我正在尝试使用 UIView 而不是 CALayer 创建“翻页效果”。这需要将 1 个 UIView 翻转 180 度并基本上将其“粘贴”到另一个 UIView 的背面。然后通过在 3D 空间中旋转超级视图来同时旋转两个 UIView。
我正在尝试移植 AFKPageFlipper's "initFlip" method 以使用 UIView 而不是 UIImage。
以下是我尝试移植它的 sn-p。初始页面翻转有效,但代码中的“前层”似乎没有出现。好像我无法看到页面的后端。当我翻页时,动画最初是正确的(背面层很好),但是页面的另一侧(正面层),我看到了第一页的倒置视图(backLayer)。
任何帮助都会很棒!
flipAnimationLayer = [[UIView alloc] init];
flipAnimationLayer.layer.anchorPoint = CGPointMake(1.0, 0.5);
flipAnimationLayer.layer.frame = rect;
[self addSubview:flipAnimationLayer];
UIView *backLayer;
UIView *frontLayer;
if (flipDirection == AFKPageFlipperDirectionRight)
backLayer = currentViewSnap2;
backLayer.layer.contentsGravity = kCAGravityLeft;
frontLayer = nextViewSnap2;
frontLayer.layer.contentsGravity = kCAGravityRight;
else
backLayer = nextViewSnap2;
backLayer.layer.contentsGravity = kCAGravityLeft;
frontLayer= currentViewSnap2;
frontLayer.layer.contentsGravity = kCAGravityRight;
backLayer.frame = flipAnimationLayer.bounds;
backLayer.layer.doubleSided = NO;
backLayer.clipsToBounds = YES;
[flipAnimationLayer addSubview:backLayer];
frontLayer.frame = flipAnimationLayer.bounds;
frontLayer.layer.doubleSided = NO;
frontLayer.clipsToBounds = YES;
frontLayer.layer.transform = CATransform3DMakeRotation(M_PI, 0, 1.0, 0);
[flipAnimationLayer addSubview:frontLayer];
if (flipDirection == AFKPageFlipperDirectionRight)
CATransform3D transform = CATransform3DMakeRotation(0.0, 0.0, 1.0, 0.0);
transform.m34 = 1.0f / 2500.0f;
flipAnimationLayer.layer.transform = transform;
currentAngle = startFlipAngle = 0;
endFlipAngle = -M_PI;
else
CATransform3D transform = CATransform3DMakeRotation(-M_PI / 1.1, 0.0, 1.0, 0.0);
transform.m34 = 1.0f / 2500.0f;
flipAnimationLayer.layer.transform = transform;
currentAngle = startFlipAngle = -M_PI;
endFlipAngle = 0;
【问题讨论】:
【参考方案1】:您的代码正在旋转图层,而不是视图。没关系。
我不希望您发布的代码能够制作动画,因为图层的背景视图不执行隐式动画,您可以使用 CABasicAnimation 使其动画。或者,您可以为前视图和后视图创建图层并将它们附加为视图图层的子图层。如果你这样做,那么在图层上操作变换将使用隐式动画。
按照您的描述,我创建自己的字体到后翻页所做的就是伪造它。
我分两步制作动画:首先从 0 度(平面)到 90 度(图层变得不可见)。在那一刻,我隐藏了第一层并使第二层可见,反之旋转 90 度,然后然后将另一层旋转回零。这会产生与显示旋转背面相同的视觉效果。
如果您使用隐式图层动画来执行此操作,您需要将变换的更改放在 CATransaction 块中并将动画时间设置为线性,或者在前半部分使用缓入,在前半部分使用缓出下半场。这是因为动画默认是缓入缓出时序,第一个90度的动画最后会变慢,然后第二个90度的动画会缓入。
【讨论】:
谢谢邓肯!! 90 度互换效果很好!! :D 所以为了更好地理解。不可能将 UIView 翻转 180 度以表示“后页”并基本上将其“粘贴”在“首页”UIView 后面?我知道这种方法对于 Layers 是可行的,但对于 UIViews 似乎是不可能的......再次感谢! 据我所知,将视图或图层旋转 180 度是不可能的。无论如何,您都必须伪造它。 有趣。我在上面发布的 AFKPageFlipper 链接完美运行,似乎通过图层“旋转 180 度/M_PI 弧度”。我可能误解了代码,但从这一行来看,它看起来像是 180 度翻转:frontLayer.transform = CATransform3DMakeRotation(M_PI, 0, 1.0, 0);以上是关于我们如何在 3D 空间中同时旋转 2 个 UIView 平面的主要内容,如果未能解决你的问题,请参考以下文章