Ddtails.vue 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450
  1. <template>
  2. <ele-modal
  3. :before-close="cancel"
  4. :close-on-click-modal="false"
  5. :maxable="true"
  6. :title="title"
  7. :visible.sync="detailsVisible"
  8. append-to-body
  9. custom-class="ele-dialog-form"
  10. width="75vw"
  11. >
  12. <el-form
  13. ref="form"
  14. :model="form"
  15. :rules="rules"
  16. label-position="right"
  17. label-width="110px"
  18. >
  19. <el-row>
  20. <headerTitle style="margin-top: 15px" title="报工信息"></headerTitle>
  21. <el-col :lg="12" :md="12" :sm="12" :xl="12" :xs="12">
  22. <el-form-item
  23. :rules="{
  24. required: true,
  25. message: '请选择实际开始时间',
  26. trigger: 'change'
  27. }"
  28. label="实际开始时间"
  29. prop="realStartTime"
  30. >
  31. <el-date-picker
  32. v-model="form.realStartTime"
  33. :disabled="inputDis"
  34. class="time_select"
  35. placeholder="选择实际开始时间"
  36. type="datetime"
  37. value-format="yyyy-MM-dd HH:mm:ss"
  38. @change="handleTimeChange"
  39. ></el-date-picker>
  40. </el-form-item>
  41. </el-col>
  42. <el-col :lg="12" :md="12" :sm="12" :xl="12" :xs="12">
  43. <el-form-item
  44. :rules="{
  45. required: true,
  46. message: '请选择实际结束时间',
  47. trigger: 'change'
  48. }"
  49. label="实际结束时间"
  50. prop="realEndTime"
  51. >
  52. <el-date-picker
  53. v-model="form.realEndTime"
  54. :disabled="inputDis"
  55. class="time_select"
  56. placeholder="选择实际结束时间"
  57. type="datetime"
  58. value-format="yyyy-MM-dd HH:mm:ss"
  59. @change="handleTimeChange"
  60. ></el-date-picker>
  61. </el-form-item>
  62. </el-col>
  63. <el-col :lg="12" :md="12" :sm="12" :xl="12" :xs="12">
  64. <el-form-item label="合格数量" prop="qualifiedQuantity">
  65. <el-input
  66. v-model.number="form.qualifiedQuantity"
  67. :disabled="inputDis"
  68. placeholder="请输入"
  69. type="number"
  70. @input="(e) => handleQuantityInput(e, 'qualifiedQuantity')"
  71. ></el-input>
  72. </el-form-item>
  73. </el-col>
  74. <el-col :lg="12" :md="12" :sm="12" :xl="12" :xs="12">
  75. <el-form-item label="不合格数量" prop="unqualifiedQuantity">
  76. <el-input
  77. v-model.number="form.unqualifiedQuantity"
  78. :disabled="inputDis"
  79. placeholder="请输入"
  80. type="number"
  81. @input="(e) => handleQuantityInput(e, 'unqualifiedQuantity')"
  82. ></el-input>
  83. </el-form-item>
  84. </el-col>
  85. <el-col :lg="12" :md="12" :sm="12" :xl="12" :xs="12">
  86. <el-form-item label="合格重量" prop="qualifiedWeight">
  87. <el-input
  88. v-model.number="form.qualifiedWeight"
  89. :disabled="inputDis"
  90. placeholder="请输入"
  91. type="number"
  92. @input="(e) => handleWeightInput(e, 'qualifiedWeight')"
  93. ></el-input>
  94. </el-form-item>
  95. </el-col>
  96. <el-col :lg="12" :md="12" :sm="12" :xl="12" :xs="12">
  97. <el-form-item label="不合格重量" prop="unqualifiedWeight">
  98. <el-input
  99. v-model.number="form.unqualifiedWeight"
  100. :disabled="inputDis"
  101. placeholder="请输入"
  102. type="number"
  103. @input="(e) => handleWeightInput(e, 'unqualifiedWeight')"
  104. ></el-input>
  105. </el-form-item>
  106. </el-col>
  107. <el-col :span="24">
  108. <el-form-item label="备注信息">
  109. <el-input
  110. v-model="form.remark"
  111. :disabled="inputDis"
  112. :rows="2"
  113. placeholder="请输入"
  114. type="textarea"
  115. ></el-input>
  116. </el-form-item>
  117. </el-col>
  118. </el-row>
  119. <el-row class="tool_btn">
  120. <el-button
  121. type="primary"
  122. size="medium"
  123. @click="submitAdd"
  124. :loading="loadingBtn"
  125. >报工</el-button
  126. >
  127. </el-row>
  128. <headerTitle style="margin-top: 15px" title="工单信息"></headerTitle>
  129. <el-row :gutter="10" class="basic">
  130. <el-col
  131. v-for="item in fieldMap.orderList"
  132. :key="item.prop"
  133. :lg="8"
  134. :md="12"
  135. :sm="12"
  136. :xl="8"
  137. :xs="12"
  138. >
  139. <el-form-item :label="item.label" class="form80">
  140. <el-input v-model="current[item.prop]" disabled>
  141. <!-- <template
  142. slot="append"
  143. v-if="item.label == '要求生产数量:'"
  144. >
  145. {{ }}
  146. </template> -->
  147. </el-input>
  148. </el-form-item>
  149. </el-col>
  150. </el-row>
  151. <headerTitle style="margin-top: 15px" title="任务信息"></headerTitle>
  152. <el-row :gutter="10" class="basic">
  153. <el-col
  154. v-for="item in fieldMap.taskList"
  155. :key="item.prop"
  156. :lg="8"
  157. :md="12"
  158. :sm="12"
  159. :xl="8"
  160. :xs="12"
  161. >
  162. <el-form-item :label="item.label" class="form80">
  163. <el-input v-model="current[item.prop]" disabled></el-input>
  164. </el-form-item>
  165. </el-col>
  166. </el-row>
  167. <el-row v-if="title === '详情'">
  168. <headerTitle style="margin-top: 15px" title="报工记录"></headerTitle>
  169. <ModifyRecord ref="ModifyRecordRef" :list="list" />
  170. </el-row>
  171. <div slot="footer" class="tool_btn">
  172. <el-button @click="cancel">关闭</el-button>
  173. </div>
  174. </el-form>
  175. </ele-modal>
  176. </template>
  177. <script>
  178. import {
  179. listWorkCenter,
  180. batchUpdateRealTime,
  181. listUpdateRealTimeRecord
  182. } from '@/api/workOrderList';
  183. import ModifyRecord from '@/views/taskList/components/ModifyRecord.vue';
  184. export default {
  185. components: {
  186. ModifyRecord
  187. },
  188. props: {
  189. currentRow: {
  190. type: Object,
  191. default: () => ({})
  192. }
  193. },
  194. data() {
  195. return {
  196. title: '详情',
  197. form: {
  198. realEndTime: '',
  199. realStartTime: '',
  200. unqualifiedWeight: '',
  201. unqualifiedQuantity: '',
  202. qualifiedWeight: '',
  203. qualifiedQuantity: '',
  204. remark: ''
  205. },
  206. rules: {
  207. qualifiedQuantity: [
  208. {
  209. required: true,
  210. message: '请输入合格数量',
  211. trigger: 'blur'
  212. }
  213. ],
  214. // qualifiedWeight: [
  215. // {
  216. // required: true,
  217. // message: '请输入合格重量',
  218. // trigger: 'blur'
  219. // }
  220. // ],
  221. unqualifiedQuantity: [
  222. {
  223. required: true,
  224. message: '请输入不合格数量',
  225. trigger: 'blur'
  226. }
  227. ]
  228. // unqualifiedWeight: [
  229. // {
  230. // required: true,
  231. // message: '请输入不合格重量',
  232. // trigger: 'blur'
  233. // }
  234. // ]
  235. },
  236. current: {},
  237. detailsVisible: false,
  238. fieldMap: {
  239. orderList: [
  240. { label: '计划批次号:', prop: 'batchNo' },
  241. { label: '工单编码:', prop: 'mesWorkOrderCode' },
  242. { label: '编码', prop: 'productCode' },
  243. { label: '名称', prop: 'productName' },
  244. { label: '规格', prop: 'specification' },
  245. { label: '生产订单编码:', prop: 'workOrderCode' },
  246. { label: '计划编号:', prop: 'productionPlanCode' },
  247. { label: '工艺路线:', prop: 'produceRoutingName' },
  248. { label: '要求生产数量:', prop: 'formingNum' },
  249. { label: '要求生产重量:', prop: 'formingWeight' },
  250. { label: '所属工厂:', prop: 'factoryName' },
  251. { label: '所属班组:', prop: 'assignTeamName' },
  252. { label: '计划开始时间:', prop: 'planStartTime' },
  253. { label: '计划结束时间:', prop: 'planCompleteTime' }
  254. ],
  255. taskList: [
  256. { label: '任务编码:', prop: 'assignCode' },
  257. { label: '工序名称:', prop: 'taskName' },
  258. { label: '执行类型:', prop: 'assigneeType' },
  259. { label: '执行对象名称:', prop: 'assigneeName' },
  260. { label: '工时:', prop: 'durationText' },
  261. { label: '任务开始时间:', prop: 'startTime' },
  262. { label: '任务结束时间:', prop: 'endTime' },
  263. { label: '任务数量:', prop: 'quantity' },
  264. { label: '任务重量(kg):', prop: 'weight' }
  265. ]
  266. },
  267. loadingBtn: false,
  268. list: []
  269. };
  270. },
  271. computed: {
  272. inputDis() {
  273. return this.title === '详情';
  274. }
  275. },
  276. methods: {
  277. open(type, row, form) {
  278. this.title = type === 'report' ? '报工' : '详情';
  279. this.detailsVisible = true;
  280. this.current = { ...row };
  281. if (form.realEndTime) {
  282. this.$nextTick(() => {
  283. this.form = { ...form };
  284. });
  285. if (type !== 'report') {
  286. listUpdateRealTimeRecord(row.apsAssigneeId)
  287. .then((res) => {
  288. if (res) {
  289. this.list = res;
  290. }
  291. })
  292. .catch((err) => {
  293. this.$message.error(err.message);
  294. });
  295. }
  296. }
  297. this.getData();
  298. },
  299. cancel() {
  300. this.form = {
  301. realEndTime: '',
  302. realStartTime: '',
  303. unqualifiedWeight: '',
  304. unqualifiedQuantity: '',
  305. qualifiedWeight: '',
  306. qualifiedQuantity: '',
  307. remark: ''
  308. };
  309. this.$refs.form.resetFields();
  310. this.detailsVisible = false;
  311. },
  312. async getData() {
  313. try {
  314. const res = await listWorkCenter(this.current.firstTaskId);
  315. this.$set(this.current, 'factoryName', res[0].factoryName);
  316. } catch (err) {
  317. this.$message.warning(err.message);
  318. }
  319. },
  320. // 时间选择
  321. handleTimeChange() {
  322. // 如果结束时间早于开始时间,清空结束时间
  323. if (this.form.realStartTime && this.current.startTime) {
  324. const realStartTime = new Date(this.form.realStartTime).getTime();
  325. const realEndTime = new Date(this.current.startTime).getTime();
  326. if (realStartTime < realEndTime) {
  327. this.form.realStartTime = '';
  328. this.$message.warning('实际开始时间不能早于任务开始时间');
  329. }
  330. }
  331. if (this.form.realStartTime && this.form.realEndTime) {
  332. const realStartTime = new Date(this.form.realStartTime).getTime();
  333. const realEndTime = new Date(this.form.realEndTime).getTime();
  334. if (realStartTime > realEndTime) {
  335. this.form.realEndTime = '';
  336. this.$message.warning('结束时间不能早于开始时间');
  337. }
  338. }
  339. },
  340. // 重量正则判断
  341. handleWeightInput(e, type) {
  342. // 过滤非数字和非小数点字符(包括负号)
  343. let value = e.replace(/[^\d.]/g, '');
  344. // 限制只能有一个小数点
  345. const dotCount = (value.match(/\./g) || []).length;
  346. if (dotCount > 1) {
  347. value = value.slice(0, value.lastIndexOf('.'));
  348. }
  349. // 限制不能以小数点开头
  350. if (value.startsWith('.')) {
  351. value = '0' + value;
  352. }
  353. // 更新绑定值
  354. this.form[type] = value;
  355. // this.calculateWeight(type);
  356. },
  357. //计算重量
  358. calculateWeight(type) {
  359. let total =
  360. this.form.qualifiedWeight - 0 + (this.form.unqualifiedWeight - 0);
  361. if (total > this.current.weight) {
  362. this.form[type] = 0;
  363. this.$message.warning('合格重量加不合格重量不能大于任务重量');
  364. }
  365. },
  366. // 计算数量
  367. calculateQuantity(type) {
  368. let total =
  369. this.form.qualifiedQuantity - 0 + (this.form.unqualifiedQuantity - 0);
  370. if (total > this.current.quantity) {
  371. this.form[type] = 0;
  372. this.$message.warning('合格数量加不合格数量不能大于任务数量');
  373. }
  374. },
  375. // 数量正则 quantity
  376. handleQuantityInput(e, type) {
  377. // 过滤非数字字符(包括负号)
  378. let value = e.replace(/[^\d]/g, '');
  379. // 限制不能以 0 开头(除非是 0 本身)
  380. if (value.startsWith('0') && value.length > 1) {
  381. value = value.slice(1);
  382. }
  383. // 更新绑定值
  384. this.form[type] = value;
  385. this.calculateQuantity(type);
  386. },
  387. submitAdd() {
  388. this.$refs.form.validate((valid) => {
  389. if (!valid) return;
  390. // if (
  391. // this.form.qualifiedQuantity -
  392. // 0 +
  393. // (this.form.unqualifiedQuantity - 0) !==
  394. // this.current.quantity
  395. // ) {
  396. // return this.$message.warning(
  397. // `合格数量加不合格数量要等于任务数量${this.current.quantity}`
  398. // );
  399. // }
  400. // if (
  401. // this.form.qualifiedWeight -
  402. // 0 +
  403. // (this.form.unqualifiedWeight - 0) !==
  404. // this.current.weight
  405. // ) {
  406. // return this.$message.warning(
  407. // `合格重量加不合格重量要等于任务重量${this.current.weight}`
  408. // );
  409. // }
  410. let data = {
  411. ...this.form,
  412. apsAssigneeId: this.current.apsAssigneeId
  413. };
  414. this.loadingBtn = true;
  415. batchUpdateRealTime([data])
  416. .then((res) => {
  417. this.loadingBtn = false;
  418. if (res) {
  419. this.$message.success('操作成功');
  420. this.cancel();
  421. this.$emit('success');
  422. }
  423. })
  424. .catch((err) => {
  425. this.loadingBtn = false;
  426. this.$message.error(err.message);
  427. });
  428. });
  429. }
  430. }
  431. };
  432. </script>
  433. <style scoped lang="scss">
  434. ::v-deep .time_select {
  435. width: 100%;
  436. }
  437. ::v-deep .tool_btn {
  438. text-align: right;
  439. .el-button {
  440. padding: 10px 18px !important;
  441. font-size: 15px !important;
  442. }
  443. }
  444. </style>