HDL Home App 第二版本 旧平台金堂用 正在使用
chenqiyang
2022-06-22 dc0309e64f02227d8e1468b7326c07955f804612
ZigbeeApp/Shared/Phone/UserCenter/CommonBase/Logic/HdlACZbGatewayUpdateLogic.cs
old mode 100755 new mode 100644
@@ -1,517 +1,525 @@
using System;
using System.Collections.Generic;
using System.Text;
using ZigBee.Device;
namespace Shared.Phone.UserCenter
{
    /// <summary>
    /// 中央空调的升级逻辑
    /// </summary>
    public class HdlACZbGatewayUpdateLogic : HdlDeviceUpdateCommonLogic
    {
        #region ■ 变量声明___________________________
        /// <summary>
        /// <para>更新状态变化的事件</para>
        /// <para>第一个参数为:</para>
        /// <para>-1:更新异常,后面的值为异常信息的翻译文本</para>
        /// <para> 0:更新状态正常变化,后面的值为状态变更的文本翻译</para>
        /// <para> 1:升级成功</para>
        /// <para> 2:主动终止升级(中央空调木允许终止)</para>
        /// <para> 3:从等待中取消(目前还没有用)</para>
        /// </summary>
        public Action<int, string> UpdateStatuChangedEvent = null;
        /// <summary>
        /// 进度值事件
        /// </summary>
        public Action<decimal> ProgressEvent = null;
        /// <summary>
        /// 设备新版本的固件信息(多个设备升级时,应该会需要公开这个对象)
        /// </summary>
        public FirmwareVersionInfo deviceFirmware = null;
        /// <summary>
        /// 网关
        /// </summary>
        private ZbGateway zbGateway = null;
        /// <summary>
        /// 升级的设备
        /// </summary>
        private OTADevice otaDevice = null;
        /// <summary>
        /// 设备对象
        /// </summary>
        private AC deviceAc = null;
        /// <summary>
        /// 前一次的最终状态
        /// </summary>
        private UpdateStatuMode oldUpdateStatu = UpdateStatuMode.None;
        /// <summary>
        /// 固件的byte数组
        /// </summary>
        private byte[] deviceFirmwareByte = null;
        #endregion
        #region ■ 初始化_____________________________
        /// <summary>
        /// <para>HDL设备升级,以下为两个重要事件</para>
        /// <para>UpdateStatuChangedEvent:更新状态变化的事件</para>
        /// <para>ProgressEvent:进度值事件</para>
        /// <para>StartUpdateReady():设备开始执行升级的函数,在调用这个之前,请先实现上面两个方法</para>
        /// </summary>
        /// <param name="i_deviceAc">设备</param>
        /// <param name="i_deviceFirmware">设备的固件信息</param>
        public HdlACZbGatewayUpdateLogic(AC i_deviceAc, FirmwareVersionInfo i_deviceFirmware)
        {
            this.ClassDiv = 2;
            this.deviceAc = i_deviceAc;
            this.otaDevice = Common.LocalDevice.Current.GetOTADevice(i_deviceAc.DeviceAddr);
            this.deviceFirmware = i_deviceFirmware;
            this.zbGateway = i_deviceAc.Gateway;
        }
        #endregion
        #region ■ 开始更新___________________________
        /// <summary>
        /// 进入执行更新操作准备阶段
        /// </summary>
        public void StartUpdateReady()
        {
            if (this.UpdateStatu == UpdateStatuMode.Wait)
            {
                //如果是等待模式,再次点击时,移除列表
                if (FirmwareUpdateResourse.dicUpdateList.ContainsKey(otaDevice.DeviceAddr) == true)
                {
                    FirmwareUpdateResourse.dicUpdateList.Remove(otaDevice.DeviceAddr);
                }
                //取消
                this.UpdateStatu = UpdateStatuMode.None;
                this.UpdateStatuChangedEvent?.Invoke(3, "");
                return;
            }
            //如果它有状态,则表示之前它被什么错误中断了
            if (this.UpdateStatu != UpdateStatuMode.None)
            {
                //保存起来,后面有用处
                this.oldUpdateStatu = this.UpdateStatu;
            }
            //进入等待模式
            this.UpdateStatu = UpdateStatuMode.Wait;
            FirmwareUpdateResourse.dicUpdateList[otaDevice.DeviceAddr] = this;
            //等待中…
            this.UpdateStatuChangedEvent?.Invoke(0, Language.StringByID(R.MyInternationalizationString.uWaitting));
            //执行下一个可更新的固件的更新操作
            HdlFirmwareUpdateLogic.DoUpdateNextFirmware();
        }
        /// <summary>
        /// 开始执行更新操作
        /// </summary>
        public override void DoStartUpdate()
        {
            //状态变更
            this.IsFinishUpdate = false;
            this.UpdateStatu = UpdateStatuMode.Action;
            //根据状态执行操作
            this.DoAdjustByStatuMode();
        }
        /// <summary>
        /// 根据状态执行操作
        /// </summary>
        private void DoAdjustByStatuMode()
        {
            //先这样写吧,有可能以后会分情况
            //首发时,从开始执行
            if (this.oldUpdateStatu == UpdateStatuMode.None)
            {
                //执行校验版本
                this.DoCheckVersion();
            }
            //设备下载失败
            else if (this.oldUpdateStatu == UpdateStatuMode.DeviceDownLoadFail)
            {
                //执行校验版本
                this.DoCheckVersion();
            }
            //设备升级失败
            else if (this.oldUpdateStatu == UpdateStatuMode.DeviceUpdateFail)
            {
                //执行校验版本
                this.DoCheckVersion();
            }
            else
            {
                //重新再来
                this.DoCheckVersion();
            }
        }
        #endregion
        #region ■ 校验版本___________________________
        /// <summary>
        /// 校验版本
        /// </summary>
        private async void DoCheckVersion()
        {
            this.UpdateStatu = UpdateStatuMode.DeviceUpdateReady;
            //检测设备版本
            this.UpdateStatuChangedEvent?.Invoke(0, Language.StringByID(R.MyInternationalizationString.uCheckDeviceVersion));
            //设置初始值
            this.SetProgressValue(0, 100);
            await System.Threading.Tasks.Task.Delay(1000);
            //下载固件资源
            var pra = new { RequestVersion = Common.CommonPage.RequestVersion, DistributedMark = this.deviceFirmware.DistributedMark };
            this.deviceFirmwareByte = await Common.CommonPage.Instance.RequestHttpsZigbeeBytesResultAsync("FirmwareMana/DownloadPlatformUploadFirmware", Encoding.UTF8.GetBytes(Newtonsoft.Json.JsonConvert.SerializeObject(pra)));
            if (this.deviceFirmwareByte == null)
            {
                //设备固件资源下载失败
                this.ShowErrorMsg(Language.StringByID(R.MyInternationalizationString.uDeviceFirmwareDownLoadFail));
                //显示重新下载模式
                this.ShowReDownLoadMode();
                this.UpdateStatu = UpdateStatuMode.DeviceDownLoadFail;
                return;
            }
            //数据偏移量,每个分包偏移量+(1-43)
            string offset = string.Empty;
            //一次发送的数据长度
            int dataLength = -1;
            //接收网关的透传数据
            Action<string, object> receiveAction = (comand, pushData) =>
            {
                string receiveData = ((CommonDevice.ClientDataPassthroughResponseData)pushData).PassData;
                if (receiveData.Length < 6)
                {
                    return;
                }
                try
                {
                    var command = receiveData[4].ToString() + receiveData[5].ToString() + receiveData[2].ToString() + receiveData[3].ToString();
                    if (command == "025c")
                    {
                        offset = receiveData.Substring(10, 8);
                        dataLength = Convert.ToInt32(receiveData.Substring(18, 2), 16);
                    }
                }
                catch { }
            };
            this.zbGateway.ReportAction += receiveAction;
            //读取空调模块版本
            var result = await HdlDeviceAirConditionerLogic.Current.ReadACFirewareVersionAsync(deviceAc);
            if (result == null || result.readACFirewareVersionResponData == null || result.readACFirewareVersionResponData.Status != 0)
            {
                //获取空调模块版本失败
                this.ShowErrorMsg(Language.StringByID(R.MyInternationalizationString.uGetAirConditionerModelVersionFail));
                //显示重新安装
                this.ShowReSetupMsg();
                this.UpdateStatu = UpdateStatuMode.DeviceUpdateFail;
                this.zbGateway.ReportAction -= receiveAction;
                //发送失败给设备
                HdlDeviceAirConditionerLogic.Current.SendFinishAsync(deviceAc, 1);
                return;
            }
            //发送升级通知
            var result2 = await HdlDeviceAirConditionerLogic.Current.UpggradeACNotificationAsync(deviceAc, result.readACFirewareVersionResponData.FirewareVersion, this.deviceFirmwareByte.Length);
            if (result2.responseData == null)
            {
                //发送升级命令失败
                this.ShowErrorMsg(Language.StringByID(R.MyInternationalizationString.uSendUpdateComandFail));
                //显示重新安装
                this.ShowReSetupMsg();
                this.UpdateStatu = UpdateStatuMode.DeviceUpdateFail;
                this.zbGateway.ReportAction -= receiveAction;
                //发送失败给设备
                HdlDeviceAirConditionerLogic.Current.SendFinishAsync(deviceAc, 1);
                return;
            }
            else if (result2.responseData.status == 1)
            {
                //版本号相同,升级失败
                this.ShowErrorMsg(Language.StringByID(R.MyInternationalizationString.uVersionIsEqualAndUpdateFail));
                //显示重新安装
                this.ShowReSetupMsg();
                this.UpdateStatu = UpdateStatuMode.DeviceUpdateFail;
                this.zbGateway.ReportAction -= receiveAction;
                //发送失败给设备
                HdlDeviceAirConditionerLogic.Current.SendFinishAsync(deviceAc, 1);
                return;
            }
            else if (result2.responseData.status != 0)
            {
                //校验版本号失败
                this.ShowErrorMsg(Language.StringByID(R.MyInternationalizationString.uCheckVersionFail));
                //显示重新安装
                this.ShowReSetupMsg();
                this.UpdateStatu = UpdateStatuMode.DeviceUpdateFail;
                this.zbGateway.ReportAction -= receiveAction;
                //发送失败给设备
                HdlDeviceAirConditionerLogic.Current.SendFinishAsync(deviceAc, 1);
                return;
            }
            int timeOut = 0;
            //等待接收偏移量
            while (dataLength == -1)
            {
                timeOut++;
                if (timeOut >= 30)
                {
                    //响应超时,检测设备版本失败
                    this.ShowErrorMsg(Language.StringByID(R.MyInternationalizationString.uResponseTimeoutsAndCheckDeviceVersionFail));
                    //显示重新安装
                    this.ShowReSetupMsg();
                    this.UpdateStatu = UpdateStatuMode.DeviceUpdateFail;
                    this.zbGateway.ReportAction -= receiveAction;
                    //发送失败给设备
                    HdlDeviceAirConditionerLogic.Current.SendFinishAsync(deviceAc, 1);
                    return;
                }
                await System.Threading.Tasks.Task.Delay(1000);
                //设置进度值
                this.SetProgressValue(timeOut, 30);
            }
            this.zbGateway.ReportAction -= receiveAction;
            //执行设备升级操作
            this.DoSetUpdateDevice(offset, dataLength);
        }
        #endregion
        #region ■ 设备升级___________________________
        /// <summary>
        /// 执行设备升级操作
        /// </summary>
        private async void DoSetUpdateDevice(string i_offset, int i_dataLength)
        {
            this.UpdateStatu = UpdateStatuMode.DeviceUpdateReady;
            //设备正在升级…
            this.UpdateStatuChangedEvent?.Invoke(0, Language.StringByID(R.MyInternationalizationString.uDeviceUpdating));
            //设置初始值
            this.SetProgressValue(0, 100);
            await System.Threading.Tasks.Task.Delay(1000);
            //发送数据的索引
            int startIndex = 0;
            int allDataLength = this.deviceFirmwareByte.Length;
            int timeOut = 0;
            //是否接收到成功命令
            bool receiveSuccess = false;
            //接收网关的透传数据
            bool hadReceive = true;
            Action<string, object> receiveAction = (comand, pushData) =>
            {
                if (comand != "DeviceRequestAcUpdateData")
                {
                    return;
                }
                string receiveData = ((CommonDevice.ClientDataPassthroughResponseData)pushData).PassData;
                if (receiveData.Length < 6)
                {
                    return;
                }
                try
                {
                    var command = receiveData[4].ToString() + receiveData[5].ToString() + receiveData[2].ToString() + receiveData[3].ToString();
                    if (command == "025c")
                    {
                        i_offset = receiveData.Substring(10, 8);
                        i_dataLength = Convert.ToInt32(receiveData.Substring(18, 2), 16);
                        hadReceive = true;
                        timeOut = 0;
                        //设置进度值
                        this.SetProgressValue(startIndex, allDataLength);
                    }
                    else if (command == "025e")
                    {
                        //成功  设置进度值直接100%
                        this.SetProgressValue(allDataLength, allDataLength);
                        receiveSuccess = true;
                        timeOut = 0;
                    }
                }
                catch { }
            };
            this.zbGateway.ReportAction += receiveAction;
            //最后一次需要等待回复结果才往下走
            while (startIndex < allDataLength)
            {
                if (receiveSuccess == true)
                {
                    //已经接收到成功的命令
                    break;
                }
                if (hadReceive == false)
                {
                    timeOut++;
                    if (timeOut >= 1500)
                    {
                        //响应超时,升级失败
                        this.ShowErrorMsg(Language.StringByID(R.MyInternationalizationString.uResponseTimeoutsAndUpdateFail));
                        //显示重新安装
                        this.ShowReSetupMsg();
                        this.UpdateStatu = UpdateStatuMode.DeviceUpdateFail;
                        this.zbGateway.ReportAction -= receiveAction;
                        //发送失败给设备
                        HdlDeviceAirConditionerLogic.Current.SendFinishAsync(deviceAc, 1);
                        return;
                    }
                    await System.Threading.Tasks.Task.Delay(50);
                    continue;
                }
                hadReceive = false;
                //因为偏移量是高位在前,所以倒过来
                string Myoffset = string.Empty;
                for (int i = 6; i >= 0; i = i - 2)
                {
                    Myoffset += i_offset.Substring(i, 2);
                }
                startIndex = Convert.ToInt32(Myoffset, 16) - i_dataLength;
                //获取一次能够发送的byte
                var listData = new List<byte>();
                for (; startIndex < allDataLength; startIndex++)
                {
                    listData.Add(this.deviceFirmwareByte[startIndex]);
                    if (listData.Count == i_dataLength)
                    {
                        break;
                    }
                }
                //发送透传数据
                var sendData = new HdlDeviceAirConditionerLogic.SendUpgradeData() { dataLength = i_dataLength, offset = i_offset };
                sendData.databytes = listData.ToArray();
                HdlDeviceAirConditionerLogic.Current.UpgradeAsync(deviceAc, sendData);
            }
            this.zbGateway.ReportAction -= receiveAction;
            //发送结束命令
            this.DoSendFinishComand();
        }
        #endregion
        #region ■ 分包结束___________________________
        /// <summary>
        /// 发送结束命令
        /// </summary>
        private async void DoSendFinishComand()
        {
            //正在发送升级完成的命令
            this.UpdateStatuChangedEvent?.Invoke(0, Language.StringByID(R.MyInternationalizationString.uSendingFinishUpdateComand));
            //发送成功命令给设备
            HdlDeviceAirConditionerLogic.Current.SendFinishAsync(deviceAc, 0);
            //等个两秒钟吧
            await System.Threading.Tasks.Task.Delay(2000);
            //显示升级完成的信息
            this.ShowFinishMsg();
        }
        #endregion
        #region ■ 设置进度___________________________
        /// <summary>
        /// 设定进度值
        /// </summary>
        /// <param name="value">进度值</param>
        /// <param name="maxValue">maxValue</param>
        private void SetProgressValue(decimal value, decimal maxValue)
        {
            this.ProgressEvent?.Invoke(value / maxValue);
        }
        /// <summary>
        /// 设置错误信息
        /// </summary>
        /// <param name="value"></param>
        private void ShowErrorMsg(string value)
        {
            this.UpdateStatuChangedEvent?.Invoke(-1, value);
        }
        #endregion
        #region ■ 升级完成提示_______________________
        /// <summary>
        /// 显示升级完成的信息
        /// </summary>
        private void ShowFinishMsg()
        {
            //状态变更
            this.IsFinishUpdate = true;
            //升级完成
            this.UpdateStatu = UpdateStatuMode.UpdateFinish;
            HdlFirmwareUpdateLogic.DoUpdateNextFirmware();
            //设备升级成功!
            this.UpdateStatuChangedEvent?.Invoke(1, Language.StringByID(R.MyInternationalizationString.uDeviceUpdateSuccess));
        }
        #endregion
        #region ■ 处理结果提示_______________________
        /// <summary>
        /// 显示重新安装的信息
        /// </summary>
        private void ShowReSetupMsg()
        {
            //状态变更
            this.IsFinishUpdate = true;
            //执行下一个升级
            HdlFirmwareUpdateLogic.DoUpdateNextFirmware();
        }
        /// <summary>
        /// 显示重新下载模式
        /// </summary>
        private void ShowReDownLoadMode()
        {
            //状态变更
            this.IsFinishUpdate = true;
            //执行下一个升级
            HdlFirmwareUpdateLogic.DoUpdateNextFirmware();
        }
        #endregion
        #region ■ 释放缓存___________________________
        /// <summary>
        /// 释放缓存
        /// </summary>
        public override void Dispose()
        {
            this.ProgressEvent = null;
            this.UpdateStatuChangedEvent = null;
        }
        #endregion
    }
}
using System;
using System.Collections.Generic;
using System.Text;
using ZigBee.Device;
namespace Shared.Phone.UserCenter
{
    /// <summary>
    /// 中央空调的升级逻辑
    /// </summary>
    public class HdlACZbGatewayUpdateLogic : HdlDeviceUpdateCommonLogic
    {
        #region ■ 变量声明___________________________
        /// <summary>
        /// <para>更新状态变化的事件</para>
        /// <para>第一个参数为:</para>
        /// <para>-1:更新异常,后面的值为异常信息的翻译文本</para>
        /// <para> 0:更新状态正常变化,后面的值为状态变更的文本翻译</para>
        /// <para> 1:升级成功</para>
        /// <para> 2:主动终止升级(中央空调木允许终止)</para>
        /// <para> 3:从等待中取消(目前还没有用)</para>
        /// </summary>
        public Action<int, string> UpdateStatuChangedEvent = null;
        /// <summary>
        /// 进度值事件
        /// </summary>
        public Action<decimal> ProgressEvent = null;
        /// <summary>
        /// 设备新版本的固件信息(多个设备升级时,应该会需要公开这个对象)
        /// </summary>
        public FirmwareVersionInfo deviceFirmware = null;
        /// <summary>
        /// 网关
        /// </summary>
        private ZbGateway zbGateway = null;
        /// <summary>
        /// 升级的设备
        /// </summary>
        private OTADevice otaDevice = null;
        /// <summary>
        /// 设备对象
        /// </summary>
        private CommonDevice deviceAc = null;
        /// <summary>
        /// 前一次的最终状态
        /// </summary>
        private UpdateStatuMode oldUpdateStatu = UpdateStatuMode.None;
        /// <summary>
        /// 固件的byte数组
        /// </summary>
        private byte[] deviceFirmwareByte = null;
        #endregion
        #region ■ 初始化_____________________________
        /// <summary>
        /// <para>HDL设备升级,以下为两个重要事件</para>
        /// <para>UpdateStatuChangedEvent:更新状态变化的事件</para>
        /// <para>ProgressEvent:进度值事件</para>
        /// <para>StartUpdateReady():设备开始执行升级的函数,在调用这个之前,请先实现上面两个方法</para>
        /// </summary>
        /// <param name="i_deviceAc">设备</param>
        /// <param name="i_deviceFirmware">设备的固件信息</param>
        public HdlACZbGatewayUpdateLogic(CommonDevice i_deviceAc, FirmwareVersionInfo i_deviceFirmware)
        {
            this.ClassDiv = 2;
            this.deviceAc = i_deviceAc;
            this.otaDevice = Common.LocalDevice.Current.GetOTADevice(i_deviceAc.DeviceAddr);
            this.deviceFirmware = i_deviceFirmware;
            this.zbGateway = i_deviceAc.Gateway;
        }
        #endregion
        #region ■ 开始更新___________________________
        /// <summary>
        /// 进入执行更新操作准备阶段
        /// </summary>
        public void StartUpdateReady()
        {
            if (this.UpdateStatu == UpdateStatuMode.Wait)
            {
                //如果是等待模式,再次点击时,移除列表
                if (FirmwareUpdateResourse.dicUpdateList.ContainsKey(otaDevice.DeviceAddr) == true)
                {
                    FirmwareUpdateResourse.dicUpdateList.Remove(otaDevice.DeviceAddr);
                }
                //取消
                this.UpdateStatu = UpdateStatuMode.None;
                this.UpdateStatuChangedEvent?.Invoke(3, "");
                return;
            }
            //如果它有状态,则表示之前它被什么错误中断了
            if (this.UpdateStatu != UpdateStatuMode.None)
            {
                //保存起来,后面有用处
                this.oldUpdateStatu = this.UpdateStatu;
            }
            //进入等待模式
            this.UpdateStatu = UpdateStatuMode.Wait;
            FirmwareUpdateResourse.dicUpdateList[otaDevice.DeviceAddr] = this;
            //等待中…
            this.UpdateStatuChangedEvent?.Invoke(0, Language.StringByID(R.MyInternationalizationString.uWaitting));
            //执行下一个可更新的固件的更新操作
            HdlFirmwareUpdateLogic.DoUpdateNextFirmware();
        }
        /// <summary>
        /// 开始执行更新操作
        /// </summary>
        public override void DoStartUpdate()
        {
            //状态变更
            this.IsFinishUpdate = false;
            this.UpdateStatu = UpdateStatuMode.Action;
            //根据状态执行操作
            this.DoAdjustByStatuMode();
        }
        /// <summary>
        /// 根据状态执行操作
        /// </summary>
        private void DoAdjustByStatuMode()
        {
            //先这样写吧,有可能以后会分情况
            //首发时,从开始执行
            if (this.oldUpdateStatu == UpdateStatuMode.None)
            {
                //执行校验版本
                this.DoCheckVersion();
            }
            //设备下载失败
            else if (this.oldUpdateStatu == UpdateStatuMode.DeviceDownLoadFail)
            {
                //执行校验版本
                this.DoCheckVersion();
            }
            //设备升级失败
            else if (this.oldUpdateStatu == UpdateStatuMode.DeviceUpdateFail)
            {
                //执行校验版本
                this.DoCheckVersion();
            }
            else
            {
                //重新再来
                this.DoCheckVersion();
            }
        }
        #endregion
        #region ■ 校验版本___________________________
        /// <summary>
        /// 校验版本
        /// </summary>
        private async void DoCheckVersion()
        {
            this.UpdateStatu = UpdateStatuMode.DeviceUpdateReady;
            //检测设备版本
            this.UpdateStatuChangedEvent?.Invoke(0, Language.StringByID(R.MyInternationalizationString.uCheckDeviceVersion));
            //设置初始值
            this.SetProgressValue(0, 100);
            await System.Threading.Tasks.Task.Delay(1000);
            //下载固件资源
            if (this.deviceFirmware.ImagType != "-100")
            {
                var pra = new { RequestVersion = Common.CommonPage.RequestVersion, DistributedMark = this.deviceFirmware.DistributedMark };
                this.deviceFirmwareByte = Common.CommonPage.Instance.RequestHttpsZigbeeBytesResultAsync("FirmwareMana/DownloadPlatformUploadFirmware", Encoding.UTF8.GetBytes(Newtonsoft.Json.JsonConvert.SerializeObject(pra)));
            }
            else
            {
                //取本地模板
                this.deviceFirmwareByte = HdlFileLogic.Current.ReadFileByteContent(this.deviceFirmware.Name);
            }
            if (this.deviceFirmwareByte == null)
            {
                //设备固件资源下载失败
                this.ShowErrorMsg(Language.StringByID(R.MyInternationalizationString.uDeviceFirmwareDownLoadFail));
                //显示重新下载模式
                this.ShowReDownLoadMode();
                this.UpdateStatu = UpdateStatuMode.DeviceDownLoadFail;
                return;
            }
            //数据偏移量,每个分包偏移量+(1-43)
            string offset = string.Empty;
            //一次发送的数据长度
            int dataLength = -1;
            //接收网关的透传数据
            Action<string, object> receiveAction = (comand, pushData) =>
            {
                string receiveData = ((CommonDevice.ClientDataPassthroughResponseData)pushData).PassData;
                if (receiveData.Length < 6)
                {
                    return;
                }
                try
                {
                    var command = receiveData[4].ToString() + receiveData[5].ToString() + receiveData[2].ToString() + receiveData[3].ToString();
                    if (command == "025c")
                    {
                        offset = receiveData.Substring(10, 8);
                        dataLength = Convert.ToInt32(receiveData.Substring(18, 2), 16);
                    }
                }
                catch { }
            };
            this.zbGateway.ReportAction += receiveAction;
            //读取空调模块版本
            var result = await HdlDeviceAirConditionerLogic.Current.ReadACFirewareVersionAsync(deviceAc);
            if (result == null || result.readACFirewareVersionResponData == null || result.readACFirewareVersionResponData.Status != 0)
            {
                //获取空调模块版本失败
                this.ShowErrorMsg(Language.StringByID(R.MyInternationalizationString.uGetAirConditionerModelVersionFail));
                //显示重新安装
                this.ShowReSetupMsg();
                this.UpdateStatu = UpdateStatuMode.DeviceUpdateFail;
                this.zbGateway.ReportAction -= receiveAction;
                //发送失败给设备
                HdlDeviceAirConditionerLogic.Current.SendFinishAsync(deviceAc, 1);
                return;
            }
            //发送升级通知
            var result2 = await HdlDeviceAirConditionerLogic.Current.UpggradeACNotificationAsync(deviceAc, result.readACFirewareVersionResponData.FirewareVersion, this.deviceFirmwareByte.Length);
            if (result2.responseData == null)
            {
                //发送升级命令失败
                this.ShowErrorMsg(Language.StringByID(R.MyInternationalizationString.uSendUpdateComandFail));
                //显示重新安装
                this.ShowReSetupMsg();
                this.UpdateStatu = UpdateStatuMode.DeviceUpdateFail;
                this.zbGateway.ReportAction -= receiveAction;
                //发送失败给设备
                HdlDeviceAirConditionerLogic.Current.SendFinishAsync(deviceAc, 1);
                return;
            }
            else if (result2.responseData.status == 1)
            {
                //版本号相同,升级失败
                this.ShowErrorMsg(Language.StringByID(R.MyInternationalizationString.uVersionIsEqualAndUpdateFail));
                //显示重新安装
                this.ShowReSetupMsg();
                this.UpdateStatu = UpdateStatuMode.DeviceUpdateFail;
                this.zbGateway.ReportAction -= receiveAction;
                //发送失败给设备
                HdlDeviceAirConditionerLogic.Current.SendFinishAsync(deviceAc, 1);
                return;
            }
            else if (result2.responseData.status != 0)
            {
                //校验版本号失败
                this.ShowErrorMsg(Language.StringByID(R.MyInternationalizationString.uCheckVersionFail));
                //显示重新安装
                this.ShowReSetupMsg();
                this.UpdateStatu = UpdateStatuMode.DeviceUpdateFail;
                this.zbGateway.ReportAction -= receiveAction;
                //发送失败给设备
                HdlDeviceAirConditionerLogic.Current.SendFinishAsync(deviceAc, 1);
                return;
            }
            int timeOut = 0;
            //等待接收偏移量
            while (dataLength == -1)
            {
                timeOut++;
                if (timeOut >= 30)
                {
                    //响应超时,检测设备版本失败
                    this.ShowErrorMsg(Language.StringByID(R.MyInternationalizationString.uResponseTimeoutsAndCheckDeviceVersionFail));
                    //显示重新安装
                    this.ShowReSetupMsg();
                    this.UpdateStatu = UpdateStatuMode.DeviceUpdateFail;
                    this.zbGateway.ReportAction -= receiveAction;
                    //发送失败给设备
                    HdlDeviceAirConditionerLogic.Current.SendFinishAsync(deviceAc, 1);
                    return;
                }
                await System.Threading.Tasks.Task.Delay(1000);
                //设置进度值
                this.SetProgressValue(timeOut, 30);
            }
            this.zbGateway.ReportAction -= receiveAction;
            //执行设备升级操作
            this.DoSetUpdateDevice(offset, dataLength);
        }
        #endregion
        #region ■ 设备升级___________________________
        /// <summary>
        /// 执行设备升级操作
        /// </summary>
        private async void DoSetUpdateDevice(string i_offset, int i_dataLength)
        {
            this.UpdateStatu = UpdateStatuMode.DeviceUpdateReady;
            //设备正在升级…
            this.UpdateStatuChangedEvent?.Invoke(0, Language.StringByID(R.MyInternationalizationString.uDeviceUpdating));
            //设置初始值
            this.SetProgressValue(0, 100);
            await System.Threading.Tasks.Task.Delay(1000);
            //发送数据的索引
            int startIndex = 0;
            int allDataLength = this.deviceFirmwareByte.Length;
            int timeOut = 0;
            //是否接收到成功命令
            bool receiveSuccess = false;
            //接收网关的透传数据
            bool hadReceive = true;
            Action<string, object> receiveAction = (comand, pushData) =>
            {
                if (comand != "DeviceRequestAcUpdateData")
                {
                    return;
                }
                string receiveData = ((CommonDevice.ClientDataPassthroughResponseData)pushData).PassData;
                if (receiveData.Length < 6)
                {
                    return;
                }
                try
                {
                    var command = receiveData[4].ToString() + receiveData[5].ToString() + receiveData[2].ToString() + receiveData[3].ToString();
                    if (command == "025c")
                    {
                        i_offset = receiveData.Substring(10, 8);
                        i_dataLength = Convert.ToInt32(receiveData.Substring(18, 2), 16);
                        hadReceive = true;
                        timeOut = 0;
                        //设置进度值
                        this.SetProgressValue(startIndex, allDataLength);
                    }
                    else if (command == "025e")
                    {
                        //成功  设置进度值直接100%
                        this.SetProgressValue(allDataLength, allDataLength);
                        receiveSuccess = true;
                        timeOut = 0;
                    }
                }
                catch { }
            };
            this.zbGateway.ReportAction += receiveAction;
            //最后一次需要等待回复结果才往下走
            while (startIndex < allDataLength)
            {
                if (receiveSuccess == true)
                {
                    //已经接收到成功的命令
                    break;
                }
                if (hadReceive == false)
                {
                    timeOut++;
                    if (timeOut >= 1500)
                    {
                        //响应超时,升级失败
                        this.ShowErrorMsg(Language.StringByID(R.MyInternationalizationString.uResponseTimeoutsAndUpdateFail));
                        //显示重新安装
                        this.ShowReSetupMsg();
                        this.UpdateStatu = UpdateStatuMode.DeviceUpdateFail;
                        this.zbGateway.ReportAction -= receiveAction;
                        //发送失败给设备
                        HdlDeviceAirConditionerLogic.Current.SendFinishAsync(deviceAc, 1);
                        return;
                    }
                    await System.Threading.Tasks.Task.Delay(50);
                    continue;
                }
                hadReceive = false;
                //因为偏移量是高位在前,所以倒过来
                string Myoffset = string.Empty;
                for (int i = 6; i >= 0; i = i - 2)
                {
                    Myoffset += i_offset.Substring(i, 2);
                }
                startIndex = Convert.ToInt32(Myoffset, 16) - i_dataLength;
                //获取一次能够发送的byte
                var listData = new List<byte>();
                for (; startIndex < allDataLength; startIndex++)
                {
                    listData.Add(this.deviceFirmwareByte[startIndex]);
                    if (listData.Count == i_dataLength)
                    {
                        break;
                    }
                }
                //发送透传数据
                var sendData = new HdlDeviceAirConditionerLogic.SendUpgradeData() { dataLength = i_dataLength, offset = i_offset };
                sendData.databytes = listData.ToArray();
                HdlDeviceAirConditionerLogic.Current.UpgradeAsync(deviceAc, sendData);
            }
            this.zbGateway.ReportAction -= receiveAction;
            //发送结束命令
            this.DoSendFinishComand();
        }
        #endregion
        #region ■ 分包结束___________________________
        /// <summary>
        /// 发送结束命令
        /// </summary>
        private async void DoSendFinishComand()
        {
            //正在发送升级完成的命令
            this.UpdateStatuChangedEvent?.Invoke(0, Language.StringByID(R.MyInternationalizationString.uSendingFinishUpdateComand));
            //发送成功命令给设备
            HdlDeviceAirConditionerLogic.Current.SendFinishAsync(deviceAc, 0);
            //等个两秒钟吧
            await System.Threading.Tasks.Task.Delay(2000);
            //显示升级完成的信息
            this.ShowFinishMsg();
        }
        #endregion
        #region ■ 设置进度___________________________
        /// <summary>
        /// 设定进度值
        /// </summary>
        /// <param name="value">进度值</param>
        /// <param name="maxValue">maxValue</param>
        private void SetProgressValue(decimal value, decimal maxValue)
        {
            this.ProgressEvent?.Invoke(value / maxValue);
        }
        /// <summary>
        /// 设置错误信息
        /// </summary>
        /// <param name="value"></param>
        private void ShowErrorMsg(string value)
        {
            this.UpdateStatuChangedEvent?.Invoke(-1, value);
        }
        #endregion
        #region ■ 升级完成提示_______________________
        /// <summary>
        /// 显示升级完成的信息
        /// </summary>
        private void ShowFinishMsg()
        {
            //状态变更
            this.IsFinishUpdate = true;
            //升级完成
            this.UpdateStatu = UpdateStatuMode.UpdateFinish;
            HdlFirmwareUpdateLogic.DoUpdateNextFirmware();
            //设备升级成功!
            this.UpdateStatuChangedEvent?.Invoke(1, Language.StringByID(R.MyInternationalizationString.uDeviceUpdateSuccess));
        }
        #endregion
        #region ■ 处理结果提示_______________________
        /// <summary>
        /// 显示重新安装的信息
        /// </summary>
        private void ShowReSetupMsg()
        {
            //状态变更
            this.IsFinishUpdate = true;
            //执行下一个升级
            HdlFirmwareUpdateLogic.DoUpdateNextFirmware();
        }
        /// <summary>
        /// 显示重新下载模式
        /// </summary>
        private void ShowReDownLoadMode()
        {
            //状态变更
            this.IsFinishUpdate = true;
            //执行下一个升级
            HdlFirmwareUpdateLogic.DoUpdateNextFirmware();
        }
        #endregion
        #region ■ 释放缓存___________________________
        /// <summary>
        /// 释放缓存
        /// </summary>
        public override void Dispose()
        {
            this.ProgressEvent = null;
            this.UpdateStatuChangedEvent = null;
        }
        #endregion
    }
}