自适应布局和仿射变换

4

我尝试在用户交互期间缩放UIView,并使用CGAffineTransform在视图上实现,如下所示:

@implementation Tileview
{
CGAffineTransform _tempTransform;
}

-(void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event
 {
_tempTransform = self.transform;
self.transform = CGAffineTransformScale(self.transform, 1.2, 1.2);
}

-(void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event
 {
self.transform = _tempTransform;
}

这段代码似乎可以很好地缩放视图,但后来我发现在屏幕上移动视图时出现了不可预测的结果。经过一些研究,我了解到这可能是因为我正在使用自动布局。建议是动画化层而不是视图对象。
于是我尝试重构上面的代码,使用CATranform3D,因为似乎无法将CAAffineTransform应用于图层,但可以使用CATransform3D。但我还没有找到如何使用该Transform对象对图层进行缩放的方法。
我尝试将变换应用于视图的层,如下所示:
self.layer.sublayerTransform = CATransform3DMakeScale(1.2, 1.2, 0.0f);

这将缩放我的视图的所有子层

但我试图将其应用于

 self.layer = CATransform3DMakeScale(1.2, 1.2, 0.0f); 

我收到一个错误,内容为“分配给只读属性”。我还查看了CATransformLayer类,但当我尝试将其分配给self.layer时,我会收到一个错误,内容为“从不兼容的类型CATransform3D分配给CATransformLayer”。因此我的问题是,有没有一种方法可以缩放UIView的层而不干扰Autolayout坐标。
1个回答

3
您为什么要使用子图层变换?以下代码应该可以解决问题:
self.layer.transform = CATransform3DScale(self.layer.transform, 1.2, 1.2, 1);

您还可以通过CATransform3DMakeAffineTransform(<#CGAffineTransform m#>)对图层应用仿射变换,如果确实需要的话。

我注意到你正在保存初始变换以在触摸结束后应用它。您可以通过以下方式简单地恢复初始变换:

self.layer.transform = CATransform3DIdentity;

谢谢提供代码。我在某个地方读到,由于CGAffineTransform与Autolayout交互的方式,我得到的结果是不可预测的。建议是将变换应用于图层而不是视图。 - Linda Keating
上面的代码是正确的并且有效。但不幸的是,将变换应用于图层而不是视图并不能解决最初的问题:当移动视图时仍会收到不可预测的结果。 - Linda Keating
@LindaKeating 我在这个领域有一些经验,如果你发布更多的代码或者一个项目链接,我可以研究一下。但是我想这应该是一个新问题。 - NKorotkov
谢谢你的提议。但是,由于我能够排除自动布局/变换问题,我查看了控制瓷砖放置的逻辑,并发现一些问题导致了意外行为。 - Linda Keating

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接