Skip to content

Commit

Permalink
1.8.0-beta1
Browse files Browse the repository at this point in the history
  • Loading branch information
jeromegournay committed Apr 9, 2021
1 parent 1b00859 commit 3e34cee
Show file tree
Hide file tree
Showing 9 changed files with 403 additions and 53 deletions.
6 changes: 3 additions & 3 deletions ArsdkEngine.podspec
Original file line number Diff line number Diff line change
@@ -1,16 +1,16 @@

Pod::Spec.new do |s|
s.name = "ArsdkEngine"
s.version = "1.7.1"
s.version = "1.8.0-beta1"
s.summary = "Parrot Drone SDK, arsdk based engine"
s.homepage = "https://developer.parrot.com"
s.license = "{ :type => 'BSD 3-Clause License', :file => 'LICENSE' }"
s.author = 'Parrot Drone SAS'
s.source = { :git => 'https://github.com/Parrot-Developers/pod_arsdkengine.git', :tag => "1.7.1" }
s.source = { :git => 'https://github.com/Parrot-Developers/pod_arsdkengine.git', :tag => "1.8.0-beta1" }
s.platform = :ios
s.ios.deployment_target = '10.0'
s.source_files = 'ArsdkEngine/**/*'
s.dependency 'GroundSdk', '1.7.1'
s.dependency 'GroundSdk', '1.8.0-beta1'
s.swift_version = '4.2'
s.pod_target_xcconfig = {'SWIFT_VERSION' => '4.2'}
s.xcconfig = { 'ONLY_ACTIVE_ARCH' => 'YES' }
Expand Down
5 changes: 3 additions & 2 deletions ArsdkEngine/Arsdk.swift
Original file line number Diff line number Diff line change
Expand Up @@ -67,7 +67,7 @@ class Arsdk: NSObject {
extension Arsdk: ArsdkCoreListener {

func onDeviceAdded(_ uid: String, type: Int, backendType: ArsdkBackendType,
name: String, handle: CShort) {
name: String, api: ArsdkApiCapabilities, handle: CShort) {
if let model = DeviceModel.from(internalId: type),
let provider = ArsdkDeviceProvider.getProvider(backendType: backendType) {
let deviceController = engine.getOrCreateDeviceController(uid: uid, model: model, name: name)
Expand Down Expand Up @@ -340,7 +340,8 @@ extension ArsdkDeviceCtrlBackend: ArsdkCoreDeviceListener {
deviceController.linkWillConnect(provider: provider)
}

func onConnected() {
func onConnected(api: ArsdkApiCapabilities) {
deviceController.apiCapabilities(api)
deviceController.linkDidConnect(provider: provider, backend: self)
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -123,6 +123,9 @@ class AnafiFamilyDroneController: DroneController {
componentControllers.append(DriController(deviceController: self))
componentControllers.append(LogControlController(deviceController: self))
componentControllers.append(CertificateUploaderController(deviceController: self))
if GroundSdkConfig.sharedInstance.enableDevToolbox {
componentControllers.append(AnafiDevToolbox(deviceController: self))
}
sendDateAndTime = { [weak self] in
let dateFormatter = DateFormatter()
dateFormatter.timeZone = NSTimeZone.system
Expand Down
6 changes: 6 additions & 0 deletions ArsdkEngine/DeviceControllers/DeviceComponentController.swift
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,12 @@ public class DeviceComponentController: NSObject {
func didReceiveCommand(_ command: OpaquePointer) {
}

/// API capabilities of the managed device are known.
///
/// - Parameter api: the API capabilities received
func apiCapabilities(_ api: ArsdkApiCapabilities) {
}

/// Send a command to the device
///
/// - Parameter encoder: encoder of the command to send
Expand Down
14 changes: 14 additions & 0 deletions ArsdkEngine/DeviceControllers/DeviceController.swift
Original file line number Diff line number Diff line change
Expand Up @@ -404,6 +404,9 @@ class DeviceController: NSObject {
/// Memorize the previous data sync allowance value in order to notify only if it has changed.
private var previousDataSyncAllowed = false

/// API Capabilities.
private var apiCapabilities = ArsdkApiCapabilities.unknown

/// Constructor
///
/// - Parameters:
Expand Down Expand Up @@ -929,6 +932,17 @@ extension DeviceController: DeviceCoreDelegate {

// Backend callbacks
extension DeviceController {
final func apiCapabilities(_ api: ArsdkApiCapabilities) {
if api != apiCapabilities {
guard api != ArsdkApiCapabilities.unknown else {
ULog.w(.ctrlTag, "Bad API capabilities \(api)")
return
}
apiCapabilities = api
componentControllers.forEach { component in component.apiCapabilities(api) }
}
}

final func linkWillConnect(provider: DeviceProvider) {
if activeProvider == nil || activeProvider == provider {
activeProvider = provider
Expand Down
177 changes: 177 additions & 0 deletions ArsdkEngine/Peripheral/AnafiDevToolbox.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,177 @@
// Copyright (C) 2019 Parrot Drones SAS
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions
// are met:
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above copyright
// notice, this list of conditions and the following disclaimer in
// the documentation and/or other materials provided with the
// distribution.
// * Neither the name of the Parrot Company nor the names
// of its contributors may be used to endorse or promote products
// derived from this software without specific prior written
// permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
// FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
// PARROT COMPANY BE LIABLE FOR ANY DIRECT, INDIRECT,
// INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
// BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
// OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
// AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
// OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
// OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
// SUCH DAMAGE.

import Foundation
import GroundSdk

/// Controller for development toolbox peripheral.
class AnafiDevToolbox: DeviceComponentController, DevToolboxBackend {

/// Development toolbox component.
private(set) var devToolbox: DevToolboxCore!

/// Debug settings indexed by id.
private var settings = [UInt: DebugSettingCore]()

/// Constructor.
///
/// - Parameter deviceController: device controller owning this component controller (weak)
override init(deviceController: DeviceController) {
super.init(deviceController: deviceController)
devToolbox = DevToolboxCore(store: deviceController.device.peripheralStore, backend: self)
}

/// Drone is connected.
override func didConnect() {
// when connected, ask all debug settings
sendCommand(ArsdkFeatureDebug.getAllSettingsEncoder())
devToolbox.publish()
}

/// Drone is disconnected.
override func didDisconnect() {
devToolbox.unpublish()
}

/// A command has been received.
///
/// - Parameter command: received command
override func didReceiveCommand(_ command: OpaquePointer) {
if ArsdkCommand.getFeatureId(command) == kArsdkFeatureDebugUid {
ArsdkFeatureDebug.decode(command, callback: self)
}
}

func set(setting: BoolDebugSettingCore) {
let strValue = setting.value ? "1" : "0"
sendCommand(ArsdkFeatureDebug.setSettingEncoder(id: setting.uid, value: strValue))
}

func set(setting: TextDebugSettingCore) {
sendCommand(ArsdkFeatureDebug.setSettingEncoder(id: setting.uid, value: setting.value))
}

func set(setting: NumericDebugSettingCore) {
let strValue = String(format: "%f", setting.value)
sendCommand(ArsdkFeatureDebug.setSettingEncoder(id: setting.uid, value: strValue))
}

func sendDebugTag(tag: String) {
sendCommand(ArsdkFeatureDebug.tagEncoder(value: tag))
}

/// Creates a debug setting.
///
/// - Parameters:
/// - id: setting unique identifier
/// - label: setting name
/// - type: setting type
/// - mode: whether setting can be modified
/// - min: setting value lower bound
/// - max: setting value upper bound
/// - step: setting value step
/// - value: setting value
/// - Returns: a new debug setting or `nil`
func createDebugSetting(id: UInt, label: String!, type: ArsdkFeatureDebugSettingType,
mode: ArsdkFeatureDebugSettingMode, min: String!, max: String!, step: String!,
value: String!) -> DebugSettingCore? {
var debugSetting: DebugSettingCore?
let readOnly = mode == .readOnly
switch type {
case .bool:
debugSetting = devToolbox.createDebugSetting(uid: id, name: label, readOnly: readOnly, value: value == "1")
case .text:
debugSetting = devToolbox.createDebugSetting(uid: id, name: label, readOnly: readOnly, value: value)
case .decimal:
let min = Double(min)
let max = Double(max)
let step = Double(step)
let value = Double(value) ?? 0.0
var range: ClosedRange<Double>?
if let min = min, let max = max {
range = min...max
}
debugSetting = devToolbox.createDebugSetting(uid: id, name: label, readOnly: readOnly, range: range,
step: step, value: value)
default:
ULog.w(.tag, "Unknown debug setting type, skipping this event.")
}
return debugSetting
}
}

/// Debug feature decode callback implementation.
extension AnafiDevToolbox: ArsdkFeatureDebugCallback {
func onSettingsInfo(listFlagsBitField: UInt, id: UInt, label: String!, type: ArsdkFeatureDebugSettingType,
mode: ArsdkFeatureDebugSettingMode, rangeMin: String!, rangeMax: String!,
rangeStep: String!, value: String!) {
if ArsdkFeatureGenericListFlagsBitField.isSet(.empty, inBitField: listFlagsBitField) {
// remove all settings
settings.removeAll()
devToolbox.update(debugSettings: Array(settings.values)).notifyUpdated()
} else {
if ArsdkFeatureGenericListFlagsBitField.isSet(.first, inBitField: listFlagsBitField) {
settings.removeAll()
}

let debugSetting = createDebugSetting(id: id, label: label, type: type, mode: mode,
min: rangeMin, max: rangeMax, step: rangeStep, value: value)
if let debugSetting = debugSetting {
settings[id] = debugSetting
}

if ArsdkFeatureGenericListFlagsBitField.isSet(.last, inBitField: listFlagsBitField) {
devToolbox.update(debugSettings: Array(settings.values)).notifyUpdated()
devToolbox.publish()
}
}
}

func onSettingsList(id: UInt, value: String!) {
let debugSetting = settings[id]
switch debugSetting {
case let debugSetting as BoolDebugSettingCore:
devToolbox.update(debugSetting: debugSetting, value: value == "1").notifyUpdated()
case let debugSetting as TextDebugSettingCore:
devToolbox.update(debugSetting: debugSetting, value: value).notifyUpdated()
case let debugSetting as NumericDebugSettingCore:
let doubleValue = Double(value)
if let doubleValue = doubleValue {
devToolbox.update(debugSetting: debugSetting, value: doubleValue).notifyUpdated()
}
default:
ULog.w(.tag, "Unknown debug setting id \(id), skipping this event.")
}
}

func onTagNotify(id: String!) {
ULog.d(.tag, "Debug tag notified by drone \(String(describing: id))")
devToolbox.update(debugTagId: id).notifyUpdated()
}
}
14 changes: 14 additions & 0 deletions ArsdkEngine/Peripheral/ArsdkSystemInfo.swift
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,7 @@ class ArsdkSystemInfo: DeviceComponentController {
case boardId = "boardId"
case firmwareVersion = "firmwareVersion"
case hardwareVersion = "hardwareVersion"
case updateRequirement = "updateRequirement"
}

private static let settingKey = "SystemInfo"
Expand Down Expand Up @@ -109,6 +110,16 @@ class ArsdkSystemInfo: DeviceComponentController {
super.willForget()
}

/// API capabilities of the managed device are known.
///
/// - Parameter api: the API capabilities received
override func apiCapabilities(_ api: ArsdkApiCapabilities) {
let isUpdateRequired = (api == ArsdkApiCapabilities.updateOnly)
deviceStore.write(key: PersistedDataKey.updateRequirement, value: isUpdateRequired).commit()
systemInfo.update(isUpdateRequired: isUpdateRequired)
systemInfo.notifyUpdated()
}

/// Called when the current firmware version changed
///
/// - Note: this function will call `notifyUpdated()`.
Expand Down Expand Up @@ -138,6 +149,9 @@ class ArsdkSystemInfo: DeviceComponentController {
if let boardId: String = deviceStore.read(key: PersistedDataKey.boardId) {
systemInfo.update(boardId: boardId)
}
if let isUpdateRequired: Bool = deviceStore.read(key: PersistedDataKey.updateRequirement) {
systemInfo.update(isUpdateRequired: isUpdateRequired)
}
}

/// Starts monitoring the blacklisted firmware version store
Expand Down
7 changes: 3 additions & 4 deletions ArsdkEngine/Peripheral/CameraFeatureCameraRouter.swift
Original file line number Diff line number Diff line change
Expand Up @@ -644,9 +644,8 @@ extension CameraFeatureCameraRouter: ArsdkFeatureCameraCallback {
} else {
mode = .none
}
// if there is no pending request and mode has changed or if the requested lock mode matches the received mode
if (cameraController.requestedExposureLockMode == nil &&
!mode.isSameRequest(as: cameraController.camera.exposureLock?.mode)) ||
// if there is no pending request or if the requested lock mode matches the received mode
if cameraController.requestedExposureLockMode == nil ||
mode.isSameRequest(as: cameraController.requestedExposureLockMode) {

cameraController.requestedExposureLockMode = nil
Expand Down Expand Up @@ -1615,7 +1614,7 @@ extension CameraExposureLockMode {
(.currentValues, .currentValues):
return true
case let (.region(lx, ly, _, _), .region(rx, ry, _, _)):
return lx == rx && ly == ry
return lx.isCloseTo(rx, withDelta: 0.1) && ly.isCloseTo(ry, withDelta: 0.1)
default:
return false
}
Expand Down
Loading

0 comments on commit 3e34cee

Please sign in to comment.