index.vue 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631
  1. <template>
  2. <div class="boxswai">
  3. <div class="boxnei">
  4. <el-row
  5. :gutter="20"
  6. style="height:100%;"
  7. >
  8. <el-col
  9. :span="5"
  10. style="height:99%;"
  11. >
  12. <div
  13. style="fontSize:18px; font-weight: 900;"
  14. class="marbottom5"
  15. >元素识别</div>
  16. <div style="height:98%;overflow: auto;width:auto;">
  17. <el-tree
  18. :data="treeData"
  19. :props="treeProps"
  20. @node-click="handleNodeClick"
  21. :load="loadNode"
  22. :expand-on-click-node="false"
  23. lazy
  24. ></el-tree>
  25. </div>
  26. </el-col>
  27. <el-col
  28. :span="19"
  29. style="height:98%;"
  30. >
  31. <div v-if="addElementForm.deptName==''">表名称</div>
  32. <div v-else>{{addElementForm.deptName}}</div>
  33. <el-row
  34. class="martop20"
  35. :gutter="20"
  36. style="height:96%;"
  37. >
  38. <el-col
  39. :span="16"
  40. style="overflow:auto;height:100%;border:1px solid black; border-radius: 4px;box-sizing: border-box;padding: 10px 10px;"
  41. >
  42. <div
  43. class="parent"
  44. id='parent'
  45. >
  46. </div>
  47. </el-col>
  48. <el-col
  49. :span="8"
  50. style="overflow:auto;height:100%;"
  51. >
  52. <div class="flexBetween flexItemsC">
  53. <el-button
  54. type="info"
  55. size="mini"
  56. :disabled="from.id==''"
  57. @click="automaticRecognition"
  58. >自动识别</el-button>
  59. <div
  60. class="el-icon-plus"
  61. @click="pushTableData"
  62. style="width:16px;height:16px;backgroundColor:#1DD81D;color:#fff;cursor: pointer;"
  63. ></div>
  64. </div>
  65. <el-table
  66. class="martop20"
  67. :data="tableData"
  68. border
  69. style="width: 100%"
  70. >
  71. <el-table-column
  72. type="index"
  73. label="坐标"
  74. >
  75. </el-table-column>
  76. <el-table-column
  77. prop="eName"
  78. label="元素名称"
  79. >
  80. <template slot-scope="scope">
  81. <el-input
  82. v-model="scope.row.eName"
  83. placeholder="请输入内容"
  84. ></el-input>
  85. </template>
  86. </el-table-column>
  87. <el-table-column
  88. prop="eType"
  89. label="数据类型"
  90. >
  91. <template slot-scope="scope">
  92. <el-select
  93. v-model="scope.row.eType"
  94. placeholder="请选择"
  95. >
  96. <el-option
  97. v-for="item in dataType"
  98. :key="item.dictKey"
  99. :label="item.dictValue"
  100. :value="item.dictKey"
  101. >
  102. </el-option>
  103. </el-select>
  104. </template>
  105. </el-table-column>
  106. <el-table-column
  107. prop="eAllowDeviation"
  108. label="允许偏差值"
  109. >
  110. <template slot-scope="scope">
  111. <el-input
  112. v-model="scope.row.eAllowDeviation"
  113. placeholder="请输入内容"
  114. ></el-input>
  115. </template>
  116. </el-table-column>
  117. <el-table-column label="操作">
  118. <template slot-scope="scope">
  119. <el-link
  120. type="danger"
  121. @click="deleteTableData(scope.$index)"
  122. >删除</el-link>
  123. </template>
  124. </el-table-column>
  125. </el-table>
  126. <el-button
  127. type="success"
  128. class="martop20 dingwei"
  129. @click="establish()"
  130. :disabled="from.id==''"
  131. >关联WBS并创建元素</el-button>
  132. </el-col>
  133. </el-row>
  134. </el-col>
  135. </el-row>
  136. <!-- 关联公共WBS模板 -->
  137. <el-dialog
  138. title="关联公共WBS模板"
  139. class="excelBox"
  140. :visible.sync="AssociatedPublicTap"
  141. modal-append-to-body
  142. append-to-body
  143. :before-close="AssociatedPublicClose"
  144. >
  145. <el-row :gutter="20">
  146. <el-col :span="12">
  147. <el-select
  148. style="width:100%;"
  149. v-model="GLExcelFrom.name"
  150. placeholder="请选择"
  151. @change="changetherr()"
  152. >
  153. <el-option
  154. v-for="(item,key) in GLExcelData"
  155. :key="key"
  156. :label="item.wbsName"
  157. :value="item.id"
  158. >
  159. </el-option>
  160. </el-select>
  161. <el-scrollbar style="height:50vh;">
  162. <el-tree
  163. v-if="GLExcelFromtag"
  164. @node-click="handleNodeClickExcel"
  165. ref="tree"
  166. class="filter-tree"
  167. style="margin-top:10px;"
  168. :props="GLExcelProps"
  169. :data="exceldata"
  170. :load="loadNodeTan"
  171. lazy
  172. node-key="id"
  173. accordion
  174. >
  175. </el-tree>
  176. </el-scrollbar>
  177. </el-col>
  178. <el-col
  179. :span="12"
  180. v-if="addElementForm.wbsId"
  181. >
  182. <el-button
  183. type="primary"
  184. style="float:right;"
  185. class="marbottom20"
  186. @click="addElementMD"
  187. :disabled="addElement"
  188. >新增元素信息表</el-button>
  189. <el-table
  190. :data="addTableData"
  191. border
  192. style="width: 100%"
  193. >
  194. <el-table-column
  195. prop="tableName"
  196. label="已有元素表名称"
  197. align="center"
  198. >
  199. </el-table-column>
  200. <el-table-column
  201. prop="name"
  202. label="操作"
  203. align="center"
  204. >
  205. <template slot-scope="scope">
  206. <el-button
  207. type="primary"
  208. size="mini"
  209. style="margin:0px;"
  210. @click="relationMD(scope.$index,'关联')"
  211. v-show="!scope.row.checknd"
  212. >选择关联</el-button>
  213. <el-button
  214. type="danger"
  215. size="mini"
  216. style="margin:0px;"
  217. @click="relationMD(scope.$index,'取消关联')"
  218. v-show="scope.row.checknd"
  219. >取消关联</el-button>
  220. </template>
  221. </el-table-column>
  222. </el-table>
  223. <div v-if="addElement">
  224. <div class="flexBetween martop40">
  225. <el-input
  226. v-model="addElementForm.deptName"
  227. placeholder="请输入表名"
  228. ></el-input>
  229. <el-select
  230. class="marleft10"
  231. v-model="addElementForm.tableType"
  232. placeholder="请选择表类型"
  233. >
  234. <el-option
  235. v-for="(item,index) in exceltypeData"
  236. :key="index"
  237. :label="item.dictValue"
  238. :value="item.dictKey"
  239. ></el-option>
  240. </el-select>
  241. </div>
  242. <el-select
  243. style="width:100%;"
  244. class="martop20 "
  245. v-model="addElementForm.tableOwner"
  246. placeholder="请选择所属方"
  247. >
  248. <el-option
  249. v-for="(item,index) in ownerTypeList"
  250. :key="index"
  251. :label="item.dictValue"
  252. :value="item.dictKey"
  253. ></el-option>
  254. </el-select>
  255. </div>
  256. </el-col>
  257. </el-row>
  258. <span
  259. slot="footer"
  260. class="dialog-footer"
  261. style="display: flex;justify-content: center;align-items: center;"
  262. >
  263. <el-button @click="AssociatedPublicClose()">取 消</el-button>
  264. <el-button
  265. style="margin-left:30px;"
  266. type="primary"
  267. @click="saveElementMD()"
  268. >确 定</el-button>
  269. </span>
  270. </el-dialog>
  271. </div>
  272. </div>
  273. </template>
  274. <script>
  275. import { tabLazytree, getExcelHtmlCol, excelType, submitExcelRelationWbsTreeAndElement, getWbsTypeList, getLazytree, } from "@/api/exctab/excelmodel";
  276. import { dictionarydataType } from "@/api/exctab/editelement";
  277. import { getColByTabId } from "@/api/manager/AdjustForm";
  278. import { selectByNodeTable } from "@/api/manager/wbstree";
  279. import { getDictionary } from "@/api/system/dict";
  280. import Vue from 'vue'
  281. export default {
  282. data () {
  283. return {
  284. //#region 左侧树节点
  285. treeData: [],
  286. treeProps: {
  287. label: 'name',
  288. children: 'children',
  289. isLeaf: 'hasChildren'
  290. },
  291. //#endregion
  292. excelSrc: '',
  293. from: {
  294. id: '',
  295. },
  296. tableData: [],//外层table
  297. dataType: [],
  298. AssociatedPublicTap: false,
  299. //#region 弹框属性
  300. GLExcelFrom: {
  301. id: "",
  302. name: '',
  303. search: '',//搜素框舒服的值
  304. },
  305. GLExcelData: [],//
  306. GLExcelProps: {
  307. label: 'title',
  308. children: 'children',
  309. isLeaf: 'isExistForm',
  310. },
  311. exceldata: [],//清表模板树数据
  312. addTableData: [],//新增元素信息表
  313. exceltypeData: [],//清表类型
  314. addElement: false,
  315. GLExcelFromtag: false,
  316. addElementForm: {
  317. id: "",
  318. initTableName: "",
  319. deptName: '',
  320. tableType: '',
  321. tableOwner: '',
  322. wbsId: '',
  323. parentId: '',
  324. },
  325. //#endregion
  326. ownerTypeList: [],
  327. }
  328. },
  329. methods: {
  330. //#region
  331. handleNodeClick (data) {//树节点点击事件
  332. console.log(data);
  333. if (data.fileType == 3) {
  334. this.getExcelHtmlCol(data.id)//获取excel模板
  335. if (this.dataType.length == 0) {
  336. this.dictionarydataType() //数据类型字典
  337. }
  338. this.addElement = false
  339. this.addElementForm.deptName = data.name
  340. this.from.id = data.id
  341. }
  342. },
  343. async loadNode (node, resolve) {//懒加载获取节点
  344. if (node.level === 0) {
  345. return resolve(await this.tabLazytree(this.$route.params.id, 0))
  346. }
  347. if (node.level > 0) {
  348. return resolve(await this.tabLazytree(this.$route.params.id, node.data.id))
  349. }
  350. },
  351. automaticRecognition () {//自动识别按钮
  352. this.getColByTabId()
  353. },
  354. pushTableData () {//
  355. if (this.from.id) {
  356. this.tableData.push({
  357. eName: '',
  358. eType: '',
  359. eAllowDeviation: ''
  360. })
  361. }
  362. },
  363. deleteTableData (key) {//删除
  364. this.tableData.splice(key, 1)
  365. },
  366. async getColByTabId () {//获取字段信息
  367. const { data: res } = await getColByTabId({ tabId: this.from.id })
  368. console.log(res);
  369. if (res.code === 200) {
  370. this.tableData = res.data
  371. }
  372. },
  373. async getExcelHtmlCol (id) {//获取excel模板
  374. const { data: res } = await getExcelHtmlCol({ id })
  375. console.log(res);
  376. if (res.code == 200) {
  377. // let _that = this
  378. var MyComponent = await Vue.extend({
  379. data () {
  380. return {
  381. formData: {}
  382. }
  383. },
  384. template: res.data,
  385. })
  386. var component = new MyComponent().$mount()
  387. let na = document.getElementById('parent')
  388. na.innerHTML = `<div
  389. class='parent'
  390. id='parent'"
  391. ></div>`
  392. document.getElementById('parent').appendChild(component.$el);
  393. }
  394. },
  395. //#endregion
  396. //#region 关联公共WBS模板弹框
  397. establish () {//关联WBS并创建元素
  398. this.getWbsTypeList()
  399. this.AssociatedPublicTap = true
  400. },
  401. AssociatedPublicClose () {//关联公共WBS模板关闭事件
  402. this.addElementForm = {
  403. id: "",
  404. initTableName: "",
  405. deptName: '',
  406. tableType: '',
  407. tableOwner: '',
  408. wbsId: '',
  409. parentId: '',
  410. }
  411. this.GLExcelFrom = {
  412. name: '',
  413. search: ''
  414. }
  415. this.exceldata = []
  416. this.addElement = false
  417. this.AssociatedPublicTap = false
  418. },
  419. async loadNodeTan (node, resolve) {//懒加载
  420. console.log(node);
  421. if (node.level === 0) {
  422. return resolve(await this.getLazytree(0));
  423. } else {
  424. return resolve(await this.getLazytree(node.data.id));
  425. }
  426. },
  427. changetherr () {//下拉框change事件
  428. this.GLExcelFromtag = false
  429. if (this.GLExcelFrom.name != "") {
  430. this.GLExcelFrom.search = ''
  431. this.exceldata = []
  432. this.addTableData = []
  433. this.addElementForm.wbsId = ''
  434. this.$nextTick(() => {
  435. this.GLExcelFromtag = true
  436. })
  437. }
  438. },
  439. addElementMD () {//新增元素信息表按钮
  440. this.excelType()
  441. this.addElement = true
  442. },
  443. async getWbsTypeList () {//获取清表模板信息
  444. const { data: res } = await getWbsTypeList({ wbsType: 1 })
  445. console.log(res);
  446. if (res.code === 200 && res.msg === '操作成功') {
  447. this.GLExcelData = res.data
  448. }
  449. },
  450. async getLazytree (parentId) {//清表树信息
  451. const { data: res } = await getLazytree({
  452. parentId: parentId,
  453. wbsId: this.GLExcelFrom.name,
  454. wbsType: '1'
  455. })
  456. console.log(res);
  457. if (res.code === 200 && res.msg === '操作成功') {
  458. res.data.forEach(val => {
  459. val.isExistForm = !!val.isExistForm
  460. })
  461. return res.data
  462. } else {
  463. return []
  464. }
  465. },
  466. handleNodeClickExcel (data) {//点击节点事件
  467. console.log(data);
  468. if (data.hasChildren) {
  469. this.addElementForm.wbsId = data.id
  470. this.addElementForm.parentId = data.parentId
  471. this.selectByNodeTable(data.id)
  472. }
  473. },
  474. async selectByNodeTable (id) {//获取清表信息
  475. const { data: res } = await selectByNodeTable(id)
  476. console.log(res);
  477. if (res.code == 200) {
  478. if (res.data.length > 0) {
  479. res.data.forEach(val => {
  480. if (val.isLinkTable == 2) {
  481. val.checknd = true
  482. } else {
  483. val.checknd = false
  484. }
  485. })
  486. this.addTableData = res.data
  487. }else{
  488. this.addTableData = []
  489. }
  490. }
  491. },
  492. async excelType () {//清表类型
  493. const { data: res } = await excelType({ code: 'sys_excltab_type' })
  494. console.log(res);
  495. if (res.code === 200) {
  496. this.exceltypeData = res.data
  497. }
  498. },
  499. relationMD (index, type) {//关联取消关联
  500. console.log(this.addTableData[index]);
  501. if (this.addTableData.length > 0) {
  502. if (type == '关联') {
  503. this.addTableData.forEach((val, k) => {
  504. if (index == k) {
  505. val.checknd = !val.checknd
  506. } else {
  507. val.checknd = false
  508. }
  509. })
  510. this.addElementForm.id = this.addTableData[index].id
  511. this.addElementForm.initTableName = this.addTableData[index].initTableName
  512. } else {
  513. this.addTableData.forEach((val, k) => {
  514. val.checknd = false
  515. })
  516. this.addElementForm.id = ''
  517. this.addElementForm.initTableName = ''
  518. }
  519. }
  520. },
  521. saveElementMD () {//保存按钮
  522. if (this.addElementForm.wbsId) {
  523. if (this.addTableData.length > 0) {
  524. let tag = false
  525. this.addTableData.forEach(val => {
  526. if ((val.checknd == true && val.isLinkTable != 2) || (val.checknd == false && val.isLinkTable == 2)) {
  527. tag = true
  528. }
  529. })
  530. if (tag) {
  531. this.submitExcelRelationWbsTreeAndElement({
  532. id: this.addElementForm.id,
  533. initTableName: this.addElementForm.initTableName,
  534. elementList: this.tableData
  535. })
  536. } else {
  537. if (this.addElementForm.deptName && this.addElementForm.tableType && this.addElementForm.tableOwner) {
  538. this.submitExcelRelationWbsTreeAndElement({
  539. deptName: this.addElementForm.deptName,
  540. tableType: this.addElementForm.tableType,
  541. tableOwner: this.addElementForm.tableOwner,
  542. wbsId: this.addElementForm.wbsId,
  543. parentId: this.addElementForm.parentId,
  544. elementList: this.tableData
  545. })
  546. }
  547. }
  548. }
  549. } else {
  550. this.$message({
  551. type: 'error',
  552. message: '请先选择WBS树节点表单'
  553. })
  554. }
  555. },
  556. async submitExcelRelationWbsTreeAndElement (da) {//保存接口
  557. const { data: res } = await submitExcelRelationWbsTreeAndElement(da)
  558. console.log(res);
  559. if (res.code == 200) {
  560. this.$message({
  561. type: 'success',
  562. message: '设置成功'
  563. })
  564. this.AssociatedPublicTap = false
  565. }
  566. },
  567. //#endregion
  568. //#region 接口
  569. async tabLazytree (modeId, parentId) {
  570. const { data: res } = await tabLazytree({ modeId, parentId })
  571. console.log(res);
  572. if (res.code == 200) {
  573. if (res.data.length > 0) {
  574. res.data.forEach(val => {
  575. val.hasChildren = !val.hasChildren
  576. });
  577. }
  578. return res.data
  579. }
  580. },
  581. async dictionarydataType () {//数据类型字典
  582. const { data: res } = await dictionarydataType()
  583. console.log(res);
  584. if (res.code == 200) {
  585. this.dataType = res.data
  586. }
  587. },
  588. //#endregion
  589. getOwnerTypelist () {
  590. if (this.ownerTypeList.length > 1) {
  591. return;
  592. }
  593. getDictionary({
  594. code: 'owner_type'
  595. }).then((res) => {
  596. res.data.data.forEach(element => {
  597. element.dictKey = Number(element.dictKey)
  598. });
  599. this.ownerTypeList = res.data.data;
  600. })
  601. },
  602. },
  603. created () {
  604. this.getOwnerTypelist();
  605. }
  606. }
  607. </script>
  608. <style lang="scss" scoped>
  609. .boxswai {
  610. padding: 0px 14px 10px 14px !important;
  611. }
  612. .dingwei {
  613. position: fixed;
  614. bottom: 40px;
  615. right: 40px;
  616. }
  617. //树结构超长后产生滚动条
  618. .el-tree > .el-tree-node {
  619. min-width: 100%;
  620. display: inline-block;
  621. }
  622. </style>