ios - Swift 按用户与 MKMapItems 的距离组织 UITableView

标签 ios swift uitableview cllocationmanager mkmapitem

有人可以帮助我了解如何按距离组织我的表格 View ,该距离已经拉取并显示有关 map 项距用户位置多远的数据。还没有看到有人对实际的桌面 View 给出答案。谢谢。

import UIKit
import MapKit

class ListedMapTableViewController: UITableViewController, CLLocationManagerDelegate {

var mapItems: [MKMapItem]!
var userLocation = CLLocationManager()
let distanceFormatter = MKDistanceFormatter()


override func numberOfSections(in tableView: UITableView) -> Int {
    return 1
}

override func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
    return mapItems.count
}

override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
    let cell = tableView.dequeueReusableCell(withIdentifier: "resultCell", for: indexPath) as! ListedTableViewCell

    // Configure the cell...
    let row = indexPath.row
    let item = mapItems[row]
    cell.nameLabel.text = item.name
    cell.detailLabel.text = item.phoneNumber
    let distanceInMeters : Double = self.userLocation.location!.distance(from: mapItems[row].placemark.location!)
    let distanceInMiles : Double = ((distanceInMeters.description as String).doubleValue * 0.00062137)
    cell.distanceLabel.text = "\(distanceInMiles.string(2)) miles away"


    return cell
}

}

//get string value of double without casting
extension String {
var doubleValue: Double {
    return (self as NSString).doubleValue
}
}

//formats a double's decimal places
extension Double {
func string(_ fractionDigits:Int) -> String {
    let formatter = NumberFormatter()
    formatter.minimumFractionDigits = fractionDigits
    formatter.maximumFractionDigits = fractionDigits
    return formatter.string(from: NSNumber(value: self))!
}
}

编辑

import UIKit
import MapKit

class ListedMapTableViewController: UITableViewController, CLLocationManagerDelegate {

var mapItems: [MKMapItem]!
var userLocation = CLLocationManager()
let distanceFormatter = MKDistanceFormatter()

func sortedMapItems() -> [MKMapItem]! {
    return self.mapItems.sorted(by: { (a, b) -> Bool in
        return self.userLocation.location!.distance(from: a.placemark.location!) > self.userLocation.location!.distance(from: b.placemark.location!)
    })
}

override func numberOfSections(in tableView: UITableView) -> Int {
    return 1
}

override func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
    return sortedMapItems().count
}

override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
    let cell = tableView.dequeueReusableCell(withIdentifier: "resultCell", for: indexPath) as! ListedTableViewCell
    // Configure the cell...
    let row = indexPath.row
    let item = sortedMapItems()[row]
    cell.nameLabel.text = item.name
    cell.detailLabel.text = item.phoneNumber
    let distanceInMeters : Double = self.userLocation.location!.distance(from: sortedMapItems()[row].placemark.location!)
    let distanceInMiles : Double = ((distanceInMeters.description as String).doubleValue * 0.00062137)
    cell.distanceLabel.text = "\(distanceInMiles.string(2)) miles away"

    return cell
}

}

//get string value of double without casting
extension String {
var doubleValue: Double {
    return (self as NSString).doubleValue
}
}

//formats a double's decimal places
extension Double {
func string(_ fractionDigits:Int) -> String {
    let formatter = NumberFormatter()
    formatter.minimumFractionDigits = fractionDigits
    formatter.maximumFractionDigits = fractionDigits
    return formatter.string(from: NSNumber(value: self))!
}
}

第二次编辑

 import UIKit
 import MapKit

 class ListedMapTableViewController: UITableViewController, CLLocationManagerDelegate {

var mapItems: [MKMapItem]!
var userLocation = CLLocationManager()
let distanceFormatter = MKDistanceFormatter()

override func viewDidLoad() {
    super.viewDidLoad()

    func sortMapItems()  {
        self.mapItems = self.mapItems.sorted(by: { (a, b) -> Bool in
            return self.userLocation.location!.distance(from: a.placemark.location!) > self.userLocation.location!.distance(from: b.placemark.location!)
        })
    }
}

override func numberOfSections(in tableView: UITableView) -> Int {
    return 1
}

override func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
    return mapItems.count
}

override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
    let cell = tableView.dequeueReusableCell(withIdentifier: "resultCell", for: indexPath) as! ListedTableViewCell
    // Configure the cell...
    let row = indexPath.row
    let item = mapItems[row]
    cell.nameLabel.text = item.name
    cell.detailLabel.text = item.phoneNumber
    let distanceInMeters : Double = self.userLocation.location!.distance(from: mapItems[row].placemark.location!)
    let distanceInMiles : Double = ((distanceInMeters.description as String).doubleValue * 0.00062137)
    cell.distanceLabel.text = "\(distanceInMiles.string(2)) miles away"

    return cell
}

}

//get string value of double without casting
extension String {
var doubleValue: Double {
    return (self as NSString).doubleValue
}
}

 //formats a double's decimal places
 extension Double {
 func string(_ fractionDigits:Int) -> String {
    let formatter = NumberFormatter()
    formatter.minimumFractionDigits = fractionDigits
    formatter.maximumFractionDigits = fractionDigits
    return formatter.string(from: NSNumber(value: self))!
}
}

最佳答案

按距离排序:

func sortedMapItems() -> [MKMapItem] {
    return self.mapItems.sorted(by: { (a, b) -> Bool in
        return self.userLocation.location!.distance(from: a.placemark.location!) > 
               self.userLocation.location!.distance(from: b.placemark.location!)
    })
}

编辑:创建一个函数来对 map 项进行排序,然后在 viewDidLoad 中调用它:

override func viewDidLoad() {
    super.viewDidLoad()
    self.sortMapItems()

}
func sortMapItems()  {
        self.mapItems = self.mapItems.sorted(by: { (a, b) -> Bool in
            return self.userLocation.location!.distance(from: a.placemark.location!) > self.userLocation.location!.distance(from: b.placemark.location!)
        })
    }

override func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
    return mapItems.count
}

override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
    let cell = tableView.dequeueReusableCell(withIdentifier: "resultCell", for: indexPath) as! ListedTableViewCell
    // Configure the cell...
    let row = indexPath.row
    let item = mapItems[row]
    cell.nameLabel.text = item.name
    cell.detailLabel.text = item.phoneNumber
    let distanceInMeters : Double = self.userLocation.location!.distance(from: mapItems[row].placemark.location!)
    let distanceInMiles : Double = ((distanceInMeters.description as String).doubleValue * 0.00062137)
    cell.distanceLabel.text = "\(distanceInMiles.string(2)) miles away"

    return cell
}

cellForRowRowAtIndexPath 中调用此答案中的原始函数 (sortedMapItems) 将过于繁重且不必要,因为该函数将被重复调用。

更好的方法是重新创建数据结构并添加每个项目与用户位置的距离,这样您就不必在 cellForRow 中再次调用 distance 函数。 .

关于ios - Swift 按用户与 MKMapItems 的距离组织 UITableView,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/43332330/

相关文章:

ios - 实例方法 'mapView(_:didFailToLocateUserWithError:)'几乎符合可选要求

ios - UITableView 缺少一些分隔线

ios - 如何定位 UITableViewCell 内容 View

iOS - iPad 模拟器中的额外空白

ios - uipageviewcontroller 中的 Swift uipageviewcontroller

ios - 如何根据 UILabel 动态调整 CollectionViewCell 的大小

ios - 在动态表中重新加载 TableViewCell 的 UILabels

ios - 找不到 SpriteBuilder 图像文件

ios - 为什么我看不到导航项的标题?

iOS:tint 颜色实际上有什么作用?