using ButcherFactory.BO;
using ButcherFactory.BO.Rpcs;
using ButcherFactory.BO.Utils;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Windows.Forms;
using ButcherFactory.Utils;
using ButcherFactory.BO.LocalBL;
using WinFormControl;
using ButcherFactory.Dialogs;

namespace ButcherFactory.SegmentProduction_
{
  public partial class SegmentProductionForm : Form, IWithRoleForm
  {
    public List<short> RoleName
    {
      get { return new List<short> { (short)设备类别.分割生产 }; }
    }

    public Form Generate()
    {
      return this;
    }

    Thread uploadData;
    BindingList<SegmentProduction> historyList;
    BindingList<SegmentProduction> unSubmitList;
    Dictionary<string, List<ClientGoodsSet_Detail>> goodsSetDic;
    long? workUnitID;
    long? batchID;
    DateTime? batchDate;

    void Start(bool start)
    {
      startBtn.Enabled = !start;
      endBtn.Enabled = start;
    }
    //GroupID 标识有没有结束，同时是总码的标识。
    //TrunOutID 标识挂起，同时标识挂起的组。 点击挂起 或者切换，需要给该字段赋值，点击切换回来，需要清空
    public SegmentProductionForm()
    {
      InitializeComponent();
      netStateWatch1.GetConnectState = () => LoginUtil.TestConnection(500);
      this.FormClosing += delegate
      {
        if (uploadData != null && uploadData.IsAlive)
          uploadData.Abort();
      };
      workUnitSelect.SelectedIndexChanged += delegate
      {
        if (workUnitSelect.SelectedValue == null)
          workUnitID = null;
        else
          workUnitID = (long)workUnitSelect.SelectedValue;
        XmlUtil.SerializerObjToFile(new SegmentProductionFormConfig { WorkUnitID = workUnitID });
      };
      productBatchSelect.SelectedIndexChanged += delegate
      {
        if (productBatchSelect.SelectedValue == null)
        {
          batchID = null;
          batchDate = null;
        }
        else
        {
          var entity = productBatchSelect.SelectedItem as ProductBatch;
          batchID = entity.ID;
          batchDate = entity.Date;
        }
      };
    }

    protected override void OnLoad(EventArgs e)
    {
      base.OnLoad(e);
      var initTask = new Thread(LoadBind);
      initTask.Start();

      uploadData = new Thread(UpLoadLocalData);
      uploadData.Start();
    }

    void LoadBind()
    {
      this.Invoke(new Action(() =>
      {
        if (netStateWatch1.NetState)
        {
          BaseInfoSyncRpc.SyncGoodsByTag(ApplyClient.分割品);
          BaseInfoSyncRpc.SyncBaseInfo<WorkUnit>();
          BaseInfoSyncRpc.SyncProductBatch(1);
        }
        productBatchSelect.EBindComboBox<ProductBatch>(x => x.Date == DateTime.Today, 6, "Date");
        var config = XmlUtil.DeserializeFromFile<SegmentProductionFormConfig>();
        var m = config.WorkUnitID;
        workUnitSelect.EBindComboBox<WorkUnit>(x => x.ID == m, top: 100);

        BindGoods();
        BindGrid();
      }));
    }

    void BindGoods()
    {
      goodsSetDic = FormClientGoodsSetBL.GetSelectedDetail();
      flowLayoutPanel1.Controls.Clear();
      flowLayoutPanel2.Controls.Clear();
      foreach (var item in goodsSetDic)
      {
        var btn = new UButton() { Width = 100, Height = 62, Text = item.Key, Font = new Font("宋体", 15), Margin = new Padding(15, 3, 15, 0), WithStataHode = true, EnableGroup = true };
        btn.Click += GroupGoodsSetClick;
        flowLayoutPanel1.Controls.Add(btn);
      }
    }

    void GroupGoodsSetClick(object sender, EventArgs e)
    {
      flowLayoutPanel2.Controls.Clear();
      var groupBtn = sender as UButton;
      var arr = goodsSetDic[groupBtn.Text];
      foreach (var item in arr)
      {
        var btn = new UButton() { Width = 127, Height = 75, Text = item.Goods_Name, Tag = item, Font = new Font("宋体", 15), Margin = new Padding(20, 10, 20, 35), PlaySound = true };
        btn.Click += GoodsBtnClick;
        flowLayoutPanel2.Controls.Add(btn);
      }
    }

    void GoodsBtnClick(object sender, EventArgs e)
    {
      if (batchID == null)
        throw new Exception("请先选择批次");
      var btn = sender as UButton;
      var detail = btn.Tag as ClientGoodsSet_Detail;
      var weight = uWeightControl1.Weight;
      if (weight == 0)
        throw new Exception("重量不能为0");
      if (detail.StandardWeight.HasValue)
      {
        if (weight < (detail.StandardWeightLow ?? 0) || weight > (detail.StandardWeightUp ?? 0))
          throw new Exception(string.Format("重量必须在{0:#0.######}-{1:#0.######}之间", detail.StandardWeightLow, detail.StandardWeightUp));
        weight = detail.StandardWeight.Value;
      }
      if (startBtn.Enabled)
        Start(true);
      var entity = SegmentProductionBL.Insert(detail.Goods_ID, weight, workUnitID, batchID.Value, batchDate.Value);
      entity.Goods_Name = detail.Goods_Name;
      entity.Goods_Spec = detail.Goods_Spec;
      GoodsLabel.Text = entity.Goods_Name;
      unSubmitList.Insert(0, entity);
      historyList.Insert(0, entity);
      if (historyList.Count > 100)
        historyList.RemoveAt(100);
      historyDataGrid.FirstDisplayedScrollingRowIndex = 0;
      historyDataGrid.Refresh();
      if (barPrintCheck.Checked)
        SegmentProductionPrint.Print(entity, batchDate, "");
    }

