SpotSense 1.0.3

SpotSense 1.0.3

Jonny ReissZak DeBrinejatin davesmit patelSumit Rana 维护。



SpotSense 1.0.3

SpotSense SDK

需求

  • iOS 10+
  • Swift 4.2+

入门

创建应用

  1. SpotSense Dashboard 中创建应用

  2. 通过以下方法通过 GitHub 或 CocoaPods 下载 SpotSense SDK

    1. 创建 XCode 项目

    2. 在终端中,导航到 Xcode 项目的目录

    3. 通过运行 pod init 创建 PodFile

    4. 在 Xcode 或文本编辑器中打开 PodFile

    5. 将以下代码添加到 PodFile 中

    target 'your-app' do
        # Pods for your-app
        pod 'SpotSense', '~>1.0.2'
    end
    
    1. 运行 pod install

    2. 打开您的应用的 .xcworkspace 文件,以启动 Xcode

  3. import spotsense 并使用仪表板中的 Client ID 和 Secret 初始化 SpotSense

import UIKit
import CoreLocation
import SpotSense

let spotsense = SpotSense(clientID: "client-id", clientSecret: "client-secret")
class ViewController: UIViewController, CLLocationManagerDelegate, SpotSenseDelegate {...}
  1. 请求使用用户的位置并添加代理以处理位置更新 注:Apple 要求开发者在 Info.plist 中添加关于为何使用用户位置的描述
let locationManager : CLLocationManager = CLLocationManager()
let notificationCenter = UNUserNotificationCenter.current()

