index.vue 28 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004
  1. <template>
  2. <div class="tenant">
  3. <!-- <Banner /> -->
  4. <div class="content">
  5. <byTable
  6. :source="sourceList.data"
  7. :pagination="sourceList.pagination"
  8. :config="config"
  9. :loading="loading"
  10. highlight-current-row
  11. :selectConfig="selectConfig"
  12. :table-events="{
  13. //element talbe事件都能传
  14. select: selectRow,
  15. 'select-all': selectRow,
  16. }"
  17. :action-list="[
  18. {
  19. text: '出货',
  20. disabled: selectData.length === 0,
  21. action: () => openModalOne(),
  22. },
  23. {
  24. text: '产品装箱',
  25. action: () => openModal(),
  26. },
  27. ]"
  28. @get-list="getList"
  29. >
  30. <template #code="{ item }">
  31. <div>
  32. <div
  33. v-for="(item, index) in getData(item.codeAPName, 'code')"
  34. :key="index"
  35. >
  36. {{ item }}
  37. </div>
  38. </div>
  39. </template>
  40. <template #productName="{ item }">
  41. <div>
  42. <div
  43. v-for="(item, index) in getData(item.codeAPName, 'productName')"
  44. :key="index"
  45. >
  46. {{ item }}
  47. </div>
  48. </div>
  49. </template>
  50. </byTable>
  51. </div>
  52. <el-dialog
  53. title="产品装箱"
  54. v-model="dialogVisible"
  55. width="800"
  56. v-loading="loading"
  57. >
  58. <el-form
  59. :model="formData.data"
  60. :rules="rules"
  61. ref="formDom"
  62. label-position="top"
  63. >
  64. <el-row :gutter="10">
  65. <el-col :span="8">
  66. <el-form-item label="客户名称" prop="customerId">
  67. <el-select
  68. v-model="formData.data.customerId"
  69. placeholder="请选择"
  70. @change="handleChangeCustomer"
  71. filterable
  72. style="width: 100%"
  73. >
  74. <el-option
  75. v-for="item in customerList"
  76. :label="item.name"
  77. :value="item.id"
  78. >
  79. </el-option>
  80. </el-select>
  81. </el-form-item>
  82. </el-col>
  83. </el-row>
  84. <el-form-item label="选择合同" prop="contractIds">
  85. <el-select
  86. v-model="formData.data.contractIds"
  87. placeholder="请选择"
  88. @change="handleChangeContract"
  89. filterable
  90. style="width: 100%"
  91. multiple
  92. >
  93. <el-option
  94. v-for="item in contractData"
  95. :label="item.code"
  96. :value="item.id"
  97. >
  98. </el-option>
  99. </el-select>
  100. </el-form-item>
  101. <el-form-item label="合同明细" prop="contractProductData">
  102. <el-table
  103. :data="formData.data.contractProductData"
  104. @select="handleSelectProduct"
  105. @select-all="handleSelectProduct"
  106. >
  107. <el-table-column type="selection" label="" width="50" />
  108. <el-table-column prop="contractCode" label="合同编码" />
  109. <el-table-column prop="productName" label="产品名称" />
  110. <el-table-column prop="cpQuantity" label="合同数量" />
  111. <el-table-column prop="waitQuantity" label="待装箱数量" />
  112. <el-table-column prop="quantity" label="装箱数量" min-width="150">
  113. <template #default="{ row, $index }">
  114. <el-form-item
  115. :prop="'contractProductData.' + $index + '.quantity'"
  116. :inline-message="true"
  117. >
  118. <el-input-number
  119. v-model="row.quantity"
  120. :precision="4"
  121. :controls="false"
  122. :min="0"
  123. />
  124. </el-form-item>
  125. </template>
  126. </el-table-column>
  127. </el-table>
  128. <el-button
  129. type="primary"
  130. style="margin-top: 10px; width: 100%"
  131. @click="handleClickPacking"
  132. >
  133. 装箱
  134. </el-button>
  135. </el-form-item>
  136. <el-form-item label="装箱明细" prop="packDetailList">
  137. <div
  138. class="box"
  139. v-for="(item, index) in formData.data.packDetailList"
  140. :key="index"
  141. >
  142. <div ref="">箱规</div>
  143. <el-row :gutter="10">
  144. <el-col :span="5">
  145. <el-form-item
  146. label="箱数"
  147. :prop="'packDetailList.' + index + '.packQuantity'"
  148. :rules="rules.packQuantity"
  149. >
  150. <el-input-number
  151. v-model="item.packQuantity"
  152. :precision="0"
  153. :controls="false"
  154. :min="1"
  155. placeholder="请输入"
  156. onmousewheel="return false;"
  157. @change="(val) => handleChangePackQuantity(val, index)"
  158. />
  159. </el-form-item>
  160. </el-col>
  161. <el-col :span="5">
  162. <el-form-item
  163. label="净重(kg)"
  164. :prop="'packDetailList.' + index + '.netWeight'"
  165. :rules="rules.netWeight"
  166. >
  167. <el-input-number
  168. v-model="item.netWeight"
  169. :precision="2"
  170. :controls="false"
  171. :min="0"
  172. placeholder="请输入"
  173. onmousewheel="return false;"
  174. />
  175. </el-form-item>
  176. </el-col>
  177. <el-col :span="5">
  178. <el-form-item
  179. label="毛重(kg)"
  180. :prop="'packDetailList.' + index + '.roughWeight'"
  181. :rules="rules.roughWeight"
  182. >
  183. <el-input-number
  184. v-model="item.roughWeight"
  185. :precision="2"
  186. :controls="false"
  187. :min="0"
  188. placeholder="请输入"
  189. onmousewheel="return false;"
  190. />
  191. </el-form-item>
  192. </el-col>
  193. <el-col :span="9">
  194. <el-row>
  195. <el-form-item label="尺寸(cm³)" required>
  196. <el-col :span="1"></el-col>
  197. <el-col :span="7">
  198. <el-form-item
  199. label=""
  200. :prop="'packDetailList.' + index + '.boxLong'"
  201. :rules="rules.boxLong"
  202. >
  203. <el-input-number
  204. v-model="item.boxLong"
  205. placeholder="长"
  206. :precision="2"
  207. :controls="false"
  208. :min="0"
  209. onmousewheel="return false;"
  210. ></el-input-number>
  211. </el-form-item>
  212. </el-col>
  213. <el-col :span="1" style="text-align: center"> * </el-col>
  214. <el-col :span="7">
  215. <el-form-item
  216. label=""
  217. :prop="'packDetailList.' + index + '.boxWide'"
  218. :rules="rules.boxWide"
  219. >
  220. <el-input-number
  221. v-model="item.boxWide"
  222. placeholder="宽"
  223. :precision="2"
  224. :controls="false"
  225. :min="0"
  226. onmousewheel="return false;"
  227. ></el-input-number>
  228. </el-form-item>
  229. </el-col>
  230. <el-col :span="1" style="text-align: center"> * </el-col>
  231. <el-col :span="7">
  232. <el-form-item
  233. label=""
  234. :prop="'packDetailList.' + index + '.boxHigh'"
  235. :rules="rules.boxHigh"
  236. >
  237. <el-input-number
  238. v-model="item.boxHigh"
  239. placeholder="高"
  240. :precision="2"
  241. :controls="false"
  242. :min="0"
  243. onmousewheel="return false;"
  244. ></el-input-number>
  245. </el-form-item>
  246. </el-col>
  247. </el-form-item>
  248. </el-row>
  249. </el-col>
  250. </el-row>
  251. <div class="line"></div>
  252. <el-form-item label="关联合同产品">
  253. <div class="flex-box">
  254. <div
  255. class="item"
  256. v-for="(product, j) in item.packDetailProductList"
  257. :key="j"
  258. >
  259. <div>合同编码:{{ product.contractCode }}</div>
  260. <div>产品名称:{{ product.productName }}</div>
  261. <div>每箱数量:{{ product.quantity }}</div>
  262. </div>
  263. </div>
  264. </el-form-item>
  265. <div
  266. class="bottom-arrow"
  267. v-show="!item.isShow"
  268. @click="item.isShow = !item.isShow"
  269. >
  270. <span style="margin-right: 5px"> 自定义装箱明细</span>
  271. <el-icon><ArrowDownBold /></el-icon>
  272. </div>
  273. <div
  274. class="bottom-arrow"
  275. v-show="item.isShow"
  276. @click="item.isShow = !item.isShow"
  277. >
  278. <span style="margin-right: 5px"> 收起</span>
  279. <el-icon><ArrowUpBold /></el-icon>
  280. </div>
  281. <el-form-item prop="packDetailGoodsList" v-show="item.isShow">
  282. <el-button
  283. type="primary"
  284. style="margin-bottom: 10px"
  285. @click="handleCustomPush(index)"
  286. >
  287. 添加行
  288. </el-button>
  289. <el-table :data="item.packDetailGoodsList">
  290. <el-table-column label="货物描述">
  291. <template #default="{ row, $index }">
  292. <el-form-item
  293. :prop="[
  294. 'packDetailList',
  295. index,
  296. 'packDetailGoodsList',
  297. $index,
  298. 'remark',
  299. ]"
  300. :rules="rules.remark"
  301. :inline-message="true"
  302. >
  303. <el-input v-model="row.remark" placeholder="请输入" />
  304. </el-form-item>
  305. </template>
  306. </el-table-column>
  307. <el-table-column label="单位" width="150">
  308. <template #default="{ row, $index }">
  309. <el-form-item
  310. :prop="[
  311. 'packDetailList',
  312. index,
  313. 'packDetailGoodsList',
  314. $index,
  315. 'unit',
  316. ]"
  317. :rules="rules.unit"
  318. :inline-message="true"
  319. >
  320. <el-input v-model="row.unit" placeholder="请输入" />
  321. </el-form-item>
  322. </template>
  323. </el-table-column>
  324. <el-table-column label="数量" width="150">
  325. <template #default="{ row, $index }">
  326. <el-form-item
  327. :prop="[
  328. 'packDetailList',
  329. index,
  330. 'packDetailGoodsList',
  331. $index,
  332. 'quantity',
  333. ]"
  334. :rules="rules.quantityOne"
  335. :inline-message="true"
  336. >
  337. <el-input-number
  338. v-model="row.quantity"
  339. :precision="4"
  340. :controls="false"
  341. :min="0"
  342. />
  343. </el-form-item>
  344. </template>
  345. </el-table-column>
  346. <el-table-column prop="zip" label="操作" width="100">
  347. <template #default="{ $index }">
  348. <el-button
  349. type="primary"
  350. link
  351. @click="handleCustomRemove(index, $index)"
  352. >删除</el-button
  353. >
  354. </template>
  355. </el-table-column>
  356. </el-table>
  357. </el-form-item>
  358. </div>
  359. </el-form-item>
  360. </el-form>
  361. <template #footer>
  362. <el-button @click="handleClose" size="large">取 消</el-button>
  363. <el-button
  364. type="primary"
  365. @click="submitForm()"
  366. size="large"
  367. :loading="submitLoading"
  368. >
  369. 确 定
  370. </el-button>
  371. </template>
  372. </el-dialog>
  373. <el-dialog
  374. title="合并出货"
  375. v-model="dialogVisibleOne"
  376. width="400"
  377. v-loading="loadingOne"
  378. >
  379. <byForm
  380. :formConfig="formConfig"
  381. :formOption="formOption"
  382. v-model="formData.dataOne"
  383. :rules="rules"
  384. ref="byform"
  385. >
  386. </byForm>
  387. <template #footer>
  388. <el-button @click="dialogVisibleOne = false" size="large"
  389. >取 消</el-button
  390. >
  391. <el-button
  392. type="primary"
  393. @click="submitFormOne()"
  394. size="large"
  395. :loading="submitLoading"
  396. >
  397. 确 定
  398. </el-button>
  399. </template>
  400. </el-dialog>
  401. </div>
  402. </template>
  403. <script setup>
  404. /* eslint-disable vue/no-unused-components */
  405. import { ElMessage, ElMessageBox } from "element-plus";
  406. import byTable from "@/components/byTable/index";
  407. import byForm from "@/components/byForm/index";
  408. import FileUpload from "@/components/FileUpload/index";
  409. import { computed, defineComponent, ref } from "vue";
  410. import { getToken } from "@/utils/auth";
  411. const uploadFileUrl = ref(import.meta.env.VITE_APP_BASE_API + "/common/upload"); // 上传文件服务器地址
  412. const headers = ref({ Authorization: "Bearer " + getToken() });
  413. const uploadData = ref({});
  414. const loading = ref(false);
  415. const loadingOne = ref(false);
  416. const submitLoading = ref(false);
  417. const sourceList = ref({
  418. data: [],
  419. pagination: {
  420. total: 3,
  421. pageNum: 1,
  422. pageSize: 10,
  423. status: "",
  424. },
  425. });
  426. let dialogVisible = ref(false);
  427. let dialogVisibleOne = ref(false);
  428. let modalType = ref("add");
  429. let fileList = ref([]);
  430. let rules = ref({
  431. contractIds: [{ required: true, message: "请选择合同", trigger: "change" }],
  432. packQuantity: [{ required: true, message: "请输入箱数", trigger: "blur" }],
  433. netWeight: [{ required: true, message: "请输入净重", trigger: "blur" }],
  434. roughWeight: [{ required: true, message: "请输入毛重", trigger: "blur" }],
  435. boxLong: [{ required: true, message: "请输入长", trigger: "blur" }],
  436. boxWide: [{ required: true, message: "请输入宽", trigger: "blur" }],
  437. boxHigh: [{ required: true, message: "请输入高", trigger: "blur" }],
  438. quantity: [{ required: true, message: "请输入装箱数量", trigger: "blur" }],
  439. quantityOne: [{ required: true, message: "请输入数量", trigger: "blur" }],
  440. unit: [{ required: true, message: "请输入单位", trigger: "blur" }],
  441. remark: [{ required: true, message: "请输入货物描述", trigger: "blur" }],
  442. contractId: [{ required: true, message: "请选择主合同", trigger: "change" }],
  443. });
  444. const { proxy } = getCurrentInstance();
  445. const selectConfig = reactive([
  446. {
  447. label: "出货状态",
  448. prop: "shipmentStatus",
  449. data: [
  450. {
  451. label: "未出货",
  452. value: "0",
  453. },
  454. {
  455. label: "已出货",
  456. value: "1",
  457. },
  458. ],
  459. },
  460. ]);
  461. const config = computed(() => {
  462. return [
  463. {
  464. type: "selection",
  465. attrs: {
  466. checkAtt: "isCheck",
  467. },
  468. },
  469. {
  470. attrs: {
  471. label: "合同号",
  472. prop: "codeAPName",
  473. slot: "code",
  474. },
  475. },
  476. {
  477. attrs: {
  478. label: "产品名称",
  479. prop: "codeAPName",
  480. slot: "productName",
  481. },
  482. },
  483. {
  484. attrs: {
  485. label: "总箱数",
  486. prop: "packQuantity",
  487. width: 90,
  488. },
  489. },
  490. {
  491. attrs: {
  492. label: "净重",
  493. prop: "netWeight",
  494. width: 90,
  495. },
  496. render(netWeight) {
  497. return netWeight + "kg";
  498. },
  499. },
  500. {
  501. attrs: {
  502. label: "毛重",
  503. prop: "roughWeight",
  504. width: 90,
  505. },
  506. render(roughWeight) {
  507. return roughWeight + "kg";
  508. },
  509. },
  510. {
  511. attrs: {
  512. label: "长",
  513. prop: "boxLong",
  514. width: 90,
  515. },
  516. render(boxLong) {
  517. return boxLong + "cm";
  518. },
  519. },
  520. {
  521. attrs: {
  522. label: "宽",
  523. prop: "boxWide",
  524. width: 90,
  525. },
  526. render(boxWide) {
  527. return boxWide + "cm";
  528. },
  529. },
  530. {
  531. attrs: {
  532. label: "高",
  533. prop: "boxHigh",
  534. width: 90,
  535. },
  536. render(boxHigh) {
  537. return boxHigh + "cm";
  538. },
  539. },
  540. {
  541. attrs: {
  542. label: "总体积",
  543. prop: "bomVolume",
  544. width: 120,
  545. },
  546. render(bomVolume) {
  547. return bomVolume + "m³";
  548. },
  549. },
  550. {
  551. attrs: {
  552. label: "出货状态",
  553. prop: "shipmentStatus",
  554. width: 90,
  555. },
  556. render(status) {
  557. return status == 1 ? "已出货" : status == 0 ? "未出货" : "";
  558. },
  559. },
  560. {
  561. attrs: {
  562. label: "出货时间",
  563. prop: "shipmentTime",
  564. width: 155,
  565. },
  566. },
  567. {
  568. attrs: {
  569. label: "操作",
  570. width: "90",
  571. align: "center",
  572. },
  573. // 渲染 el-button,一般用在最后一列。
  574. renderHTML(row) {
  575. return [
  576. // {
  577. // attrs: {
  578. // label: "打印",
  579. // type: "primary",
  580. // text: true,
  581. // },
  582. // el: "button",
  583. // click() {
  584. // getDtl(row);
  585. // },
  586. // },
  587. // {
  588. // attrs: {
  589. // label: "删除",
  590. // type: "primary",
  591. // text: true,
  592. // disabled: row.status != 30,
  593. // },
  594. // el: "button",
  595. // click() {
  596. // ElMessageBox.confirm(
  597. // "此操作将永久作废该数据, 是否继续?",
  598. // "提示",
  599. // {
  600. // confirmButtonText: "确定",
  601. // cancelButtonText: "取消",
  602. // type: "warning",
  603. // }
  604. // ).then(() => {
  605. // // 删除
  606. // proxy
  607. // .post("/subscribeDetail/edit", {
  608. // ...row,
  609. // status: 99,
  610. // })
  611. // .then((res) => {
  612. // ElMessage({
  613. // message: "作废成功",
  614. // type: "success",
  615. // });
  616. // getList();
  617. // });
  618. // });
  619. // },
  620. // },
  621. ];
  622. },
  623. },
  624. ];
  625. });
  626. const formDom = ref(null);
  627. let formData = reactive({
  628. data: {},
  629. dataOne: {},
  630. });
  631. const formOption = reactive({
  632. inline: true,
  633. labelWidth: 100,
  634. itemWidth: 100,
  635. rules: [],
  636. });
  637. const byform = ref(null);
  638. const treeData = ref([]);
  639. const formConfig = reactive([
  640. {
  641. type: "select",
  642. prop: "contractId",
  643. label: "主合同",
  644. required: true,
  645. data: [],
  646. },
  647. ]);
  648. const getList = async (req) => {
  649. selectData.value = [];
  650. sourceList.value.pagination = { ...sourceList.value.pagination, ...req };
  651. loading.value = true;
  652. proxy
  653. .post("/packDetail/page", sourceList.value.pagination)
  654. .then((message) => {
  655. sourceList.value.data = message.rows.map((x) => ({
  656. ...x,
  657. isCheck: x.shipmentStatus == 1 ? false : true,
  658. }));
  659. sourceList.value.pagination.total = message.total;
  660. setTimeout(() => {
  661. loading.value = false;
  662. }, 200);
  663. });
  664. };
  665. const openModal = () => {
  666. modalType.value = "add";
  667. formData.data = {
  668. packDetailList: [],
  669. contractIds: [],
  670. };
  671. dialogVisible.value = true;
  672. handleChangeCustomer("");
  673. };
  674. const openModalOne = () => {
  675. formData.dataOne = {
  676. ids: [],
  677. contractId: "",
  678. };
  679. let ids = []; //合同id
  680. let idsOne = []; //包装id
  681. const list = selectData.value;
  682. for (let i = 0; i < list.length; i++) {
  683. const e = list[i];
  684. ids = [...ids, ...e.contractIds.split(",")];
  685. idsOne.push(e.id);
  686. }
  687. formData.dataOne.ids = idsOne;
  688. proxy.post(`/contract/getByIds`, ids).then((res) => {
  689. formConfig[0].data = res.map((x) => ({
  690. label: x.code,
  691. value: x.id,
  692. }));
  693. dialogVisibleOne.value = true;
  694. });
  695. };
  696. const submitForm = () => {
  697. formDom.value.validate((vaild) => {
  698. if (vaild) {
  699. if (!formData.data.packDetailList.length > 0) {
  700. return ElMessage({
  701. message: "请添加装箱明细!",
  702. type: "info",
  703. });
  704. }
  705. submitLoading.value = true;
  706. loadingOne.value = true;
  707. for (let i = 0; i < formData.data.packDetailList.length; i++) {
  708. const e = formData.data.packDetailList[i];
  709. e.bomVolume = (e.boxLong * e.boxWide * e.boxHigh) / 1000000;
  710. }
  711. formData.data.contractIds = formData.data.contractIds.join(",");
  712. proxy.post("/pack/" + modalType.value, formData.data).then(
  713. (res) => {
  714. ElMessage({
  715. message: modalType.value == "add" ? "添加成功" : "编辑成功",
  716. type: "success",
  717. });
  718. dialogVisible.value = false;
  719. submitLoading.value = false;
  720. loadingOne.value = false;
  721. getList();
  722. },
  723. (err) => {
  724. submitLoading.value = false;
  725. loading.value = false;
  726. }
  727. );
  728. }
  729. });
  730. };
  731. const submitFormOne = () => {
  732. byform.value.handleSubmit((valid) => {
  733. loading.value = true;
  734. submitLoading.value = true;
  735. proxy.post("/packDetail/shipment", formData.dataOne).then(
  736. (res) => {
  737. ElMessage({
  738. message: "出货成功",
  739. type: "success",
  740. });
  741. dialogVisibleOne.value = false;
  742. submitLoading.value = false;
  743. loading.value = false;
  744. getList();
  745. selectData.value = [];
  746. },
  747. (err) => {
  748. submitLoading.value = false;
  749. loading.value = false;
  750. }
  751. );
  752. });
  753. };
  754. const selectData = ref([]);
  755. const selectRow = (data) => {
  756. selectData.value = data;
  757. };
  758. const selectProductData = ref([]);
  759. const handleSelectProduct = (data) => {
  760. selectProductData.value = data;
  761. };
  762. const handleClickPacking = () => {
  763. if (selectProductData.value.length > 0) {
  764. const list = selectProductData.value;
  765. for (let i = 0; i < list.length; i++) {
  766. const e = list[i];
  767. if (!e.quantity) {
  768. return ElMessage({
  769. message: "请输入装箱数量",
  770. type: "info",
  771. });
  772. }
  773. }
  774. for (let i = 0; i < list.length; i++) {
  775. const e = list[i];
  776. for (let j = 0; j < formData.data.contractProductData.length; j++) {
  777. const jele = formData.data.contractProductData[j];
  778. if (e.id === jele.id && e.quantity > Number(jele.waitQuantity)) {
  779. return ElMessage({
  780. message: "装箱数量不可大于袋装箱数量",
  781. type: "info",
  782. });
  783. }
  784. }
  785. }
  786. const packDetailProductList = list.map((x) => ({
  787. contractCode: x.contractCode,
  788. contractId: x.contractId,
  789. contractProductId: x.id,
  790. quantity: x.quantity,
  791. productId: x.productId,
  792. productName: x.productName,
  793. }));
  794. const customerId = formData.data.customerId ? formData.data.customerId : "";
  795. const contractIds = formData.data.contractIds
  796. ? formData.data.contractIds.join(",")
  797. : "";
  798. let item = {
  799. customerId: customerId,
  800. contractIds: contractIds,
  801. packQuantity: 1,
  802. netWeight: null,
  803. roughWeight: null,
  804. boxLong: null,
  805. boxWide: null,
  806. boxHigh: null,
  807. bomVolume: "",
  808. remark: "",
  809. packDetailGoodsList: [],
  810. packDetailProductList: packDetailProductList,
  811. isShow: false,
  812. };
  813. formData.data.packDetailList.push(item);
  814. handleChangePackQuantity(
  815. item.packQuantity,
  816. formData.data.packDetailList.length - 1
  817. );
  818. selectProductData.value = [];
  819. } else {
  820. return ElMessage({
  821. message: "请选择产品 !",
  822. type: "info",
  823. });
  824. }
  825. };
  826. const handleChangePackQuantity = (val, index) => {
  827. const obj = {};
  828. for (let i = 0; i < formData.data.contractProductData.length; i++) {
  829. const e = formData.data.contractProductData[i];
  830. obj[e.contractId + "_" + e.productId + ""] =
  831. Number(e.cpQuantity) - Number(e.sumPackQuantity);
  832. }
  833. // 计算数量 即装箱数量 * 箱数 新增字段放在最外层
  834. for (let i = 0; i < formData.data.packDetailList.length; i++) {
  835. const ele = formData.data.packDetailList[i];
  836. for (let j = 0; j < ele.packDetailProductList.length; j++) {
  837. const jele = ele.packDetailProductList[j];
  838. ele[jele.contractId + "_" + jele.productId + ""] =
  839. Number(ele.packQuantity) * jele.quantity;
  840. }
  841. }
  842. // 计算新的待装箱数量
  843. for (let i = 0; i < formData.data.packDetailList.length; i++) {
  844. const e = formData.data.packDetailList[i];
  845. for (const key in obj) {
  846. if (e.hasOwnProperty(key)) {
  847. obj[key] = obj[key] - e[key];
  848. if (obj[key] < 0) {
  849. e.packQuantity = null;
  850. handleChangePackQuantity(null, index);
  851. return ElMessage({
  852. message: "装箱数量 * 箱数不可大于待装箱数量",
  853. type: "info",
  854. });
  855. }
  856. }
  857. }
  858. }
  859. // 赋值
  860. for (let i = 0; i < formData.data.contractProductData.length; i++) {
  861. const e = formData.data.contractProductData[i];
  862. for (const key in obj) {
  863. if (e.contractId + "_" + e.productId + "" === key) {
  864. e.waitQuantity = obj[key];
  865. }
  866. }
  867. }
  868. // }
  869. };
  870. const handleCustomPush = (index) => {
  871. formData.data.packDetailList[index].packDetailGoodsList.push({
  872. unit: "",
  873. quantity: "",
  874. remark: "",
  875. });
  876. };
  877. const handleCustomRemove = (index, sonIndex) => {
  878. formData.data.packDetailList[index].packDetailGoodsList.splice(sonIndex, 1);
  879. };
  880. const customerList = ref([]);
  881. const getSelectData = () => {
  882. proxy.post("/customer/page", { pageNum: 1, pageSize: 999 }).then((res) => {
  883. customerList.value = res.rows.map((item) => {
  884. return {
  885. ...item,
  886. label: item.name,
  887. value: item.id,
  888. };
  889. });
  890. });
  891. };
  892. const contractData = ref([]);
  893. const handleChangeCustomer = (val) => {
  894. proxy
  895. .get(`/contract/getNoPackContractByCustomerId?customerId=${val}`)
  896. .then((res) => {
  897. contractData.value = res.data;
  898. formData.data.contractIds = [];
  899. });
  900. };
  901. const handleChangeContract = (val) => {
  902. const customerId = formData.data.customerId ? formData.data.customerId : "";
  903. proxy
  904. .get(
  905. `/contractProduct/getNoPackContractProductById?customerId=${customerId}&contractIds=${val}`
  906. )
  907. .then((res) => {
  908. formData.data.contractProductData = res.data.map((x) => ({
  909. ...x,
  910. waitQuantity: Number(x.cpQuantity) - Number(x.sumPackQuantity),
  911. quantity: null,
  912. }));
  913. handleChangePackQuantity();
  914. });
  915. };
  916. const getData = (data, type) => {
  917. if (!data) return [];
  918. const arr = data.split(",");
  919. if (arr && arr.length > 0) {
  920. const arrOne = [];
  921. for (let i = 0; i < arr.length; i++) {
  922. const e = arr[i];
  923. if (type === "code") {
  924. arrOne.push(e.split("_")[0]);
  925. } else if (type === "productName") {
  926. arrOne.push(e.split("_")[1]);
  927. }
  928. }
  929. return arrOne;
  930. }
  931. return [];
  932. };
  933. const handleClose = () => {
  934. dialogVisible.value = false;
  935. selectProductData.value = [];
  936. };
  937. getSelectData();
  938. getList();
  939. </script>
  940. <style lang="scss" scoped>
  941. .tenant {
  942. padding: 20px;
  943. }
  944. :deep(.el-collapse-item__header) {
  945. background-color: #fde6c8;
  946. border: none;
  947. }
  948. :deep(.el-collapse-item__wrap) {
  949. background-color: #fde6c8;
  950. border: none;
  951. }
  952. .box {
  953. padding: 15px;
  954. background: #fde6c8;
  955. border: 1px solid #7fb5e3;
  956. margin-bottom: 10px;
  957. .flex-box {
  958. width: 100%;
  959. display: flex;
  960. flex-wrap: wrap;
  961. .item {
  962. width: 50%;
  963. div {
  964. line-height: 22px;
  965. }
  966. }
  967. }
  968. .line {
  969. width: 100%;
  970. height: 1px;
  971. background: #7fb5e3;
  972. margin: 20px 0;
  973. }
  974. .bottom-arrow {
  975. text-align: center;
  976. cursor: pointer;
  977. color: #0084ff;
  978. }
  979. }
  980. </style>