From c2579eee213d73ba25523bef6c08f75bb9ecb12c Mon Sep 17 00:00:00 2001 From: Autli Date: Tue, 6 Oct 2026 13:50:55 +0500 Subject: [PATCH] feat: call updateFromServer on every tick to sync IOBluetooth state from daemon --- .../blts_tracker/Services/BluetoothTracker.swift | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) diff --git a/Sources/blts_tracker/Services/BluetoothTracker.swift b/Sources/blts_tracker/Services/BluetoothTracker.swift index ebdd2ce..79817a8 100644 --- a/Sources/blts_tracker/Services/BluetoothTracker.swift +++ b/Sources/blts_tracker/Services/BluetoothTracker.swift @@ -18,6 +18,7 @@ public final class BluetoothTracker: ObservableObject { private var timerSource: DispatchSourceTimer? + private typealias VoidFn = @convention(c) (AnyObject, Selector) -> Void private typealias IntBatteryGetter = @convention(c) (AnyObject, Selector) -> Int private typealias BoolGetter = @convention(c) (AnyObject, Selector) -> Bool @@ -95,6 +96,12 @@ public final class BluetoothTracker: ObservableObject { let device = IOBluetoothDevice(addressString: address) ?? pairedDev let name = device.nameOrAddress ?? pairedDev.nameOrAddress ?? "Unknown Device" + // Force sync state from bluetooth daemon + syncFromServer(device: device) + if device !== pairedDev { + syncFromServer(device: pairedDev) + } + let isAudioOutput = activeAudioName != nil && ( name.caseInsensitiveCompare(activeAudioName!) == .orderedSame || activeAudioName!.localizedCaseInsensitiveContains(name) || @@ -172,6 +179,15 @@ public final class BluetoothTracker: ObservableObject { } } + private func syncFromServer(device: IOBluetoothDevice) { + let selUpdate = Selector(("updateFromServer")) + if device.responds(to: selUpdate) { + let imp = device.method(for: selUpdate) + let fn = unsafeBitCast(imp, to: VoidFn.self) + fn(device, selUpdate) + } + } + public func getActiveCoreAudioDeviceName() -> String? { var defaultOutputDeviceID = AudioDeviceID(0) var propertySize = UInt32(MemoryLayout.size)