|
|
@@ -571,10 +571,11 @@ namespace Business.ResourceExamineManagement
|
|
|
/// <summary>
|
|
|
/// 产能计算
|
|
|
/// </summary>
|
|
|
- /// <param name="tech_id">工艺路径主键</param>
|
|
|
+ /// <param name="bom_number">bom编号</param>
|
|
|
+ /// <param name="version">版本号</param>
|
|
|
/// <param name="packages">需要生产产品件数</param>
|
|
|
/// <returns>生产时长</returns>
|
|
|
- public async Task<decimal> ProductiveExamine(string bom_number, int packages)
|
|
|
+ public async Task<decimal> ProductiveExamine(string bom_number, string version, int packages)
|
|
|
{
|
|
|
if (packages <= 0)
|
|
|
{
|
|
|
@@ -582,7 +583,7 @@ namespace Business.ResourceExamineManagement
|
|
|
}
|
|
|
#region 1、数据准备
|
|
|
//1.1、获取工艺路径数据
|
|
|
- mes_technique tech = _mes_technique.Find(p => p.bom == bom_number && p.tenant_id == param.tenantId && p.factory_id == param.factoryId && !p.IsDeleted).Result.FirstOrDefault();
|
|
|
+ mes_technique tech = _mes_technique.Find(p => p.bom == bom_number && p.bomver == version && p.tenant_id == param.tenantId && p.factory_id == param.factoryId && !p.IsDeleted).Result.FirstOrDefault();
|
|
|
if (tech == null)
|
|
|
{
|
|
|
throw new NotImplementedException("请先配置工艺路径!");
|
|
|
@@ -606,10 +607,6 @@ namespace Business.ResourceExamineManagement
|
|
|
List<mes_tech_proc_workshop> tech_Proc_Workshops = await _mes_tech_proc_workshop.GetManyByCondition(p => techProcIds.Contains(p.tech_proc_id.Value) && p.tenant_id == param.tenantId && p.factory_id == param.factoryId && !p.IsDeleted);
|
|
|
#endregion
|
|
|
|
|
|
- #region 计算产能,得到耗时
|
|
|
- decimal sumTimes = 0.00m;//总耗时(分钟)
|
|
|
- //工序需要等待时间记录
|
|
|
- List<StartTimeDto> starts = new List<StartTimeDto>();
|
|
|
//1、获取工艺路径下的第一层级工序
|
|
|
List<mes_tech_process> fistChilds = tech_Processes.Where(p => p.parentprocid == tech.Id).ToList();
|
|
|
if (fistChilds.Count == 0)
|
|
|
@@ -620,89 +617,168 @@ namespace Business.ResourceExamineManagement
|
|
|
//添加最后一个工序
|
|
|
var last = fistChilds.First(p => p.nextprocid == null);
|
|
|
sortChilds.Add(last);
|
|
|
+ //递归按工序先后顺序排序
|
|
|
SortProcess(fistChilds, last.Id, sortChilds);
|
|
|
+ //总耗时(分钟)
|
|
|
+ //decimal sumTimes = CalcTakeTimeByLq(sortChilds, packages);//通过Lq计算
|
|
|
+ decimal sumTimes = CalcTakeTimeByLqt(sortChilds, packages);//通过Lqt计算
|
|
|
+ return sumTimes;
|
|
|
+ }
|
|
|
+
|
|
|
+ /// <summary>
|
|
|
+ /// 递归:工序按照先后顺序排序-暂时不考虑两个分支合并到一个分支的情况
|
|
|
+ /// </summary>
|
|
|
+ /// <param name="Processes"></param>
|
|
|
+ /// <param name="processId"></param>
|
|
|
+ /// <param name="sortProcesses"></param>
|
|
|
+ private void SortProcess(List<mes_tech_process> Processes, long processId, List<mes_tech_process> sortProcesses)
|
|
|
+ {
|
|
|
+ var curProcess = Processes.Where(p => p.nextprocid == processId).FirstOrDefault();
|
|
|
+ if (curProcess != null)
|
|
|
+ {
|
|
|
+ sortProcesses.AddFirst(curProcess);
|
|
|
+ SortProcess(Processes, curProcess.Id, sortProcesses);
|
|
|
+ }
|
|
|
+ }
|
|
|
|
|
|
- decimal curTakeTime = 0.00m;//当前工序耗时(分钟)
|
|
|
- //添加第一个工序需要等待时间记录
|
|
|
+ /// <summary>
|
|
|
+ /// 通过Lq计算工艺耗时
|
|
|
+ /// </summary>
|
|
|
+ /// <param name="Processes"></param>
|
|
|
+ /// <param name="packages"></param>
|
|
|
+ /// <returns></returns>
|
|
|
+ private decimal CalcTakeTimeByLq(List<mes_tech_process> Processes, int packages)
|
|
|
+ {
|
|
|
+ decimal sumTimes = 0.00m;//总耗时(分钟)
|
|
|
+ //工序需要等待时间记录
|
|
|
+ List<StartTimeDto> starts = new List<StartTimeDto>();
|
|
|
StartTimeDto dto;
|
|
|
- foreach (var chd in fistChilds)
|
|
|
+ foreach (var chd in Processes)
|
|
|
{
|
|
|
dto = new StartTimeDto();
|
|
|
if (chd.nextprocid == null)//最后一个工序
|
|
|
{
|
|
|
//计算最后一个工序耗时
|
|
|
- curTakeTime = CalcTakeTime(chd, packages);
|
|
|
+ dto = CalcProcTakeTimeByLq(chd, packages, packages);
|
|
|
}
|
|
|
else
|
|
|
{
|
|
|
- curTakeTime = CalcTakeTime(chd, chd.lq.Value);
|
|
|
+ dto = CalcProcTakeTimeByLq(chd, chd.lq.Value, packages);
|
|
|
}
|
|
|
- sumTimes += curTakeTime;
|
|
|
- //添加耗时记录
|
|
|
- dto.tech_id = tech.Id;
|
|
|
- dto.proc_id = chd.proc_id.Value;
|
|
|
- dto.nextproc_id = chd.nextprocid;
|
|
|
- dto.wait_time = curTakeTime;
|
|
|
+ sumTimes += dto.wait_time;
|
|
|
+ //添加记录
|
|
|
starts.Add(dto);
|
|
|
}
|
|
|
- #endregion
|
|
|
-
|
|
|
return sumTimes;
|
|
|
}
|
|
|
|
|
|
/// <summary>
|
|
|
- /// 递归:工序按照先后顺序排序-暂时不考虑两个分支合并到一个分支的情况
|
|
|
+ /// 通过Lq计算当前工序前置准备时间
|
|
|
+ /// </summary>
|
|
|
+ /// <param name="proc"></param>
|
|
|
+ /// <param name="quantity">LeadQuantity to Start Next</param>
|
|
|
+ /// <param name="packages">件数</param>
|
|
|
+ /// <returns></returns>
|
|
|
+ private StartTimeDto CalcProcTakeTimeByLq(mes_tech_process proc, decimal quantity, int packages)
|
|
|
+ {
|
|
|
+ //记录当前工序耗时
|
|
|
+ StartTimeDto dto = new StartTimeDto();
|
|
|
+ //添加耗时记录
|
|
|
+ dto.tech_id = proc.tech_id.Value;
|
|
|
+ dto.proc_id = proc.proc_id.Value;
|
|
|
+ dto.nextproc_id = proc.nextprocid;
|
|
|
+ if (proc.wctype == 1)//人工型:数量/uph(一小时生产数量)*60(小时转换为分钟)/wsinuse(工位数)
|
|
|
+ {
|
|
|
+ dto.wait_time = quantity / proc.uph.Value * 60 / proc.wsinuse.Value;
|
|
|
+ dto.take_time = packages / proc.uph.Value * 60 / proc.wsinuse.Value;
|
|
|
+ }
|
|
|
+ else if (proc.wctype == 2)//流水线型:数量*ct(生产一件所需时间)/wsinuse(工位数)
|
|
|
+ {
|
|
|
+ dto.wait_time = quantity * proc.ct.Value / proc.wsinuse.Value;
|
|
|
+ dto.take_time = packages * proc.ct.Value / proc.wsinuse.Value;
|
|
|
+ }
|
|
|
+ else if (proc.wctype == 3)//设备型:向上取整(数量/一次可加工数量/wsinuse(工位数))*ct(老化一次所需时间)
|
|
|
+ {
|
|
|
+ dto.wait_time = Math.Ceiling(quantity / proc.upe.Value / proc.wsinuse.Value) * proc.ct.Value;
|
|
|
+ dto.take_time = Math.Ceiling(packages / proc.upe.Value / proc.wsinuse.Value) * proc.ct.Value;
|
|
|
+ }
|
|
|
+ return dto;
|
|
|
+ }
|
|
|
+
|
|
|
+ /// <summary>
|
|
|
+ /// 通过Lqt计算工艺耗时
|
|
|
/// </summary>
|
|
|
/// <param name="Processes"></param>
|
|
|
- /// <param name="processId"></param>
|
|
|
- /// <param name="sortProcesses"></param>
|
|
|
- private void SortProcess(List<mes_tech_process> Processes, long processId, List<mes_tech_process> sortProcesses)
|
|
|
+ /// <param name="packages"></param>
|
|
|
+ /// <returns></returns>
|
|
|
+ private decimal CalcTakeTimeByLqt(List<mes_tech_process> Processes, int packages)
|
|
|
{
|
|
|
- var curProcess = Processes.Where(p => p.nextprocid == processId).FirstOrDefault();
|
|
|
- if (curProcess != null)
|
|
|
+ //总耗时
|
|
|
+ decimal sumTimes = 0;
|
|
|
+ //工序需要等待时间记录
|
|
|
+ List<StartTimeDto> starts = new List<StartTimeDto>();
|
|
|
+ StartTimeDto dto;
|
|
|
+ foreach (var chd in Processes)
|
|
|
{
|
|
|
- sortProcesses.AddFirst(curProcess);
|
|
|
- SortProcess(Processes, curProcess.Id, sortProcesses);
|
|
|
+ dto = new StartTimeDto();
|
|
|
+ //添加耗时记录
|
|
|
+ dto.tech_id = chd.tech_id.Value;
|
|
|
+ dto.proc_id = chd.proc_id.Value;
|
|
|
+ dto.nextproc_id = chd.nextprocid;
|
|
|
+
|
|
|
+ //计算当前工序生产耗时
|
|
|
+ dto.take_time = CalcProcTakeTime(chd, packages);
|
|
|
+ if (chd.nextprocid == null)//最后一个工序
|
|
|
+ {
|
|
|
+ dto.wait_time = dto.take_time;
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+ dto.wait_time = chd.lqt.Value;
|
|
|
+ }
|
|
|
+ sumTimes += dto.wait_time;
|
|
|
+ //添加记录
|
|
|
+ starts.Add(dto);
|
|
|
}
|
|
|
+ return sumTimes;
|
|
|
}
|
|
|
|
|
|
/// <summary>
|
|
|
- /// 计算当前工序前置准备时间
|
|
|
+ /// 计算当前工序生产时间
|
|
|
/// </summary>
|
|
|
/// <param name="proc"></param>
|
|
|
- /// <param name="quantity">LeadQuantity to Start Next</param>
|
|
|
+ /// <param name="packages">件数</param>
|
|
|
/// <returns></returns>
|
|
|
- private decimal CalcTakeTime(mes_tech_process proc, decimal quantity)
|
|
|
+ private decimal CalcProcTakeTime(mes_tech_process proc, int packages)
|
|
|
{
|
|
|
- decimal takeTime = 0.00m;//当前工序前置准备时间(分钟)
|
|
|
+ //当前工序生产时间
|
|
|
+ decimal takeTiem = 0.00m;
|
|
|
+
|
|
|
if (proc.wctype == 1)//人工型:数量/uph(一小时生产数量)*60(小时转换为分钟)/wsinuse(工位数)
|
|
|
{
|
|
|
- takeTime = quantity / proc.uph.Value * 60 / proc.wsinuse.Value;
|
|
|
- return takeTime;
|
|
|
+ takeTiem = packages / proc.uph.Value * 60 / proc.wsinuse.Value;
|
|
|
}
|
|
|
else if (proc.wctype == 2)//流水线型:数量*ct(生产一件所需时间)/wsinuse(工位数)
|
|
|
{
|
|
|
- takeTime = quantity * proc.ct.Value / proc.wsinuse.Value;
|
|
|
- return takeTime;
|
|
|
+ takeTiem = packages * proc.ct.Value / proc.wsinuse.Value;
|
|
|
}
|
|
|
else if (proc.wctype == 3)//设备型:向上取整(数量/一次可加工数量/wsinuse(工位数))*ct(老化一次所需时间)
|
|
|
{
|
|
|
- takeTime = Math.Ceiling(quantity / proc.upe.Value / proc.wsinuse.Value) * proc.ct.Value;
|
|
|
- return takeTime;
|
|
|
+ takeTiem = Math.Ceiling(packages / proc.upe.Value / proc.wsinuse.Value) * proc.ct.Value;
|
|
|
}
|
|
|
- return takeTime;
|
|
|
+ return takeTiem;
|
|
|
}
|
|
|
|
|
|
-
|
|
|
/// <summary>
|
|
|
/// 生成工单
|
|
|
/// </summary>
|
|
|
/// <param name="seorderentry">销售订单子表</param>
|
|
|
/// <param name="BomNumber">Bom编号</param>
|
|
|
+ /// <param name="version">Bom版本</param>
|
|
|
/// <param name="number">物料编码</param>
|
|
|
/// <param name="Quantity"></param>
|
|
|
/// <param name="ParentId"></param>
|
|
|
- public void GenerateMorder(crm_seorderentry seorderentry, string BomNumber, string number, decimal? Quantity, long? ParentId)
|
|
|
+ public void GenerateMorder(crm_seorderentry seorderentry, string BomNumber,string version, string number, decimal? Quantity, long? ParentId)
|
|
|
{
|
|
|
//1.库存、在制工单检查完成后 当前BOM需要自制时 产生工单。
|
|
|
|
|
|
@@ -732,7 +808,7 @@ namespace Business.ResourceExamineManagement
|
|
|
mes_Morder.moentry_sys_stime = StartDate;
|
|
|
if (!string.IsNullOrEmpty(BomNumber))
|
|
|
{
|
|
|
- var ProductiveDate = ProductiveExamine(BomNumber, (int)(Quantity.Value));
|
|
|
+ var ProductiveDate = ProductiveExamine(BomNumber, version,(int)(Quantity.Value));
|
|
|
//系统建议完工日期为 开工日期+产能检查时间=完工日期
|
|
|
var Day = ProductiveDate.Result / (60 * 10); //返回的分钟除以十个小时得出工作天数;
|
|
|
mes_Morder.moentry_sys_etime = StartDate.AddDays((double)Day);
|