    void BindGrid()
    {
      unSubmitList = SegmentProductionBL.GetListByState(false);
      historyList = SegmentProductionBL.GetListByState(true);
      foreach (var item in unSubmitList)
        historyList.Insert(0, item);

      historyDataGrid.DataSource = historyList;
      historyDataGrid.Refresh();

      var first = unSubmitList.FirstOrDefault(x => x.GroupID == null && x.TrunOutID == null);
      if (first == null)
        Start(false);
      else
      {
        GoodsLabel.Text = first.Goods_Name;
        Start(true);
      }
    }

    void UpLoadLocalData()
    {
      while (true)
      {
        if (this.IsHandleCreated)
        {
          this.Invoke(new Action(() =>
          {
            if (netStateWatch1.NetState)
              SegmentProductionBL.UploadSegmentInfo();
          }));
        }
        Thread.Sleep(2000);
      }
    }

    private void closeBtn_Click(object sender, EventArgs e)
    {
      Close();
    }

    private void startBtn_Click(object sender, EventArgs e)
    {
      Start(true);
    }

    private void endBtn_Click(object sender, EventArgs e)
    {
      var arr = unSubmitList.Where(x => x.GroupID == null && x.TrunOutID == null);
      if (arr.Any())
      {
        var groupID = SegmentProductionBL.SetListGroupID(arr.Select(x => x.ID));
        var bk = new List<SegmentProduction>();
        foreach (var item in arr)
        {
          item.GroupID = groupID;
          bk.Add(item);
        }
        Start(false);
        if (barPrintCheck.Checked)
          SegmentProductionPrint.PrintEnd(bk);
      }
      else
        throw new Exception("本次开始之后未生产任何商品");
    }

    private void trunOutBtn_Click(object sender, EventArgs e)
    {
      var arr = unSubmitList.Where(x => x.GroupID == null && x.TrunOutID == null);
      long id = 0;
      if (arr.Any())
      {
        id = arr.First().ID;
        SegmentProductionBL.BatchUpdate(arr.Select(x => x.ID), new Tuple<string, object>("TrunOutID", id));
      }
      foreach (var item in arr)
        item.TrunOutID = id;
      GoodsLabel.Text = string.Empty;
      Start(false);
    }

    private void switchBtn_Click(object sender, EventArgs e)
    {
      trunOutBtn_Click(sender, e);
      var arr = unSubmitList.Where(x => x.GroupID == null && x.TrunOutID.HasValue);
      var r = new BindingList<SegmentProduction>();
      foreach (var item in arr.GroupBy(x => x.TrunOutID))
        r.Add(item.First());
      var dialog = new TrunOutDialog(r);
      if (dialog.ShowDialog() == DialogResult.OK)
      {
        var back = dialog.Back;
        var targets = arr.Where(x => x.TrunOutID == back.TrunOutID);
        SegmentProductionBL.TrunBack(targets.Select(x => x.ID));
        foreach (var item in targets)
          item.TrunOutID = null;
        GoodsLabel.Text = back.Goods_Name;
        Start(true);
      }
    }

    private void goodsSetBtn_Click(object sender, EventArgs e)
    {
      new ClientGoodsSetDialog().ShowDialog();
    }

    private void rePrintBtn_Click(object sender, EventArgs e)
    {
      if (barPrintCheck.Checked)
      {
        if (historyDataGrid.CurrentRow == null)
          throw new Exception("请先选择要补打的记录");
        var item = historyDataGrid.CurrentRow.DataBoundItem as SegmentProduction;
        SegmentProductionPrint.Print(item, batchDate, "");
      }
    }

    private void deleteBtn_Click(object sender, EventArgs e)
    {
      if (historyDataGrid.CurrentRow == null)
        throw new Exception("请先选中要删除的记录");
      var id = (long)historyDataGrid.CurrentRow.Cells[0].Value;
      var first = unSubmitList.FirstOrDefault(x => x.ID == id && x.GroupID == null);
      if (first == null)
        throw new Exception("已结束，无法删除");
      if (MessageBox.Show(string.Format("确认删除{0} {1}的记录？", first.RowIndex, first.Goods_Name), "删除确认", MessageBoxButtons.OKCancel) == DialogResult.OK)
      {
        var item = historyDataGrid.CurrentRow.DataBoundItem as SegmentProduction;
        SegmentProductionBL.SetAsDelete(item.ID, item.BarCode);
        unSubmitList.Remove(first);
        historyList.Remove(first);
        historyDataGrid.Refresh();
      }
    }

    private void submitBtn_Click(object sender, EventArgs e)
    {
      var arrs = unSubmitList.Where(x => x.GroupID.HasValue).ToList();
      if (arrs.Any())
      {
        SegmentProductionBL.BatchUpdate(arrs.Select(x => x.ID), new Tuple<string, object>("Submited", true));
        foreach (var item in arrs)
          unSubmitList.Remove(item);
      }
      UMessageBox.Show("已提交");
    }
  }
}
