projectDetails.vue 26 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950
  1. <template>
  2. <div>
  3. <el-row style="height: 800px">
  4. <el-col :span="10">
  5. <el-card
  6. style="height: 100%"
  7. >
  8. <template #header>
  9. <el-row align="middle">
  10. <el-col :span="6">
  11. <el-text size="large">项目基本信息</el-text>
  12. </el-col>
  13. <el-col
  14. :span="4"
  15. :offset="14"
  16. >
  17. <el-button
  18. type="primary"
  19. :icon="Edit"
  20. @click="basicEditShow"
  21. >信息编辑
  22. </el-button>
  23. </el-col>
  24. </el-row>
  25. </template>
  26. <el-tabs
  27. v-model="activeName"
  28. class="demo-tabs"
  29. type="border-card"
  30. @tab-click="handleClick"
  31. >
  32. <el-tab-pane
  33. label="甲方信息"
  34. name="first"
  35. >
  36. <el-row class="mt-2">
  37. <el-text
  38. size="large"
  39. :line-clamp="1"
  40. >
  41. <b>项目名称:</b>{{ information.name }}
  42. </el-text>
  43. </el-row>
  44. <el-row class="mt-10">
  45. <el-text
  46. size="large"
  47. :line-clamp="1"
  48. >
  49. <b>项目地址:</b>{{ information.address }}
  50. </el-text>
  51. </el-row>
  52. <el-row class="mt-10">
  53. <el-text
  54. size="large"
  55. :line-clamp="1"
  56. >
  57. <b>甲方负责人:</b>{{ information.firstPrincipal }}
  58. </el-text>
  59. </el-row>
  60. <el-row class="mt-10">
  61. <el-text
  62. size="large"
  63. :line-clamp="1"
  64. >
  65. <b>甲方负责人电话:</b>{{ information.firstPhone }}
  66. </el-text>
  67. </el-row>
  68. </el-tab-pane>
  69. <el-tab-pane
  70. label="乙方信息"
  71. name="second"
  72. >
  73. <el-row class="mt-2">
  74. <el-text
  75. size="large"
  76. :line-clamp="1"
  77. >
  78. <b>乙方负责人:</b>{{ information.secondPrincipal }}
  79. </el-text>
  80. </el-row>
  81. <el-row class="mt-10">
  82. <el-text
  83. size="large"
  84. :line-clamp="1"
  85. >
  86. <b>合同金额:</b>{{ information.projectPrice }}元
  87. </el-text>
  88. </el-row>
  89. <el-row class="mt-10">
  90. <el-text
  91. size="large"
  92. >
  93. <b>合同签订时间:</b>{{ information.signTime }}
  94. </el-text>
  95. </el-row>
  96. <el-row class="mt-10">
  97. <el-text
  98. size="large"
  99. >
  100. <b>进场施工时间:</b>{{ information.intoConstructionTime }}
  101. </el-text>
  102. </el-row>
  103. <el-row class="mt-10">
  104. <el-text
  105. size="large"
  106. >
  107. <b>竣工时间:</b>{{ information.completedTime }}
  108. </el-text>
  109. </el-row>
  110. <el-row class="mt-10">
  111. <el-text
  112. size="large"
  113. >
  114. <b>项目状态:</b>{{ currentState }}
  115. </el-text>
  116. </el-row>
  117. <el-row class="mt-10">
  118. <el-col :span="3">
  119. <el-text
  120. size="large"
  121. >
  122. <b>项目说明:</b>
  123. </el-text>
  124. </el-col>
  125. <el-col :span="20">
  126. <el-text
  127. size="large"
  128. :line-clamp="4"
  129. >
  130. {{ information.illustrate }}
  131. </el-text>
  132. </el-col>
  133. </el-row>
  134. </el-tab-pane>
  135. <el-tab-pane
  136. label="丙方信息"
  137. name="third"
  138. >
  139. <el-row class="mt-2">
  140. <el-text
  141. size="large"
  142. :line-clamp="1"
  143. >
  144. <b>监理人姓名:</b>{{ information.supervisorName }}
  145. </el-text>
  146. </el-row>
  147. <el-row class="mt-10">
  148. <el-text
  149. size="large"
  150. >
  151. <b>监理单位:</b>{{ information.supervisorUint }}
  152. </el-text>
  153. </el-row>
  154. <el-row class="mt-10">
  155. <el-text
  156. size="large"
  157. >
  158. <b>监理人电话:</b>{{ information.supervisorPhone }}
  159. </el-text>
  160. </el-row>
  161. </el-tab-pane>
  162. </el-tabs>
  163. </el-card>
  164. </el-col>
  165. <el-col
  166. :span="13"
  167. class="ml-5"
  168. >
  169. <el-card
  170. style="height: 100%"
  171. >
  172. <template #header>
  173. <el-row align="middle">
  174. <el-col :span="6">
  175. <el-text size="large">项目文件列表</el-text>
  176. </el-col>
  177. <el-col
  178. :span="6"
  179. :offset="12"
  180. >
  181. <el-button
  182. type="primary"
  183. :icon="Edit"
  184. @click="openOptionEdit"
  185. >项目状态和文件类型编辑
  186. </el-button>
  187. </el-col>
  188. </el-row>
  189. </template>
  190. <el-row>
  191. <el-col :span="6">
  192. <el-input
  193. v-model="fileCondition.name"
  194. placeholder="请输入文件名称"
  195. clearable
  196. />
  197. </el-col>
  198. <el-col
  199. :span="4"
  200. :offset="1"
  201. >
  202. <el-select
  203. v-model="fileType"
  204. clearable
  205. placeholder="文件类型"
  206. @change="changeFileType"
  207. >
  208. <el-option
  209. v-for="item in editor.typeList"
  210. :key="item.ID"
  211. :label="item.name"
  212. :value="item.ID"
  213. />
  214. </el-select>
  215. </el-col>
  216. <el-col
  217. :span="3"
  218. :offset="1"
  219. >
  220. <el-button
  221. type="primary"
  222. :icon="Search"
  223. @click="queryFile"
  224. >查询
  225. </el-button>
  226. </el-col>
  227. <el-col
  228. :span="3"
  229. >
  230. <el-button
  231. type="primary"
  232. :icon="RefreshLeft"
  233. @click="resetData"
  234. >
  235. 重置
  236. </el-button>
  237. </el-col>
  238. <el-col
  239. :span="3"
  240. >
  241. <el-dropdown
  242. split-button
  243. type="primary"
  244. >
  245. 菜单
  246. <template #dropdown>
  247. <el-dropdown-menu>
  248. <el-dropdown-item>
  249. <el-button
  250. type="primary"
  251. :icon="Upload"
  252. @click="fileDialog = true"
  253. >
  254. 上传
  255. </el-button>
  256. </el-dropdown-item>
  257. <el-dropdown-item>
  258. <el-button
  259. type="primary"
  260. :icon="Download"
  261. @click="downloadTips"
  262. >
  263. 下载
  264. </el-button>
  265. </el-dropdown-item>
  266. <el-dropdown-item>
  267. <el-button
  268. type="primary"
  269. :icon="Delete"
  270. @click="projectDeletes"
  271. >
  272. 删除
  273. </el-button>
  274. </el-dropdown-item>
  275. </el-dropdown-menu>
  276. </template>
  277. </el-dropdown>
  278. </el-col>
  279. </el-row>
  280. <el-row style="margin-top: 20px">
  281. <el-col :span="24">
  282. <el-table
  283. :data="fileList"
  284. row-class-name="row-class"
  285. border
  286. height="562px"
  287. stripe
  288. >
  289. <el-table-column
  290. prop="ID"
  291. align="center"
  292. label="ID"
  293. width="180"
  294. />
  295. <el-table-column
  296. prop="name"
  297. label="文件名称"
  298. align="center"
  299. width="350"
  300. />
  301. <el-table-column
  302. label="项目操作"
  303. align="center"
  304. fixed="right"
  305. >
  306. <template #default="scope">
  307. <el-button
  308. text
  309. type="primary"
  310. :icon="Download"
  311. size="large"
  312. @click="oneDownload(scope.row)"
  313. >
  314. 下载
  315. </el-button>
  316. <el-button
  317. text
  318. type="primary"
  319. :icon="Delete"
  320. size="large"
  321. @click="projectDelete(scope.row)"
  322. >
  323. 删除
  324. </el-button>
  325. </template>
  326. </el-table-column>
  327. </el-table>
  328. </el-col>
  329. </el-row>
  330. <el-row justify="end">
  331. <el-pagination
  332. :page-size="9"
  333. background
  334. layout="prev, pager, next"
  335. :total="fileTotal"
  336. @change="changeFilePage"
  337. />
  338. </el-row>
  339. </el-card>
  340. </el-col>
  341. </el-row>
  342. <el-dialog
  343. v-model="fileDialog"
  344. title="上传文件"
  345. width="40%"
  346. :before-close="fileDialogClose"
  347. :align-center="true"
  348. >
  349. <el-form>
  350. <el-row style="margin-top: 20px">
  351. <el-col :span="8">
  352. <el-form-item label="文件类型:">
  353. <el-select
  354. v-model="uploadFileType"
  355. clearable
  356. placeholder="请选择上传文件的类型"
  357. @change="changeUploadFileType"
  358. >
  359. <el-option
  360. v-for="item in editor.typeList"
  361. :key="item.ID"
  362. :label="item.name"
  363. :value="item.ID"
  364. />
  365. </el-select>
  366. </el-form-item>
  367. </el-col>
  368. </el-row>
  369. </el-form>
  370. <el-row style="margin-top: 20px">
  371. <el-col :span="24">
  372. <el-upload
  373. class="upload-demo"
  374. drag
  375. multiple
  376. :auto-upload="false"
  377. :file-list="uploadFileData"
  378. :on-change="changeFileData"
  379. :on-remove="removeFileData"
  380. >
  381. <el-icon class="el-icon--upload">
  382. <upload-filled />
  383. </el-icon>
  384. <div class="el-upload__text">
  385. 请选择需要上传的文件
  386. </div>
  387. <template #tip>
  388. <div class="el-upload__tip">
  389. 选择的文件不要超过500MB
  390. </div>
  391. </template>
  392. </el-upload>
  393. </el-col>
  394. </el-row>
  395. <template #footer>
  396. <div class="dialog-footer">
  397. <el-button @click="fileDialog = false">取消</el-button>
  398. <el-button
  399. type="primary"
  400. @click="supplementFile"
  401. >
  402. 上传
  403. </el-button>
  404. </div>
  405. </template>
  406. </el-dialog>
  407. <el-dialog
  408. v-model="stateTypeShow"
  409. title="状态和类型编辑"
  410. width="40%"
  411. >
  412. <option-edit />
  413. </el-dialog>
  414. <el-drawer
  415. v-model="basicEditDisplay"
  416. title="项目基本信息编辑"
  417. >
  418. <el-form
  419. size="large"
  420. style="margin-top: 10px"
  421. label-position="left"
  422. label-width="110"
  423. >
  424. <el-tabs v-model="editItem">
  425. <el-tab-pane
  426. label="甲方信息"
  427. name="first"
  428. >
  429. <el-form-item
  430. label="项目名称:"
  431. >
  432. <el-input
  433. v-model="editData.name"
  434. placeholder="请输入项目名称"
  435. />
  436. </el-form-item>
  437. <el-form-item
  438. label="项目地址:"
  439. >
  440. <el-input
  441. v-model="editData.address"
  442. placeholder="请输入项目名称"
  443. />
  444. </el-form-item>
  445. <el-form-item
  446. label="甲方负责人:"
  447. >
  448. <el-input
  449. v-model="editData.firstPrincipal"
  450. placeholder="请输入甲方负责人"
  451. />
  452. </el-form-item>
  453. <el-form-item
  454. label="负责人电话:"
  455. >
  456. <el-input
  457. v-model="editData.firstPhone"
  458. placeholder="请输入甲方负责人电话"
  459. />
  460. </el-form-item>
  461. </el-tab-pane>
  462. <el-tab-pane
  463. label="乙方信息"
  464. name="second"
  465. >
  466. <el-form-item label="乙方负责人:">
  467. <el-input
  468. v-model="editData.secondPrincipal"
  469. placeholder="请输入乙方负责人姓名"
  470. />
  471. </el-form-item>
  472. <el-form-item label="合同金额:">
  473. <el-input-number v-model="editData.projectPrice" />
  474. </el-form-item>
  475. <el-form-item label="合同签订日期:">
  476. <el-date-picker
  477. v-model="editData.signTime"
  478. type="date"
  479. placeholder="请选择合同签订时间"
  480. format="YYYY-MM-DD"
  481. value-format="YYYY-MM-DD"
  482. clearable
  483. @clear="editData.signTime = ''"
  484. />
  485. </el-form-item>
  486. <el-form-item label="进场施工时间:">
  487. <el-date-picker
  488. v-model="editData.intoConstructionTime"
  489. type="date"
  490. placeholder="请选择进场施工时间"
  491. format="YYYY-MM-DD"
  492. value-format="YYYY-MM-DD"
  493. clearable
  494. @clear="editData.intoConstructionTime = ''"
  495. />
  496. </el-form-item>
  497. <el-form-item label="竣工时间:">
  498. <el-date-picker
  499. v-model="editData.completedTime"
  500. type="date"
  501. placeholder="请选择竣工时间"
  502. format="YYYY-MM-DD"
  503. value-format="YYYY-MM-DD"
  504. clearable
  505. @clear="editData.completedTime = ''"
  506. />
  507. </el-form-item>
  508. <el-form-item label="项目状态:">
  509. <el-select
  510. v-model="editData.state"
  511. >
  512. <el-option
  513. v-for="item in editor.stateList"
  514. :key="item.ID"
  515. :label="item.name"
  516. :value="item.ID"
  517. />
  518. </el-select>
  519. </el-form-item>
  520. <el-form-item label="项目说明:">
  521. <el-input
  522. v-model="editData.illustrate"
  523. :rows="5"
  524. type="textarea"
  525. placeholder="请输入项目说明"
  526. />
  527. </el-form-item>
  528. </el-tab-pane>
  529. <el-tab-pane
  530. label="丙方信息"
  531. name="third"
  532. >
  533. <el-form-item label="监理人姓名:">
  534. <el-input
  535. v-model="editData.supervisorName"
  536. placeholder="请输入监理人姓名"
  537. />
  538. </el-form-item>
  539. <el-form-item label="监理单位:">
  540. <el-input
  541. v-model="editData.supervisorUint"
  542. placeholder="请输入监理单位"
  543. />
  544. </el-form-item>
  545. <el-form-item label="监理电话:">
  546. <el-input
  547. v-model="editData.supervisorPhone"
  548. placeholder="请输入监理电话"
  549. />
  550. </el-form-item>
  551. </el-tab-pane>
  552. </el-tabs>
  553. </el-form>
  554. <template #footer>
  555. <div class="dialog-footer">
  556. <el-button
  557. size="large"
  558. @click="basicEditDisplay = false"
  559. >
  560. 取消
  561. </el-button>
  562. <el-button
  563. type="primary"
  564. size="large"
  565. @click="basicDataEdit"
  566. >
  567. 确定
  568. </el-button>
  569. </div>
  570. </template>
  571. </el-drawer>
  572. </div>
  573. </template>
  574. <script setup>
  575. import { getProjectMessage, editProject } from '@/api/project'
  576. import { onMounted, reactive, ref } from 'vue'
  577. import { getAllUsers } from '@/api/user'
  578. import { queryFileList, createProjectFile, downloadProjectFile, deleteProjectFile, deleteProjectFiles } from '@/api/file'
  579. import { Download, Upload, Delete, Search, RefreshLeft, Edit } from '@element-plus/icons-vue'
  580. import { ElMessage, ElMessageBox } from 'element-plus'
  581. import OptionEdit from './components/optionEdit.vue'
  582. import { editorData } from '@/pinia/project/project'
  583. import { fileDownload } from '@/api/dailyFile'
  584. import { useRoute, useRouter } from 'vue-router'
  585. // eslint-disable-next-line no-unused-vars
  586. const router = useRouter()
  587. const route = useRoute()
  588. defineOptions({
  589. name: 'ProjectDetails'
  590. })
  591. // ......................................
  592. // 基本信息编辑
  593. const activeName = ref('first')
  594. const handleClick = () => {}
  595. const basicEditDisplay = ref(false)
  596. const basicEditShow = () => {
  597. basicEditDisplay.value = true
  598. Object.assign(editData, information)
  599. }
  600. const editItem = ref('first')
  601. const basicDataEdit = () => {
  602. const edit = {
  603. id: editData.ID,
  604. code: route.query.code, // 项目编号
  605. name: editData.name, // 项目名称
  606. address: editData.address, // 项目地址
  607. firstPrincipal: editData.firstPrincipal, // 甲方负责人
  608. firstPhone: editData.firstPhone, // 甲方电话
  609. projectPrice: editData.projectPrice, // 合同金额
  610. secondPrincipal: editData.secondPrincipal, // 乙方负责人
  611. signTime: editData.signTime, // 合同签订日期
  612. intoConstructionTime: editData.intoConstructionTime, // 进场施工时间
  613. completedTime: editData.completedTime, // 竣工时间
  614. supervisorUint: editData.supervisorUint, // 监理单位
  615. supervisorName: editData.supervisorName, // 监理姓名
  616. supervisorPhone: editData.supervisorPhone, // 监理电话
  617. illustrate: editData.illustrate, // 说明
  618. state: editData.state // 状态
  619. }
  620. for (const i in edit) {
  621. if (edit[i] === '' || edit[i] === 0 || edit[i] === null) {
  622. ElMessage.error('请将甲乙丙三方的信息填写完整')
  623. return
  624. }
  625. }
  626. editProject(edit).then(res => {
  627. if (res.code === 0) {
  628. ElMessage({
  629. message: '编辑成功',
  630. type: 'success',
  631. showClose: true,
  632. duration: 2000
  633. })
  634. basicEditDisplay.value = false
  635. projectMessage(route.query.code)
  636. }
  637. })
  638. }
  639. // 数据
  640. const editor = editorData()
  641. const fileCondition = reactive({
  642. code: route.query.code,
  643. name: '',
  644. genre: 0,
  645. pageInfo: {
  646. page: 1,
  647. pageSize: 9
  648. }
  649. })
  650. const information = reactive({})
  651. // 用于编辑的数据
  652. const editData = reactive({})
  653. // 项目用户列表
  654. const userList = reactive([])
  655. // 项目文件列表
  656. const fileList = reactive([])
  657. const fileTotal = ref(0)
  658. // 项目文件类型列表
  659. const fileTypeList = reactive([])
  660. // 项目文件类型
  661. const fileType = ref('')
  662. // 上传文件弹窗
  663. const fileDialog = ref(false)
  664. const uploadFileType = ref('')
  665. const uploadFileData = ref([])
  666. const stateTypeShow = ref(false)
  667. const currentState = ref('')
  668. // 方法
  669. onMounted(() => {
  670. projectMessage(route.query.code)
  671. queryFile()
  672. editor.getStateList()
  673. editor.getTypeList()
  674. getAllUsers().then(res => {
  675. if (res.code === 0) {
  676. userList.push(...res.data)
  677. }
  678. })
  679. })
  680. // 初始化项目数据
  681. const projectMessage = (code) => {
  682. getProjectMessage(code).then(res => {
  683. if (res.code === 0) {
  684. const data = res.data
  685. console.log(data)
  686. data.CreatedAt = formatDate(data.CreatedAt)
  687. data.UpdatedAt = formatDate(data.UpdatedAt)
  688. Object.keys(data).forEach(key => {
  689. information[key] = data[key]
  690. editData[key] = data[key]
  691. })
  692. currentState.value = information.projectState.name
  693. }
  694. })
  695. }
  696. // 重置
  697. const resetData = () => {
  698. fileCondition.code = route.query.code
  699. fileCondition.name = ''
  700. fileCondition.genre = 0
  701. fileCondition.pageInfo = {
  702. page: 1,
  703. pageSize: 9
  704. }
  705. queryFile()
  706. }
  707. const changeFileType = (value) => {
  708. if (typeof value === 'number') {
  709. fileTypeList.forEach(item => {
  710. if (item.ID === value) {
  711. fileType.value = item.name
  712. }
  713. })
  714. fileCondition.genre = value
  715. } else {
  716. fileCondition.genre = 0
  717. }
  718. }
  719. // 查询文件
  720. const queryFile = () => {
  721. queryFileList(fileCondition).then(res => {
  722. if (res.code === 0) {
  723. fileTotal.value = res.data.total
  724. fileList.length = 0
  725. fileList.push(...res.data.list)
  726. }
  727. })
  728. }
  729. // 上传文件
  730. const fileDialogClose = () => {
  731. fileDialog.value = false
  732. }
  733. const changeUploadFileType = (value) => {
  734. if (typeof value === 'number') {
  735. uploadFileType.value = value
  736. } else {
  737. uploadFileType.value = ''
  738. }
  739. }
  740. const changeFileData = (file, fileList) => {
  741. uploadFileData.value = fileList
  742. }
  743. const removeFileData = (file, fileList) => {
  744. uploadFileData.value = fileList
  745. }
  746. const supplementFile = () => {
  747. if (uploadFileType.value === '') {
  748. ElMessage.error('请选择文件类型')
  749. } else if (uploadFileData.value.length === 0) {
  750. ElMessage.error('暂未选择文件')
  751. } else {
  752. const formData = new FormData()
  753. uploadFileData.value.forEach(item => {
  754. formData.append('file', item.raw)
  755. })
  756. formData.append('genre', uploadFileType.value)
  757. formData.append('code', route.query.code)
  758. createProjectFile(formData).then(res => {
  759. if (res.code === 0) {
  760. fileDialog.value = false
  761. ElMessage.success(res.msg)
  762. uploadFileType.value = ''
  763. uploadFileData.value = []
  764. queryFile()
  765. } else {
  766. ElMessage.error(res.msg)
  767. }
  768. })
  769. }
  770. }
  771. // 下载文件
  772. const downloadTips = () => {
  773. ElMessageBox.confirm(
  774. '确定要下载列表中的所有文件吗?',
  775. '文件下载',
  776. {
  777. confirmButtonText: '下载',
  778. cancelButtonText: '取消',
  779. type: 'warning',
  780. }
  781. )
  782. .then(() => {
  783. const type = fileType.value === '' ? 0 : fileType.value
  784. const data = {
  785. code: route.query.code,
  786. genre: type,
  787. name: fileCondition.name
  788. }
  789. downloadProjectFile(data).then(res => {
  790. const link = document.createElement('a')
  791. const href = window.URL.createObjectURL(res) // 创建下载的链接
  792. link.href = href
  793. link.download = route.query.code + '.zip' // 下载后文件名
  794. document.body.appendChild(link)
  795. link.click() // 点击下载
  796. document.body.removeChild(link) // 下载完成移除元素
  797. window.URL.revokeObjectURL(href) // 释放掉blob对象
  798. })
  799. })
  800. .catch(() => {
  801. ElMessage({
  802. type: 'info',
  803. message: '取消下载',
  804. })
  805. })
  806. }
  807. // 单文件下载
  808. const oneDownload = async(val) => {
  809. await fileDownload(val).then(res => {
  810. const link = document.createElement('a')
  811. const href = window.URL.createObjectURL(res) // 创建下载的链接
  812. link.href = href
  813. link.download = val.name // 下载后文件名
  814. document.body.appendChild(link)
  815. link.click() // 点击下载
  816. document.body.removeChild(link) // 下载完成移除元素
  817. window.URL.revokeObjectURL(href) // 释放掉blob对象
  818. })
  819. }
  820. // 单文件删除
  821. const projectDelete = async(val) => {
  822. ElMessageBox.confirm(
  823. '你确定进行删除操作吗?',
  824. '删除',
  825. {
  826. confirmButtonText: '确定',
  827. cancelButtonText: '取消',
  828. type: 'warning',
  829. }
  830. )
  831. .then(async() => {
  832. await deleteProjectFile(val).then(res => {
  833. if (res.code === 0) {
  834. ElMessage.success('删除成功')
  835. }
  836. })
  837. queryFile()
  838. })
  839. .catch(() => {
  840. ElMessage({
  841. type: 'info',
  842. message: '取消删除',
  843. })
  844. })
  845. }
  846. // 多文件删除
  847. const projectDeletes = async() => {
  848. ElMessageBox.confirm(
  849. '你确定进行删除操作吗?',
  850. '删除',
  851. {
  852. confirmButtonText: '确定',
  853. cancelButtonText: '取消',
  854. type: 'warning',
  855. }
  856. )
  857. .then(async() => {
  858. const type = fileType.value === '' ? 0 : fileType.value
  859. const data = {
  860. code: route.query.code,
  861. genre: type,
  862. name: fileCondition.name
  863. }
  864. await deleteProjectFiles(data).then(res => {
  865. if (res.code === 0) {
  866. ElMessage.success('删除成功')
  867. }
  868. })
  869. queryFile()
  870. })
  871. .catch(() => {
  872. ElMessage({
  873. type: 'info',
  874. message: '取消删除',
  875. })
  876. })
  877. }
  878. // 日期格式化
  879. const formatDate = (dateString, locale = 'en-US', timezone = 'Asia/Shanghai') => {
  880. // 使用 Date 构造函数解析日期字符串
  881. const date = new Date(dateString)
  882. // 检查日期是否有效
  883. if (isNaN(date.getTime())) {
  884. throw new Error('Invalid date string')
  885. }
  886. // 使用 Date 对象的年份、月份和日期来构建新的日期字符串
  887. // 注意:JavaScript 中的月份是从 0 开始的,所以我们需要加 1
  888. return `${date.getFullYear()}-${('0' + (date.getMonth() + 1)).slice(-2)}-${('0' + date.getDate()).slice(-2)}`
  889. }
  890. const changeFilePage = (value) => {
  891. fileCondition.pageInfo.page = value
  892. queryFile()
  893. }
  894. const openOptionEdit = () => {
  895. stateTypeShow.value = true
  896. }
  897. </script>
  898. <style scoped lang="scss">
  899. @mixin basic {
  900. width: 50%;
  901. display: flex;
  902. align-items: center;
  903. }
  904. .basicInformation {
  905. height: 50px;
  906. background-color: #f8fafd;
  907. display: flex;
  908. .basicTitle {
  909. @include basic;
  910. padding-left: 40px;
  911. }
  912. .basicEdit {
  913. @include basic;
  914. justify-content: end;
  915. padding-right: 40px;
  916. }
  917. }
  918. </style>