dataMap.vue 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469
  1. <template>
  2. <div class="layout-container">
  3. <div class="panel" ref="panel1">
  4. <div
  5. class="parent hc-excel-table-form"
  6. id="parent"
  7. @click="parentClick($event)"
  8. ></div>
  9. </div>
  10. <div class="splitter"></div>
  11. <div class="panel" ref="panel2">
  12. <div style="margin-bottom: 20px; text-align: right">
  13. <el-button @click="goBack">返回上一级</el-button>
  14. <el-button type="primary" @click="saveInfo" :loading="saveLoaing"
  15. >保存</el-button
  16. >
  17. </div>
  18. <div class="right_box">
  19. <div>
  20. <span>选择表单</span>
  21. <el-select
  22. v-model="formVal"
  23. placeholder="请选择"
  24. style="width: 65%; margin-left: 10px"
  25. @change="changeform"
  26. >
  27. <el-option
  28. v-for="item in formoptions"
  29. :key="item.initTabId"
  30. :label="item.tabName"
  31. :value="item.initTabId"
  32. >
  33. </el-option>
  34. </el-select>
  35. </div>
  36. <div>
  37. <span>选择元素</span>
  38. <el-select
  39. v-model="eleVal"
  40. placeholder="请选择"
  41. style="width: 65%; margin-left: 10px; margin-top: 15px"
  42. @change="changeEle"
  43. filterable
  44. >
  45. <el-option
  46. v-for="item in eleOptions"
  47. :key="item.ekey"
  48. :label="item.eName"
  49. :value="item.ekey"
  50. >
  51. </el-option>
  52. </el-select>
  53. </div>
  54. <div class="martop20 replace_box">
  55. <div style="width: 100%; height: 100%; overflow-y: auto">
  56. <el-row class="mb-4">
  57. <div class="form_text">
  58. <div>表单名称:{{ infoDetail.tabName }}</div>
  59. <div>元素字段:{{ infoDetail.elementName }}</div>
  60. </div>
  61. </el-row>
  62. </div>
  63. </div>
  64. </div>
  65. </div>
  66. </div>
  67. </template>
  68. <script>
  69. import {
  70. getLinkHtml,
  71. getLinkTablist,
  72. getLinkElelist,
  73. getLinkDetail,
  74. saveLinkDetail,
  75. getLinkData,
  76. } from "@/api/tentative/testcollect";
  77. import Vue from "vue";
  78. import Split from "split.js";
  79. export default {
  80. data() {
  81. return {
  82. formoptions: [],
  83. eleOptions: [],
  84. heights: "",
  85. formVal: "",
  86. formpid: "",
  87. formname: "",
  88. classId: "",
  89. eleVal: "",
  90. eleId: "",
  91. clickKeyname: "",
  92. infoDetail: {
  93. elementName: "",
  94. tabName: "",
  95. id: "",
  96. },
  97. saveLoaing: false,
  98. clickArr: [], //需要绑定的数组
  99. curItem: {
  100. elementId: "",
  101. elementKey: "",
  102. htmlKeyName: "",
  103. trialTabId: "",
  104. trialTabName: "",
  105. },
  106. linkedData: [], //已经绑定的数组
  107. };
  108. },
  109. watch: {
  110. curItem: {
  111. handler(newVal, oldVal) {
  112. if (
  113. this.curItem.elementId &&
  114. this.curItem.elementKey &&
  115. this.curItem.htmlKeyName &&
  116. this.curItem.trialTabId &&
  117. this.curItem.trialTabName
  118. ) {
  119. const newItem = Object.assign({}, newVal);
  120. const isContained = this.containsObject(
  121. this.clickArr,
  122. "htmlKeyName",
  123. newItem.htmlKeyName
  124. );
  125. if (isContained) {
  126. this.clickArr.forEach((ele) => {
  127. if (ele.htmlKeyName === newItem.htmlKeyName) {
  128. ele.elementId = newItem.elementId;
  129. ele.elementKey = newItem.elementKey;
  130. ele.htmlKeyName = newItem.htmlKeyName;
  131. ele.trialTabId = newItem.trialTabId;
  132. ele.trialTabName = newItem.trialTabName;
  133. }
  134. });
  135. } else {
  136. this.clickArr.push(newItem);
  137. }
  138. }
  139. // 在这里执行你想要的操作
  140. },
  141. deep: true, // 指定为深度监听,
  142. },
  143. },
  144. methods: {
  145. // 判断数组中是否包含目标对象的函数
  146. containsObject(array, keyName, targetValue) {
  147. for (let i = 0; i < array.length; i++) {
  148. if (array[i][keyName] === targetValue) {
  149. return true;
  150. }
  151. }
  152. return false;
  153. },
  154. async getExcelHtmlCol(classId, form) {
  155. //获取excel模板
  156. const { data: res } = await getLinkHtml({ classId });
  157. console.log(res);
  158. if (res.code == 200) {
  159. // let _that = this
  160. var MyComponent = await Vue.extend({
  161. data() {
  162. return {
  163. formData: form,
  164. };
  165. },
  166. //监听数据,伪双向绑定(v-model)
  167. watch: {
  168. formData: {
  169. handler(obj) {
  170. this.formData = obj;
  171. },
  172. deep: true,
  173. immediate: true,
  174. },
  175. },
  176. template: res.data,
  177. methods: {
  178. //改变表单数据
  179. // setFormData(obj) {
  180. // this.formData = obj
  181. // _that.setFormData2(obj)
  182. // console.log(this.formData,'this.formData1111111');
  183. // },
  184. contextmenuClick() {},
  185. getInformation() {},
  186. formUploadSuccess() {},
  187. formUploadExceed() {},
  188. formUploadLoading() {},
  189. delTableFormFile() {},
  190. formUploadError() {},
  191. uploadprogress() {},
  192. formRemoteMethod() {},
  193. getRegularExpression() {},
  194. checkboxGroupChange() {},
  195. formRemoteChange() {},
  196. dateKeydown() {},
  197. keyupShiftUp() {},
  198. keyupShiftDown() {},
  199. keyupShiftLeft() {},
  200. keyupShiftRight() {},
  201. inputLeftClick() {},
  202. },
  203. });
  204. var component = new MyComponent().$mount();
  205. let na = document.getElementById("parent");
  206. na.innerHTML = `<div
  207. class='parent'
  208. id='parent'"
  209. ></div>`;
  210. document.getElementById("parent").appendChild(component.$el);
  211. }
  212. },
  213. //excel父节点点击检测
  214. async parentClick(e) {
  215. let target = e.target;
  216. let bgs = document.querySelectorAll("#parent .oldlace-bg");
  217. //console.log(bgs)
  218. let tdEle = this.getParentTD(target);
  219. let target1;
  220. if (tdEle) {
  221. let mydiv = tdEle.getElementsByTagName("div");
  222. target1 = mydiv[0];
  223. } else {
  224. tdEle = target;
  225. let mydiv = tdEle.getElementsByTagName("div");
  226. target = mydiv[0];
  227. }
  228. for (let i = 0; i < bgs.length; i++) {
  229. bgs[i].classList.remove("oldlace-bg");
  230. }
  231. if (
  232. target.getAttribute("trindex") !== null &&
  233. target.getAttribute("tdindex")
  234. ) {
  235. target = target;
  236. } else {
  237. target = target1;
  238. }
  239. //console.log(target.getAttribute('trindex'))
  240. if (
  241. target.getAttribute("trindex") !== null &&
  242. target.getAttribute("tdindex")
  243. ) {
  244. let tdEle = this.getParentTD(target);
  245. if (tdEle) {
  246. target.classList.add("oldlace-bg");
  247. let trtd =
  248. target.getAttribute("trindex") +
  249. "_" +
  250. target.getAttribute("tdindex");
  251. this.$nextTick(() => {
  252. let row = document.querySelectorAll(".warning-row");
  253. if (row.length) {
  254. this.$refs.tablescroll.$el.scrollTop = row[0].offsetTop;
  255. }
  256. });
  257. }
  258. this.clickKeyname =
  259. target.getAttribute("keyname") || target1.getAttribute("keyname");
  260. await this.getInfoDEtail();
  261. this.$set(this.curItem, "htmlKeyName", this.clickKeyname);
  262. }
  263. },
  264. getParentTD(ele) {
  265. let targetParent = ele.parentNode;
  266. while (targetParent.nodeName !== "TD") {
  267. if (targetParent.id == "parent") {
  268. return null;
  269. }
  270. targetParent = targetParent.parentNode;
  271. }
  272. return targetParent;
  273. },
  274. setFormData2(obj) {
  275. console.log(obj, "obj");
  276. },
  277. goBack() {
  278. this.$router.go(-1);
  279. },
  280. //获取表单类别
  281. async getFormoptions() {
  282. const { data: res } = await getLinkTablist({
  283. classId: this.classId,
  284. });
  285. if (res.code === 200) {
  286. this.formoptions = res.data;
  287. } else {
  288. this.formoptions = [];
  289. }
  290. },
  291. //获取当前清表表所有已匹配的映射字段列表
  292. async getLinkedData() {
  293. const { data: res } = await getLinkData({
  294. id: this.classId,
  295. });
  296. if (res.code === 200) {
  297. this.linkedData = res.data;
  298. const mappedObject = Object.fromEntries(
  299. res.data.map((item) => [item.htmlKeyName, item.elementValue])
  300. );
  301. this.linkedData = mappedObject;
  302. } else {
  303. this.linkedData = [];
  304. }
  305. },
  306. //选择表单获
  307. changeform(val) {
  308. this.getEleList(val);
  309. this.formoptions.forEach((ele) => {
  310. if (ele.initTabId === val) {
  311. this.formpid = ele.pkeyId;
  312. this.formname = ele.initTableName;
  313. this.infoDetail.tabName = ele.tabName;
  314. this.$set(this.curItem, "trialTabId", ele.pkeyId);
  315. this.$set(this.curItem, "trialTabName", ele.initTableName);
  316. }
  317. });
  318. },
  319. changeEle(val) {
  320. this.eleOptions.forEach((ele) => {
  321. if (ele.ekey === val) {
  322. this.eleId = ele.id;
  323. this.infoDetail.elementName = ele.eName;
  324. this.$set(this.curItem, "elementKey", val);
  325. this.$set(this.curItem, "elementId", ele.id);
  326. }
  327. });
  328. },
  329. //获取元素列表
  330. async getEleList(val) {
  331. const { data: res } = await getLinkElelist({
  332. id: val,
  333. });
  334. console.log(res);
  335. if (res.code === 200) {
  336. this.eleOptions = res.data;
  337. } else {
  338. this.eleOptions = [];
  339. }
  340. },
  341. //获取数据映射源
  342. async getInfoDEtail() {
  343. const { data: res } = await getLinkDetail({
  344. classId: this.classId,
  345. keyName: this.clickKeyname,
  346. });
  347. if (res.code === 200) {
  348. this.infoDetail = res.data;
  349. if (this.infoDetail && this.infoDetail.id) {
  350. this.formoptions.forEach((ele) => {
  351. if (ele.tabName === this.infoDetail.tabName) {
  352. this.formVal = ele.initTabId;
  353. this.$set(this.curItem, "trialTabName", ele.initTableName);
  354. this.$set(this.curItem, "trialTabId", ele.pkeyId);
  355. }
  356. });
  357. await this.getEleList(this.formVal);
  358. this.eleOptions.forEach((ele) => {
  359. if (ele.eName === this.infoDetail.elementName) {
  360. this.eleVal = ele.ekey;
  361. // this.curItem.elementId=ele.id
  362. // this.curItem.elementKey=ele.ekey
  363. this.$set(this.curItem, "elementId", ele.id);
  364. this.$set(this.curItem, "elementKey", ele.ekey);
  365. }
  366. });
  367. } else {
  368. this.infoDetail = {};
  369. this.formVal = "";
  370. this.eleVal = "";
  371. this.curItem = {};
  372. // this.curItem.htmlKeyName=this.clickKeyname
  373. this.$set(this.curItem, "htmlKeyName", this.clickKeyname);
  374. }
  375. } else {
  376. this.infoDetail = {};
  377. }
  378. },
  379. //映射数据保存
  380. async saveInfo() {
  381. console.log(this.clickArr, "this.clickArr");
  382. if (this.clickArr.length === 0) {
  383. this.$message.warning("请进行数据映射配置");
  384. return;
  385. }
  386. this.saveLoaing = true;
  387. const { data: res } = await saveLinkDetail({
  388. classId: this.classId,
  389. reflectionBeanList: this.clickArr,
  390. });
  391. console.log(res);
  392. this.saveLoaing = false;
  393. if (res.code === 200) {
  394. this.$message({
  395. type: "success",
  396. message: res.msg,
  397. });
  398. await this.getLinkedData();
  399. await this.getExcelHtmlCol(this.classId, this.linkedData); //获取excel模板
  400. this.clickArr = [];
  401. }
  402. },
  403. },
  404. async created() {
  405. this.classId = this.$route.query.classId;
  406. await this.getLinkedData();
  407. await this.getExcelHtmlCol(this.classId, this.linkedData); //获取excel模板
  408. this.getFormoptions();
  409. },
  410. mounted() {
  411. Split([this.$refs.panel1, this.$refs.panel2], {
  412. direction: "horizontal", // 设置分割方向,'horizontal' 或 'vertical'
  413. gutterSize: 10, // 设置分割条的大小
  414. sizes: [75, 25], // 初始化各个面板的宽度比例
  415. minSize: 100, // 设置面板的最小尺寸
  416. onDragEnd: () => {
  417. // 拖动结束后的回调,可以执行一些额外的操作
  418. console.log("Panel sizes adjusted");
  419. },
  420. });
  421. },
  422. };
  423. </script>
  424. <style scoped>
  425. .layout-container {
  426. display: flex;
  427. height: 100vh;
  428. width: 100%;
  429. }
  430. .panel {
  431. background: white;
  432. border: 1px solid #ccc;
  433. padding: 10px;
  434. box-sizing: border-box;
  435. overflow: auto;
  436. }
  437. .panel:nth-child(odd) {
  438. background: white;
  439. }
  440. .gutter {
  441. background-color: #eee;
  442. background-repeat: no-repeat;
  443. background-position: 50%;
  444. }
  445. #parent ::v-deep .oldlace-bg {
  446. background-color: oldlace;
  447. }
  448. </style>
  449. <style>
  450. .gutter-horizontal {
  451. background-image: url('/img/split.png') !important;
  452. cursor: col-resize;
  453. background-repeat: no-repeat;
  454. background-position: center;
  455. }
  456. </style>