Sfoglia il codice sorgente

模块问题,自动休眠和启动

lvjincheng 4 anni fa
parent
commit
19e4d0a37e

+ 340 - 4
Assets/BowArrow/Scripts/Bluetooth/BluetoothAim.cs

@@ -23,6 +23,7 @@ public class BluetoothAim : MonoBehaviour
 
     void Start() {
         ins = this;
+        InitAutoDormancy();
     }
 
     void OnDestroy()
@@ -53,6 +54,7 @@ public class BluetoothAim : MonoBehaviour
         canConnect = true;
         SetStatus(BluetoothStatusEnum.ConnectFail);
         BowCamera.isTouchMode = true;
+        DestroyWhenDisconenct();
     }
 
     void Update()
@@ -126,9 +128,13 @@ public class BluetoothAim : MonoBehaviour
                         }
                     }
                 }
-                CallDelay(1, OpenInfrared);
-                CallDelay(2, OpenReceiveData);
-                CallDelay(3, RequestBattery);
+                // CallDelay(1, OpenInfrared);
+                // CallDelay(2, OpenReceiveData);
+                // CallDelay(3, RequestBattery);
+                CallDelay(2, () => {
+                    if (status != BluetoothStatusEnum.ConnectSuccess) return;
+                    InitWhenConenct();
+                });
             };
             bluetoothHelper.OnConnectionFailed += (BluetoothHelper helper) =>
             {
@@ -177,6 +183,120 @@ public class BluetoothAim : MonoBehaviour
         }
     }
 
+    #region 自动进入/退出休眠状态, 这里做程指令发送队列,为了控制连续发送指令的间隔,避免硬件收不到或处理不过来
+        class CmdToSend {
+            public string[] cmds;
+            public Action onComplete;
+            public Func<bool> canDo; 
+            public CmdToSend(string[] cmds, Action onComplete, Func<bool> canDo) {
+                this.cmds = cmds; 
+                this.onComplete = onComplete;
+                this.canDo = canDo;
+            }
+        }
+        Queue<CmdToSend> cmdWaitingList = new Queue<CmdToSend>();
+        bool isSendCmdLocked = false;
+        bool canAutoDormancy = false;
+        bool isStartUp = false;
+        JC.CS.CountLocker needModularAwake = new JC.CS.CountLocker();
+        void CheckAndStartUp() {
+            if (needModularAwake.IsLocked()) {
+                StartUp();
+            } else {
+                Dormancy();
+            }
+        }
+        void InitAutoDormancy() {
+            GlobalEventCenter.ins.onGameSceneLoad += () => { 
+                needModularAwake.Lock(); 
+                CheckAndStartUp();
+            };
+            GlobalEventCenter.ins.onGameSceneDestroy += () => { 
+                needModularAwake.Unlock(); 
+                CheckAndStartUp();
+            };
+            GlobalEventCenter.ins.onSimulateMouseAwakeChanged += (waked) => {
+                if (waked) needModularAwake.Lock();
+                else needModularAwake.Unlock();;
+                CheckAndStartUp();
+            };
+        }
+        void InitWhenConenct() { 
+            canAutoDormancy = true;
+            //刚连上时先获取电量
+            SendCDM(null, () => {
+                CheckAndStartUp();
+            }, "b", "b");
+        }
+        void DestroyWhenDisconenct() {
+            canAutoDormancy = false;
+            sendCMD_CheckAndDoStop(null);
+
+        }
+        //启动
+        void StartUp() {
+            SendCDM(() => {
+                return !isStartUp;
+            }, () => {
+                isStartUp = true;
+            }, "b", "w", "1", "3");
+        }
+        //休眠
+        void Dormancy() {
+            SendCDM(() => {
+                return isStartUp;
+            }, () => {
+                isStartUp = false;
+            }, "4", "s", "S");
+        }
+        void SendCDM(Func<bool> canDo, Action onComplete, params string[] cmds) {
+            CmdToSend cmdToSend = new CmdToSend(cmds, onComplete, canDo);
+            if (isSendCmdLocked) {
+                cmdWaitingList.Enqueue(cmdToSend);
+                return;
+            }
+            sendCMD_NotCheck(cmdToSend);
+        }   
+        void sendCMD_NotCheck(CmdToSend cmdToSend) {
+            if (cmdToSend.canDo != null && !cmdToSend.canDo.Invoke()) {
+                sendCMD_CheckNext();
+                return;
+            }
+            isSendCmdLocked = true;
+            Sequence sequence = DOTween.Sequence();
+            foreach (var cmd in cmdToSend.cmds) {
+                sequence.AppendCallback(() => {
+                    bool stopped = sendCMD_CheckAndDoStop(sequence);
+                    if (!stopped) WriteData(cmd);
+                });
+                sequence.AppendInterval(0.5f);
+            }
+            sequence.AppendCallback(() => {
+                bool stopped = sendCMD_CheckAndDoStop(sequence);
+                if (!stopped) {
+                    isSendCmdLocked = false;
+                    cmdToSend.onComplete?.Invoke();
+                    sendCMD_CheckNext();
+                }
+            });
+            sequence.SetUpdate(true);
+        }
+        void sendCMD_CheckNext() {
+            if (cmdWaitingList.Count <= 0) return;
+            CmdToSend cmdToSend = cmdWaitingList.Dequeue();
+            sendCMD_NotCheck(cmdToSend);
+        }
+        bool sendCMD_CheckAndDoStop(Sequence sequence) {
+            if (canAutoDormancy) return false;
+            isStartUp = false;
+            isSendCmdLocked = false;
+            cmdWaitingList.Clear();
+            if (sequence != null) sequence.Kill();
+            return true;
+        }
+    #endregion
+
+
     void OpenInfrared()
     {
         WriteData("1");
@@ -190,10 +310,13 @@ public class BluetoothAim : MonoBehaviour
     }
 
     public void RequestBattery() {
+        if (!isStartUp) return;
+        if (isSendCmdLocked) return;
         WriteData("b");
     }
 
     public void ReplyInfraredShoot() {
+        if (isSendCmdLocked) return;
         WriteData("I");
     }
 
