HDL Home App 第二版本 旧平台金堂用 正在使用
ZigbeeApp/Shared/Phone/Category/Controls/DeviceRow/Base/DeviceRowCommon.cs
New file
@@ -0,0 +1,605 @@
using Shared.Phone.UserCenter;
using System;
using System.Collections.Generic;
using System.Text;
using ZigBee.Device;
namespace Shared.Phone.Category.Controls
{
  /// <summary>
  /// 分类的设备行控件底层共通
  /// </summary>
  public class DeviceRowCommon : RowLayoutControl
  {
    #region ■ 变量声明___________________________
    /// <summary>
    /// 是否拥有状态功能(默认拥有)
    /// </summary>
    public bool hadStatuFunction = true;
    /// <summary>
    /// 控件需要被移除的事件
    /// </summary>
    public Action RowNeedRemoveEvent = null;
    /// <summary>
    /// 设备对象
    /// </summary>
    public CommonDevice device;
    /// <summary>
    /// 设备图标背景控件
    /// </summary>
    private FrameLayout frameIconBackGroud = null;
    /// <summary>
    /// 设备图标控件
    /// </summary>
    private IconViewControl btnDeviceIcon = null;
    /// <summary>
    /// 设备名字控件
    /// </summary>
    private NormalViewControl btnDeviceName = null;
    /// <summary>
    /// 状态控件
    /// </summary>
    private NormalViewControl btnStatu = null;
    /// <summary>
    /// 开关控件
    /// </summary>
    private MostRightIconControl btnSwitch = null;
    /// <summary>
    /// 电池控件
    /// </summary>
    private IconViewControl btnBattery = null;
    /// <summary>
    /// 是否获取网关反馈的结果  0:没有获取得到  1:已经获取得到
    /// </summary>
    private int ResponeResult = 0;
    /// <summary>
    /// 判断是否有开关功能
    /// </summary>
    private bool isHadOpenSwitch = true;
    /// <summary>
    /// 当前选择的房间
    /// </summary>
    public Common.Room nowSelectRoom = null;
    #endregion
    #region ■ 初始化_____________________________
    /// <summary>
    /// 未分配界面的设备选择控件
    /// </summary>
    public DeviceRowCommon()
    {
      this.SetCornerWithSameRadius(Application.GetRealHeight(58), HDLUtils.RectCornerTopLeft);
      this.Width = Application.GetRealWidth(1022);
    }
    /// <summary>
    /// 初始化控件
    /// </summary>
    /// <param name="i_device">设备对象</param>
    /// <param name="i_nowSelectRoom">当前选择的房间(有点用处)</param>
    public virtual void InitControl(CommonDevice i_device, Common.Room i_nowSelectRoom)
    {
      this.device = i_device;
      this.nowSelectRoom = i_nowSelectRoom;
      //设备图标背景控件
      this.frameIconBackGroud = new FrameLayout();
      frameIconBackGroud.Height = this.GetPictrueRealSize(112);
      frameIconBackGroud.Width = this.GetPictrueRealSize(112);
      frameIconBackGroud.Gravity = Gravity.CenterVertical;
      frameIconBackGroud.X = Application.GetRealWidth(46);
      frameIconBackGroud.Radius = (uint)this.GetPictrueRealSize(112 / 2);
      frameIconBackGroud.BackgroundColor = Common.ZigbeeColor.Current.GXCGrayBackgroundColor;
      this.frameTable.AddChidren(frameIconBackGroud, ChidrenBindMode.NotBind);
      if (chidrenYaxis != 0)
      {
        frameIconBackGroud.Y += chidrenYaxis;
      }
      //设备图标控件
      this.btnDeviceIcon = new IconViewControl(78);
      btnDeviceIcon.Gravity = Gravity.Center;
      Common.LocalDevice.Current.SetDeviceIconToControl(btnDeviceIcon, i_device);
      frameIconBackGroud.AddChidren(btnDeviceIcon);
      //重新绑定事件
      this.frameTable.ChangedChidrenBindMode(frameIconBackGroud, ChidrenBindMode.BindEvent);
      //设备名字
      this.btnDeviceName = new NormalViewControl(600, 60, true);
      if (this.device.Type == DeviceType.WindowCoveringDevice || this.device.Type == DeviceType.Airer)
      {
        //窗帘和晾衣架因为右边有三个按钮,所以需要所有名字的宽度
        this.btnDeviceName.Width = Application.GetRealWidth(360);
      }
      btnDeviceName.X = Application.GetRealWidth(181);
      //当指定实际坐标时,这里需要的偏移量为2倍
      btnDeviceName.Y = Application.GetRealHeight(16) + this.chidrenYaxis * 2;
      btnDeviceName.Text = Common.LocalDevice.Current.GetDeviceEpointName(i_device);
      btnDeviceName.SelectedTextColor = Common.ZigbeeColor.Current.GXCTextSelectedColor;
      this.frameTable.AddChidren(btnDeviceName, ChidrenBindMode.BindEvent);
      if (this.hadStatuFunction == false)
      {
        //没有状态功能,则把设备名字控件中
        this.btnDeviceName.Gravity = Gravity.CenterVertical;
        btnDeviceName.Y += this.chidrenYaxis;
      }
      //拥有状态功能
      if (this.hadStatuFunction == true)
      {
        //状态
        this.btnStatu = new NormalViewControl(600, 50, true);
        btnStatu.X = Application.GetRealWidth(181);
        //当指定实际坐标时,这里需要的偏移量为2倍
        btnStatu.Y = Application.GetRealHeight(70) + this.chidrenYaxis * 2;
        btnStatu.TextSize = 10;
        btnStatu.TextColor = UserCenterColor.Current.TextGrayColor1;
        this.frameTable.AddChidren(btnStatu, ChidrenBindMode.BindEvent);
      }
      //底线
      var btnBottomLine = new NormalViewControl(Application.GetRealWidth(841), ControlCommonResourse.BottomLineHeight, false);
      btnBottomLine.X = Application.GetRealWidth(181);
      btnBottomLine.Y = this.Height - ControlCommonResourse.BottomLineHeight;
      btnBottomLine.BackgroundColor = UserCenterColor.Current.ButtomLine;
      this.frameTable.AddChidren(btnBottomLine, ChidrenBindMode.NotBind);
      //开关控件(暂时不加入父控件)
      this.btnSwitch = new MostRightIconControl(69, 69);
      btnSwitch.UnSelectedImagePath = "Item/Switch.png";
      btnSwitch.SelectedImagePath = "Item/SwitchSelected.png";
      //电池控件
      if (this.device.Type == DeviceType.IASZone)
      {
        this.btnBattery = new IconViewControl(69);
        btnBattery.X = this.Width - Application.GetRealWidth(69 + 29);
        btnBattery.UnSelectedImagePath = "Item/Battery.png";
        btnBattery.Gravity = Gravity.CenterVertical;
        this.frameTable.AddChidren(btnBattery, ChidrenBindMode.BindEvent);
        if (chidrenYaxis != 0)
        {
          btnBattery.Y += chidrenYaxis;
        }
        if (this.device.IsBatteryDown == false)
        {
          btnBattery.Visible = false;
        }
      }
      //分享的房间,则不能编辑和删除
      if (this.nowSelectRoom.IsSharedRoom == false)
      {
        //编辑
        var btnEditor = this.AddEditorControl();
        btnEditor.ButtonClickEvent += (sender, e) =>
        {
          var detailInfo = new MainPage.DeviceDetailInfoForm();
          detailInfo.AddForm(i_device, this.nowSelectRoom);
          detailInfo.FormCloseEvent += () =>
                  {
              if (this.nowSelectRoom.IsLove == true)
              {
                        //当前是喜爱房间时
                        if (HdlRoomLogic.Current.IsCollectInRoom(this.device) == false)
                {
                          //回调控件被移除的事件
                          this.RowNeedRemoveEvent?.Invoke();
                          //房间改变了
                          this.RemoveFromParent();
                  return;
                }
              }
              var curRoom = HdlRoomLogic.Current.GetRoomByDevice(this.device);
              if (curRoom == null || this.nowSelectRoom.Id != curRoom.Id)
              {
                        //回调控件被移除的事件
                        this.RowNeedRemoveEvent?.Invoke();
                        //房间改变了
                        this.RemoveFromParent();
                return;
              }
                      //刷新控件状态
                      this.RefreshControlInfo(i_device);
            };
        };
        //删除
        var btnDelete = this.AddDeleteControl();
        btnDelete.ButtonClickEvent += (sender, e) =>
        {
                  //确定要移除该功能?
                  var alert = new ShowMsgControl(ShowMsgType.Confirm, Language.StringByID(R.MyInternationalizationString.DeleteFunction));
          alert.Show();
          alert.ConfirmClickEvent += () =>
                  {
                      //移除收藏(不管什么情况,收藏都要移除)
                      HdlRoomLogic.Current.DeleteLoveDevice(i_device);
              if (this.nowSelectRoom.IsLove == false)
              {
                        //从房间中移除
                        HdlRoomLogic.Current.DeleteDevice(i_device);
              }
                      //回调控件被移除的事件
                      this.RowNeedRemoveEvent?.Invoke();
              this.RemoveFromParent();
                      //上传空间区域信息
                      HdlRoomLogic.Current.SetRoomInfoToGateway();
            };
        };
      }
      //刷新控件状态
      this.RefreshControlInfo(i_device);
    }
    #endregion
    #region ■ 添加开关控件_______________________
    /// <summary>
    /// 添加开关控件
    /// </summary>
    /// <returns></returns>
    public MostRightIconControl AddSwitchControl()
    {
      this.frameTable.AddChidren(this.btnSwitch, ChidrenBindMode.NotBind);
      btnSwitch.InitControl();
      btnSwitch.X -= ControlCommonResourse.XXLeft;
      btnSwitch.Y += this.chidrenYaxis;
      return btnSwitch;
    }
    #endregion
    #region ■ 刷新控件状态_______________________
    /// <summary>
    /// 刷新控件状态
    /// </summary>
    /// <param name="i_device">设备对象,不是推送的那个</param>
    public virtual void RefreshControlInfo(CommonDevice i_device)
    {
      //设备图标也刷新
      Common.LocalDevice.Current.SetDeviceIconToControl(btnDeviceIcon, i_device);
      //设备名字
      this.btnDeviceName.Text = Common.LocalDevice.Current.GetDeviceEpointName(i_device);
      //检测设备是否是打开状态
      bool isOpen = this.CheckIsOpenStatu(i_device);
      if (this.isHadOpenSwitch == true && i_device.HadReadDeviceStatu == false)
      {
        //如果这个卡片有开关功能,并且网关还没有回复之前,默认是关闭状态
        //等待网关回复后会重新刷新,不然一直是关闭状态
        isOpen = false;
      }
      //如果是传感器类,则默认是关的效果
      if (this.device.Type == DeviceType.PMSensor || this.device.Type == DeviceType.IASZone
          || this.device.Type == DeviceType.TemperatureSensor)
      {
        isOpen = false;
      }
      this.SetRowOpenStatu(isOpen);
    }
    /// <summary>
    /// 设置行控件的打开或者关闭的状态
    /// </summary>
    /// <param name="isOpen"></param>
    public void SetRowOpenStatu(bool isOpen)
    {
      //设备状态必须刷新
      if (this.btnStatu != null)
      {
        this.btnStatu.Text = HdlDeviceOtherLogic.Current.GetDeviceStatu(this.device);
      }
      //开关控件
      if (this.btnSwitch != null && this.btnSwitch.IsSelected != isOpen)
      {
        this.btnSwitch.IsSelected = isOpen;
      }
      //切换卡片状态特效
      this.SwitchRowStatuAppeal(isOpen);
    }
    /// <summary>
    /// 设置行控件的在线状态
    /// </summary>
    /// <param name="isOnline">在线</param>
    public void SetRowOnlineStatu(bool isOnline)
    {
      if (this.isHadOpenSwitch == true)
      {
        //如果这个设备有开关功能,则在线状态不会改变状态
        return;
      }
      this.SetRowOpenStatu(isOnline);
    }
    /// <summary>
    /// 设置设备的状态文本
    /// </summary>
    /// <param name="i_Text">状态文本</param>
    public void SetDeviceStatuText(string i_Text)
    {
      if (this.btnStatu != null)
      {
        this.btnStatu.Text = i_Text;
      }
    }
    #endregion
    #region ■ 发送获取状态命令___________________
    /// <summary>
    /// 发送获取状态命令
    /// </summary>
    public virtual void SendStatuComand()
    {
      return;
    }
    #endregion
    #region ■ 检测设备打开状态___________________
    /// <summary>
    /// 检测设备是否是打开状态
    /// </summary>
    /// <param name="i_device"></param>
    /// <returns></returns>
    public virtual bool CheckIsOpenStatu(CommonDevice i_device)
    {
      //如果这个函数被重写的话,则代表这个设备有开关功能
      this.isHadOpenSwitch = false;
      //默认用在线状态来判断
      return Common.LocalDevice.Current.CheckDeviceIsOnline(i_device);
    }
    #endregion
    #region ■ 深度卡片信息的返回事件_____________
    /// <summary>
    /// 深度卡片信息的返回事件(底层专用)
    /// </summary>
    /// <param name="device">设备</param>
    public void CardDetailInfoBackEvent(CommonDevice device)
    {
      if (this.nowSelectRoom.IsLove == true)
      {
        //已经取消的收藏
        if (HdlRoomLogic.Current.IsCollectInRoom(device) == false)
        {
          //回调控件被移除的事件
          this.RowNeedRemoveEvent?.Invoke();
          //移除这个控件
          this.RemoveFromParent();
          return;
        }
      }
      else
      {
        //如果这个设备改变了房间的话,回调卡片被删除的函数
        var nowRoom = HdlRoomLogic.Current.GetRoomByDevice(device);
        if (nowRoom == null || nowRoom.Id != this.nowSelectRoom.Id)
        {
          //回调控件被移除的事件
          this.RowNeedRemoveEvent?.Invoke();
          //移除这个控件
          this.RemoveFromParent();
          return;
        }
      }
      //如果它还在这个房间的话,刷新卡片信息
      this.RefreshControlInfo(device);
    }
    #endregion
    #region ■ 是否获取网关反馈的结果_____________
    /// <summary>
    /// <para>检测是否获取网关反馈的结果,如果网关没有回复,则会弹出消息</para>
    /// <para>获取到回复结果之后,记得调用SetHadGetResponeResultStatu()函数设置状态</para>
    /// </summary>
    /// <param name="oldOpenStatu">设备目前的开关状态</param>
    public void StartCheckResponeResult(bool oldOpenStatu)
    {
      this.ResponeResult = 0;
      HdlThreadLogic.Current.RunThread(() =>
      {
        int waitime = 40;
        while (waitime > 0)
        {
          System.Threading.Thread.Sleep(100);
          if (this.ResponeResult == 1)
          {
                  //已经获取得到数据
                  break;
          }
          waitime--;
                //2秒的时候,还是接受不到的话,强制再次刷新设备状态
                if (waitime == 20)
          {
                  //从新发送获取设备的状态(强制)
                  this.device.HadReadDeviceStatu = false;
            this.SendStatuComand();
          }
        }
        if (waitime <= 0 && this.Parent != null)
        {
                //没有获取得到结果
                HdlThreadLogic.Current.RunMain(() =>
                {
                var msgContr = new ShowMsgControl(ShowMsgType.Tip, Language.StringByID(R.MyInternationalizationString.FAIL));
                msgContr.Show();
                      //变更回原来的状态
                      this.SetRowOpenStatu(oldOpenStatu);
              });
        }
      });
    }
    /// <summary>
    /// 设置已经获取到网关的反馈结果
    /// </summary>
    public void SetHadGetResponeResultStatu()
    {
      this.ResponeResult = 1;
    }
    /// <summary>
    /// 接收网关回复的状态(true:已经接收到网关的回复 false:还没有接收到网关回复)
    /// </summary>
    /// <returns></returns>
    public bool ReceiveResponeResultStatu()
    {
      return this.ResponeResult == 1;
    }
    #endregion
    #region ■ 显示低电量_________________________
    /// <summary>
    /// 刷新电池电量状态
    /// </summary>
    public void RefreshBatteryStatu()
    {
      if (this.btnBattery == null) { return; }
      if (this.device.IsBatteryDown == true)
      {
        //电量低,显示图标
        if (this.btnBattery.Visible == false)
        {
          this.btnBattery.Visible = true;
        }
      }
      else
      {
        //电量足够,隐藏图标
        if (this.btnBattery.Visible == true)
        {
          this.btnBattery.Visible = false;
        }
      }
    }
    #endregion
    #region ■ 一般方法___________________________
    /// <summary>
    /// 检测能否发送获取状态命令
    /// </summary>
    /// <returns></returns>
    public bool CheckCanSendStatuComand()
    {
      if (this.device.HadReadDeviceStatu == false)
      {
        //还没有读取过数据
        return true;
      }
      if ((DateTime.Now - this.device.LastDateTime).TotalMinutes >= 10)
      {
        //10分钟后可以再次获取
        return true;
      }
      return false;
    }
    #endregion
    #region ■ 行闪烁特效_________________________
    /// <summary>
    /// 是否处于特效中
    /// </summary>
    private bool isAppeal = false;
    /// <summary>
    /// 开启行闪烁特效
    /// </summary>
    public void StartRowLightAppeal()
    {
      //设备状态必须刷新
      this.btnStatu.Text = HdlDeviceOtherLogic.Current.GetDeviceStatu(this.device);
      if (this.isAppeal == true) { return; }
      this.isAppeal = true;
      HdlThreadLogic.Current.RunThread(() =>
      {
              //闪烁5秒,间隔400毫秒
              int count = 5000 / 400;
        bool isOpen = false;
        while (this.Parent != null && count >= 0)
        {
                //闪烁特效
                HdlThreadLogic.Current.RunMain(() =>
                {
                isOpen = !isOpen;
                this.SwitchRowStatuAppeal(isOpen);
              });
          System.Threading.Thread.Sleep(400);
          count--;
        }
        if (this.Parent != null && isOpen == false)
        {
          HdlThreadLogic.Current.RunMain(() =>
                {
                      //结束时,默认为打开特效
                      this.SwitchRowStatuAppeal(true);
              }, ShowErrorMode.NO);
        }
        this.isAppeal = false;
      }, ShowErrorMode.NO);
    }
    /// <summary>
    /// 切换卡片状态特效
    /// </summary>
    public void SwitchRowStatuAppeal(bool isOpen)
    {
      if (this.btnDeviceName.IsSelected == isOpen)
      {
        //状态一样,则不需要处理
        return;
      }
      //设备名称控件
      this.btnDeviceName.IsSelected = isOpen;
      this.btnDeviceName.IsBold = isOpen;
      //设备的背景圆圈图
      if (isOpen == true)
      {
        this.frameIconBackGroud.BackgroundColor = Common.ZigbeeColor.Current.GXCSelectedBackgroundColor;
      }
      else
      {
        this.frameIconBackGroud.BackgroundColor = Common.ZigbeeColor.Current.GXCGrayBackgroundColor;
      }
      //设备图标控件
      this.btnDeviceIcon.IsSelected = isOpen;
    }
    #endregion
    #region ■ 控件摧毁___________________________
    /// <summary>
    /// 控件摧毁
    /// </summary>
    public override void RemoveFromParent()
    {
      this.RowNeedRemoveEvent = null;
      base.RemoveFromParent();
    }
    #endregion
  }
}