You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 

538 lines
17 KiB

using ButcherFactory.BO;
using ButcherFactory.BO.LocalBL;
using ButcherFactory.BO.Utils;
using ButcherFactory.Controls;
using ButcherFactory.Dialogs;
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 WinFormControl;
namespace ButcherFactory.SegmentStockUp_
{
public partial class SegmentStockUpForm : FormTemplate, IWithRoleForm
{
#region IWithRoleForm
public List<short> RoleName
{
get { return new List<short> { (short). }; }
}
public Form Generate()
{
return this;
}
#endregion
Tuple<string, long> selectedCustomer;
DateTime sendTime = DateTime.Today;
SegmentStockUpConfig config;
BindingList<SaleOutStoreInfo> mainList;
BindingList<SegmentStockUp> detailList;
BindingList<DeliverGoodsLineTemp> finishList;
List<SaleOutStoreInfo> allMain;
List<SegmentStockUp> allDetail;
List<AlreadyStockUp> alreadyList;
Thread syncStockdNumber;
Thread refreshFromServer;
Thread loadBindTask;//onetime
List<long> mLineGroupIds = new List<long>();
public SegmentStockUpForm()
{
config = XmlUtil.DeserializeFromFile<SegmentStockUpConfig>();
InitializeComponent();
finishList = new BindingList<DeliverGoodsLineTemp>();
allMain = new List<SaleOutStoreInfo>();
allDetail = new List<SegmentStockUp>();
alreadyList = new List<AlreadyStockUp>();
// dataPicker.Text = sendTime.ToString("yyyy-MM-dd");
uScanPanel1.AfterScan += uScanPanel1_AfterScan;
this.FormClosing += delegate
{
AbortTask();
};
}
void AbortTask()
{
if (loadBindTask != null && loadBindTask.IsAlive)
loadBindTask.Abort();
if (syncStockdNumber != null && syncStockdNumber.IsAlive)
syncStockdNumber.Abort();
if (refreshFromServer != null && refreshFromServer.IsAlive)
refreshFromServer.Abort();
}
protected override void OnLoad(EventArgs e)
{
BindDeliverLineGroup(false);
downWeightBox.Text = string.Format("{0:#0.######}", config.AllowDownWeight);
StartTask();
base.OnLoad(e);
}
void StartTask()
{
allDetail = SegmentStockUpBL.GetLocalList(sendTime);
loadBindTask = new Thread(LoadBind);
loadBindTask.Start();
syncStockdNumber = new Thread(SyncStockdNumber);
syncStockdNumber.Start();
refreshFromServer = new Thread(RefreshFromServer);
refreshFromServer.Start();
}
private void LoadBind()
{
var mainList = SegmentStockUpBL.GetSaleOutStoreList(sendTime);
var appendAlready = SegmentStockUpBL.SyncAlreadyNumber(mainList.Select(x => x.DetailID), null);
ReBind(mainList, appendAlready);
}
object _lock = new object();
//loadBind,Refresh, taskMain,taskAlready,Scan
void ReBind(List<SaleOutStoreInfo> mainList, List<AlreadyStockUp> appendAlready)
{
lock (_lock)
{
AppendData(mainList, appendAlready);
var needRefresh = PrepareFinishList();
if (needRefresh)
BindFinishGrid();
}
}
void AppendData(List<SaleOutStoreInfo> mainList, List<AlreadyStockUp> appendAlready)
{
if (mainList.Any())
allMain = mainList;
foreach (var item in appendAlready)
{
var first = alreadyList.FirstOrDefault(x => x.DetailID == item.DetailID);
if (first == null)
{
first = item;
alreadyList.Add(item);
}
else if (first.MaxID < item.MaxID)
{
first.MaxID = item.MaxID;
first.UnitNum = (first.UnitNum ?? 0) + (item.UnitNum ?? 0);
first.SecondNumber = (first.SecondNumber ?? 0) + (item.SecondNumber ?? 0);
}
else
continue;
//局部更新
if (!mainList.Any())
UpdateMainInfo(first);
}
//全量更新
if (mainList.Any())
{
foreach (var item in alreadyList)
UpdateMainInfo(item);
}
}
void UpdateMainInfo(AlreadyStockUp item)
{
var mainFirst = allMain.FirstOrDefault(x => x.DetailID == item.DetailID);
if (mainFirst != null)
{
mainFirst.StandardPic = false;// item.StandardPic;
mainFirst.SUnitNum = item.UnitNum;
mainFirst.SSecondNumber = item.SecondNumber;
mainFirst.DownFloat = config.AllowDownWeight;
}
}
//返回是否需要更新Grid;
bool PrepareFinishList()
{
var old = finishList.ToList();
var append = new List<DeliverGoodsLineTemp>();
finishList = new BindingList<DeliverGoodsLineTemp>();
var idx = 0;
foreach (var item in allMain.GroupBy(x => x.Customer_Name).Where(x => x.All(y => y.Finishd)))
{
var detail = new DeliverGoodsLineTemp();
detail.RowIndex = ++idx;
detail.Name = item.Key;
detail.UnitNum = item.Sum(x => x.UnitNum ?? 0);
detail.SecondNumber = item.Sum(x => x.SecondNumber ?? 0);
detail.SUnitNum = item.Sum(x => x.SUnitNum ?? 0);
detail.SSecondNumber = item.Sum(x => x.SSecondNumber ?? 0);
if (!old.Any(x => x.Name == item.Key))
{
idx--;
append.Add(detail);
}
else
finishList.Insert(0, detail);
}
foreach (var item in append)
{
item.RowIndex = ++idx;
finishList.Insert(0, item);
}
if (old.Count != finishList.Count)
return true;
return old.Except(finishList).Count() != 0;
}
void BindFinishGrid()
{
this.Invoke(new Action(() =>
{
finishGrid.DataSource = finishList;
if (finishList.Any())
finishGrid.Rows[0].Selected = true;
finishGrid.Refresh();
}));
}
private void SyncStockdNumber()
{
while (true)
{
Thread.Sleep(2000);
IEnumerable<long> tags = new List<long>();
long? maxID = null;
if (alreadyList.Any())
maxID = alreadyList.Max(x => x.MaxID);
else
tags = allMain.Select(x => x.DetailID);
if (maxID.HasValue || tags.Any())
{
var temp = SegmentStockUpBL.SyncAlreadyNumber(tags, maxID);
if (temp.Any())
{
ReBind(new List<SaleOutStoreInfo>(), temp);
}
}
}
}
private void RefreshFromServer()
{
while (true)
{
Thread.Sleep(2 * 60 * 1000);
var temp = SegmentStockUpBL.GetSaleOutStoreList(sendTime);
if (temp.Any())
{
ReBind(temp, new List<AlreadyStockUp>());
}
}
}
void uScanPanel1_AfterScan()
{
var code = uScanPanel1.TextBox.Text;
if (string.IsNullOrEmpty(code))
return;
if (allDetail.Any(x => x.BarCode == code))
{
InfoBox.Show("错误", "条码已使用过", Color.Green, 1, this);
return;
}
var info = SegmentStockUpBL.StockUpScan(code);
if (info == null)
{
InfoBox.Show("错误", "条码未入库", Color.Blue, 1, this);
return;
}
InsertDetail(info);
}
void InsertDetail(Tuple<string, decimal?, bool> scan)
{
SaleOutStoreInfo saleOutStore;
if (selectedCustomer != null)
saleOutStore = allMain.FirstOrDefault(x => x.Customer_Name == selectedCustomer.Item1 && !x.Finishd && x.Goods_Code == scan.Item1);
else
saleOutStore = allMain.FirstOrDefault(x => mLineGroupIds.Contains(x.DeliverLineGroup_ID ?? 0) && !x.Finishd && x.Goods_Code == scan.Item1);
if (saleOutStore == null)
{
InfoBox.Show("提示", "没有订单", Color.Red, 1, this);
return;
}
var detail = new SegmentStockUp();
detail.BarCode = uScanPanel1.TextBox.Text;
detail.Date = sendTime;
detail.DetailID = saleOutStore.DetailID;
detail.DeliverGoodsLine_Name = saleOutStore.DeliverGoodsLine_Name;
detail.Goods_Name = saleOutStore.Goods_Name;
//detail.BillID = saleOutStore.BillID;
detail.Customer_Name = saleOutStore.Customer_Name;
detail.UnitNumber = scan.Item2;
detail.StandardPic = scan.Item3;
//if (detail.UnitNumber.HasValue && saleOutStore.Rate.HasValue)
// detail.SecondNumber = detail.UnitNumber * saleOutStore.Rate;
//else
detail.SecondNumber = 1;
var number = 0m;
if (saleOutStore.StockUpBySecondNum)
number = saleOutStore.SecondNumber ?? 0;
else
number = (saleOutStore.UnitNum ?? 0) - (config.AllowDownWeight ?? 0);
//if (!detail.StandardPic)
// number = saleOutStore.SecondNumber;
var already = alreadyList.FirstOrDefault(x => x.DetailID == detail.DetailID);
if (already == null)
already = new AlreadyStockUp() { DetailID = detail.DetailID };//StandardPic = detail.StandardPic
var back = SegmentStockUpBL.Insert(detail, already, number, saleOutStore.StockUpBySecondNum);
if (back == null)
{
InfoBox.Show("提示", "网络错误!", Color.Red, 1, this);
return;
}
if (back.State == -1)
{
InfoBox.Show("提示", "条码已使用过", Color.Green, 1, this);
return;
}
//back.StandardPic = detail.StandardPic;
back.DetailID = detail.DetailID;
if (back.State == 0)
{
ReBind(new List<SaleOutStoreInfo>(), new List<AlreadyStockUp> { back });
InsertDetail(scan);
return;
}
if (back.State != 1)
{
InfoBox.Show("提示", "未知状态" + back.State, Color.Green, 1, this);
return;
}
ReBind(new List<SaleOutStoreInfo>(), new List<AlreadyStockUp> { back });
allDetail.Add(detail);
if (printCk.Checked)
{
var last = 0m;
// allMain.Where(x => x.Goods_Name == saleOutStore.Goods_Name && x.DeliverGoodsLine_Name == saleOutStore.DeliverGoodsLine_Name)
// .Sum(x => ((x.UnitNum ?? 0) - (x.SUnitNum ?? 0)) < 0 ? 0 : ((x.UnitNum ?? 0) - (x.SUnitNum ?? 0)));
//if (last < 0)
// last = 0;
SegmentStockUpPrint.Print(detail, last, saleOutStore);
}
var hasUnFinish = allMain.Where(x => x.Customer_Name == saleOutStore.Customer_Name).Any(x => !x.Finishd);
if (!hasUnFinish)
InfoBox.Show("提示", string.Format("{0} 备货完成", saleOutStore.Customer_Name), Color.Green, 1, this);
BindMainGrid(saleOutStore);
}
void BindMainGrid(SaleOutStoreInfo saleOutStore)
{
var main = new List<SaleOutStoreInfo>();
foreach (var g in allMain.Where(x => x.Goods_Name == saleOutStore.Goods_Name).GroupBy(x => x.Customer_Name))
{
var item = new SaleOutStoreInfo();
var f = g.First();
main.Add(item);
item.Customer_Name = g.Key;
item.Goods_Name = f.Goods_Name;
item.Goods_Spec = f.Goods_Spec;
item.SecondNumber = g.Sum(x => x.SecondNumber ?? 0);
item.UnitNum = g.Sum(x => x.UnitNum ?? 0);
item.SSecondNumber = g.Sum(x => x.SSecondNumber ?? 0);
item.SUnitNum = g.Sum(x => x.SUnitNum ?? 0);
item.DownFloat = config.AllowDownWeight;
item.StockUpBySecondNum = f.StockUpBySecondNum;
item.FinishAssign = f.FinishAssign;
}
mainList = new BindingList<SaleOutStoreInfo>(main.OrderBy(x => x.Finishd).ToList());
mainGridView.DataSource = mainList;
mainGridView.Refresh();
BindDetail(main.Where(x => x.Customer_Name == saleOutStore.Customer_Name).First());
}
void BindDetail(SaleOutStoreInfo first)
{
//if (first != null)
//{
driveLineLbl.Text = first.DeliverGoodsLine_Name;
goodsLbl.Text = first.Goods_Name;
dhNumberLbl.Text = string.Format("{0:#0.##}", first.SecondNumber);
dhUnitNumLbl.Text = string.Format("{0:#0.##}", first.UnitNum);
bhNumberLbl.Text = string.Format("{0:#0.##}", first.SSecondNumber);
bhUnitNumLbl.Text = string.Format("{0:#0.##}", first.SUnitNum);
var detail = allDetail.Where(x => x.Customer_Name == first.Customer_Name && x.Goods_Name == first.Goods_Name).OrderByDescending(x => x.ID);
detailList = new BindingList<SegmentStockUp>(detail.ToList());
//}
//else
//{
// driveLineLbl.Text = string.Empty;
// goodsLbl.Text = string.Empty;
// dhNumberLbl.Text = string.Empty;
// dhUnitNumLbl.Text = string.Empty;
// bhNumberLbl.Text = string.Empty;
// bhUnitNumLbl.Text = string.Empty;
// detailList = new BindingList<SegmentStockUp>();
//}
detailGridView.DataSource = detailList;
detailGridView.Refresh();
}
private void refresh_Click(object sender, EventArgs e)
{
AbortTask();
StartTask();
}
private void mainGridView_CellClick(object sender, DataGridViewCellEventArgs e)
{
if (e.RowIndex < 0)
return;
var item = mainGridView.CurrentRow.DataBoundItem as SaleOutStoreInfo;
BindDetail(item);
}
private void mainGridView_RowPrePaint(object sender, DataGridViewRowPrePaintEventArgs e)
{
DataGridViewRow dgrSingle = mainGridView.Rows[e.RowIndex];
var v = (bool)dgrSingle.Cells["D_Finishd"].Value;
if (v)
{
dgrSingle.DefaultCellStyle.BackColor = Color.YellowGreen;
}
}
private void colorButton1_Click(object sender, EventArgs e)
{
var detail = new SegmentStockUp() { DeliverGoodsLine_Name = "青岛龙钰聚祥万福批发部", Date = DateTime.Today, BarCode = "260912011201905120100005" };
var last = 5.234m;
var saleOutStore = new SaleOutStoreInfo() { Customer_Name = "青岛市大客户", SendQueue = 51 };
SegmentStockUpPrint.Print(detail, last, saleOutStore);
}
private void label2_Click(object sender, EventArgs e)
{
var dialog = new SelectCustomerDialog();
if (dialog.ShowDialog() == DialogResult.OK)
{
selectedCustomer = dialog.Result;
if (selectedCustomer == null)
label2.Text = "请选择";
else
label2.Text = selectedCustomer.Item1;
}
}
private void downWeightBox_Click(object sender, EventArgs e)
{
var pad = new NumberPad();
if (pad.ShowDialog() == true)
{
decimal? weight = null;
if (!string.IsNullOrEmpty(pad.Result))
{
decimal v;
if (decimal.TryParse(pad.Result, out v))
weight = v;
else
throw new Exception("输入错误");
}
downWeightBox.Text = string.Format("{0:#0.######}", weight);
config.AllowDownWeight = weight;
XmlUtil.SerializerObjToFile(config);
}
}
private void lineGroupSetBtn_Click(object sender, EventArgs e)
{
new DeliverLineGroupSelectDialog().ShowDialog();
BindDeliverLineGroup(true);
}
Color color = Color.FromArgb(105, 105, 105);
Color selectColor = Color.FromArgb(250, 120, 24);
void BindDeliverLineGroup(bool loadNew)
{
flowLayoutPanel1.Controls.Clear();
mLineGroupIds.Clear();
if (loadNew)
config = XmlUtil.DeserializeFromFile<SegmentStockUpConfig>();
foreach (var item in config.LineGroup)
{
var btn = new ColorButton() { Width = 150, Height = 60, Text = item.Name, Tag = item, Font = new Font("宋体", 14), Margin = new Padding(30) };
btn.BackColor = color;
btn.Click += DeliverLineBtn_Click;
flowLayoutPanel1.Controls.Add(btn);
}
}
private void DeliverLineBtn_Click(object sender, EventArgs e)
{
var btn = sender as ColorButton;
var item = (DeliverLineGroup)btn.Tag;
var first = mLineGroupIds.FirstOrDefault(x => x == item.ID);
if (first == 0)
{
mLineGroupIds.Add(item.ID);
btn.BackColor = selectColor;
}
else
{
mLineGroupIds.Remove(item.ID);
btn.BackColor = color;
}
}
}
class DeliverGoodsLineTemp
{
public string Name { get; set; }
public int RowIndex { get; set; }
public decimal? SecondNumber { get; set; }
public decimal? UnitNum { get; set; }
public decimal? SSecondNumber { get; set; }
public decimal? SUnitNum { get; set; }
public override bool Equals(object obj)
{
var tag = obj as DeliverGoodsLineTemp;
return tag.Name == this.Name
&& tag.UnitNum == this.UnitNum
&& tag.SecondNumber == this.SecondNumber
&& tag.SUnitNum == this.SUnitNum
&& tag.SSecondNumber == this.SSecondNumber;
}
public override int GetHashCode()
{
var hc1 = Name.GetHashCode();
var hc2 = UnitNum.GetHashCode();
var hc3 = SecondNumber.GetHashCode();
var hc4 = SUnitNum.GetHashCode();
var hc5 = SSecondNumber.GetHashCode();
return hc1 ^ hc2 ^ hc3 ^ hc4 ^ hc5;
}
}
}