purchase.vue 28 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726
  1. <template>
  2. <div>
  3. <byForm :formConfig="formConfig" :formOption="formOption" v-model="formData.data" :rules="rules" ref="submit">
  4. <template #supplier>
  5. <div style="width: 100%">
  6. <el-form-item label="供应商" prop="supplierId" style="width: 100%; margin-bottom: 18px">
  7. <el-col :span="12">
  8. <el-select v-model="formData.data.supplierId" placeholder="请选择供应商" clearable style="width: 100%" @change="changeSupplier">
  9. <el-option v-for="item in supplierList" :key="item.dictKey" :label="item.dictValue" :value="item.dictKey" />
  10. </el-select>
  11. </el-col>
  12. </el-form-item>
  13. <el-form-item label="地址" required style="width: 100%; margin-bottom: 18px">
  14. <el-col :span="6">
  15. <el-form-item prop="province" style="width: 100%">
  16. <el-input v-model="formData.data.province" placeholder="请输入省份" />
  17. </el-form-item>
  18. </el-col>
  19. <el-col :span="6">
  20. <el-form-item prop="city" style="width: 100%">
  21. <el-input v-model="formData.data.city" placeholder="请输入城市" />
  22. </el-form-item>
  23. </el-col>
  24. <el-col :span="6">
  25. <el-form-item prop="detailedAddress" style="width: 100%">
  26. <el-input v-model="formData.data.detailedAddress" placeholder="请输入地址" />
  27. </el-form-item>
  28. </el-col>
  29. </el-form-item>
  30. <el-form-item label="联系人" required style="width: 100%">
  31. <el-col :span="6">
  32. <el-form-item prop="contactPerson" style="width: 100%">
  33. <el-input v-model="formData.data.contactPerson" placeholder="请输入联系人" />
  34. </el-form-item>
  35. </el-col>
  36. <el-col :span="6">
  37. <el-form-item prop="contactNumber" style="width: 100%">
  38. <el-input v-model="formData.data.contactNumber" placeholder="请输入联系人电话" />
  39. </el-form-item>
  40. </el-col>
  41. </el-form-item>
  42. </div>
  43. </template>
  44. <template #purchaseBomList>
  45. <div style="width: 100%">
  46. <el-table :data="formData.data.purchaseBomList" :row-style="{ height: '35px' }" header-row-class-name="tableHeader">
  47. <el-table-column label="品号" prop="bomSpecCode" width="120" />
  48. <el-table-column label="品名" prop="bomSpecName" min-width="240" />
  49. <el-table-column label="颜色" prop="bomSpecColour" width="140" />
  50. <el-table-column label="尺寸(长宽高,cm)" width="160">
  51. <template #default="{ row }">
  52. <div>{{ row.bomSpecLength }} * {{ row.bomSpecWidth }} * {{ row.bomSpecHeight }}</div>
  53. </template>
  54. </el-table-column>
  55. <el-table-column label="含税单价" width="140">
  56. <template #default="{ row, $index }">
  57. <el-form-item
  58. :prop="'purchaseBomList.' + $index + '.unitPrice'"
  59. :rules="rules.unitPrice"
  60. :inline-message="true"
  61. style="width: 100%"
  62. @change="calculatedTotalAmount">
  63. <el-input-number
  64. onmousewheel="return false;"
  65. v-model="row.unitPrice"
  66. placeholder="含税单价"
  67. style="width: 100%"
  68. :controls="false"
  69. :min="0"
  70. :precision="3" />
  71. </el-form-item>
  72. </template>
  73. </el-table-column>
  74. <el-table-column label="税率" width="120">
  75. <template #default="{ row, $index }">
  76. <el-form-item
  77. :prop="'purchaseBomList.' + $index + '.taxRate'"
  78. :rules="rules.taxRate"
  79. :inline-message="true"
  80. style="width: 100%"
  81. @change="calculatedTotalAmount">
  82. <el-input-number
  83. onmousewheel="return false;"
  84. v-model="row.taxRate"
  85. placeholder="税率"
  86. style="width: 100%"
  87. :controls="false"
  88. :min="0"
  89. :max="100"
  90. :precision="2" />
  91. </el-form-item>
  92. </template>
  93. </el-table-column>
  94. <el-table-column label="不含税单价" width="100">
  95. <template #default="{ row }">
  96. <div>{{ moneyFormat(Number(Math.round(((row.unitPrice * 100) / (100 + row.taxRate)) * 1000) / 1000), 3) }}</div>
  97. </template>
  98. </el-table-column>
  99. <el-table-column label="可采购数量" width="100">
  100. <template #default="{ row }">
  101. <span v-if="route.query.processType && route.query.processType == 30">
  102. {{ Number(Math.round(row.quantity - row.purchasedQuantity - row.frozenQuantity + row.thisTimeQuantity)) }}
  103. </span>
  104. <span v-else>
  105. {{ Number(Math.round(row.quantity - row.purchasedQuantity - row.frozenQuantity)) }}
  106. </span>
  107. </template>
  108. </el-table-column>
  109. <el-table-column label="采购数量" width="120">
  110. <template #default="{ row, $index }">
  111. <el-form-item
  112. :prop="'purchaseBomList.' + $index + '.purchaseQuantity'"
  113. :rules="rules.purchaseQuantity"
  114. :inline-message="true"
  115. style="width: 100%"
  116. @change="calculatedTotalAmount">
  117. <el-input-number
  118. onmousewheel="return false;"
  119. v-model="row.purchaseQuantity"
  120. placeholder="采购数量"
  121. style="width: 100%"
  122. :controls="false"
  123. :min="0"
  124. :precision="0" />
  125. </el-form-item>
  126. </template>
  127. </el-table-column>
  128. <el-table-column label="在途数量" prop="inTransitQuantity" width="100" />
  129. <el-table-column label="到货数量" prop="arrivalQuantity" width="100" />
  130. <el-table-column label="含税小计" align="right" width="120">
  131. <template #default="{ row }">
  132. <div>{{ moneyFormat(Number(Math.round(row.unitPrice * row.purchaseQuantity * 1000) / 1000), 3) }}</div>
  133. </template>
  134. </el-table-column>
  135. <el-table-column label="不含税小计" align="right" width="120">
  136. <template #default="{ row }">
  137. <div>
  138. {{
  139. moneyFormat(
  140. Number(Math.round((Math.round(((row.unitPrice * 100) / (100 + row.taxRate)) * 1000) / 1000) * row.purchaseQuantity * 1000) / 1000),
  141. 3
  142. )
  143. }}
  144. </div>
  145. </template>
  146. </el-table-column>
  147. <el-table-column label="操作" align="center" fixed="right" width="60">
  148. <template #default="{ $index }">
  149. <el-button type="danger" @click="clickDelete($index)" text>删除</el-button>
  150. </template>
  151. </el-table-column>
  152. </el-table>
  153. </div>
  154. </template>
  155. <template #deliveryAddress>
  156. <div style="width: 100%">
  157. <el-form-item label=" " prop="receiveGoodsType" style="width: 100%; margin-bottom: 18px">
  158. <el-radio-group v-model="formData.data.receiveGoodsType" @change="changeReceiveGoodsType">
  159. <el-radio :label="1">供应商运输</el-radio>
  160. <el-radio :label="2">自取</el-radio>
  161. </el-radio-group>
  162. </el-form-item>
  163. <el-form-item label="地址" required style="width: 100%; margin-bottom: 18px" v-if="formData.data.receiveGoodsType == 1">
  164. <el-col :span="6">
  165. <el-form-item prop="receiveProvince" style="width: 100%">
  166. <el-input v-model="formData.data.receiveProvince" placeholder="请输入省份" />
  167. </el-form-item>
  168. </el-col>
  169. <el-col :span="6">
  170. <el-form-item prop="receiveCity" style="width: 100%">
  171. <el-input v-model="formData.data.receiveCity" placeholder="请输入城市" />
  172. </el-form-item>
  173. </el-col>
  174. <el-col :span="8">
  175. <el-form-item prop="receiveDetailedAddress" style="width: 100%">
  176. <el-input v-model="formData.data.receiveDetailedAddress" placeholder="请输入地址" />
  177. </el-form-item>
  178. </el-col>
  179. <el-col :span="4">
  180. <el-form-item prop="receivePostcode" style="width: 100%">
  181. <el-input v-model="formData.data.receivePostcode" placeholder="请输入邮编" />
  182. </el-form-item>
  183. </el-col>
  184. </el-form-item>
  185. <el-form-item label="联系人" required style="width: 100%" v-if="formData.data.receiveGoodsType == 1">
  186. <el-col :span="6">
  187. <el-form-item prop="receiveContactPerson" style="width: 100%">
  188. <el-input v-model="formData.data.receiveContactPerson" placeholder="请输入联系人" />
  189. </el-form-item>
  190. </el-col>
  191. <el-col :span="6">
  192. <el-form-item prop="receiveContactNumber" style="width: 100%">
  193. <el-input v-model="formData.data.receiveContactNumber" placeholder="请输入联系人电话" />
  194. </el-form-item>
  195. </el-col>
  196. </el-form-item>
  197. </div>
  198. </template>
  199. <template #balancePayment>
  200. <div style="width: 100%">{{ computeBalancePayment() }}</div>
  201. </template>
  202. <template #paymentDate>
  203. <div style="width: 100%">
  204. <span v-if="supplierData && supplierData.paymentType == 1">{{ formData.data.paymentDate }}</span>
  205. <el-date-picker v-model="formData.data.paymentDate" type="date" placeholder="请选择" value-format="YYYY-MM-DD" v-else />
  206. </div>
  207. </template>
  208. <template #money>
  209. <div style="width: 100%">
  210. <div style="padding: 8px; background-color: #e9f5fb; font-size: 12px; font-weight: 700">
  211. <span>含税总金额: {{ moneyFormat(formData.data.totalAmountIncludingTax, 3) }} ({{ formData.data.totalAmountIncludingTaxCn }})</span>
  212. <span style="margin-left: 32px">
  213. 不含税总金额: {{ moneyFormat(formData.data.totalAmountExcludingTax, 3) }} ({{ formData.data.totalAmountExcludingTaxCn }})
  214. </span>
  215. </div>
  216. </div>
  217. </template>
  218. <template #attachments>
  219. <div style="width: 100%">
  220. <el-upload
  221. v-model:fileList="fileList"
  222. action="https://winfaster.obs.cn-south-1.myhuaweicloud.com"
  223. :data="uploadFileData"
  224. multiple
  225. :before-upload="beforeUpload"
  226. :on-success="onSuccessFile"
  227. :on-preview="onPreviewFile">
  228. <el-button style="background: #20b2aa; color: #fff; border: 1px solid #20b2aa">上传</el-button>
  229. </el-upload>
  230. </div>
  231. </template>
  232. <template #template>
  233. <div style="width: 100%">
  234. <el-form-item label="合同模板" prop="contractTemplateId" style="width: 100%; margin-bottom: 18px">
  235. <el-col :span="12">
  236. <el-select v-model="formData.data.contractTemplateId" placeholder="请选择合同模板" clearable style="width: 100%" @change="changeTemplate">
  237. <el-option v-for="item in templateList" :key="item.dictKey" :label="item.dictValue" :value="item.dictKey" />
  238. </el-select>
  239. </el-col>
  240. </el-form-item>
  241. <div v-if="formOption.disabled">
  242. <div v-html="formData.data.contract"></div>
  243. </div>
  244. <Editor v-else :value="formData.data.contract" @updateValue="updateValue" ref="editor" />
  245. </div>
  246. </template>
  247. </byForm>
  248. </div>
  249. </template>
  250. <script setup>
  251. import byForm from "/src/components/byForm/index";
  252. import { useRoute } from "vue-router";
  253. import Editor from "/src/components/Editor/index.vue";
  254. import { ElMessage } from "element-plus";
  255. const route = useRoute();
  256. // 接收父组件的传值
  257. const props = defineProps({
  258. queryData: Object,
  259. });
  260. const { proxy } = getCurrentInstance();
  261. const supplierList = ref([]);
  262. const templateList = ref([]);
  263. const formData = reactive({
  264. data: {
  265. receiveGoodsType: 1,
  266. contract: "",
  267. purchaseBomList: [],
  268. fileList: [],
  269. receiveProvince: "福建省",
  270. receiveCity: "福州市",
  271. receiveDetailedAddress: "福清市三山镇横坑村金园路18号3号楼",
  272. receivePostcode: "350000",
  273. },
  274. });
  275. const judgeStatus = () => {
  276. if (route.query.processType == 20 || route.query.processType == 10) {
  277. return true;
  278. }
  279. if (props.queryData.recordList && props.queryData.recordList.length > 0) {
  280. let data = props.queryData.recordList.filter((item) => item.status === 2 && item.nodeType !== 1);
  281. if (data && data.length > 0) {
  282. return true;
  283. }
  284. }
  285. return false;
  286. };
  287. const formOption = reactive({
  288. inline: true,
  289. labelWidth: "100px",
  290. itemWidth: 100,
  291. rules: [],
  292. labelPosition: "right",
  293. disabled: false,
  294. });
  295. const formConfig = computed(() => {
  296. return [
  297. {
  298. type: "title",
  299. title: "供应商",
  300. label: "",
  301. },
  302. {
  303. type: "slot",
  304. slotName: "supplier",
  305. },
  306. {
  307. type: "title",
  308. title: "采购清单",
  309. label: "",
  310. },
  311. {
  312. type: "slot",
  313. slotName: "purchaseBomList",
  314. },
  315. {
  316. type: "title",
  317. title: "收货地址",
  318. label: "",
  319. },
  320. {
  321. type: "slot",
  322. slotName: "deliveryAddress",
  323. },
  324. {
  325. type: "title",
  326. title: "付款信息",
  327. label: "",
  328. },
  329. {
  330. type: "select",
  331. label: "结算方式",
  332. prop: "settlementMethod",
  333. data: proxy.useUserStore().allDict["settlement_method"],
  334. itemWidth: 33,
  335. },
  336. {
  337. type: "select",
  338. label: "发票类型",
  339. prop: "invoiceType",
  340. data: proxy.useUserStore().allDict["invoice_type"],
  341. itemWidth: 33,
  342. },
  343. {
  344. type: "date",
  345. prop: "deliveryDate",
  346. label: "交付日期",
  347. format: "YYYY-MM-DD HH:mm:ss",
  348. itemType: "datetime",
  349. itemWidth: 34,
  350. },
  351. {
  352. type: "select",
  353. label: "币种",
  354. prop: "currency",
  355. data: proxy.useUserStore().allDict["currency"],
  356. itemWidth: 33,
  357. },
  358. {
  359. type: "number",
  360. prop: "advancePayment",
  361. label: "预付款 (%)",
  362. min: 0,
  363. max: 100,
  364. precision: 2,
  365. controls: false,
  366. itemWidth: 33,
  367. },
  368. {
  369. type: "slot",
  370. slotName: "balancePayment",
  371. label: "尾款 (%)",
  372. itemWidth: 34,
  373. },
  374. {
  375. type: "slot",
  376. prop: "paymentDate",
  377. slotName: "paymentDate",
  378. label: "付款日期",
  379. },
  380. {
  381. type: "title",
  382. title: "款项金额",
  383. label: "",
  384. },
  385. {
  386. type: "slot",
  387. slotName: "money",
  388. },
  389. {
  390. type: "title",
  391. title: "附件",
  392. label: "",
  393. },
  394. {
  395. type: "slot",
  396. slotName: "attachments",
  397. label: "附件",
  398. },
  399. {
  400. type: "title",
  401. title: "合同内容",
  402. label: "",
  403. },
  404. {
  405. type: "slot",
  406. slotName: "template",
  407. },
  408. ];
  409. });
  410. const rules = ref({
  411. supplierId: [{ required: true, message: "请选择供应商", trigger: "change" }],
  412. province: [{ required: true, message: "请输入省份", trigger: "blur" }],
  413. city: [{ required: true, message: "请输入城市", trigger: "blur" }],
  414. detailedAddress: [{ required: true, message: "请输入地址", trigger: "blur" }],
  415. contactPerson: [{ required: true, message: "请输入联系人", trigger: "blur" }],
  416. contactNumber: [{ required: true, message: "请输入联系人电话", trigger: "blur" }],
  417. unitPrice: [{ required: true, message: "请输入含税单价", trigger: "blur" }],
  418. taxRate: [{ required: true, message: "请输入税率", trigger: "blur" }],
  419. purchaseQuantity: [{ required: true, message: "请输入采购数量", trigger: "blur" }],
  420. receiveProvince: [{ required: true, message: "请输入省份", trigger: "blur" }],
  421. receiveCity: [{ required: true, message: "请输入城市", trigger: "blur" }],
  422. receiveDetailedAddress: [{ required: true, message: "请输入详细地址", trigger: "blur" }],
  423. receivePostcode: [{ required: true, message: "请输入邮编", trigger: "blur" }],
  424. receiveContactPerson: [{ required: true, message: "请输入联系人", trigger: "blur" }],
  425. receiveContactNumber: [{ required: true, message: "请输入联系人电话", trigger: "blur" }],
  426. settlementMethod: [{ required: true, message: "请选择结算方式", trigger: "change" }],
  427. invoiceType: [{ required: true, message: "请选择发票类型", trigger: "change" }],
  428. deliveryDate: [{ required: true, message: "请选择交付日期", trigger: "change" }],
  429. currency: [{ required: true, message: "请选择币种", trigger: "change" }],
  430. advancePayment: [{ required: true, message: "请输入预付款", trigger: "blur" }],
  431. paymentDate: [{ required: true, message: "请选择付款日期", trigger: "change" }],
  432. });
  433. const getDemandData = () => {
  434. proxy.post("/supplier/page", { pageNum: 1, pageSize: 999 }).then((res) => {
  435. if (res.rows && res.rows.length > 0) {
  436. supplierList.value = res.rows.map((item) => {
  437. return {
  438. ...item,
  439. dictKey: item.id,
  440. dictValue: item.name,
  441. };
  442. });
  443. }
  444. });
  445. proxy.post("/contractTemplate/page", { pageNum: 1, pageSize: 999 }).then((res) => {
  446. if (res.rows && res.rows.length > 0) {
  447. templateList.value = res.rows.map((item) => {
  448. return {
  449. ...item,
  450. dictKey: item.id,
  451. dictValue: item.name,
  452. };
  453. });
  454. }
  455. });
  456. };
  457. getDemandData();
  458. const supplierData = ref({});
  459. const changeSupplier = () => {
  460. if (formData.data.supplierId) {
  461. let list = supplierList.value.filter((item) => item.id === formData.data.supplierId);
  462. if (list && list.length > 0) {
  463. supplierData.value = list[0];
  464. formData.data.province = list[0].province;
  465. formData.data.city = list[0].city;
  466. formData.data.detailedAddress = list[0].detailedAddress;
  467. formData.data.contactPerson = list[0].contactPerson1;
  468. formData.data.contactNumber = list[0].contactNumber1;
  469. formData.data.paymentDate = "到货后次月1号起" + list[0].nextMonthDays + "天内,结算费用";
  470. }
  471. } else {
  472. supplierData.value = {};
  473. formData.data.province = "";
  474. formData.data.city = "";
  475. formData.data.detailedAddress = "";
  476. formData.data.contactPerson = "";
  477. formData.data.contactNumber = "";
  478. }
  479. };
  480. const calculatedTotalAmount = () => {
  481. let money = 0;
  482. let notTaxMoney = 0;
  483. if (formData.data.purchaseBomList && formData.data.purchaseBomList.length > 0) {
  484. for (let i = 0; i < formData.data.purchaseBomList.length; i++) {
  485. if (formData.data.purchaseBomList[i].unitPrice && formData.data.purchaseBomList[i].purchaseQuantity) {
  486. money = Number(Math.round((money + formData.data.purchaseBomList[i].unitPrice * formData.data.purchaseBomList[i].purchaseQuantity) * 1000) / 1000);
  487. if (formData.data.purchaseBomList[i].taxRate) {
  488. notTaxMoney = Number(
  489. Math.round(
  490. (notTaxMoney +
  491. (Math.round(((formData.data.purchaseBomList[i].unitPrice * 100) / (100 + formData.data.purchaseBomList[i].taxRate)) * 1000) / 1000) *
  492. formData.data.purchaseBomList[i].purchaseQuantity) *
  493. 1000
  494. ) / 1000
  495. );
  496. }
  497. }
  498. }
  499. }
  500. formData.data.totalAmountIncludingTax = money;
  501. formData.data.totalAmountIncludingTaxCn = proxy.NumberToChinese(money);
  502. formData.data.totalAmountExcludingTax = notTaxMoney;
  503. formData.data.totalAmountExcludingTaxCn = proxy.NumberToChinese(notTaxMoney);
  504. };
  505. const clickDelete = (index) => {
  506. formData.data.purchaseBomList.splice(index, 1);
  507. };
  508. const changeReceiveGoodsType = () => {
  509. if (formData.data.receiveGoodsType == 1) {
  510. formData.data.receiveProvince = "福建省";
  511. formData.data.receiveCity = "福州市";
  512. formData.data.receiveDetailedAddress = "福清市三山镇横坑村金园路18号3号楼";
  513. formData.data.receivePostcode = "350000";
  514. } else {
  515. formData.data.receiveProvince = "";
  516. formData.data.receiveCity = "";
  517. formData.data.receiveDetailedAddress = "";
  518. formData.data.receivePostcode = "";
  519. }
  520. formData.data.receiveContactPerson = "";
  521. formData.data.receiveContactNumber = "";
  522. };
  523. const changeTemplate = () => {
  524. if (formData.data.contractTemplateId) {
  525. proxy.post("/contractTemplate/detail", { id: formData.data.contractTemplateId }).then((res) => {
  526. proxy.$refs.editor.changeHtml(res.content);
  527. });
  528. }
  529. };
  530. const updateValue = (val) => {
  531. formData.data.contract = val;
  532. };
  533. const handleSubmit = async (flag) => {
  534. if (flag) {
  535. return true;
  536. } else {
  537. let status = await proxy.$refs.submit.handleSubmit(() => {});
  538. if (status) {
  539. if (!(formData.data.purchaseBomList && formData.data.purchaseBomList.length > 0)) {
  540. ElMessage("请添加采购清单");
  541. return false;
  542. } else {
  543. if (!route.query.processType) {
  544. for (let i = 0; i < formData.data.purchaseBomList.length; i++) {
  545. if (
  546. Number(
  547. Math.round(
  548. formData.data.purchaseBomList[i].quantity -
  549. formData.data.purchaseBomList[i].purchasedQuantity -
  550. formData.data.purchaseBomList[i].frozenQuantity
  551. )
  552. ) < formData.data.purchaseBomList[i].purchaseQuantity
  553. ) {
  554. ElMessage("采购数量不能大于可采购数量");
  555. return false;
  556. }
  557. }
  558. } else if (route.query.processType == 30) {
  559. for (let i = 0; i < formData.data.purchaseBomList.length; i++) {
  560. if (
  561. Number(
  562. Math.round(
  563. formData.data.purchaseBomList[i].quantity -
  564. formData.data.purchaseBomList[i].purchasedQuantity -
  565. formData.data.purchaseBomList[i].frozenQuantity +
  566. formData.data.purchaseBomList[i].thisTimeQuantity
  567. )
  568. ) < formData.data.purchaseBomList[i].purchaseQuantity
  569. ) {
  570. ElMessage("采购数量不能大于可采购数量");
  571. return false;
  572. }
  573. }
  574. }
  575. }
  576. if (fileList.value && fileList.value.length > 0) {
  577. for (let i = 0; i < fileList.value.length; i++) {
  578. if (fileList.value[i].raw.uploadState) {
  579. ElMessage("文件上传中,请稍后提交");
  580. return false;
  581. }
  582. }
  583. formData.data.fileList = fileList.value.map((item) => {
  584. return {
  585. id: item.raw.id,
  586. fileName: item.raw.fileName,
  587. fileUrl: item.raw.fileUrl,
  588. };
  589. });
  590. } else {
  591. formData.data.fileList = [];
  592. }
  593. return true;
  594. } else {
  595. setTimeout(() => {
  596. const errorDiv = document.getElementsByClassName("is-error");
  597. errorDiv[0].scrollIntoView();
  598. }, 0);
  599. }
  600. return false;
  601. }
  602. };
  603. const getFormData = () => {
  604. return proxy.deepClone(formData.data);
  605. };
  606. const fileList = ref([]);
  607. const uploadFileData = ref({});
  608. const beforeUpload = async (file) => {
  609. const res = await proxy.post("/fileInfo/getSing", { fileName: file.name });
  610. uploadFileData.value = res.uploadBody;
  611. file.id = res.id;
  612. file.fileName = res.fileName;
  613. file.fileUrl = res.fileUrl;
  614. file.uploadState = true;
  615. return true;
  616. };
  617. const onSuccessFile = (any, UploadFile) => {
  618. UploadFile.raw.uploadState = false;
  619. };
  620. const onPreviewFile = (file) => {
  621. window.open(file.raw.fileUrl, "_blank");
  622. };
  623. watch(
  624. () => props.queryData,
  625. (newValue) => {
  626. formOption.disabled = judgeStatus();
  627. if (props.queryData && ["10", "20", "30", "40"].includes(route.query.processType)) {
  628. formData.data = proxy.deepClone(newValue);
  629. if (formData.data.contract) {
  630. proxy.$refs.editor.changeHtml(formData.data.contract);
  631. }
  632. formData.data.totalAmountIncludingTaxCn = proxy.NumberToChinese(formData.data.totalAmountIncludingTax);
  633. formData.data.totalAmountExcludingTaxCn = proxy.NumberToChinese(formData.data.totalAmountExcludingTax);
  634. if (formData.data.applyBuyId) {
  635. proxy.post("/applyBuy/detail", { id: formData.data.applyBuyId, purchaseId: formData.data.id }).then((res) => {
  636. if (formData.data.purchaseBomList && formData.data.purchaseBomList.length > 0 && res.applyBuyBomList && res.applyBuyBomList.length > 0) {
  637. for (let i = 0; i < formData.data.purchaseBomList.length; i++) {
  638. formData.data.purchaseBomList[i].thisTimeQuantity = proxy.deepClone(formData.data.purchaseBomList[i].purchaseQuantity);
  639. for (let j = 0; j < res.applyBuyBomList.length; j++) {
  640. if (formData.data.purchaseBomList[i].applyBuyBomId === res.applyBuyBomList[j].id) {
  641. formData.data.purchaseBomList[i].quantity = res.applyBuyBomList[j].quantity;
  642. formData.data.purchaseBomList[i].purchasedQuantity = res.applyBuyBomList[j].purchaseQuantity;
  643. formData.data.purchaseBomList[i].frozenQuantity = res.applyBuyBomList[j].frozenQuantity;
  644. formData.data.purchaseBomList[i].arrivalQuantity = res.applyBuyBomList[j].arrivalQuantity;
  645. formData.data.purchaseBomList[i].inTransitQuantity = res.applyBuyBomList[j].inTransitQuantity;
  646. }
  647. }
  648. }
  649. }
  650. });
  651. }
  652. if (formData.data.id) {
  653. proxy.post("/fileInfo/getList", { businessIdList: [formData.data.id] }).then((fileObj) => {
  654. if (fileObj[formData.data.id] && fileObj[formData.data.id].length > 0) {
  655. fileList.value = fileObj[formData.data.id].map((item) => {
  656. return {
  657. raw: item,
  658. name: item.fileName,
  659. url: item.fileUrl,
  660. };
  661. });
  662. } else {
  663. fileList.value = [];
  664. }
  665. });
  666. }
  667. }
  668. },
  669. {
  670. deep: true,
  671. }
  672. );
  673. onMounted(() => {
  674. if (route.query.subscribeId) {
  675. formData.data.applyBuyId = route.query.subscribeId;
  676. proxy.post("/applyBuy/detail", { id: route.query.subscribeId }).then((res) => {
  677. if (res.applyBuyBomList && res.applyBuyBomList.length > 0) {
  678. formData.data.purchaseBomList = res.applyBuyBomList.map((item) => {
  679. let frozenQuantity = 0;
  680. if (item.frozenQuantity) {
  681. frozenQuantity = item.frozenQuantity;
  682. }
  683. return {
  684. applyBuyBomId: item.id,
  685. bomSpecId: item.bomSpecId,
  686. unitPrice: undefined,
  687. taxRate: undefined,
  688. purchaseQuantity: undefined,
  689. bomSpecCode: item.bomSpecCode,
  690. bomSpecName: item.bomSpecName,
  691. bomSpecColour: item.bomSpecColour,
  692. bomSpecLength: item.bomSpecLength,
  693. bomSpecWidth: item.bomSpecWidth,
  694. bomSpecHeight: item.bomSpecHeight,
  695. quantity: item.quantity,
  696. purchasedQuantity: item.purchaseQuantity,
  697. frozenQuantity: frozenQuantity,
  698. };
  699. });
  700. }
  701. });
  702. }
  703. });
  704. const computeBalancePayment = () => {
  705. let num = 100;
  706. if (formData.data.advancePayment) {
  707. num = Number(Math.round((num - formData.data.advancePayment) * 100) / 100);
  708. }
  709. return num + "%";
  710. };
  711. // 向父组件暴露
  712. defineExpose({ getFormData, handleSubmit });
  713. </script>
  714. <style lang="scss" scoped>
  715. ::v-deep(.el-input-number .el-input__inner) {
  716. text-align: left;
  717. }
  718. :deep(.el-dialog) {
  719. margin-top: 10px !important;
  720. margin-bottom: 10px !important;
  721. }
  722. </style>