蓝牙电池电量获取故障:无法显示、已连接却显示未配对
蓝牙设备电池电量显示问题排查与解决
核心问题梳理
- 非BLE蓝牙设备无法读取电池电量
- 已连接设备在代码中显示“未配对”
- 通过
System.Devices.BatteryLifePercent属性无法获取有效电量数据
问题原因分析
- 配对状态显示异常:
DeviceInformation.Pairing.IsPaired仅反映系统配对记录,部分蓝牙设备连接后可能未完成完整配对流程,或系统配对状态未实时同步。 - 非BLE设备的电量传输逻辑:BLE设备依赖GATT服务传递电量数据,但传统蓝牙设备(如经典蓝牙鼠标、耳机)的电量通常通过HID协议、厂商自定义通道或WMI暴露,
System.Devices.BatteryLifePercent并非对所有设备通用。
分步解决方案
一、修复配对/连接状态显示问题
- 打开系统蓝牙设置,确认目标设备是否显示“已配对”。若系统显示正常但代码识别异常:
- 取消配对后重新绑定设备
- 重启系统的Bluetooth Support Service服务
- 代码中补充实际连接状态判断,替代单一的配对状态检查:
bool isConnected = false; if (deviceInfo.Properties.ContainsKey("System.Devices.Aep.IsConnected")) { isConnected = (bool)deviceInfo.Properties["System.Devices.Aep.IsConnected"]; } string status = isConnected ? "Connected" : (deviceInfo.Pairing.IsPaired ? "Paired but Disconnected" : "Not Paired");
二、非BLE设备的电量获取方案
方案1:读取HID电池报告(适用于鼠标、键盘等HID类设备)
部分经典蓝牙设备通过HID协议传输电池报告,可通过HidDevice类读取:
private async Task<string> GetHidBatteryLevelAsync(DeviceInformation deviceInfo) { try { var hidDevice = await HidDevice.FromIdAsync(deviceInfo.Id, FileAccessMode.Read); if (hidDevice == null) return "(No HID Access)"; var capabilities = hidDevice.DeviceCapabilities; if (capabilities.BatteryReportingSupported) { var report = await hidDevice.GetBatteryReportAsync(); if (report?.RemainingCapacityInMilliwattHours.HasValue == true) { return $"{report.RemainingCapacityInMilliwattHours} mWh"; } } return "(HID Battery Not Supported)"; } catch (Exception ex) { return $"Error: {ex.Message}"; } }
方案2:WMI查询(适用于部分品牌设备)
部分设备会通过WMI暴露电池数据,可查询Win32_Battery类:
private string GetWmiBatteryLevel(string deviceName) { try { var searcher = new ManagementObjectSearcher("root\\CIMV2", "SELECT * FROM Win32_Battery"); foreach (var queryObj in searcher.Get()) { if (queryObj["Name"]?.ToString().Contains(deviceName) == true) { var percent = queryObj["EstimatedChargeRemaining"]; return percent != null ? $"{percent}%" : "(WMI Data Null)"; } } return "(No WMI Battery Data)"; } catch (Exception ex) { return $"WMI Error: {ex.Message}"; } }
方案3:厂商专属API
如果是品牌设备(如罗技、索尼),直接使用厂商提供的SDK或API获取电量(例如罗技G HUB SDK、索尼Headphones Connect API)。
三、整合方案后的完整代码
private async Task LoadBluetoothDevicesAsync() { var selector = BluetoothDevice.GetDeviceSelector(); var devices = await DeviceInformation.FindAllAsync(selector); BluetoothList.Items.Clear(); foreach (var deviceInfo in devices) { string name = string.IsNullOrWhiteSpace(deviceInfo.Name) ? "(Unnamed)" : deviceInfo.Name; // 检查实际连接状态 bool isConnected = false; if (deviceInfo.Properties.ContainsKey("System.Devices.Aep.IsConnected")) { isConnected = (bool)deviceInfo.Properties["System.Devices.Aep.IsConnected"]; } string status = isConnected ? "Connected" : (deviceInfo.Pairing.IsPaired ? "Paired but Disconnected" : "Not Paired"); // 多方式尝试获取电量 string battery = "(Unknown)"; // 1. 系统属性优先 if (deviceInfo.Properties.ContainsKey("System.Devices.BatteryLifePercent")) { object batteryObj = deviceInfo.Properties["System.Devices.BatteryLifePercent"]; if (batteryObj != null) { double percent = (double)batteryObj * 100; battery = $"{Math.Round(percent)}%"; } } // 2. 系统属性失败,尝试HID if (battery == "(Unknown)") { battery = await GetHidBatteryLevelAsync(deviceInfo); } // 3. 最后尝试WMI if (battery == "(Unknown)" || battery.StartsWith("Error")) { battery = GetWmiBatteryLevel(name); } string result = $"Name: {name}\nStatus: {status}\nBattery: {battery}"; BluetoothList.Items.Add(result); } }
内容的提问来源于stack exchange,提问作者pemk
相关产品推荐
相关产品推荐