@@ -218,4 +341,217 @@ public class BluetoothAim : MonoBehaviour
             textUI.text = text;
         }
     }
-}
+}
+// public class BluetoothAim : MonoBehaviour
+// {
+//     BluetoothHelper bluetoothHelper;
+//     BluetoothHelperCharacteristic characteristicWrite;
+//     BluetoothHelperService bluetoothService;
+//     string targetDeviceName = "Bbow_20210501";
+//     string deviceName = "";
+//     bool canConnect = true;
+//     [SerializeField] Text textUI;
+//     public BluetoothStatusEnum status = BluetoothStatusEnum.Connect;
+//     public bool hasData = false;
+//     public long hasDataTime;
+//     public static bool scanLock = false; //防止同时扫描冲突
+//     public static BluetoothAim ins;
+
+//     void Start() {
+//         ins = this;
+//     }
+
+//     void OnDestroy()
+//     {
+//         if (bluetoothHelper != null)
+//         {
+//             bluetoothHelper.Disconnect();
+//         }
+//     }
+
+//     private bool userDoConnect = false;
+//     private bool doConnect = false;
+//     public void DoConnect() {
+//         if (status == BluetoothStatusEnum.Connect) {
+//             userDoConnect = true;
+//             doConnect = true;
+//             SetStatus(BluetoothStatusEnum.Connecting);
+//         } else if (status == BluetoothStatusEnum.ConnectSuccess) {
+//             userDoConnect = false;
+//             doConnect = false;
+//             OnDisconnect();
+//             bluetoothHelper.Disconnect();
+//         }
+//     }
+
+//     void OnDisconnect() {
+//         hasData = false;
+//         canConnect = true;
+//         SetStatus(BluetoothStatusEnum.ConnectFail);
+//         BowCamera.isTouchMode = true;
+//     }
+
+//     void Update()
+//     {
+//         if (userDoConnect && status == BluetoothStatusEnum.Connect) {
+//             DoConnect();
+//         }
+//         if (doConnect) Connect();
+//     }
+
+//     void SetStatus(BluetoothStatusEnum statusValue) 
+//     {
+//         status = statusValue;
+//         if (status == BluetoothStatusEnum.ConnectFail) {
+//             Sequence sequence = DOTween.Sequence();
+//             sequence.AppendInterval(2f);
+//             sequence.AppendCallback(delegate() {
+//                 if (status == BluetoothStatusEnum.ConnectFail) {
+//                     status = BluetoothStatusEnum.Connect;        
+//                 }
+//             });
+//             sequence.SetUpdate(true);
+//             DeviceReconnectView.Show();
+//         }
+//     }
+
+//     void Connect()
+//     {
+//         if (BluetoothShoot.scanLock)
+//         {
+//             return;
+//         }
+//         if (!canConnect)
+//         {
+//             return;
+//         }
+//         doConnect = false;
+//         scanLock = true;
+//         canConnect = false;
+//         SetStatus(BluetoothStatusEnum.Connecting);
+//         try
+//         {
+//             BluetoothHelper.BLE = true;
+//             bluetoothHelper = BluetoothHelper.GetNewInstance();
+
+//             bluetoothHelper.OnConnected += (BluetoothHelper helper) =>
+//             {
+//                 Log("连接成功\n" + helper.getDeviceName());
+//                 SetStatus(BluetoothStatusEnum.ConnectSuccess);
+//                 BowCamera.isTouchMode = false;
+//                 foreach (BluetoothHelperService service in helper.getGattServices())
+//                 {
+                
+//                     if (service.getName().ToLower().StartsWith("0000fff0"))
+//                     {
+//                         bluetoothService = service;
+
+//                         foreach (BluetoothHelperCharacteristic characteristic in service.getCharacteristics())
+//                         {
+//                             if (characteristic.getName().ToLower().StartsWith("0000fff2"))
+//                             {
+//                                 characteristicWrite = characteristic;
+//                             }
+//                             else if (characteristic.getName().ToLower().StartsWith("0000fff1"))
+//                             {
+
+//                                 BluetoothHelperCharacteristic ch = new BluetoothHelperCharacteristic(characteristic.getName());
+//                                 ch.setService(bluetoothService.getName());
+//                                 bluetoothHelper.Subscribe(ch);
+//                             }
+//                         }
+//                     }
+//                 }
+//                 CallDelay(1, OpenInfrared);
+//                 CallDelay(2, OpenReceiveData);
+//                 CallDelay(3, RequestBattery);
+//             };
+//             bluetoothHelper.OnConnectionFailed += (BluetoothHelper helper) =>
+//             {
+//                 Log("连接失败\n" + helper.getDeviceName());
+//                 OnDisconnect();
+//             };
+//             bluetoothHelper.OnCharacteristicChanged += (helper, value, characteristic) =>
+//             {
+//                 if (!hasData) hasDataTime = JC.CS.Utility.GetTimestamp();
+//                 hasData = true;
+//                 byte[] bytes = value;
+//                 // Log(String.Join(",", bytes));
+//                 BluetoothClient.UploadData(0, bytes);
+//                 if (AimHandler.ins)
+//                 {
+//                     AimHandler.ins.OnDataReceived(bytes);
+//                 }
+//             };
+//             bluetoothHelper.OnScanEnded += (BluetoothHelper helper, LinkedList<BluetoothDevice> nearbyDevices) =>
+//             {
+//                 scanLock = false;
+//                 foreach (BluetoothDevice device in nearbyDevices)
+//                 {
+//                     if (device.DeviceName == targetDeviceName)
+//                     {
+//                         deviceName = device.DeviceName;
+//                         bluetoothHelper.setDeviceName(deviceName);
+//                         bluetoothHelper.Connect();
+//                         Log("发现设备\n" + device.DeviceName);
+//                         return;
+//                     }
+//                 }
+//                 canConnect = true;
+//                 Log("没有发现设备");
+//                 SetStatus(BluetoothStatusEnum.ConnectFail);
+//             };
+
+//             bluetoothHelper.ScanNearbyDevices();
+//             Log("正在扫描设备");
+//         }
+//         catch (Exception e)
+//         {
+//             Debug.Log(e.Message);
+//             canConnect = true;
+//             Log("请打开蓝牙");
+//         }
+//     }
+
+//     void OpenInfrared()
+//     {
+//         WriteData("1");
+//         Log("红外线准备完成\n" + deviceName);
+//     }
+
+//     void OpenReceiveData()
+//     {
+//         WriteData("3");
+//         Log("瞄准模块准备完成\n" + deviceName);
+//     }
+
+//     public void RequestBattery() {
+//         WriteData("b");
+//     }
+
+//     public void ReplyInfraredShoot() {
+//         WriteData("I");
+//     }
+
+//     void CallDelay(float delayTime, TweenCallback callback)
+//     {
+//         Sequence sequence = DOTween.Sequence();
+//         sequence.PrependInterval(delayTime).AppendCallback(callback);
+//         sequence.SetUpdate(true);
+//     }
+
+//     public void WriteData(string data)
+//     {
+//         BluetoothHelperCharacteristic ch = new BluetoothHelperCharacteristic(characteristicWrite.getName());
+//         ch.setService(bluetoothService.getName());
+//         bluetoothHelper.WriteCharacteristic(ch, data);
+//     }
+
+//     void Log(string text)
+//     {
+//         if (textUI) 
+//         {
+//             textUI.text = text;
+//         }
+//     }
+// }