override func viewDidLoad() {
    super.viewDidLoad()

    txtLog = UITextView(frame: CGRect(x: 0, y: 0, width: 100, height: 10))
    txtLog.isScrollEnabled = true
    txtLog.textColor = UIColor.white
    txtLog.backgroundColor = UIColor.black
    txtLog.isEditable = false
    self.view.addSubview(txtLog)
    txtLog.translatesAutoresizingMaskIntoConstraints = false
    txtLog.leftAnchor.constraint(equalTo: self.view.leftAnchor, constant: 0).isActive = true
    txtLog.topAnchor.constraint(equalTo: self.view.topAnchor, constant: 55).isActive = true
    txtLog.rightAnchor.constraint(equalTo: self.view.rightAnchor, constant: 0).isActive = true
    txtLog.bottomAnchor.constraint(equalTo: self.view.bottomAnchor, constant: -55).isActive = true
                    
            // get notification permission, only required if sending notifications with SpotSense
    notificationCenter.requestAuthorization(options: [.alert, .sound]) { (granted, error) in
        spotsense.notificationStatus(enabled: granted);
        }
            
            // get location permissions
            locationManager.delegate = self
            locationManager.activityType = .automotiveNavigation
            locationManager.desiredAccuracy = kCLLocationAccuracyNearestTenMeters
            locationManager.distanceFilter = 5.0
            locationManager.requestAlwaysAuthorization()
            locationManager.startUpdatingLocation()
            spotsense.delegate = self; // attach spotsense delegate to self
            
            if (CLLocationManager.authorizationStatus() == .authorizedAlways || CLLocationManager.authorizationStatus() == .authorizedWhenInUse) {
                if CLLocationManager.isMonitoringAvailable(for: CLCircularRegion.self) { // Make sure region monitoring is supported.
                }
            }

    
     let logg = Logger()
     logg.log("App started")
            if let fileURL = logg.logFile {
           
                do{
                  self.txtLog.text = try String(contentsOf: fileURL, encoding: .utf8)
                }
                catch {/* error handling here */}
            }
    spotsense.delegate = self
}

 func ruleDidTrigger(response: NotifyResponse, ruleID: String) {
        
     if let segueID = response.segueID { // performs screenchange
                performSegue(withIdentifier: segueID, sender: nil)
            } else if (response.getActionType() == "http") {
                _ = response.getHTTPResponse()
            }
 }
 
 func locationManager(_ manager: CLLocationManager, didEnterRegion region: CLRegion) {

     spotsense.handleRegionState(region: region, state: .inside)
         
         let logg = Logger()
         
         if let fileURL = logg.logFile {
                        do {
                         self.txtLog.text = try String(contentsOf: fileURL, encoding: .utf8)
                        }
                        catch {/* error handling here */}
         }
     }
     
     func locationManager(_ manager: CLLocationManager, didExitRegion region: CLRegion) {
         
         spotsense.handleRegionState(region: region, state: .outside)

         let logg = Logger()
                logg.log("didExitRegion : \(region.identifier)")

                if let fileURL = logg.logFile {
                    //reading
                               do {
                                self.txtLog.text = try String(contentsOf: fileURL, encoding: .utf8)
                               }
                               catch {/* error handling here */}
                }
     }


 func didUpdateBeacon(beaconScanner: SpotSense, beaconInfo: BeaconInfo, data: NSDictionary) {
     
 }
 
 func didFindBeacon(beaconScanner: SpotSense, beaconInfo: BeaconInfo, data: NSDictionary) {

     NSLog("FIND: %@", beaconInfo.description)
     
     spotsense.handleBeaconEnterState(beaconScanner: beaconScanner, beaconInfo: beaconInfo, data: data)
     
     DispatchQueue.main.async {

          let logg = Logger()
               logg.log("FIND : \(beaconInfo.description)")
                       if let fileURL = logg.logFile {
               do {
                       self.txtLog.text = try String(contentsOf: fileURL, encoding: .utf8)
                       }
               catch {/* error handling here */}
                       }
     }
   
  }
  func didLoseBeacon(beaconScanner: SpotSense, beaconInfo: BeaconInfo, data: NSDictionary) {

     NSLog("LOST: %@", beaconInfo.description)
     
     spotsense.handleBeaconExitState(beaconScanner: beaconScanner, beaconInfo: beaconInfo, data: data)
     
     DispatchQueue.main.async {

     let logg = Logger()
     logg.log("LOST : \(beaconInfo.description)")
     if let fileURL = logg.logFile {
     do {
         self.txtLog.text = try String(contentsOf: fileURL, encoding: .utf8)
     }
     catch {/* error handling here */}
     }
         }

  }
  func didUpdateBeacon(beaconScanner: SpotSense, beaconInfo: BeaconInfo) {
    //NSLog("UPDATE: %@", beaconInfo.description)
  }
  func didObserveURLBeacon(beaconScanner: SpotSense, URL: NSURL, RSSI: Int) {
    //NSLog("URL SEEN: %@, RSSI: %d", URL, RSSI)
  }
  
  class Logger {

       var logFile: URL? {
          
          guard let documentsDirectory = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask).first else { return nil }
          let formatter = DateFormatter()
          formatter.dateFormat = "dd-MM-yyyy"
          let dateString = formatter.string(from: Date())
          let fileName = "\(dateString).log"
          return documentsDirectory.appendingPathComponent(fileName)
      }

       func log(_ message: String) {
          guard let logFile = logFile else {
              return
          }

          let formatter = DateFormatter()
          formatter.dateFormat = "h:mm a"
          let timestamp = formatter.string(from: Date())
          guard let data = (timestamp + ": " + message + "\n").data(using: String.Encoding.utf8) else { return }

          if FileManager.default.fileExists(atPath: logFile.path) {
              if let fileHandle = try? FileHandle(forWritingTo: logFile) {
                  fileHandle.seekToEndOfFile()
                  fileHandle.write(data)
                  fileHandle.closeFile()
              }
          } else {
              try? data.write(to: logFile, options: .atomicWrite)
          }
      }
  }
  extension UIViewController {

    func presentAlert(withTitle title: String, message : String) {
      let alertController = UIAlertController(title: title, message: message, preferredStyle: .alert)
      let OKAction = UIAlertAction(title: "OK", style: .default) { action in
          print("You've pressed OK Button")
      }
      alertController.addAction(OKAction)
      self.present(alertController, animated: true, completion: nil)
    }
  }
  1. 选择您的应用并在 SpotSense Dashboard 中创建规则
  2. 在真实世界或在 iOS 模拟器中测试您的规则!

有问题或遇到困难?请在SpotSense Slack社区中告诉我们,或发送电子邮件([email protected])。很高兴为您提供帮助!