如何删除位置?

时间:2019-07-12 08:39:34

标签: swift

用户可以保存其位置并将其保存在列表中。 问题是,当用户删除某个位置时似乎可以使用,但是如果您关闭该应用程序并再次打开它,您将看到之前已删除的位置... 我留下了位置文件和LocationsStorage文件。 谢谢您的帮助

import Foundation
import CoreLocation

class Location: Codable {
  static let dateFormatter: DateFormatter = {
    let formatter = DateFormatter()
    formatter.dateStyle = .medium
    formatter.timeStyle = .medium
    return formatter
  }()

  var coordinates: CLLocationCoordinate2D {
    return CLLocationCoordinate2D(latitude: latitude, longitude: longitude)
  }

  let latitude: Double
  let longitude: Double
  let date: Date
  let dateString: String
  let description: String

  init(_ location: CLLocationCoordinate2D, date: Date, descriptionString: String) {
    latitude =  location.latitude
    longitude =  location.longitude
    self.date = date
    dateString = Location.dateFormatter.string(from: date)
    description = descriptionString
  }

  convenience init(visit: CLVisit, descriptionString: String) {
    self.init(visit.coordinate, date: visit.arrivalDate, descriptionString: descriptionString)
  }
}

现在LocationsStorage文件

import Foundation
import CoreLocation

class LocationsStorage {
  static let shared = LocationsStorage()

  var locations: [Location]
  private let fileManager: FileManager
  private let documentsURL: URL

  init() {
    let fileManager = FileManager.default
    documentsURL = try! fileManager.url(for: .documentDirectory, in: .userDomainMask, appropriateFor: nil, create: false)    
    self.fileManager = fileManager

    let jsonDecoder = JSONDecoder()

    let locationFilesURLs = try! fileManager.contentsOfDirectory(at: documentsURL,
                                                                 includingPropertiesForKeys: nil)
    locations = locationFilesURLs.compactMap { url -> Location? in
      guard !url.absoluteString.contains(".DS_Store") else {
        return nil
      }
      guard let data = try? Data(contentsOf: url) else {
        return nil
      }
      return try? jsonDecoder.decode(Location.self, from: data)
    }.sorted(by: { $0.date < $1.date })
  }

  func saveLocationOnDisk(_ location: Location) {
    let encoder = JSONEncoder()
    let timestamp = location.date.timeIntervalSinceNow
    let fileURL = documentsURL.appendingPathComponent("\(timestamp)")

    let data = try! encoder.encode(location)
    try! data.write(to: fileURL)

    locations.append(location)

    NotificationCenter.default.post(name: .newLocationSaved, object: self, userInfo: ["location": location])
  }

  func saveCLLocationToDisk(_ clLocation: CLLocation) {
    let currentDate = Date()
    AppDelegate.geoCoder.reverseGeocodeLocation(clLocation) { placemarks, _ in
      if let place = placemarks?.first {
        let location = Location(clLocation.coordinate, date: currentDate, descriptionString: "\(place)")
        self.saveLocationOnDisk(location)
      }
    }
  }
}

extension Notification.Name {
  static let newLocationSaved = Notification.Name("newLocationSaved")
}

1 个答案:

答案 0 :(得分:0)

要删除磁盘上的位置,您必须更改LocationsStorage类。

目前,文件名是根据当前日期由时间戳创建的。这样(从根本上)就不可能从给定位置识别文件名。

最重要的更改是替换行

let timestamp = location.date.timeIntervalSinceNow

使用

let timestamp = location.date.timeIntervalSinceReferenceDate

并在文件名中添加文件扩展名

let fileURL = documentsURL.appendingPathComponent("\(timestamp).json")

取决于timeIntervalSinceReferenceDate的时间戳使从date的{​​{1}}属性中识别文件名成为可能。

文件扩展名不是至关重要的,而是一种好习惯,您可以通过扩展名过滤位置文件

Location

现在您可以添加一种从磁盘删除位置的方法

locations = locationFilesURLs.compactMap { url -> Location? in
    guard url.pathExtension == "json" else {
        return nil
    }
...

要在表格视图中删除位置

func deleteLocation(_ location : Location) {
    let timestamp = location.date.timeIntervalSinceReferenceDate
    let fileURL = documentsURL.appendingPathComponent("\(timestamp).json")
    do {
        try self.fileManager.removeItem(at: fileURL)
    } catch {
        print(error)
    }
}
相关问题