蓝牙设置通过wifi同步
This commit is contained in:
parent
d6eda72140
commit
e69d3e4cbb
@ -9,7 +9,8 @@ extern "C" {
|
||||
// 0 = Unknown, 1 = Resetting, 2 = Unsupported, 3 = Unauthorized, 4 = PoweredOff, 5 = PoweredOn
|
||||
int GetBluetoothStateIOS() {
|
||||
if (centralManager == nil) {
|
||||
centralManager = [[CBCentralManager alloc] initWithDelegate:nil queue:nil options:@{CBCentralManagerOptionShowPowerAlertKey: @NO}];
|
||||
// 使用 @YES 允许 iOS 系统在蓝牙关闭时自动弹出"打开蓝牙"对话框
|
||||
centralManager = [[CBCentralManager alloc] initWithDelegate:nil queue:nil options:@{CBCentralManagerOptionShowPowerAlertKey: @YES}];
|
||||
}
|
||||
|
||||
switch (centralManager.state) {
|
||||
|
||||
@ -339,18 +339,18 @@ namespace Kill.Bluetooth
|
||||
Log("iOS 蓝牙已开启");
|
||||
onBluetoothReady?.Invoke();
|
||||
}
|
||||
// 4 = PoweredOff (蓝牙关闭)
|
||||
// 4 = PoweredOff (蓝牙关闭) — iOS 系统会自动弹出蓝牙开启对话框,无需手动跳转设置
|
||||
else if (state == 4)
|
||||
{
|
||||
Log("iOS 蓝牙未开启,跳转到系统设置...");
|
||||
ShowIOSTurnOnBluetoothPrompt();
|
||||
// 等待用户从设置返回(检测焦点变化 + 轮询蓝牙状态)
|
||||
Log("iOS 蓝牙未开启,等待系统弹出蓝牙开启提示...");
|
||||
// 不调用 ShowIOSTurnOnBluetoothPrompt(),让 iOS 原生弹窗处理
|
||||
// 等待蓝牙状态变化(检测焦点变化 + 轮询蓝牙状态)
|
||||
_enableBtCoroutine = StartCoroutine(WaitForIOSBluetoothEnabled(onBluetoothReady));
|
||||
}
|
||||
// 3 = Unauthorized (未授权)
|
||||
// 3 = Unauthorized (未授权) — 需要跳转到应用设置页面让用户开启蓝牙权限
|
||||
else if (state == 3)
|
||||
{
|
||||
Log("iOS 蓝牙未授权,跳转到系统设置...");
|
||||
Log("iOS 蓝牙未授权,跳转到应用设置页...");
|
||||
ShowIOSTurnOnBluetoothPrompt();
|
||||
_enableBtCoroutine = StartCoroutine(WaitForIOSBluetoothEnabled(onBluetoothReady));
|
||||
}
|
||||
|
||||
@ -229,6 +229,73 @@ namespace Kill.Managers
|
||||
|
||||
#endregion
|
||||
|
||||
/// <summary>
|
||||
/// 同步设备配置到服务器(WiFi在线时调用,由各设置页面Sync方法调用)
|
||||
/// </summary>
|
||||
public async void SyncDeviceConfigToServer()
|
||||
{
|
||||
if (!hasWifi) return;
|
||||
await UpdateDeviceConfig(selectedDevice.ble_mac, deviceConfig);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 更新定时任务到服务器
|
||||
/// </summary>
|
||||
public async Task<bool> UpdateScheduleTasksToServer(string deviceSn, List<ScheduleTaskData> tasks)
|
||||
{
|
||||
var requestData = new ScheduleTasksUploadRequest
|
||||
{
|
||||
device_sn = deviceSn,
|
||||
tasks = tasks
|
||||
};
|
||||
|
||||
var response = await NetworkCtrl.Instance.Post<NoDataResponse>(
|
||||
"/api/v1/device/schedule-tasks", JsonUtility.ToJson(requestData));
|
||||
|
||||
bool success = false;
|
||||
ResponseCodeHandler.HandleResponse(response,
|
||||
onSuccess: (data) =>
|
||||
{
|
||||
success = true;
|
||||
Debug.Log($"[DataManager] 定时任务已同步到服务器,共 {tasks.Count} 条");
|
||||
},
|
||||
onError: (code, msg) =>
|
||||
{
|
||||
Debug.LogError($"[DataManager] 同步定时任务失败: {msg}");
|
||||
}
|
||||
);
|
||||
return success;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 更新指纹列表到服务器
|
||||
/// </summary>
|
||||
public async Task<bool> UpdateFingerprintsToServer(string deviceSn, List<FingerprintUserData> fingerprints)
|
||||
{
|
||||
var requestData = new FingerprintsUploadRequest
|
||||
{
|
||||
device_sn = deviceSn,
|
||||
fingerprints = fingerprints
|
||||
};
|
||||
|
||||
var response = await NetworkCtrl.Instance.Post<NoDataResponse>(
|
||||
"/api/v1/device/fingerprints", JsonUtility.ToJson(requestData));
|
||||
|
||||
bool success = false;
|
||||
ResponseCodeHandler.HandleResponse(response,
|
||||
onSuccess: (data) =>
|
||||
{
|
||||
success = true;
|
||||
Debug.Log($"[DataManager] 指纹列表已同步到服务器,共 {fingerprints.Count} 条");
|
||||
},
|
||||
onError: (code, msg) =>
|
||||
{
|
||||
Debug.LogError($"[DataManager] 同步指纹列表失败: {msg}");
|
||||
}
|
||||
);
|
||||
return success;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 通过WiFi获取指纹列表
|
||||
/// </summary>
|
||||
@ -352,4 +419,18 @@ namespace Kill.Managers.ResponseModels
|
||||
public string mode;
|
||||
public byte repeat_mask;
|
||||
}
|
||||
|
||||
[System.Serializable]
|
||||
public class ScheduleTasksUploadRequest
|
||||
{
|
||||
public string device_sn;
|
||||
public List<ScheduleTaskData> tasks;
|
||||
}
|
||||
|
||||
[System.Serializable]
|
||||
public class FingerprintsUploadRequest
|
||||
{
|
||||
public string device_sn;
|
||||
public List<FingerprintUserData> fingerprints;
|
||||
}
|
||||
}
|
||||
|
||||
@ -173,6 +173,10 @@ public class ConnectDevicePageCtrl : MonoBehaviour
|
||||
if (success)
|
||||
{
|
||||
UnityEngine.Debug.Log("WiFi 配置成功");
|
||||
DataManager.Instance.deviceConfig.wifi_enable = true;
|
||||
DataManager.Instance.deviceConfig.wifi_ssid = ssid;
|
||||
DataManager.Instance.deviceConfig.wifi_password = password;
|
||||
DataManager.Instance.SyncDeviceConfigToServer();
|
||||
ShowSuccessPage();
|
||||
}
|
||||
else
|
||||
|
||||
@ -128,14 +128,18 @@ namespace Kill.UI.Pages
|
||||
LoadingUI.Show();
|
||||
BLECommunicationManager.Instance.SetFingerprintEnable(nowUserid, isOn, (response) =>
|
||||
{
|
||||
Loom.QueueOnMainThread(() =>
|
||||
Loom.QueueOnMainThread(async () =>
|
||||
{
|
||||
if (response.IsSuccess)
|
||||
{
|
||||
if (isOn)
|
||||
SetFingerprint();
|
||||
else
|
||||
{
|
||||
// 禁用指纹成功,同步到服务器
|
||||
await SyncFingerprintsToServerAsync();
|
||||
LoadingUI.Hide();
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -150,11 +154,13 @@ namespace Kill.UI.Pages
|
||||
{
|
||||
BLECommunicationManager.Instance.StartFingerprintRecord(nowUserid, (response) =>
|
||||
{
|
||||
Loom.QueueOnMainThread(() =>
|
||||
Loom.QueueOnMainThread(async () =>
|
||||
{
|
||||
if (response.IsSuccess)
|
||||
{
|
||||
fingerTip.SetActive(true);
|
||||
// 录制成功,同步到服务器
|
||||
await SyncFingerprintsToServerAsync();
|
||||
LoadingUI.Hide();
|
||||
}
|
||||
else
|
||||
@ -165,6 +171,14 @@ namespace Kill.UI.Pages
|
||||
});
|
||||
}
|
||||
|
||||
private async Task SyncFingerprintsToServerAsync()
|
||||
{
|
||||
if (!DataManager.Instance.hasWifi) return;
|
||||
await DataManager.Instance.UpdateFingerprintsToServer(
|
||||
DataManager.Instance.selectedDevice.device_sn,
|
||||
DataManager.Instance.fingerprintUserDatas);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 读取RGB设置
|
||||
/// </summary>
|
||||
|
||||
@ -171,6 +171,7 @@ namespace Kill.UI.Pages
|
||||
if (success)
|
||||
{
|
||||
SyncSleepConfig();
|
||||
DataManager.Instance.SyncDeviceConfigToServer();
|
||||
UpdateUI();
|
||||
}
|
||||
else
|
||||
|
||||
@ -80,6 +80,7 @@ namespace Kill.UI.Pages
|
||||
if (success)
|
||||
{
|
||||
SyncRGBConfig();
|
||||
DataManager.Instance.SyncDeviceConfigToServer();
|
||||
UpdateUI();
|
||||
}
|
||||
else
|
||||
|
||||
@ -124,6 +124,7 @@ namespace Kill.UI.Pages
|
||||
if (success)
|
||||
{
|
||||
SyncMultimediaConfig();
|
||||
DataManager.Instance.SyncDeviceConfigToServer();
|
||||
UpdateUI();
|
||||
}
|
||||
else
|
||||
|
||||
@ -372,6 +372,7 @@ namespace Kill.UI.Pages
|
||||
Debug.Log($"[FovSettingPage] 角度设置成功: {selectedAngle}°");
|
||||
currentAngle = selectedAngle;
|
||||
DataManager.Instance.deviceConfig.fov_angle = selectedAngle * 10;
|
||||
DataManager.Instance.SyncDeviceConfigToServer();
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -431,6 +432,7 @@ namespace Kill.UI.Pages
|
||||
vllEnabled = newVllState;
|
||||
UpdateVllButton();
|
||||
DataManager.Instance.deviceConfig.laser_visible_enable = newVllState;
|
||||
DataManager.Instance.SyncDeviceConfigToServer();
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -515,6 +517,7 @@ namespace Kill.UI.Pages
|
||||
currentAngle = originalAngle;
|
||||
selectedAngle = originalAngle;
|
||||
DataManager.Instance.deviceConfig.fov_angle = originalAngle * 10;
|
||||
DataManager.Instance.SyncDeviceConfigToServer();
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
@ -471,6 +471,7 @@ namespace Kill.UI.Pages
|
||||
{
|
||||
currentWorkMode = (WorkMode)mode;
|
||||
deviceCtrl?.InitWrokMode(mode);
|
||||
DataManager.Instance.deviceConfig.work_mode = DeviceConfig.ToServerString((WorkMode)mode);
|
||||
}
|
||||
return;
|
||||
}
|
||||
@ -511,6 +512,9 @@ namespace Kill.UI.Pages
|
||||
{
|
||||
deviceCtrl?.InitWrokMode(mode);
|
||||
});
|
||||
|
||||
DataManager.Instance.deviceConfig.work_mode = DeviceConfig.ToServerString(setting.Mode);
|
||||
DataManager.Instance.SyncDeviceConfigToServer();
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -1175,11 +1179,15 @@ namespace Kill.UI.Pages
|
||||
DeviceLockControl deviceLockControl = new DeviceLockControl();
|
||||
deviceLockControl.IsLocked = false;
|
||||
OnLockReceived(deviceLockControl);
|
||||
DataManager.Instance.deviceConfig.is_locked = false;
|
||||
DataManager.Instance.SyncDeviceConfigToServer();
|
||||
LoadingUI.Hide();
|
||||
}
|
||||
else
|
||||
{
|
||||
deviceCtrl.InitDeviceControl(false);
|
||||
DataManager.Instance.deviceConfig.is_locked = true;
|
||||
DataManager.Instance.SyncDeviceConfigToServer();
|
||||
LoadingUI.Hide();
|
||||
}
|
||||
|
||||
@ -1197,6 +1205,7 @@ namespace Kill.UI.Pages
|
||||
if (success)
|
||||
{
|
||||
Debug.Log($"[HomePageCtrl] WiFi锁定设置成功: {(lockControl.IsLocked ? "锁定" : "解锁")}");
|
||||
DataManager.Instance.deviceConfig.is_locked = lockControl.IsLocked;
|
||||
if (lockControl.IsLocked)
|
||||
{
|
||||
deviceCtrl?.InitDeviceControl(false);
|
||||
@ -1486,7 +1495,11 @@ namespace Kill.UI.Pages
|
||||
{
|
||||
Loom.QueueOnMainThread(() =>
|
||||
{
|
||||
|
||||
if (success)
|
||||
{
|
||||
DataManager.Instance.deviceConfig.language = isChinese ? 1 : 0;
|
||||
DataManager.Instance.SyncDeviceConfigToServer();
|
||||
}
|
||||
ReceiveStatus();
|
||||
|
||||
});
|
||||
|
||||
@ -454,6 +454,7 @@ namespace Kill.UI.Pages
|
||||
Debug.Log($"[LensSettingPage] 距离设置成功: {selectedLensValue}m");
|
||||
currentLensValue = selectedLensValue;
|
||||
DataManager.Instance.deviceConfig.detection_distance = (int)(selectedLensValue * 10);
|
||||
DataManager.Instance.deviceConfig.aim_distance = (int)(selectedLensValue * 10);
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -473,6 +474,8 @@ namespace Kill.UI.Pages
|
||||
Debug.Log($"[LensSettingPage] 距离设置成功: {selectedLensValue}m");
|
||||
currentLensValue = selectedLensValue;
|
||||
DataManager.Instance.deviceConfig.detection_distance = (int)(selectedLensValue * 10);
|
||||
DataManager.Instance.deviceConfig.aim_distance = (int)(selectedLensValue * 10);
|
||||
DataManager.Instance.SyncDeviceConfigToServer();
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -531,6 +534,7 @@ namespace Kill.UI.Pages
|
||||
vllEnabled = newVllState;
|
||||
UpdateVllButton();
|
||||
DataManager.Instance.deviceConfig.laser_visible_enable = newVllState;
|
||||
DataManager.Instance.SyncDeviceConfigToServer();
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -650,6 +654,7 @@ namespace Kill.UI.Pages
|
||||
currentLensValue = originalLensValue;
|
||||
selectedLensValue = originalLensValue;
|
||||
DataManager.Instance.deviceConfig.detection_distance = (ushort)Mathf.RoundToInt(originalLensValue * 10);
|
||||
DataManager.Instance.deviceConfig.aim_distance = (ushort)Mathf.RoundToInt(originalLensValue * 10);
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -673,6 +678,8 @@ namespace Kill.UI.Pages
|
||||
currentLensValue = originalLensValue;
|
||||
selectedLensValue = originalLensValue;
|
||||
DataManager.Instance.deviceConfig.detection_distance = (ushort)Mathf.RoundToInt(originalLensValue * 10);
|
||||
DataManager.Instance.deviceConfig.aim_distance = (ushort)Mathf.RoundToInt(originalLensValue * 10);
|
||||
DataManager.Instance.SyncDeviceConfigToServer();
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
@ -396,6 +396,7 @@ namespace Kill.UI.Pages
|
||||
{
|
||||
Debug.Log($"[LightSettingPage] 灯光设置成功: 开关={selectedLightEnabled}, 类型={selectedLightType}, 强度={selectedIntensity}");
|
||||
SyncLightConfigFromCurrent();
|
||||
DataManager.Instance.SyncDeviceConfigToServer();
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
@ -438,6 +438,7 @@ namespace Kill.UI.Pages
|
||||
{
|
||||
Debug.Log($"[SafetySettingPage] 视觉检测设置成功: 开关={selectedVisualEnabled}, 灵敏度={selectedVisualSensitivity}");
|
||||
SyncVisualConfig();
|
||||
DataManager.Instance.SyncDeviceConfigToServer();
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -498,6 +499,7 @@ namespace Kill.UI.Pages
|
||||
{
|
||||
Debug.Log($"[SafetySettingPage] 毫米波雷达设置成功: 灵敏度={selectedWaveSensitivity}");
|
||||
SyncRadarConfig();
|
||||
DataManager.Instance.SyncDeviceConfigToServer();
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -513,7 +515,9 @@ namespace Kill.UI.Pages
|
||||
private void SyncRadarConfig()
|
||||
{
|
||||
var config = DataManager.Instance.deviceConfig;
|
||||
config.radar_enable = true;
|
||||
config.radar_sensitivity = DeviceConfig.ToServerString(selectedWaveSensitivity);
|
||||
config.radar_safe_distance = 10;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
||||
@ -5,6 +5,7 @@ using Kill.Bluetooth;
|
||||
using Kill.Bluetooth.Protocol;
|
||||
using Kill.Core;
|
||||
using Kill.Managers;
|
||||
using Kill.Managers.ResponseModels;
|
||||
using Kill.UI.Components;
|
||||
using UnityEngine;
|
||||
using UnityEngine.UI;
|
||||
@ -607,7 +608,7 @@ namespace Kill.UI.Pages
|
||||
|
||||
BLECommunicationManager.Instance.WriteScheduleTasks(tasksToSave.ToArray(), (success) =>
|
||||
{
|
||||
Loom.QueueOnMainThread(() =>
|
||||
Loom.QueueOnMainThread(async () =>
|
||||
{
|
||||
// 隐藏Loading
|
||||
LoadingUI.Hide();
|
||||
@ -615,6 +616,28 @@ namespace Kill.UI.Pages
|
||||
if (success)
|
||||
{
|
||||
Debug.Log("[ScheduleSettingPage] 定时任务保存成功");
|
||||
|
||||
// WiFi在线时同步到服务器
|
||||
if (DataManager.Instance.hasWifi)
|
||||
{
|
||||
var tasksData = new List<ScheduleTaskData>();
|
||||
foreach (var t in tasksToSave)
|
||||
{
|
||||
tasksData.Add(new ScheduleTaskData
|
||||
{
|
||||
task_id = t.TaskId,
|
||||
enabled = t.Enabled,
|
||||
start_hour = t.StartHour,
|
||||
start_minute = t.StartMinute,
|
||||
end_hour = t.EndHour,
|
||||
end_minute = t.EndMinute,
|
||||
mode = ToModeString(t.Mode),
|
||||
repeat_mask = t.Repeat
|
||||
});
|
||||
}
|
||||
await DataManager.Instance.UpdateScheduleTasksToServer(
|
||||
DataManager.Instance.selectedDevice.device_sn, tasksData);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -636,6 +659,19 @@ namespace Kill.UI.Pages
|
||||
LoadingUI.Hide();
|
||||
Destroy(gameObject);
|
||||
}
|
||||
|
||||
private static string ToModeString(ScheduleTaskMode mode)
|
||||
{
|
||||
switch (mode)
|
||||
{
|
||||
case ScheduleTaskMode.Scan:
|
||||
return "SCAN";
|
||||
case ScheduleTaskMode.Sterilize:
|
||||
return "STERILIZE";
|
||||
default:
|
||||
return "STANDBY";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@ -18,9 +18,9 @@ PlayerSettings:
|
||||
cursorHotspot: {x: 0, y: 0}
|
||||
m_SplashScreenBackgroundColor: {r: 0.12156863, g: 0.12156863, b: 0.1254902, a: 1}
|
||||
m_ShowUnitySplashScreen: 0
|
||||
m_ShowUnitySplashLogo: 1
|
||||
m_ShowUnitySplashLogo: 0
|
||||
m_SplashScreenOverlayOpacity: 1
|
||||
m_SplashScreenAnimation: 1
|
||||
m_SplashScreenAnimation: 2
|
||||
m_SplashScreenLogoStyle: 1
|
||||
m_SplashScreenDrawMode: 0
|
||||
m_SplashScreenBackgroundAnimationZoom: 1
|
||||
@ -39,7 +39,11 @@ PlayerSettings:
|
||||
y: 0
|
||||
width: 1
|
||||
height: 1
|
||||
m_SplashScreenLogos: []
|
||||
m_SplashScreenLogos:
|
||||
- logo: {fileID: 21300000, guid: 0ddd579c89aad104fba3a316bd6c82fa, type: 3}
|
||||
duration: 2
|
||||
- logo: {fileID: 21300000, guid: ca5bf37fb627d9e4690c05d832243763, type: 3}
|
||||
duration: 2
|
||||
m_VirtualRealitySplashScreen: {fileID: 0}
|
||||
m_HolographicTrackingLossScreen: {fileID: 0}
|
||||
defaultScreenWidth: 1920
|
||||
@ -269,7 +273,7 @@ PlayerSettings:
|
||||
AndroidTargetArchitectures: 2
|
||||
AndroidTargetDevices: 1
|
||||
AndroidSplashScreenScale: 0
|
||||
androidSplashScreen: {fileID: 0}
|
||||
androidSplashScreen: {fileID: 2800000, guid: 0ddd579c89aad104fba3a316bd6c82fa, type: 3}
|
||||
AndroidKeystoreName:
|
||||
AndroidKeyaliasName:
|
||||
AndroidEnableArmv9SecurityFeatures: 0
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user