index.vue 18 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466
  1. <template>
  2. <div class="page-container row-container">
  3. <!-- 左侧区域 -->
  4. <section class="list-part-container" style="flex: 3">
  5. <!-- 搜索区 -->
  6. <el-form class="list-search-container" :model="queryDayworkParams" ref="queryRef" :inline="true"
  7. style="margin-right: 0px">
  8. <el-form-item class="section-title" label="生产批次" />
  9. <el-form-item label="生产计划单号:">
  10. <el-input placeholder="请输入生产计划单号/批次号" v-model.trim="queryDayworkParams.productionPlanNo"
  11. @keydown.enter.prevent clearable style="width: 100px" />
  12. </el-form-item>
  13. <el-form-item label="产品描述:">
  14. <el-input placeholder="请输入产品描述" v-model.trim="queryDayworkParams.productDescription" @keydown.enter.prevent
  15. clearable style="width: 100px" />
  16. </el-form-item>
  17. <el-form-item class="section-title" label="请选择当前工段:">
  18. <el-select-v2 v-model="queryDayworkParams.deptId" :options="deptList" placeholder="请选择工段" style="width: 100px"
  19. @change="handleDeptChange" />
  20. </el-form-item>
  21. <el-form-item class="section-title" label="查询设备:" prop="equipmentDetailCode">
  22. <el-input placeholder="请输入设备名称" v-model.trim="queryDayworkParams.equipmentDetailCode" @keydown.enter.prevent
  23. clearable style="width: 100px" />
  24. </el-form-item>
  25. <el-form-item style="margin-left: 0">
  26. <el-button type="info" icon="Search" :disabled="deptList.length === 0" @click="handleQuery">搜索
  27. </el-button>
  28. </el-form-item>
  29. </el-form>
  30. <div class="el-table-container">
  31. <div class="el-table-inner-container">
  32. <el-table ref="dayworkTable" :data="dayworkList" v-loading="dayworkLoading" highlight-current-row
  33. height="100%" @current-change="handleDayworkCurrentChange">
  34. <el-table-column label="客户简称" prop="companyAlias" width="120" align="center" />
  35. <el-table-column label="生产计划单号" prop="productionPlanNo" width="100" align="center" />
  36. <el-table-column label="批次号" min-width="120" prop="lotCode" align="center">
  37. <template #default="scope">
  38. <el-button link type="primary" v-hasPermi="['business:productionPlan:query']"
  39. @click="handleColumnClick(scope.row)"><span>{{ scope.row.lotCode }}</span></el-button>
  40. </template>
  41. </el-table-column>
  42. <el-table-column label="产品描述" prop="productDescription" align="center" />
  43. <el-table-column label="图纸版本" prop="technologyVersion" width="60" align="center" />
  44. <el-table-column label="投产量" prop="productionQuantity" width="60" align="center" />
  45. <el-table-column label="下达日期" prop="createTime" width="100" align="center">
  46. <template #default="scope">
  47. <span>{{
  48. proxy.moment(scope.row.createTime).format("YYYY-MM-DD")
  49. }}</span>
  50. </template>
  51. </el-table-column>
  52. <el-table-column label="报工总时长" prop="totalWorkingHours" width="150" align="center" />
  53. </el-table>
  54. </div>
  55. </div>
  56. <!-- 分页 -->
  57. <pagination v-show="total > 0" :total="total" v-model:page="queryDayworkParams.pageNum"
  58. v-model:limit="queryDayworkParams.pageSize" @pagination="getDayworks" />
  59. </section>
  60. <!-- 右侧区域 -->
  61. <section class="list-part-container" style="flex: 2">
  62. <el-form class="list-search-container" :inline="true">
  63. <el-form-item class="section-title" label="报工信息" />
  64. <el-form-item class="section-title" label="请选择工序:" prop="processId">
  65. <el-select-v2 v-model="queryItemParams.processId" clearable :options="processList" placeholder="请选择工序"
  66. style="width: 100%" @change="handleProcessChange" />
  67. </el-form-item>
  68. </el-form>
  69. <div class="el-table-container">
  70. <div class="el-table-inner-container">
  71. <el-table :data="dayworkItemList" v-loading="dayworkItemLoading" height="100%">
  72. <el-table-column label="操作者" prop="nickName" width="60" align="center" />
  73. <el-table-column label="工序名称" prop="processAlias" align="center" />
  74. <el-table-column label="投产量" prop="prodNum" width="60" align="center" />
  75. <el-table-column label="合格数" prop="qualifiedNum" width="60" align="center" />
  76. <el-table-column label="废品数" prop="rejectNum" width="60" align="center" />
  77. <el-table-column label="开始时间" prop="startTime" width="160" align="center" />
  78. <el-table-column label="结束时间" prop="endTime" width="160" align="center" />
  79. <el-table-column label="总工时" prop="workingHours" width="160" align="center" />
  80. <el-table-column label="生产状态" prop="status" width="100" align="center">
  81. <template #default="scope">
  82. <dict-tag :options="daywork_status" :value="scope.row.status" />
  83. </template>
  84. </el-table-column>
  85. <el-table-column fixed="right" label="操作" align="center" width="200px">
  86. <template #default="scope">
  87. <el-button v-show="scope.row.deptProcessStatus &&
  88. (scope.row.status == 2 || scope.row.status == 3) &&
  89. scope.row.id == latestProcessId && scope.row.deptId == latestDeptId && !(lastStatus == 4 || lastStatus == 5 || lastStatus == 7)
  90. " link type="warning" icon="Edit" @click="handleUpdateDayworkItem(scope.row)">编辑
  91. </el-button>
  92. <el-button link type="primary" icon="View" @click="handleCheckDayworkItem(scope.row)">查看
  93. </el-button>
  94. <el-button v-show="scope.row.deptProcessStatus &&
  95. (scope.row.status == 2 || scope.row.status == 3) &&
  96. scope.row.id == latestProcessId && scope.row.deptId == latestDeptId && !(lastStatus == 4 || lastStatus == 5 || lastStatus == 7) &&
  97. (scope.row.processStepNumber != lastProcessStepNumber) && currentDaywork.status !=2
  98. " v-hasPermi="['business:daywork:remove']" link type="danger" icon="Delete"
  99. @click="handleDeletedItem(scope.row.id)">删除
  100. </el-button>
  101. </template>
  102. </el-table-column>
  103. </el-table>
  104. </div>
  105. </div>
  106. <!-- 分页 -->
  107. <pagination v-show="itemTotal > 0" :total="itemTotal" v-model:page="queryItemParams.pageNum"
  108. v-model:limit="queryItemParams.pageSize" @pagination="getDayworkItems" />
  109. </section>
  110. <!-- 报工信息表单 -->
  111. <daywork-item-form ref="dayworkItemRef" @handleSaveSuccess="handleGetDayworkItems" />
  112. <!-- 分选报工信息表单 -->
  113. <sort-item-form ref="sortItemRef" @handleSaveSuccess="handleGetDayworkItems" />
  114. </div>
  115. </template>
  116. <script setup>
  117. import {
  118. listDaywork,
  119. listDayworkItem,
  120. getProcessList,
  121. delDayworkItem
  122. } from "@/api/business/daywork.js";
  123. import { listDeptProcess } from "@/api/business/deptProcess";
  124. import { getDept } from "@/api/business/planDetailSubDetail.js";
  125. import router from "@/router";
  126. import dayworkItemForm from "./form";
  127. import sortItemForm from "./sortForm"
  128. const { proxy } = getCurrentInstance();
  129. /** 字典 */
  130. const { daywork_status } = proxy.useDict("daywork_status");
  131. /** 生产批次 */
  132. const dayworkList = ref([]);
  133. const dayworkTable = ref(null);
  134. const currentDaywork = ref({});
  135. const dayworkLoading = ref(false);
  136. const total = ref(0);
  137. /**工段 */
  138. const deptList = ref([]);
  139. const loading = ref(false);
  140. /** 报工信息 */
  141. const dayworkItemList = ref([]);
  142. const dayworkItemLoading = ref(false);
  143. const itemTotal = ref(0);
  144. const lastStatus = ref(null)
  145. const latestProcessId = ref(null);
  146. const latestDeptId = ref(null)
  147. const lastProcessStepNumber = ref(null)
  148. const deptProcessList = ref([]);
  149. /**工序 */
  150. const processList = ref([]);
  151. /** 查询对象 */
  152. const queryDayworkParams = ref({
  153. productDescription: "",
  154. deptId: "",
  155. lotCode: "",
  156. pageNum: 1,
  157. pageSize: 10,
  158. });
  159. const queryItemParams = ref({
  160. dayworkId: "0",
  161. isAmend: 0,
  162. isWasteRecycling: 0,
  163. pageNum: 1,
  164. pageSize: 10,
  165. technologicalProcessDetailId: null,
  166. });
  167. /*********************** 工段相关事件 ****************************/
  168. function getList() {
  169. loading.value = true;
  170. getDept().then((response) => {
  171. deptList.value = response.data;
  172. loading.value = false;
  173. if (deptList.value.length > 0) {
  174. queryDayworkParams.value.deptId = deptList.value[0].value;
  175. getDayworks();
  176. } else {
  177. dayworkList.value = [];
  178. }
  179. });
  180. }
  181. //切换工段
  182. function handleDeptChange() {
  183. getDayworks();
  184. }
  185. /*********************** 生产批次相关事件 ****************************/
  186. /** 查询计划明细 */
  187. function getDayworks() {
  188. dayworkLoading.value = true;
  189. listDaywork(queryDayworkParams.value).then((res) => {
  190. dayworkList.value = res.rows;
  191. for (var i = 0; i < dayworkList.value.length; i++) {
  192. let timeStamp = dayworkList.value[i].totalWorkingHours;
  193. let seconds = Math.floor((timeStamp / 1000) % 60);
  194. let minutes = Math.floor((timeStamp / (1000 * 60)) % 60);
  195. let hours = Math.floor(timeStamp / (1000 * 60 * 60));
  196. let time = `${hours}小时${minutes}分钟${seconds}秒`;
  197. dayworkList.value[i].totalWorkingHours = time;
  198. }
  199. total.value = res.total;
  200. dayworkLoading.value = false;
  201. // 批次
  202. if (dayworkList.value.length > 0) {
  203. proxy.$refs.dayworkTable.setCurrentRow(dayworkList.value[0]);
  204. console.log(dayworkList.value[0])
  205. } else {
  206. dayworkItemList.value = [];
  207. itemTotal.value = 0;
  208. }
  209. });
  210. }
  211. /** 打开批次详情页 */
  212. function handleColumnClick(row) {
  213. router.push({ path: "/reviseBath/lotFormParticulars/" + row.lotCode });
  214. }
  215. /** 生产计划明细 current-change 事件 */
  216. function handleDayworkCurrentChange(row) {
  217. if (row) {
  218. queryItemParams.value.processId = null;
  219. currentDaywork.value = row;
  220. queryItemParams.value.dayworkId = currentDaywork.value.id;
  221. queryItemParams.value.isAmend = row.isAmend;
  222. queryItemParams.value.isWasteRecycling = row.isWasteRecycling;
  223. queryItemParams.value.technologicalProcessDetailId = null;
  224. queryItemParams.value.technologicalProcessId = row.technologicalProcessId;
  225. getDayworkItems();
  226. getProcess();
  227. } else {
  228. dayworkItemList.value = [];
  229. itemTotal.value = 0;
  230. }
  231. }
  232. /*********************** 报工信息相关事件 ****************************/
  233. //查询报工信息数据
  234. function handleGetDayworkItems() {
  235. dayworkLoading.value = true;
  236. listDaywork(queryDayworkParams.value).then((res) => {
  237. dayworkList.value = res.rows;
  238. for (var i = 0; i < dayworkList.value.length; i++) {
  239. let timeStamp = dayworkList.value[i].totalWorkingHours;
  240. let seconds = Math.floor((timeStamp / 1000) % 60);
  241. let minutes = Math.floor((timeStamp / (1000 * 60)) % 60);
  242. let hours = Math.floor(timeStamp / (1000 * 60 * 60));
  243. let time = `${hours}小时${minutes}分钟${seconds}秒`;
  244. dayworkList.value[i].totalWorkingHours = time;
  245. }
  246. total.value = res.total;
  247. dayworkLoading.value = false;
  248. if (dayworkList.value.length > 0) {
  249. for (var i = 0; i < dayworkList.value.length; i++) {
  250. if (dayworkList.value[i].id == currentDaywork.value.id) {
  251. var index = i;
  252. break;
  253. }
  254. }
  255. }
  256. proxy.$refs.dayworkTable.setCurrentRow(dayworkList.value[index]);
  257. });
  258. }
  259. //删除报工信息
  260. function handleDeletedItem(id) {
  261. proxy.$modal
  262. .confirm("是否确认删除选中的数据项?")
  263. .then(function () {
  264. delDayworkItem(id).then(res => {
  265. if (res.code == 200) {
  266. proxy.$modal.msgSuccess("删除成功")
  267. listDaywork(queryDayworkParams.value).then((res) => {
  268. dayworkList.value = res.rows;
  269. for (var i = 0; i < dayworkList.value.length; i++) {
  270. let timeStamp = dayworkList.value[i].totalWorkingHours;
  271. let seconds = Math.floor((timeStamp / 1000) % 60);
  272. let minutes = Math.floor((timeStamp / (1000 * 60)) % 60);
  273. let hours = Math.floor(timeStamp / (1000 * 60 * 60));
  274. let time = `${hours}小时${minutes}分钟${seconds}秒`;
  275. dayworkList.value[i].totalWorkingHours = time;
  276. }
  277. total.value = res.total;
  278. // 批次
  279. proxy.$refs.dayworkTable.setCurrentRow(dayworkList.value[dayworkList.value.findIndex(daywork => daywork.id == currentDaywork.value.id)]);
  280. });
  281. }
  282. })
  283. })
  284. }
  285. //修改报工信息
  286. function handleUpdateDayworkItem(row) {
  287. //同工序下状态是否有工序已完成
  288. let processFinish = false;
  289. //除了编辑此条以外的同工序合格数
  290. let totalQuailifiedNum = 0;
  291. for (let i = 0; i < dayworkItemList.value.length; i++) {
  292. if (
  293. row.processId == dayworkItemList.value[i].processId &&
  294. (dayworkItemList.value[i].status == 2 ||
  295. dayworkItemList.value[i].status == 3) &&
  296. row.id != dayworkItemList.value[i].id
  297. ) {
  298. totalQuailifiedNum += dayworkItemList.value[i].qualifiedNum;
  299. }
  300. if (
  301. row.processId == dayworkItemList.value[i].processId &&
  302. dayworkItemList.value[i].status == 3 &&
  303. row.id != dayworkItemList.value[i].id
  304. ) {
  305. processFinish = true;
  306. }
  307. }
  308. let maxQuailifiedNum =
  309. Math.floor(row.prodNum * 1.03 - totalQuailifiedNum) > 0
  310. ? Math.floor(row.prodNum * 1.03 - totalQuailifiedNum)
  311. : 0;
  312. //该daywork合格数总数不能超过投产数的103%
  313. row.technologicalProcessId = queryItemParams.value.technologicalProcessId;
  314. row.deptId = queryDayworkParams.value.deptId;
  315. row.productionPlanDetailId = currentDaywork.value.productionPlanDetailId;
  316. row.dayworkId = currentDaywork.value.id;
  317. row.lotId = currentDaywork.value.lotId;
  318. row.isAmend = currentDaywork.value.isAmend;
  319. row.isWasteRecycling = currentDaywork.value.isWasteRecycling;
  320. row.maxQuailifiedNum = maxQuailifiedNum;
  321. row.totalQuailifiedNum = totalQuailifiedNum;
  322. //判断是否是当前工段
  323. if (row.deptId == currentDaywork.value.deptId) {
  324. row.currentDept = true;
  325. } else {
  326. row.currentDept = false;
  327. }
  328. //修改向form表单传一个状态值
  329. row.editStatus = true;
  330. //如果为true,则同工序已有工序已完成
  331. row.processFinish = processFinish;
  332. if(row.isSort == 0){
  333. proxy.$refs.dayworkItemRef.open(row);
  334. }else{
  335. proxy.$refs.sortItemRef.open(row);
  336. }
  337. }
  338. //查看报工信息
  339. function handleCheckDayworkItem(row) {
  340. row.technologicalProcessId = queryItemParams.value.technologicalProcessId;
  341. row.deptId = queryDayworkParams.value.deptId;
  342. row.productionPlanDetailId = currentDaywork.value.productionPlanDetailId;
  343. row.isAmend = currentDaywork.value.isAmend;
  344. row.isWasteRecycling = currentDaywork.value.isWasteRecycling;
  345. row.dayworkId = currentDaywork.value.id;
  346. row.lotId = currentDaywork.value.lotId;
  347. //判断是否是当前工段
  348. if (row.deptId == currentDaywork.value.deptId) {
  349. row.currentDept = true;
  350. } else {
  351. row.currentDept = false;
  352. }
  353. //修改向form表单传一个状态值
  354. row.editStatus = false;
  355. // row.returnFlag = false;
  356. // //如果是最新工序的已接收,则传一个状态值,给form表单一个退回按钮
  357. // if (row.processId == latestProcessId.value && row.status == 7) {
  358. // row.returnFlag = true;
  359. // }
  360. if(row.isSort == 0){
  361. proxy.$refs.dayworkItemRef.open(row);
  362. }else{
  363. proxy.$refs.sortItemRef.open(row);
  364. }
  365. }
  366. /**切换工序 */
  367. function handleProcessChange() {
  368. getDayworkItems();
  369. }
  370. /** 报工详情列表 */
  371. function getDayworkItems() {
  372. dayworkItemLoading.value = true;
  373. //查询该工段在工段资源分配时绑定的工序,传一个flag,如果flag有值则后端查询不分页
  374. listDeptProcess({ deptId: queryDayworkParams.value.deptId, flag: 1 }).then(
  375. (res) => {
  376. deptProcessList.value = res.rows;
  377. listDayworkItem(queryItemParams.value).then((res) => {
  378. console.log(currentDaywork.value);
  379. for (let i = 0; i < res.rows.length; i++) {
  380. //如果时首序,投产数是单批数
  381. if (res.rows[i].processStepNumber === res.others.isFirst && res.rows[i].prodNum == 0) {
  382. if (currentDaywork.value.isLast == 1) {
  383. res.rows[i].prodNum = currentDaywork.value.lastLotQuantity;
  384. } else {
  385. res.rows[i].prodNum = currentDaywork.value.oneLotQuantity;
  386. }
  387. }
  388. //拿到最新一条报工信息的工序id,只能编辑当前序
  389. // if (res.rows[i] == res.rows[res.rows.length - 1]) {
  390. // latestProcessId.value = res.rows[i].processId;
  391. // }
  392. }
  393. if (res.others != null && res.others.latestProcessId != null) {
  394. latestProcessId.value = res.others.latestProcessId
  395. }
  396. if (res.others != null && res.others.lastItem != null) {
  397. latestDeptId.value = res.others.lastItem.deptId
  398. lastStatus.value = res.others.lastItem.status
  399. }
  400. for (var i = 0; i < res.rows.length; i++) {
  401. let timeStamp = res.rows[i].workingHours;
  402. let seconds = Math.floor((timeStamp / 1000) % 60);
  403. let minutes = Math.floor((timeStamp / (1000 * 60)) % 60);
  404. let hours = Math.floor(timeStamp / (1000 * 60 * 60));
  405. let time = `${hours}小时${minutes}分钟${seconds}秒`;
  406. res.rows[i].workingHours = time;
  407. res.rows[i].deptProcessStatus = false;
  408. //报工记录的工序id是该工段绑定的工序时,允许编辑
  409. for (var item = 0; item < deptProcessList.value.length; item++) {
  410. if (res.rows[i].processId == deptProcessList.value[item].processId) {
  411. res.rows[i].deptProcessStatus = true;
  412. }
  413. }
  414. console.log(res.rows[i].deptProcessStatus)
  415. }
  416. dayworkItemList.value = res.rows;
  417. getProcess();
  418. itemTotal.value = res.total;
  419. dayworkItemLoading.value = false;
  420. });
  421. }
  422. );
  423. }
  424. //工序信息
  425. function getProcess() {
  426. //工序下拉框
  427. getProcessList({
  428. technologicalProcessId: queryItemParams.value.technologicalProcessId,
  429. isWasteRecycling: currentDaywork.value.isWasteRecycling,
  430. isAmend: currentDaywork.value.isAmend,
  431. lotId: currentDaywork.value.lotId,
  432. }).then((res) => {
  433. processList.value = res.data;
  434. });
  435. }
  436. /** 搜索按钮操作 */
  437. function handleQuery() {
  438. getDayworks();
  439. }
  440. onMounted(() => {
  441. getList();
  442. });
  443. </script>
  444. <style scoped>
  445. .el-form--inline .el-form-item {
  446. margin-right: 20px;
  447. }
  448. </style>