feat(sdk): 帧间隔 frameIntervalMs 配置化(默认 35ms,[0,500] clamp)

DuooomiBleConfig 新增 frameIntervalMs,BleProtocolService 构造期注入。
顺手清死代码 FrameConstants.frameIntervalNanos、修 sendFrames 0.035 字面量
(统一走 config)。demo 加可调输入框 + UserDefaults 持久化。
越界 warn 不抛错,使用点 min/max 兜底。

设计稿:docs/superpowers/specs/2026-05-20-frame-interval-config-design.md

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
km2023
2026-05-20 14:02:04 +08:00
parent b967471532
commit 09088121b5
6 changed files with 35 additions and 11 deletions

View File

@@ -29,6 +29,9 @@ final class DemoViewModel: NSObject, ObservableObject, DuooomiBleSDKDelegate {
@Published var configScanPrefix: String {
didSet { defaults.set(configScanPrefix, forKey: Self.keyScanPrefix) }
}
@Published var configFrameIntervalMs: String {
didSet { defaults.set(configFrameIntervalMs, forKey: Self.keyFrameIntervalMs) }
}
// MARK: - SDK State (driven by delegate)
@@ -50,26 +53,31 @@ final class DemoViewModel: NSObject, ObservableObject, DuooomiBleSDKDelegate {
private static let keyBrand = "demo.config.brand"
private static let keyApiKey = "demo.config.apiKey"
private static let keyScanPrefix = "demo.config.scanPrefix"
private static let keyFrameIntervalMs = "demo.config.frameIntervalMs"
/// demo UserDefaults 使 DemoSecrets
private static let defaultBrand = DemoSecrets.brand
private static let defaultApiKey = DemoSecrets.apiKey
private static let defaultScanPrefix = DemoSecrets.scanNamePrefix
private static let defaultFrameIntervalMs = "35"
override init() {
let d = UserDefaults.standard
let brand = d.string(forKey: Self.keyBrand) ?? Self.defaultBrand
let apiKey = d.string(forKey: Self.keyApiKey) ?? Self.defaultApiKey
let scanPrefix = d.string(forKey: Self.keyScanPrefix) ?? Self.defaultScanPrefix
let frameIntervalMs = d.string(forKey: Self.keyFrameIntervalMs) ?? Self.defaultFrameIntervalMs
self.configBrand = brand
self.configApiKey = apiKey
self.configScanPrefix = scanPrefix
self.configFrameIntervalMs = frameIntervalMs
self.sdk = DuooomiBleSDK(config: .init(
apiKey: apiKey,
brand: brand,
scanNamePrefix: scanPrefix
scanNamePrefix: scanPrefix,
frameIntervalMs: Int(frameIntervalMs) ?? 35
))
super.init()
@@ -83,7 +91,8 @@ final class DemoViewModel: NSObject, ObservableObject, DuooomiBleSDKDelegate {
let new = DuooomiBleSDK(config: .init(
apiKey: configApiKey,
brand: configBrand,
scanNamePrefix: configScanPrefix
scanNamePrefix: configScanPrefix,
frameIntervalMs: Int(configFrameIntervalMs) ?? 35
))
new.delegate = self
self.sdk = new