【问题标题】:iOS memory warning in SwiftSwift 中的 iOS 内存警告
【发布时间】:2017-09-21 21:55:05
【问题描述】:

我使用了一个计时器,每 0.1 秒触发一个函数重复,以使用 UIGraphicsGetImageFromCurrentImageContext 获取 UIImage 并分配给 @IBOutllet 弱 UImageView.image.(coverImageView)

var timer:Timer?

func fireTimer() {
    timer = Timer.scheduledTimer(withTimeInterval: 0.1, repeats: true, block: { [weak self] _ in
        self?.lightTheFier()
    })
}

func invalidateTimer() {
    timer?.invalidate()
    timer = nil
}

func lightTheFier() {
    var points = [CGPoint]()
    for pin in pins {
        let point = mapView.convert(pin.coordinate, toPointTo: coverImageView)
        points.append(point)
    }
    coverImageView.image = getMaskedImage(points: points, zoomLevel: Int(mapView.zoomLevel()))
}

func getOringinalImageFromPath() -> UIImage{
    UIGraphicsBeginImageContextWithOptions(coverImageView.bounds.size, false, 0.0)
    let path = UIBezierPath(rect: coverImageView.bounds)
    UIColor.black.setFill()
    path.fill()
    let image = UIGraphicsGetImageFromCurrentImageContext()
    UIGraphicsEndImageContext()
    return image!
}

func getMaskImageFromPath(points:[CGPoint], scale:CGFloat) -> UIImage {
    UIGraphicsBeginImageContextWithOptions(coverImageView.bounds.size, false, 0.0)
    let radius:CGFloat = 10.0
    UIColor.blue.setFill()
    for point in points {
        let rect = CGRect(x: point.x - (scale*radius/2), y: point.y - (scale*radius/2), width: scale*radius, height: scale*radius)
        let path = UIBezierPath(ovalIn: rect)
        path.fill()
    }
    let image = UIGraphicsGetImageFromCurrentImageContext()
    UIGraphicsEndImageContext()
    return image!
}

func getMaskedImage(points:[CGPoint], zoomLevel:Int) -> UIImage{
    let orImage = getOringinalImageFromPath().cgImage
    let maskImage = getMaskImageFromPath(points: points, scale: CGFloat(zoomLevel)).cgImage
    let mask = CGImage(maskWidth: maskImage!.width, height: maskImage!.height, bitsPerComponent: maskImage!.bitsPerComponent, bitsPerPixel: maskImage!.bitsPerPixel, bytesPerRow: maskImage!.bytesPerRow, provider: maskImage!.dataProvider!, decode: nil, shouldInterpolate: true)
    let maskRef = orImage?.masking(mask!)
    let image = UIImage(cgImage: maskRef!)
    return image
}

以上所有代码都在 ViewController.swift 中进行测试。

函数运行时内存在增加没关系,我想要的是当我使定时器失效时它可以释放内存。

我应该如何解决这个问题?

【问题讨论】:

  • 输入你尝试过的代码
  • 我已经编辑过了,谢谢!
  • 在 ARC 中,要释放某些变量,使用该引用的所有变量都需要超出范围。查看coverImageView 将超出范围的位置。更好的方法是在需要时请求图像,而不是使用计时器。因此,当需要显示图像时,请检查图像是否已经可用,否则获取它。
  • 您好 user1046037,感谢您的回复。实际上,当 mapView 进行任何区域更改时,我必须更新图像(并在更改期间不断更新图像),但是委托仅提供将更改并确实更改。感谢您给我任何建议,如果我能做得更好!

标签: ios iphone swift memory-management


【解决方案1】:

您正在启动图像上下文:UIGraphicsBeginImageContextWithOptions,但您永远不会结束它。您需要将UIGraphicsEndImageContext() 添加到您的getMaskImageFromPathgetOringinalImageFromPath 方法中:

func getMaskImageFromPath(points:[CGPoint], scale:CGFloat) -> UIImage {
    UIGraphicsBeginImageContextWithOptions(coverImageView.bounds.size, false, 0.0)
    let radius:CGFloat = 10.0
    UIColor.blue.setFill()
    for point in points {
        let rect = CGRect(x: point.x - (scale*radius/2), y: point.y - (scale*radius/2), width: scale*radius, height: scale*radius)
        let path = UIBezierPath(ovalIn: rect)
        path.fill()
    }
    let image = UIGraphicsGetImageFromCurrentImageContext()
    UIGraphicsEndImageContext() // Missing this line
    return image!
}

【讨论】:

  • 运行循环保留定时器。
  • 嗨,戴夫,在我修复它并运行之后,它节省了很多内存!好吧,但是在我不断触发和使计时器无效后,内存只会增加但不会减少,我该如何解决它?
  • 或者给我指示找出问题所在,非常感谢!
  • 您还在收到内存警告吗?如果您只是查看 Instruments 报告的已使用内存,那通常包括稍后将被释放的内存。
  • 原来如此,我只是按照你说的看内存仪器,我会继续检查的,谢谢!!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2012-06-20
  • 2014-12-24
  • 1970-01-01
  • 2013-10-04
  • 2012-03-04
  • 1970-01-01
相关资源
最近更新 更多