+ 8 - 0
Assets/BowArrow/Scripts/Event.meta

@@ -0,0 +1,8 @@
+fileFormatVersion: 2
+guid: 251f8dc086098524a9a62f63f9297e04
+folderAsset: yes
+DefaultImporter:
+  externalObjects: {}
+  userData: 
+  assetBundleName: 
+  assetBundleVariant: 

+ 1 - 1
Assets/BowArrow/Scripts/Game/GameEventCenter.cs → Assets/BowArrow/Scripts/Event/GameEventCenter.cs

@@ -11,7 +11,7 @@ public class GameEventCenter : MonoBehaviour
     public static GameEventCenter ins {
         get {
             if (!_ins) {
-                _ins = new GameObject().AddComponent<GameEventCenter>();
+                _ins = new GameObject("GameEventCenter").AddComponent<GameEventCenter>();
             }
             return _ins;
         }

+ 0 - 0
Assets/BowArrow/Scripts/Game/GameEventCenter.cs.meta → Assets/BowArrow/Scripts/Event/GameEventCenter.cs.meta


+ 21 - 0
Assets/BowArrow/Scripts/Event/GlobalEventCenter.cs

@@ -0,0 +1,21 @@
+using System.Collections;
+using System.Collections.Generic;
+using UnityEngine;
+
+public class GlobalEventCenter : MonoBehaviour
+{
+    public System.Action onGameSceneLoad;
+    public System.Action onGameSceneDestroy;
+    public System.Action<bool> onSimulateMouseAwakeChanged; //Param0:激活/熄灭
+
+    private static GlobalEventCenter _ins;
+    public static GlobalEventCenter ins {
+        get {
+            if (!_ins) {
+                _ins = new GameObject("GlobalEventCenter").AddComponent<GlobalEventCenter>();
+                DontDestroyOnLoad(_ins);
+            }
+            return _ins;
+        }
+    }
+}

+ 11 - 0
Assets/BowArrow/Scripts/Event/GlobalEventCenter.cs.meta

@@ -0,0 +1,11 @@
+fileFormatVersion: 2
+guid: 41578b61832bf634dab5a5eccc95c1f5
+MonoImporter:
+  externalObjects: {}
+  serializedVersion: 2
+  defaultReferences: []
+  executionOrder: 0
+  icon: {instanceID: 0}
+  userData: 
+  assetBundleName: 
+  assetBundleVariant: 

+ 3 - 0
Assets/BowArrow/Scripts/Expand/SB_EventSystem.cs

@@ -61,6 +61,9 @@ public class SB_EventSystem : MonoBehaviour
             simulateMouseIsAwaked = !simulateMouse.gameObject.activeSelf;
             simulateMouse.gameObject.SetActive(simulateMouseIsAwaked);
             hasAxisQuat = false;
+             try { 
+                GlobalEventCenter.ins.onSimulateMouseAwakeChanged?.Invoke(simulateMouseIsAwaked); 
+            } catch (System.Exception e) { Debug.LogError(e.Message); }
         }
     #endregion 鼠标激活/关闭
 

+ 6 - 0
Assets/BowArrow/Scripts/Manager/GameMgr.cs

@@ -41,10 +41,16 @@ public class GameMgr : MonoBehaviour
 
     void Start() 
     {
+        try { 
+            GlobalEventCenter.ins.onGameSceneLoad?.Invoke(); 
+        } catch (System.Exception e) { Debug.LogError(e.Message); }
         if (ShootCheck.ins) ShootCheck.ins.AdjustNormalOrHightMode();
     }
 
     void OnDestroy() {
+        try { 
+            GlobalEventCenter.ins.onGameSceneDestroy?.Invoke(); 
+        } catch (System.Exception e) { Debug.LogError(e.Message); }
         if (AimHandler.ins) AimHandler.ins.BanControlObjRotate(false);
     }