我有一个 TabelViewController。TableViewCells 中的数据正在通过 tableview.reloadData() 以高频率(假设为 10 Hz)更新。到目前为止,这有效。但是当我滚动 TableView 时,更新会暂停,直到用户交互结束。我的应用程序中的所有其他进程也都暂停了。我怎样才能解决这个问题?
这是一个示例 TableViewController。如果您在模拟器上运行它并检查调试区域内的输出,您会注意到,当您滚动并按住 tableview 时,不仅图形(这里是标签)的更新被暂停,而且通知也被暂停。如果您在另一个类中有一个进程,情况也是如此。
有趣的是,如果您与 MapView 交互,则不会出现这种进程阻塞。我在这里缺少什么?
import UIKit
class TableViewController: UITableViewController {
var text = 0
var timer = Timer()
override func viewDidLoad() {
super.viewDidLoad()
NotificationCenter.default.addObserver(self, selector: #selector(self.recieveNotification), name: NSNotification.Name(rawValue: "testNotificatiion"), object: nil)
scheduledTimerWithTimeInterval()
}
func scheduledTimerWithTimeInterval(){
timer = Timer.scheduledTimer(timeInterval: 1/10, target: self, selector: #selector(self.updateCounting), userInfo: nil, repeats: true)
}
@objc func updateCounting(){
text += 1
let userInfo = ["test": text]
NotificationCenter.default.post(name: NSNotification.Name(rawValue: "testNotificatiion"), object: nil, userInfo: userInfo)
tableView.reloadData()
}
@objc func recieveNotification(notification: Notification){
if let userInfo = notification.userInfo! as? [String: Int]
{
if let recieved = userInfo["test"] {
print("Notification recieved with userInfo: \(recieved)")
}
}
}
// MARK: - Table view data source
override func numberOfSections(in tableView: UITableView) -> Int {
return 1
}
override func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return 10
}
override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
var cell: UITableViewCell?
cell = tableView.dequeueReusableCell(withIdentifier: "rightDetail", for: indexPath)
cell?.detailTextLabel?.text = String(text)
return cell!
}
}
UITableView
滚动a 时计时器不会触发。在此处查看Quinn The Eskimo 的答案。
将您的方法更改为这样,它甚至在滚动时也能工作。
func scheduleMyTimer() {
let t = Timer(timeInterval: 1.0, repeats: true) { _ in
self.updateCounting()
}
RunLoop.current.add(t, forMode: RunLoop.Mode.common)
}
CoreLocation
UITableView
滚动a 时也不会触发回调。这是一个解决方法。
从文档中CLLocationManagerDelegate
:
Core Location 从初始化 CLLocationManager 的线程调用 runloop 上的委托对象的方法。该线程本身必须有一个活动的运行循环,就像在您的应用程序的主线程中找到的那样。
所以我CLLocationManager
从这个改变了init:
class AppDelegate {
var lm = CLLocationManager()
}
对此:
class AppDelegate {
var lm: CLLocationManager!
var thread: Thread!
func didFinishLaunching() {
thread = Thread {
self.lm = CLLocationManager()
while true {
RunLoop.current.run()
}
}
thread.start()
}
}
然后,即使在滚动时,委托回调也会继续触发。这个答案有帮助。
本文收集自互联网,转载请注明来源。
如有侵权,请联系 [email protected] 删除。
我来说两句