iOS: Swift: объедините данные акселерометра и ориентации для получения сопоставимых результатов

#ios #swift #accelerometer #gesture #core-motion

#iOS #быстрый #акселерометр #жест #ядро-движение

Вопрос:

Идея

Моя идея состоит в том, чтобы написать небольшое приложение для моего iOS-устройства, чтобы записывать движение после начала записи нажатием кнопки UIButton и сохранять данные с акселерометра для этого движения. После записи я могу сохранить эти данные, чтобы использовать их в готовом приложении для повторного обнаружения этого движения.

Итак, я ищу способ сравнить два NSMutableArrays, каждый из которых представляет собой набор данных о движении, и хочу проверить, соответствует ли текущее NSMutableArray тому же движению, что и записанное.

Проблемы

Чтобы реализовать эту идею, я обнаружил три проблемы, которые я не могу решить сам:

  1. Как сравнить два NSMutableArrays и получить, например, уровень индекса сходства или процент, например, эквивалент 97,32%.
  2. Что, если пользователь совершает движение с разной скоростью? Например, медленно или быстро.
  3. Последняя проблема: как обрабатывать разные ориентации устройств? Есть ли способ рассчитать данные с акселерометра до нейтрального уровня в любой ориентации? Я думаю, что у меня есть подход к решению этой последней проблемы, но не знаю, как перенести это в код: у нас есть данные ориентации для тангажа, крена и рыскания. Может быть, мы можем рассчитать с этими значениями нейтральные данные для акселерометра?

Код

На данный момент у меня есть только код для получения данных с акселерометра и данных ориентации, как из MotionManager. Я несколько часов работал со своим кодом и много искал в Google, но не могу найти правильный способ…

 import UIKit
import CoreMotion

var motionManager = CMMotionManager()

var x:Float = 0.0
var y:Float = 0.0
var z:Float = 0.0
var roll:Float = 0.0
var pitch:Float = 0.0
var yaw:Float = 0.0

class FirstViewController: UIViewController {
       override func viewDidLoad() {
            super.viewDidLoad()

            motionManager.accelerometerUpdateInterval = 1
            motionManager.deviceMotionUpdateInterval = 1
       }

       @IBAction func startRecording() {
        accelerometerData = NSMutableArray()
        motionManager.startDeviceMotionUpdates(using: CMAttitudeReferenceFrame.xMagneticNorthZVertical, to:
            OperationQueue.current!, withHandler: {
                (deviceMotion, error) -> Void in
                let attitude = deviceMotion?.attitude
                let roll = self.degrees(radians: attitude!.roll)
                let pitch = self.degrees(radians: attitude!.pitch)
                let yaw = self.degrees(radians: attitude!.yaw)

                self.roll = Float(roll)
                self.pitch = Float(pitch)
                self.yaw = Float(yaw)

                let accX = deviceMotion?.userAcceleration.x
                let accY = deviceMotion?.userAcceleration.y
                let accZ = deviceMotion?.userAcceleration.z
                self.x = Float(accX!)
                self.y = Float(accY!)
                self.z = Float(accZ!)
        })
    }
}
  

Обновить

Я обновлю этот вопрос, когда узнаю больше.

Проблема 2: решение:
С помощью атрибута CMAttitudeReferenceFrame.xMagneticNorthZVertical для motionManager.startDeviceMotionUpdates -метода вы можете нейтрализовать все данные датчиков для определенной ориентации. Вы также можете получить доступ к данным акселерометра здесь. Я также обновил приведенный выше код.