Swift - UIImageView 缩放比 UIScrollView 更大

Posted

技术标签:

【中文标题】Swift - UIImageView 缩放比 UIScrollView 更大【英文标题】:Swift - UIImageView zooms bigger than UIScrollView 【发布时间】:2017-08-15 08:19:06 【问题描述】:

我在缩放 UIImageView 时遇到问题,该UIImageView 设置在 UIScrollView 内。图像会根据用户的捏合输入进行缩放,但图像会缩放并变大,直到占据整个屏幕而不是停留在我的UIScrollView 的范围内。我查看了一堆不同的 SO 问题、文章和 YouTube 视频,试图找到问题的根源,但没有找到任何东西。

以下 SO 问题似乎关系松散,但在查看后我仍然无法解决我的问题:

content size of UIScrollView UIScrollView with scaled UIImageView using autolayout UIScrollView squashes UIImageView image Swift UIImageView Stretched Aspect UIImageView pinch zoom swift

我的UIScrollView 是在我的故事板中创建的,我使用在界面构建器中创建的布局约束将其固定到位。我在viewDidLoad() 中将滚动视图的委托设置为self(并将UIScrollViewDelegate 添加到我的班级顶部)。 UIImageView 是以编程方式创建的。我在类的顶部声明图像视图如下:

class VCImageViewer: UIViewController, UIScrollViewDelegate 
@IBOutlet weak var lblImageTitle: UILabel!
@IBOutlet weak var btnBack: UIButton!
@IBOutlet weak var scrollView: UIScrollView!

var imageView:UIImageView = UIImageView()  // <-- Image view

然后我将图像视图添加为我的UIScrollView 的子视图,并使用以下代码行,在viewDidLoad() 期间调用:

self.scrollView.addSubview(self.imageView)

将图像视图添加到滚动视图后,我将图像加载到图像视图中。我从 URL 获取图像,并使用以下代码将其加载。同样,这是在 viewDidLoad() 中调用的。

self.imageView.image = UIImage(data: data)
            self.imageView.frame = CGRect(origin: CGPoint(x: 0, y: 0), size: (self.imageView.image?.size)!)
            if self.imageView.image != nil 
                self.lblError.isHidden = true
                self.FormatImageViewerWithImage()
            

这确认图像已正确加载,隐藏我将显示的警告标签(如果没有),并调用self.FormatImageViewerWithImage(),如下所示:

func FormatImageViewerWithImage() 
    // Constraints
    let constraintImageViewTop:NSLayoutConstraint = NSLayoutConstraint(item: self.imageView, attribute: NSLayoutAttribute.top, relatedBy: NSLayoutRelation.equal, toItem: self.scrollView, attribute: NSLayoutAttribute.top, multiplier: 1, constant: 0)
    let constraintImageViewBottom:NSLayoutConstraint = NSLayoutConstraint(item: self.imageView, attribute: NSLayoutAttribute.bottom, relatedBy: NSLayoutRelation.equal, toItem: self.scrollView, attribute: NSLayoutAttribute.bottom, multiplier: 1, constant: 0)
    let constraintImageViewLeft:NSLayoutConstraint = NSLayoutConstraint(item: self.imageView, attribute: NSLayoutAttribute.left, relatedBy: NSLayoutRelation.equal, toItem: self.scrollView, attribute: NSLayoutAttribute.left, multiplier: 1, constant: 0)
    let constraintImageViewRight:NSLayoutConstraint = NSLayoutConstraint(item: self.imageView, attribute: NSLayoutAttribute.right, relatedBy: NSLayoutRelation.equal, toItem: self.scrollView, attribute: NSLayoutAttribute.right, multiplier: 1, constant: 0)
    self.view.addConstraints([constraintImageViewTop, constraintImageViewBottom, constraintImageViewLeft, constraintImageViewRight])

    self.scrollView.contentSize = self.imageView.image!.size
    self.scrollView.clipsToBounds = false
    let scrollViewFrame = scrollView.frame
    let scaleWidth = scrollViewFrame.size.width / self.scrollView.contentSize.width
    let scaleHeight = scrollViewFrame.size.height / self.scrollView.contentSize.height
    let minScale = min(scaleWidth, scaleHeight)
    self.scrollView.minimumZoomScale = minScale

    self.scrollView.maximumZoomScale = 1.0
    self.scrollView.zoomScale = minScale

我还通过以下方式实现了scrollViewDidZoom

func scrollViewDidZoom(_ scrollView: UIScrollView) 
    self.CentreScrollViewContents()

func CentreScrollViewContents() 
    let boundsSize = self.scrollView.bounds.size
    var contentsFrame = self.imageView.frame
    if contentsFrame.size.width < boundsSize.width 
        contentsFrame.origin.x = (boundsSize.width - contentsFrame.size.width) / 2
     else 
        contentsFrame.origin.x = 0
    
    if contentsFrame.size.height < boundsSize.height 
        contentsFrame.origin.y = (boundsSize.height - contentsFrame.size.height) / 2
     else 
        contentsFrame.origin.y = 0
    
    self.imageView.frame = contentsFrame

viewForZooming 与:

func viewForZooming(in scrollView: UIScrollView) -> UIView? 
    return self.imageView

我已经看到以前的问题(包括上面列出的一些问题)建议向viewWillLayoutSubviews() 添加代码,但我没有成功,所以我的viewWillLayoutSubviews() 是空的。

谁能看出我做错了什么?

【问题讨论】:

把这个:self.scrollView.clipsToBounds = false 改成这个 self.scrollView.clipsToBounds = true @MohammadBashirSidani 传奇!太感谢你了,我为此扯了头发。如果您想将其添加为答案,我会为您接受。 很高兴它成功了!我会添加它作为答案,谢谢! 【参考方案1】:

请更改此行:

self.scrollView.clipsToBounds = false

到这一行:

self.scrollView.clipsToBounds = true

希望这会有所帮助!

【讨论】:

以上是关于Swift - UIImageView 缩放比 UIScrollView 更大的主要内容,如果未能解决你的问题,请参考以下文章

使用 Swift、autolayout 和 SnapKit 使带有 UIImageView 的 UIScrollView 自动缩放内容

UIImageView:如何显示缩放图像?

UIImageView 缩放图片

将 UIImages 高度缩放到 UIImageView 高度

使用 Swift 缩放图像视图

Swift/Math - 缩放时保持原点