settingIndexDrawer.vue 58 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672
  1. <script setup lang="ts">
  2. import { ref, reactive, watch } from "vue";
  3. import { ElMessageBox, ElMessage } from "element-plus";
  4. import { calculator } from "./evaluate";
  5. import {
  6. getIndexInfo,
  7. postUpdate,
  8. calculateScoreByConditionMoCondition
  9. } from "@/api/templateInfo";
  10. import { conditionVerify } from "@/api/formula";
  11. import jishuanqi from "./jishuanqi.vue";
  12. import {
  13. postListTreeWithUser,
  14. postListTree,
  15. postListTreeWithUserApi,
  16. treeDept
  17. } from "@/api/department";
  18. import type { DrawerProps, FormItemProps, FormProps } from "element-plus";
  19. import { formulaParamsChange, echoParamsChange } from "@/utils/business";
  20. // const itemLabelPosition = ref<FormItemProps["labelPosition"]>("");
  21. const drawer = ref(false);
  22. const disabledValue = ref(true);
  23. const GONG_SHI = [
  24. "完成值",
  25. "目标值",
  26. "门槛值",
  27. "挑战值",
  28. "增幅",
  29. "降幅",
  30. "上期完成值",
  31. "上上期完成值"
  32. ];
  33. // 判断 score 字符串是否包含 GONG_SHI 中的关键字
  34. function containsKeywordInScore(score, keywordss) {
  35. // 确保 score 是字符串,keywords 是数组
  36. if (score && typeof score == "string") {
  37. const cleanedScore = score.replace(/[\s\-]/g, ""); // 去除空格和破折号
  38. const cleanedKeywords = keywordss.map(keyword =>
  39. keyword.replace(/[\s\-]/g, "")
  40. );
  41. return cleanedKeywords.some(keyword => cleanedScore.includes(keyword));
  42. // 遍历 keywords 数组,检查 score 是否包含其中的任何一个关键字
  43. } else {
  44. return false;
  45. }
  46. }
  47. const direction = ref<DrawerProps["direction"]>("rtl");
  48. const formLabelAlign = reactive({
  49. name: "",
  50. region: "",
  51. grade: "",
  52. compute: "1",
  53. type: ""
  54. });
  55. const params = reactive({
  56. id: "",
  57. tpId: "",
  58. dimId: "",
  59. indId: "",
  60. valueInput: "",
  61. scoreStandard: 0,
  62. designatedPersonnel: "",
  63. remark: "",
  64. scoreRule: "",
  65. targetValue: "",
  66. finalValue: "",
  67. formulaType: 0,
  68. challengeValue: "",
  69. startValue: "",
  70. datasoure: "",
  71. weight: "",
  72. valueScore: null,
  73. scoreValue: "",
  74. formula: {
  75. noConditionFormula: ""
  76. },
  77. personList: ""
  78. });
  79. // 详情信息
  80. const getIndexInfoApi = async id => {
  81. const { data, code, msg } = await getIndexInfo(id);
  82. // console.log("1111", data);
  83. if (code === 200) {
  84. Object.assign(params, data);
  85. if (data.designatedPersonnel) {
  86. params.personList = data.designatedPersonnel.split(",");
  87. } else {
  88. params.personList = "";
  89. }
  90. if (!data.formulaType) {
  91. params.formulaType = 0;
  92. }
  93. if (data.formulaType === 0) {
  94. params.formula = {
  95. noConditionFormula: params.formula
  96. };
  97. } else if (data.formulaType === 1) {
  98. Object.assign(addmanyChange, echoParamsChange(data.formulaParams));
  99. }
  100. // if (isValidJSON(data.formula)) {
  101. // if (params.formulaType == 0) {
  102. // params.formula = isValidJSON(data.formula);
  103. // } else if (params.formulaType == 1) {
  104. // let aa = JSON.parse(data.formula);
  105. // let bb = JSON.parse(aa.noConditionFormula);
  106. // Object.assign(addmanyChange, bb);
  107. // }
  108. // }
  109. if (!data.formula) {
  110. params.formula = {
  111. noConditionFormula: ""
  112. };
  113. } else {
  114. }
  115. } else {
  116. ElMessage.error(msg);
  117. }
  118. };
  119. const $emit = defineEmits(["refresh"]);
  120. // 更新指标
  121. const postUpdateApi = async () => {
  122. if (params.formulaType == 0) {
  123. params.formula = params.formula.noConditionFormula;
  124. } else {
  125. params.formula = {
  126. noConditionFormula: ""
  127. };
  128. // 判断是公式还是数字
  129. if (containsKeywordInScore(addmanyChange.outerConditionValue, GONG_SHI)) {
  130. addmanyChange.outerConditionValueExpress =
  131. addmanyChange.outerConditionValue;
  132. }
  133. addmanyChange.innerConditionExpression.map(inn => {
  134. if (containsKeywordInScore(inn?.startValue, GONG_SHI)) {
  135. inn.startExpress = inn.startValue;
  136. }
  137. if (containsKeywordInScore(inn?.endValue, GONG_SHI)) {
  138. inn.endExpress = inn.endValue;
  139. }
  140. if (containsKeywordInScore(inn?.innerScore, GONG_SHI)) {
  141. inn.innerScoreExpress = inn.innerScore;
  142. }
  143. if (
  144. containsKeywordInScore(
  145. inn?.scoreRuleMoreInnerVO[0]?.innerConditionValue,
  146. GONG_SHI
  147. )
  148. ) {
  149. inn.scoreRuleMoreInnerVO[0].innerConditionValueExpress =
  150. inn.scoreRuleMoreInnerVO[0].innerConditionValue;
  151. }
  152. inn?.scoreRuleMoreInnerVO[0]?.scoreRules.map(isc => {
  153. if (containsKeywordInScore(isc?.score, GONG_SHI)) {
  154. isc.scoreExpress = isc.score;
  155. }
  156. if (containsKeywordInScore(isc?.startValue, GONG_SHI)) {
  157. isc.startExpress = isc.startValue;
  158. }
  159. if (containsKeywordInScore(isc?.endValue, GONG_SHI)) {
  160. isc.endExpress = isc.endValue;
  161. }
  162. });
  163. });
  164. params.formula.noConditionFormula = JSON.stringify(addmanyChange);
  165. delete params.formula;
  166. params.formulaParams = formulaParamsChange(addmanyChange);
  167. }
  168. const { msg, code } = await postUpdate(params);
  169. if (code === 200) {
  170. ElMessage({
  171. message: "编辑成功",
  172. type: "success"
  173. });
  174. $emit("refresh");
  175. disabledValue.value = true;
  176. editShow.value = true;
  177. drawer.value = !drawer.value;
  178. }
  179. };
  180. // 公式验证
  181. const dialogFormVisibleFormula = ref(false);
  182. const formulaForm = ref([]);
  183. const grade = ref();
  184. const conditionVerifyApi = async () => {
  185. grade.value = null;
  186. formulaForm.value = [];
  187. dialogFormVisibleFormula.value = true;
  188. try {
  189. formulaForm.value = [];
  190. grade.value = "";
  191. console.log("params", params);
  192. const keywords = [
  193. "完成值",
  194. "目标值",
  195. "门槛值",
  196. "挑战值",
  197. "增幅",
  198. "降幅",
  199. "上期完成值",
  200. "上上期完成值"
  201. ];
  202. let str = params.formula.noConditionFormula;
  203. // 创建一个正则表达式,匹配这些关键词
  204. const regex = new RegExp(keywords.join("|"), "g");
  205. // 提取字符串中的所有关键词
  206. let matches = str.match(regex);
  207. console.log("匹配到的关键词:", matches);
  208. matches.forEach(matchItem => {
  209. formulaForm.value.push({
  210. name: matchItem,
  211. value: ""
  212. });
  213. });
  214. let result = str.replace(regex, match => {
  215. return `${match}`;
  216. });
  217. } catch (err) {
  218. //
  219. }
  220. };
  221. // 计算
  222. // 多条件公式计算
  223. function reverseReplace(oldValue, dataObject) {
  224. // 确保 formulaForm 是一个数组
  225. if (!Array.isArray(oldValue)) {
  226. throw new Error("formulaForm 应该是一个数组");
  227. }
  228. oldValue.forEach(item => {
  229. // 遍历外部条件和内部条件的表达式
  230. for (const key in dataObject) {
  231. const value = dataObject[key];
  232. if (typeof value === "string") {
  233. // 如果字符串中包含当前name,则替换该值
  234. if (value.includes(item.name)) {
  235. dataObject[key] = value.replace(item.name, item.value);
  236. }
  237. } else if (Array.isArray(value)) {
  238. // 如果是数组,递归替换数组中的每个对象
  239. value.forEach(innerObj => {
  240. for (const innerKey in innerObj) {
  241. const innerValue = innerObj[innerKey];
  242. if (
  243. typeof innerValue === "string" &&
  244. innerValue.includes(item.name)
  245. ) {
  246. innerObj[innerKey] = innerValue.replace(item.name, item.value);
  247. }
  248. }
  249. });
  250. }
  251. }
  252. });
  253. return dataObject;
  254. }
  255. function calculateScore(inputString) {
  256. // 将 formulaForm.value 转换为一个键值对映射,方便替换
  257. const valueMap = formulaForm.value.reduce((map, item) => {
  258. map[item.name] = item.value !== null ? item.value : 0; // 用 0 替代 null
  259. return map;
  260. }, {});
  261. // 替换字符串中的关键字为对应的 value 值
  262. let formula = inputString;
  263. for (const [key, value] of Object.entries(valueMap)) {
  264. if (formula.includes(key)) {
  265. // 使用正则替换所有匹配的关键字
  266. const regex = new RegExp(key, "g");
  267. formula = formula.replace(regex, value);
  268. }
  269. }
  270. try {
  271. // 使用 eval 计算公式
  272. const result = eval(formula);
  273. return result;
  274. } catch (error) {
  275. console.error("公式计算出错:", error);
  276. return null;
  277. }
  278. }
  279. const countComputed = async () => {
  280. try {
  281. if (params.formulaType == 0) {
  282. const params0: {
  283. formulaType: number;
  284. formula?: string;
  285. } = {
  286. formulaType: params.formulaType
  287. };
  288. if (params.formula && params.formula.noConditionFormula) {
  289. params0.formula = `(${params.formula.noConditionFormula})`;
  290. }
  291. const { code, msg } = await conditionVerify(params0);
  292. if (code == 200) {
  293. const keywords = [
  294. "完成值",
  295. "目标值",
  296. "门槛值",
  297. "挑战值",
  298. "增幅",
  299. "降幅",
  300. "上期完成值",
  301. "上上期完成值"
  302. ];
  303. let str = params.formula.noConditionFormula;
  304. // 创建一个正则表达式,匹配这些关键词
  305. const regex = new RegExp(keywords.join("|"), "g");
  306. let result = str.replace(regex, match => {
  307. // 在 formulaForm.value 中查找匹配的项
  308. let matchedItem = formulaForm.value.find(item => item.name === match);
  309. // 如果找到匹配项,返回其 value,否则返回原始匹配值
  310. if (matchedItem) {
  311. return matchedItem.value; // 替换为对应的值
  312. }
  313. return match; // 如果没有匹配项,返回原始匹配值
  314. });
  315. // calculator.calculate(result);
  316. // grade.value = calculator.get();
  317. grade.value = eval(result).toFixed(2);
  318. } else {
  319. ElMessageBox.confirm(
  320. "如果不修改将无法计算得分",
  321. "公式计算错误,修改后确认",
  322. {
  323. type: "warning"
  324. }
  325. ).then(() => {
  326. dialogFormVisibleFormula.value = false;
  327. });
  328. }
  329. } else if (params.formulaType == 1) {
  330. // 判断是公式还是数字
  331. if (containsKeywordInScore(addmanyChange.outerConditionValue, GONG_SHI)) {
  332. addmanyChange.outerConditionValueExpress =
  333. addmanyChange.outerConditionValue;
  334. }
  335. // let oldValue = JSON.parse(JSON.stringify(addmanyChange));
  336. // const formulaPar = JSON.stringify(oldValue);
  337. const params1: {
  338. formulaType: number;
  339. formulaParams?: any[];
  340. } = {
  341. formulaType: params.formulaType
  342. };
  343. if (addmanyChange) {
  344. params1.formulaParams = formulaParamsChange(addmanyChange);
  345. }
  346. const res = await conditionVerify(params1);
  347. if (res.code == 200) {
  348. // if (oldValue.outerConditionValue) {
  349. // oldValue.outerConditionValue = calculateScore(
  350. // oldValue.outerConditionValue
  351. // );
  352. // }
  353. // 暂时注释上面代码,不知道会不会影响到其他业务逻辑,待验证
  354. const oldValue = JSON.parse(JSON.stringify(addmanyChange));
  355. if (formulaForm.value && Array.isArray(formulaForm.value) && oldValue) {
  356. const keywordss = [
  357. "完成值",
  358. "目标值",
  359. "门槛值",
  360. "挑战值",
  361. "增幅",
  362. "降幅",
  363. "上期完成值",
  364. "上上期完成值"
  365. ];
  366. if (
  367. keywordss.find(item => oldValue.outerConditionValueExpress == item)
  368. ) {
  369. for (const item of formulaForm.value) {
  370. if (oldValue.outerConditionValueExpress === item.name) {
  371. oldValue.outerConditionValue = item.value;
  372. break;
  373. }
  374. }
  375. } else {
  376. const keywords = [
  377. "完成值",
  378. "目标值",
  379. "门槛值",
  380. "挑战值",
  381. "增幅",
  382. "降幅",
  383. "上期完成值",
  384. "上上期完成值"
  385. ];
  386. let str = oldValue.outerConditionValueExpress;
  387. // 创建一个正则表达式,匹配这些关键词
  388. const regex = new RegExp(keywords.join("|"), "g");
  389. let result = str.replace(regex, match => {
  390. // 在 formulaForm.value 中查找匹配的项
  391. let matchedItem = formulaForm.value.find(
  392. item => item.name === match
  393. );
  394. // 如果找到匹配项,返回其 value,否则返回原始匹配值
  395. if (matchedItem) {
  396. return matchedItem.value; // 替换为对应的值
  397. }
  398. return match; // 如果没有匹配项,返回原始匹配值
  399. });
  400. // calculator.calculate(result);
  401. // grade.value = calculator.get();
  402. oldValue.outerConditionValue = eval(result).toFixed(2);
  403. }
  404. }
  405. if (oldValue.innerConditionExpression.length > 0) {
  406. oldValue.innerConditionExpression.map(itEx => {
  407. if (itEx.startValue) {
  408. itEx.startValue = calculateScore(itEx.startValue);
  409. }
  410. if (itEx.endValue) {
  411. itEx.endValue = calculateScore(itEx.endValue);
  412. }
  413. if (itEx.innerScore) {
  414. itEx.innerScore = calculateScore(itEx.innerScore);
  415. }
  416. if (itEx?.scoreRuleMoreInnerVO[0]?.innerConditionValue) {
  417. itEx.scoreRuleMoreInnerVO[0].innerConditionValue = calculateScore(
  418. itEx.scoreRuleMoreInnerVO[0].innerConditionValue
  419. );
  420. }
  421. if (itEx?.scoreRuleMoreInnerVO[0]?.scoreRules.length > 0) {
  422. itEx.scoreRuleMoreInnerVO[0].scoreRules.map(itRule => {
  423. if (itRule.score) {
  424. itRule.score = calculateScore(itRule.score);
  425. }
  426. if (itRule.startValue) {
  427. itRule.startValue = calculateScore(itRule.startValue);
  428. }
  429. if (itRule.endValue) {
  430. itRule.endValue = calculateScore(itRule.endValue);
  431. }
  432. });
  433. }
  434. });
  435. }
  436. console.log(formulaForm.value, "-----");
  437. // let newValue = reverseReplace(formListNum, oldValue);
  438. // console.log(oldValue, "oldValue--最终传值");
  439. const { code, msg, data } = await calculateScoreByConditionMoCondition({
  440. ...params1,
  441. calculateScore: formulaForm.value.reduce((map, item) => {
  442. map[item.name] = item.value !== null ? item.value : 0; // 用 0 替代 null
  443. return map;
  444. }, {})
  445. });
  446. if (code == 200) {
  447. grade.value = data;
  448. }
  449. } else {
  450. ElMessageBox.confirm(
  451. "如果不修改将无法计算得分",
  452. "公式计算错误,修改后确认",
  453. {
  454. type: "warning"
  455. }
  456. ).then(() => {
  457. dialogFormVisibleFormula.value = false;
  458. });
  459. }
  460. }
  461. } catch (err) {
  462. console.log(err);
  463. }
  464. };
  465. // 判断是否为json
  466. function isValidJSON(str) {
  467. try {
  468. if (!str.includes("\\\\")) {
  469. return JSON.parse(str);
  470. } else {
  471. return JSON.parse(JSON.parse(str));
  472. }
  473. // return true; // 如果解析成功,返回true
  474. } catch (e) {
  475. return false; // 如果解析失败,返回false
  476. }
  477. }
  478. const handleClose = (done: () => void) => {
  479. drawer.value = false;
  480. disabledValue.value = true;
  481. editShow.value = true;
  482. // ElMessageBox.confirm("配置项未保存,确认关闭", {
  483. // type: "warning"
  484. // }).then(() => {
  485. // });
  486. };
  487. function cancelClick() {
  488. drawer.value = false;
  489. Object.assign(params, {
  490. id: "",
  491. tpId: "",
  492. dimId: "",
  493. indId: "",
  494. valueInput: "",
  495. scoreStandard: 0,
  496. remark: "",
  497. scoreRule: "",
  498. targetValue: "",
  499. finalValue: "",
  500. formulaType: 0,
  501. challengeValue: "",
  502. startValue: "",
  503. datasoure: "",
  504. weight: "",
  505. scoreValue: "",
  506. formula: {
  507. noConditionFormula: ""
  508. },
  509. personList: ""
  510. });
  511. disabledValue.value = true;
  512. editShow.value = true;
  513. }
  514. function confirmClick() {
  515. postUpdateApi();
  516. }
  517. const open = row => {
  518. drawer.value = true;
  519. params.designatedPersonnel = "";
  520. Object.assign(params, {
  521. id: "",
  522. tpId: "",
  523. dimId: "",
  524. indId: "",
  525. valueInput: "",
  526. scoreStandard: 0,
  527. designatedPersonnel: "",
  528. remark: "",
  529. scoreRule: "",
  530. targetValue: "",
  531. finalValue: "",
  532. formulaType: 0,
  533. challengeValue: "",
  534. startValue: "",
  535. datasoure: "",
  536. weight: "",
  537. valueScore: null,
  538. scoreValue: "",
  539. formula: {
  540. noConditionFormula: ""
  541. },
  542. personList: ""
  543. });
  544. Object.assign(addmanyChange, {
  545. outerConditionValue: "",
  546. outerConditionValueExpress: "",
  547. innerConditionExpression: [
  548. {
  549. startValue: null,
  550. endValue: null,
  551. select: null,
  552. comparisonStart: null,
  553. comparisonEnd: null,
  554. innerScore: null,
  555. innerScoreExpress: null,
  556. scoreRuleMoreInnerVO: []
  557. }
  558. ]
  559. });
  560. console.log("打印是否触发数据");
  561. getIndexInfoApi(row.id);
  562. calculatorShow.value = true;
  563. };
  564. const editShow = ref(true);
  565. defineExpose({
  566. open
  567. });
  568. const timer = ref("");
  569. // 公式计算
  570. const compute = [
  571. {
  572. value: 0,
  573. label: "无条件公式"
  574. },
  575. {
  576. value: 1,
  577. label: "多条件公式"
  578. }
  579. ];
  580. const bgColor = ref(null);
  581. const rolesList = reactive({
  582. data: [
  583. { name: "完成值 / 目标值", id: 1 },
  584. { name: "完成值 - 目标值", id: 2 },
  585. { name: "目标值 - 完成值", id: 3 },
  586. { name: "门槛值", id: 4 },
  587. { name: "目标值", id: 5 },
  588. { name: "挑战值", id: 6 },
  589. { name: "完成值", id: 7 },
  590. { name: "增幅", id: 8 },
  591. { name: "降幅", id: 9 },
  592. { name: "上期完成值", id: 10 },
  593. { name: "上上期完成值", id: 11 }
  594. ],
  595. value: "",
  596. num: null
  597. });
  598. // 监听formulaType变化
  599. const watchFormulaType = value => {
  600. if (value == 0 && typeof params.formula == "string") {
  601. let aa = JSON.parse(params.formula);
  602. params.formula = aa;
  603. params.formula.noConditionFormula = "";
  604. }
  605. };
  606. const lookRoles = item => {
  607. if (isValidJSON(params.formula)) {
  608. params.formula = JSON.parse(params.formula);
  609. }
  610. bgColor.value = item.id;
  611. params.formula.noConditionFormula =
  612. params.formula.noConditionFormula + item.name;
  613. };
  614. // 字符拼接
  615. const countNumber = (item: string) => {
  616. params.formula.noConditionFormula = params.formula.noConditionFormula + item;
  617. };
  618. // 清除
  619. const remove = () => {
  620. if (params.formula.noConditionFormula.length > 0) {
  621. params.formula.noConditionFormula = params.formula.noConditionFormula.slice(
  622. 0,
  623. -1
  624. );
  625. }
  626. };
  627. // 清空
  628. const removeVoid = () => {
  629. params.formula.noConditionFormula = "";
  630. };
  631. // 计算确认
  632. //
  633. const calculatorShow = ref(true);
  634. const count = item => {
  635. ElMessageBox.confirm("配置项确认保存?确认关闭", {
  636. type: "warning"
  637. }).then(() => {
  638. calculatorShow.value = false;
  639. });
  640. // try {
  641. // calculator.calculate(rolesList.value);
  642. // rolesList.num = calculator.get();
  643. // } catch (error) {
  644. // ElMessage({
  645. // message: "计算错误",
  646. // type: "warning"
  647. // });
  648. // console.log(error);
  649. // }
  650. };
  651. // 多条件公式
  652. const addmanyChange = reactive({
  653. outerConditionValue: "",
  654. outerConditionValueExpress: "",
  655. innerConditionExpression: [
  656. {
  657. startValue: null,
  658. endValue: null,
  659. select: null,
  660. comparisonStart: null,
  661. comparisonEnd: null,
  662. innerScore: null,
  663. innerScoreExpress: null,
  664. scoreRuleMoreInnerVO: [
  665. // {
  666. // innerConditionValue: null,
  667. // scoreRules: [
  668. // {
  669. // score: null,
  670. // startValue: null,
  671. // select: "",
  672. // endValue: null,
  673. // comparisonStart: null,
  674. // comparisonEnd: null
  675. // }
  676. // ]
  677. // }
  678. ]
  679. }
  680. ]
  681. });
  682. // 添加子条件
  683. const addItemFormulaList = (item, index) => {
  684. addmanyChange.innerConditionExpression[index].scoreRuleMoreInnerVO = [
  685. {
  686. innerConditionValue: null,
  687. innerConditionValueExpress: null,
  688. scoreRules: [
  689. {
  690. score: null,
  691. scoreExpress: null,
  692. startValue: null,
  693. startExpress: null,
  694. endValue: null,
  695. endExpress: null,
  696. select: null,
  697. comparisonStart: null,
  698. comparisonEnd: null
  699. }
  700. ]
  701. }
  702. ];
  703. addmanyChange.innerConditionExpression[index].innerScore = "";
  704. changeAddMay();
  705. };
  706. const deleteItem = index => {
  707. addmanyChange.innerConditionExpression.splice(index, 1);
  708. changeAddMay();
  709. };
  710. const dataleListItem = (index, indexList) => {
  711. addmanyChange.innerConditionExpression[
  712. index
  713. ].scoreRuleMoreInnerVO[0].scoreRules.splice(indexList, 1);
  714. changeAddMay();
  715. };
  716. // 条件变量
  717. const dataleListItemAll = (item, index) => {
  718. item.scoreRuleMoreInnerVO = [];
  719. changeAddMay();
  720. };
  721. const addNewItem = () => {
  722. addmanyChange.innerConditionExpression.push({
  723. startValue: null,
  724. endValue: null,
  725. select: null,
  726. comparisonStart: null,
  727. comparisonEnd: null,
  728. scoreRuleMoreInnerVO: []
  729. });
  730. changeAddMay();
  731. };
  732. const addNewItemOldValue = item => {
  733. addmanyChange.innerConditionExpression.push({
  734. startValue: item.endValue,
  735. select: null,
  736. endValue: null,
  737. comparisonStart: item.comparisonEnd == ">" ? "≥" : ">",
  738. comparisonEnd: null,
  739. scoreRuleMoreInnerVO: []
  740. });
  741. changeAddMay();
  742. };
  743. const addItemDataList = (
  744. index: number,
  745. itemList: any,
  746. indexList: number,
  747. item
  748. ) => {
  749. addmanyChange.innerConditionExpression[
  750. index
  751. ].scoreRuleMoreInnerVO[0].scoreRules.push({
  752. select: null,
  753. score: null,
  754. scoreExpress: null,
  755. startValue: itemList.endValue,
  756. endValue: null,
  757. comparisonStart: itemList.comparisonEnd,
  758. comparisonEnd: null
  759. });
  760. addmanyChange.innerConditionExpression[index].innerScore = "";
  761. changeAddMay();
  762. };
  763. // 多条件公式验证
  764. const keywords = [
  765. "目标值",
  766. "完成值",
  767. "挑战值",
  768. "门槛值",
  769. "增幅",
  770. "降幅",
  771. "上期完成值",
  772. "上上期完成值"
  773. ];
  774. // 处理字符串,提取关键词
  775. function extractKeywords(value) {
  776. // 如果是字符串,处理包含的关键词
  777. if (typeof value === "string") {
  778. // 提取所有关键词
  779. keywords.forEach(keyword => {
  780. if (value.includes(keyword)) {
  781. formulaForm.value.push({
  782. name: keyword,
  783. value: null // 可以根据需求赋值
  784. });
  785. }
  786. });
  787. }
  788. }
  789. // 遍历对象并处理
  790. function traverseObject(obj) {
  791. if (obj && typeof obj === "object") {
  792. for (const key in obj) {
  793. if (obj.hasOwnProperty(key)) {
  794. const value = obj[key];
  795. // 如果值是字符串,调用提取函数
  796. if (typeof value === "string") {
  797. extractKeywords(value);
  798. }
  799. // 如果值是数组,递归处理
  800. if (Array.isArray(value)) {
  801. value.forEach(item => traverseObject(item));
  802. }
  803. }
  804. }
  805. }
  806. }
  807. function extractKeywordsAndPush(keywordsList, inputString) {
  808. keywords.forEach(keyword => {
  809. if (
  810. inputString?.includes(keyword) && // 检查字符串是否包含关键字
  811. !formulaForm.value.some(item => item.name === keyword) // 确保没有重复
  812. ) {
  813. // 如果包含且未重复,构造对象并push到formulaForm.value
  814. formulaForm.value.push({
  815. name: keyword,
  816. value: null // 根据需求赋值
  817. });
  818. }
  819. });
  820. return formulaForm;
  821. }
  822. const manyConditions = () => {
  823. grade.value = null;
  824. dialogFormVisibleFormula.value = true;
  825. formulaForm.value = [];
  826. // 提取 addmanyChange 对象中的条件值
  827. let oldValue = addmanyChange;
  828. if (oldValue.outerConditionValue) {
  829. extractKeywordsAndPush(keywords, oldValue.outerConditionValue);
  830. }
  831. if (oldValue.innerConditionExpression.length > 0) {
  832. oldValue.innerConditionExpression.map(itemExp => {
  833. if (itemExp.startValue) {
  834. extractKeywordsAndPush(keywords, itemExp.startValue);
  835. }
  836. if (itemExp.endValue) {
  837. extractKeywordsAndPush(keywords, itemExp.endValue);
  838. }
  839. if (itemExp.innerScore) {
  840. extractKeywordsAndPush(keywords, itemExp.innerScore);
  841. }
  842. if (itemExp?.scoreRuleMoreInnerVO[0]?.innerConditionValue) {
  843. extractKeywordsAndPush(
  844. keywords,
  845. itemExp.scoreRuleMoreInnerVO[0].innerConditionValue
  846. );
  847. }
  848. if (itemExp?.scoreRuleMoreInnerVO.length > 0) {
  849. if (itemExp?.scoreRuleMoreInnerVO[0]?.scoreRules.length > 0) {
  850. itemExp?.scoreRuleMoreInnerVO[0]?.scoreRules.map(itSc => {
  851. if (itSc.score) {
  852. extractKeywordsAndPush(keywords, itSc.score);
  853. }
  854. if (itSc.startValue) {
  855. extractKeywordsAndPush(keywords, itSc.startValue);
  856. }
  857. if (itSc.endValue) {
  858. extractKeywordsAndPush(keywords, itSc.endValue);
  859. }
  860. });
  861. }
  862. }
  863. });
  864. }
  865. };
  866. // 计算器
  867. const jishuanqiRef = ref();
  868. const countNoConditionFormula = item => {
  869. addmanyChange.outerConditionValue = item;
  870. changeAddMay();
  871. };
  872. const jishuanqiRef1 = ref();
  873. const countNoConditionFormula1 = (item, index) => {
  874. addmanyChange.innerConditionExpression[index].endValue = item;
  875. changeAddMay();
  876. };
  877. const jishuanqiRef2 = ref();
  878. const countNoConditionFormula2 = (item, index) => {
  879. // innerConditionValue
  880. addmanyChange.innerConditionExpression[
  881. index
  882. ].scoreRuleMoreInnerVO[0].innerConditionValue = item;
  883. changeAddMay();
  884. };
  885. const jishuanqiRef3 = ref();
  886. const countNoConditionFormula3 = (item, index, indexList) => {
  887. addmanyChange.innerConditionExpression[
  888. index
  889. ].scoreRuleMoreInnerVO[0].scoreRules[indexList].endValue = item;
  890. changeAddMay();
  891. };
  892. const countNoConditionFormula4 = (item, index, indexList) => {
  893. addmanyChange.innerConditionExpression[
  894. index
  895. ].scoreRuleMoreInnerVO[0].scoreRules[indexList].score = item;
  896. changeAddMay();
  897. };
  898. const countNoConditionFormulaInnerScore = (item, index, indexList) => {
  899. addmanyChange.innerConditionExpression[index].innerScore = item;
  900. changeAddMay();
  901. };
  902. // 转换函数 --- 人员
  903. const convertDepartmentDataRecursive_Person = data => {
  904. return data.map(department => {
  905. const { userNameNew, userCodeNew, children, type } = department;
  906. // 递归处理子节点
  907. const processedChildren =
  908. children.length > 0
  909. ? convertDepartmentDataRecursive_Person(children)
  910. : [];
  911. // 检查子节点是否有 type 为 "user" 的节点
  912. const hasUserInChildren = processedChildren.some(child => !child.disabled);
  913. // 当前节点是否为 user 类型
  914. const isUser = type === "user";
  915. // 判断当前节点是否需要禁用
  916. const shouldDisable = !isUser && !hasUserInChildren;
  917. return {
  918. value: userCodeNew,
  919. label: userNameNew,
  920. children: processedChildren,
  921. disabled: shouldDisable
  922. };
  923. });
  924. };
  925. postListTreeWithUserApi();
  926. const assessmentTypeRef = ref();
  927. const handleRreeSelect = () => {
  928. const arr = assessmentTypeRef.value.getCheckedNodes().filter(item => {
  929. return item.children.length == 0;
  930. });
  931. params.designatedPersonnel = arr.map(item => item.value).join(",");
  932. };
  933. // 取消计算
  934. const quxiaoCmputed = () => {
  935. formulaForm.value = [];
  936. dialogFormVisibleFormula.value = false;
  937. };
  938. // 监听数据变化
  939. const changeAddMay = () => {
  940. let addmanyChangeOldVal = JSON.parse(JSON.stringify(addmanyChange));
  941. addmanyChange.innerConditionExpression.forEach((item, index, arr) => {
  942. if (index + 1 <= arr.length) {
  943. if (item.endValue) {
  944. if (addmanyChangeOldVal.innerConditionExpression.length > 1) {
  945. addmanyChangeOldVal.innerConditionExpression[index + 1].startValue =
  946. item?.endValue;
  947. addmanyChangeOldVal.innerConditionExpression[index + 1].startExpress =
  948. item?.endExpress;
  949. addmanyChangeOldVal.innerConditionExpression[
  950. index + 1
  951. ].comparisonStart = item?.comparisonEnd == "≥" ? ">" : "≥";
  952. }
  953. }
  954. if (item.scoreRuleMoreInnerVO.length > 0) {
  955. if (item.scoreRuleMoreInnerVO[0].scoreRules.length > 0) {
  956. item.scoreRuleMoreInnerVO[0].scoreRules.map((it, id, arrChild) => {
  957. if (id + 1 <= arrChild.length) {
  958. if (it.endValue) {
  959. // if (
  960. // addmanyChangeOldVal.innerConditionExpression[index + 1]
  961. // .scoreRuleMoreInnerVO.length > 0
  962. // ) {
  963. addmanyChangeOldVal.innerConditionExpression[
  964. index
  965. ].scoreRuleMoreInnerVO[0].scoreRules[id + 1].startValue =
  966. it?.endValue;
  967. addmanyChangeOldVal.innerConditionExpression[
  968. index
  969. ].scoreRuleMoreInnerVO[0].scoreRules[id + 1].startExpress =
  970. it?.startExpress;
  971. addmanyChangeOldVal.innerConditionExpression[
  972. index
  973. ].scoreRuleMoreInnerVO[0].scoreRules[id + 1].comparisonStart =
  974. it?.comparisonEnd == "≥" ? ">" : "≥";
  975. // }
  976. }
  977. }
  978. });
  979. }
  980. }
  981. }
  982. });
  983. Object.assign(addmanyChange, addmanyChangeOldVal);
  984. };
  985. const formulaFocus = () => {
  986. calculatorShow.value = true;
  987. };
  988. const changeValueInput = val => {
  989. if (val == 4 || val == "4") {
  990. params.valueScore = 0;
  991. }
  992. };
  993. // { deep: true };
  994. </script>
  995. <template>
  996. <div>
  997. <el-drawer
  998. v-model="drawer"
  999. :direction="direction"
  1000. :before-close="handleClose"
  1001. size="700px"
  1002. >
  1003. <template #header>
  1004. <h4>指标设置</h4>
  1005. </template>
  1006. <template #default>
  1007. <div>
  1008. <el-form label-position="top" label-width="auto" :model="params">
  1009. <el-form-item label="完成值录入人" label-position="top">
  1010. <el-select
  1011. v-model="params.valueInput"
  1012. placeholder="请选择"
  1013. @change="changeValueInput"
  1014. >
  1015. <el-option label="被考核人" :value="0" />
  1016. <!-- <el-option label="上级" :value="1" /> -->
  1017. <el-option label="指定人员" :value="2" />
  1018. <el-option label="考核管理员" :value="3" />
  1019. <el-option label="指标自动采集" :value="4" />
  1020. </el-select>
  1021. <el-tree-select
  1022. v-if="params.valueInput == 2"
  1023. ref="assessmentTypeRef"
  1024. v-model="params.personList"
  1025. multiple
  1026. :data="convertDepartmentDataRecursive_Person(treeDept)"
  1027. :render-after-expand="false"
  1028. show-checkbox
  1029. style="margin-top: 10px"
  1030. @check-change="handleRreeSelect()"
  1031. />
  1032. </el-form-item>
  1033. <el-form-item
  1034. v-if="params.valueInput == 4"
  1035. label="完成值计算方式"
  1036. label-position="top"
  1037. >
  1038. <el-radio-group v-model="params.valueScore">
  1039. <el-radio :value="0" size="large">统计计算</el-radio>
  1040. <el-radio :value="1" size="large">累加计算</el-radio>
  1041. </el-radio-group>
  1042. </el-form-item>
  1043. <el-form-item label="评分方式" label-position="top">
  1044. <el-select v-model="params.scoreStandard" placeholder="请选择">
  1045. <el-option label="手动输入" :value="0" />
  1046. <el-option label="公式自动计算" :value="1" />
  1047. </el-select>
  1048. </el-form-item>
  1049. <div v-if="params.scoreStandard === 1">
  1050. <el-form-item label="公式类型" label-position="top">
  1051. <el-select
  1052. v-model="params.formulaType"
  1053. placeholder="请选择"
  1054. @change="watchFormulaType"
  1055. >
  1056. <el-option
  1057. v-for="item in compute"
  1058. :key="item.value"
  1059. :label="item.label"
  1060. :value="item.value"
  1061. />
  1062. </el-select>
  1063. </el-form-item>
  1064. <el-form-item
  1065. v-if="params.formulaType === 0"
  1066. label="公式设置"
  1067. label-position="top"
  1068. >
  1069. <div>
  1070. <div>
  1071. <el-text>得分 =</el-text>
  1072. <el-input
  1073. v-model="params.formula.noConditionFormula"
  1074. class="ml-2 mr-2"
  1075. style="width: 240px"
  1076. @focus="formulaFocus"
  1077. />
  1078. <el-text>
  1079. <el-button type="primary" @click="conditionVerifyApi"
  1080. >公式验证</el-button
  1081. >
  1082. </el-text>
  1083. </div>
  1084. <div
  1085. v-if="calculatorShow"
  1086. class="w-[500px] compute h-64 mt-1 ml-12 flex justify-evenly items-center"
  1087. style="user-select: none"
  1088. >
  1089. <div class="w-1/3 h-60 pl-1 bg-white rounded-md">
  1090. <div class="w-[100%] text-xs mt-2">
  1091. <div><el-text type="info">:::变量</el-text></div>
  1092. </div>
  1093. <el-scrollbar height="200px">
  1094. <div v-for="item in rolesList.data" :key="item.id">
  1095. <div
  1096. :class="[
  1097. 'cursor-pointer text-xs mt-1',
  1098. { bgBack: bgColor === item.id }
  1099. ]"
  1100. @click="lookRoles(item)"
  1101. >
  1102. <el-text class="">{{ item.name }}</el-text>
  1103. </div>
  1104. </div>
  1105. </el-scrollbar>
  1106. </div>
  1107. <div class="w-3/5 ml-2 h-60 flex flex-col">
  1108. <div class="w-[100%] text-xs h-24 bg-white rounded-md">
  1109. <div class="p-1"><el-text>得分 = </el-text></div>
  1110. <!-- style="height: 95px" -->
  1111. <el-input
  1112. v-model="params.formula.noConditionFormula"
  1113. :rows="3"
  1114. disabled
  1115. type="textarea"
  1116. placeholder='示例:"完成值" / "目标值" * 100'
  1117. />
  1118. </div>
  1119. <div class="w-[100%] h-32 mt-2 rounded-md flex flex-col">
  1120. <div class="flex justify-between h-8">
  1121. <div
  1122. class="h-full w-[50px] bg-white mx-1 flex justify-center items-center rounded-lg cursor-pointer"
  1123. @click="countNumber('1')"
  1124. >
  1125. 1
  1126. </div>
  1127. <div
  1128. class="h-full w-[50px] bg-white mx-1 flex justify-center items-center rounded-lg cursor-pointer"
  1129. @click="countNumber('2')"
  1130. >
  1131. 2
  1132. </div>
  1133. <div
  1134. class="h-full w-[50px] bg-white mx-1 flex justify-center items-center rounded-lg cursor-pointer"
  1135. @click="countNumber('3')"
  1136. >
  1137. 3
  1138. </div>
  1139. <div
  1140. class="h-full w-[50px] bg-white mx-1 flex justify-center items-center rounded-lg cursor-pointer"
  1141. @click="countNumber('+')"
  1142. >
  1143. +
  1144. </div>
  1145. <div
  1146. class="h-full w-[50px] text-white bg-orange-400 mx-1 flex justify-center items-center rounded-lg cursor-pointer"
  1147. @click="remove"
  1148. >
  1149. x
  1150. </div>
  1151. </div>
  1152. <div class="flex justify-between h-8 mt-1">
  1153. <div
  1154. class="h-full w-[50px] bg-white mx-1 flex justify-center items-center rounded-lg cursor-pointer"
  1155. @click="countNumber('4')"
  1156. >
  1157. 4
  1158. </div>
  1159. <div
  1160. class="h-full w-[50px] bg-white mx-1 flex justify-center items-center rounded-lg cursor-pointer"
  1161. @click="countNumber('5')"
  1162. >
  1163. 5
  1164. </div>
  1165. <div
  1166. class="h-full w-[50px] bg-white mx-1 flex justify-center items-center rounded-lg cursor-pointer"
  1167. @click="countNumber('6')"
  1168. >
  1169. 6
  1170. </div>
  1171. <div
  1172. class="h-full w-[50px] bg-white mx-1 flex justify-center items-center rounded-lg cursor-pointer"
  1173. @click="countNumber('-')"
  1174. >
  1175. -
  1176. </div>
  1177. <div
  1178. class="text-xs h-full w-[50px] text-white bg-orange-400 mx-1 flex justify-center items-center rounded-lg cursor-pointer"
  1179. @click="removeVoid"
  1180. >
  1181. 清空
  1182. </div>
  1183. </div>
  1184. <div class="flex justify-between h-16 mt-1">
  1185. <div>
  1186. <div class="flex justify-between">
  1187. <div
  1188. class="h-full w-[50px] bg-white mx-1 flex justify-center items-center rounded-lg cursor-pointer"
  1189. @click="countNumber('7')"
  1190. >
  1191. 7
  1192. </div>
  1193. <div
  1194. class="h-full ml-1 w-[50px] bg-white mx-1 flex justify-center items-center rounded-lg cursor-pointer"
  1195. @click="countNumber('8')"
  1196. >
  1197. 8
  1198. </div>
  1199. <div
  1200. class="h-full ml-2 w-[50px] bg-white mx-1 flex justify-center items-center rounded-lg cursor-pointer"
  1201. @click="countNumber('9')"
  1202. >
  1203. 9
  1204. </div>
  1205. <div
  1206. class="h-full w-[50px] bg-white mx-1 flex justify-center items-center rounded-lg cursor-pointer"
  1207. @click="countNumber('*')"
  1208. >
  1209. *
  1210. </div>
  1211. </div>
  1212. <div class="flex mt-1 justify-between">
  1213. <div
  1214. class="h-full w-[50px] bg-white mx-1 flex justify-center items-center rounded-lg cursor-pointer"
  1215. @click="countNumber('0')"
  1216. >
  1217. 0
  1218. </div>
  1219. <div
  1220. class="h-full ml-1 w-[50px] bg-white mx-1 flex justify-center items-center rounded-lg cursor-pointer"
  1221. @click="countNumber('.')"
  1222. >
  1223. .
  1224. </div>
  1225. <div
  1226. class="h-full ml-2 w-[50px] bg-white mx-1 flex justify-between items-center rounded-lg cursor-pointer"
  1227. >
  1228. <div
  1229. class="w-1/2 h-full text-center border-r text-gray-100"
  1230. @click="countNumber('(')"
  1231. >
  1232. <span class="text-black"> (</span>
  1233. </div>
  1234. <div
  1235. class="w-1/2 h-full text-center"
  1236. @click="countNumber(')')"
  1237. >
  1238. )
  1239. </div>
  1240. </div>
  1241. <div
  1242. class="h-full w-[50px] bg-white mx-1 flex justify-center items-center rounded-lg cursor-pointer"
  1243. @click="countNumber('/')"
  1244. >
  1245. /
  1246. </div>
  1247. </div>
  1248. </div>
  1249. <div
  1250. class="h-full mr-1 w-[50px] text-white flex justify-center items-center rounded-lg cursor-pointer areYouOK"
  1251. @click="count"
  1252. >
  1253. 确认
  1254. </div>
  1255. </div>
  1256. </div>
  1257. </div>
  1258. </div>
  1259. </div>
  1260. </el-form-item>
  1261. <el-form-item v-else label="公式设置">
  1262. <div class="w-full">
  1263. <div class="flex items-center">
  1264. <el-text>条件值 = </el-text>
  1265. <!-- <el-input
  1266. v-model="addmanyChange.outerConditionValue"
  1267. class="ml-2"
  1268. style="width: 240px"
  1269. /> -->
  1270. <jishuanqi
  1271. ref="jishuanqiRef"
  1272. :outerConditionValue="addmanyChange.outerConditionValue"
  1273. @handClick="countNoConditionFormula"
  1274. />
  1275. </div>
  1276. <div class="w-full mt-2">
  1277. <div
  1278. v-for="(
  1279. item, index
  1280. ) in addmanyChange.innerConditionExpression"
  1281. :key="index"
  1282. >
  1283. <div class="mt-3">
  1284. <div class="flex">
  1285. <el-text class="w-[15px]" type="primary">
  1286. {{ index + 1 }}
  1287. </el-text>
  1288. <div class="w-[40px] ml-4">
  1289. {{ item.startValue }}
  1290. </div>
  1291. <div class="mr-2">
  1292. {{ item.comparisonStart }}
  1293. </div>
  1294. <div class="mr-2">条件值</div>
  1295. <el-select
  1296. v-model="item.comparisonEnd"
  1297. style="width: 60px"
  1298. placeholder=""
  1299. :disabled="
  1300. index + 1 ==
  1301. addmanyChange.innerConditionExpression.length &&
  1302. index >= 1
  1303. ? true
  1304. : false
  1305. "
  1306. >
  1307. <el-option label=">" value=">" />
  1308. <el-option label="≥" value="≥" />
  1309. </el-select>
  1310. <el-select
  1311. v-model="item.select"
  1312. class="ml-2"
  1313. style="width: 80px"
  1314. placeholder=""
  1315. :disabled="
  1316. index + 1 ==
  1317. addmanyChange.innerConditionExpression.length &&
  1318. index >= 1
  1319. ? true
  1320. : false
  1321. "
  1322. >
  1323. <el-option label="数值" value="数值" />
  1324. <el-option label="公式" value="公式" />
  1325. </el-select>
  1326. <el-input
  1327. v-if="
  1328. index + 1 ==
  1329. addmanyChange.innerConditionExpression.length &&
  1330. index >= 1
  1331. "
  1332. disabled
  1333. class="ml-2 mr-5"
  1334. style="width: 80px"
  1335. />
  1336. <div v-else>
  1337. <jishuanqi
  1338. v-if="item.select == '公式'"
  1339. ref="jishuanqiRef"
  1340. :index="index"
  1341. :outerConditionValue="item.endValue"
  1342. class="ml-2 mr-5"
  1343. style="width: 80px"
  1344. @handClick="countNoConditionFormula1"
  1345. />
  1346. <el-input
  1347. v-else
  1348. v-model="item.endValue"
  1349. class="ml-2 mr-5"
  1350. style="width: 80px"
  1351. @blur="changeAddMay"
  1352. />
  1353. </div>
  1354. <el-text v-if="item.scoreRuleMoreInnerVO.length == 0"
  1355. >得分 =
  1356. </el-text>
  1357. <!-- <el-input
  1358. v-if="
  1359. index + 1 ==
  1360. addmanyChange.innerConditionExpression.length &&
  1361. index >= 1
  1362. "
  1363. disabled
  1364. class="ml-2 mr-5"
  1365. style="width: 100px"
  1366. /> -->
  1367. <div>
  1368. <jishuanqi
  1369. v-if="item.scoreRuleMoreInnerVO.length == 0"
  1370. ref="jishuanqiRef"
  1371. :index="index"
  1372. :outerConditionValue="item.innerScore"
  1373. class="ml-2 mr-6"
  1374. style="width: 100px"
  1375. @handClick="countNoConditionFormulaInnerScore"
  1376. />
  1377. </div>
  1378. <el-text type="danger" @click="deleteItem(index)">
  1379. <el-icon>
  1380. <Delete />
  1381. </el-icon>
  1382. </el-text>
  1383. </div>
  1384. <div
  1385. v-for="(itemVO, indexOV) in item.scoreRuleMoreInnerVO"
  1386. :key="indexOV"
  1387. >
  1388. <div class="flex mt-2 ml-20">
  1389. <div class="mr-2">条件值{{ index + 1 }} =</div>
  1390. <!-- <el-input v-if="
  1391. index + 1 ==
  1392. addmanyChange.innerConditionExpression
  1393. .length && index >= 1
  1394. " disabled class="ml-2 mr-6" style="width: 208px" /> -->
  1395. <jishuanqi
  1396. ref="jishuanqiRef"
  1397. :index="index"
  1398. :outerConditionValue="itemVO.innerConditionValue"
  1399. class="ml-2 mr-6"
  1400. style="width: 208px"
  1401. @handClick="countNoConditionFormula2"
  1402. />
  1403. <!-- <el-input v-model="itemVO.innerConditionValue" class="ml-2 mr-6" style="width: 208px" /> -->
  1404. <el-text
  1405. type="danger"
  1406. @click="dataleListItemAll(item, index)"
  1407. >
  1408. <el-icon>
  1409. <Delete />
  1410. </el-icon>
  1411. </el-text>
  1412. </div>
  1413. <div
  1414. v-for="(itemList, indexList) in itemVO.scoreRules"
  1415. :key="indexList"
  1416. class="ml-3"
  1417. >
  1418. <div class="flex mt-2 ml-16 items-center">
  1419. <div class="text_border">{{ indexList + 1 }}</div>
  1420. <!-- manyChange.dataList[index].dataList -->
  1421. <div class="w-[40px] ml-2">
  1422. {{ itemList.startValue }}
  1423. </div>
  1424. <div class="mr-2">
  1425. {{ itemList.comparisonStart }}
  1426. </div>
  1427. <div class="mr-2">条件值{{ index + 1 }}</div>
  1428. <el-select
  1429. v-model="itemList.comparisonEnd"
  1430. style="width: 60px"
  1431. placeholder=""
  1432. :disabled="
  1433. indexList + 1 == itemVO.scoreRules.length
  1434. ? true
  1435. : false
  1436. "
  1437. >
  1438. <el-option label=">" value=">" />
  1439. <el-option label="≥" value="≥" />
  1440. </el-select>
  1441. <el-select
  1442. v-model="itemList.select"
  1443. class="ml-2"
  1444. style="width: 80px"
  1445. placeholder=""
  1446. :disabled="
  1447. indexList + 1 == itemVO.scoreRules.length
  1448. ? true
  1449. : false
  1450. "
  1451. >
  1452. <el-option label="数值" value="数值" />
  1453. <el-option label="公式" value="公式" />
  1454. </el-select>
  1455. <el-input
  1456. v-if="indexList + 1 == itemVO.scoreRules.length"
  1457. disabled
  1458. class="ml-2"
  1459. style="width: 80px"
  1460. />
  1461. <div v-else>
  1462. <jishuanqi
  1463. v-if="itemList.select == '公式'"
  1464. ref="jishuanqiRef"
  1465. :index="index"
  1466. :indexList="indexList"
  1467. :outerConditionValue="itemList.endValue"
  1468. class="ml-2"
  1469. style="width: 80px"
  1470. @handClick="countNoConditionFormula3"
  1471. />
  1472. <el-input
  1473. v-else
  1474. v-model="itemList.endValue"
  1475. class="ml-2"
  1476. style="width: 80px"
  1477. @blur="changeAddMay"
  1478. />
  1479. </div>
  1480. <div
  1481. class="w-[150px] ml-2 mr-2 flex justify-between items-center"
  1482. >
  1483. <div>得分</div>
  1484. <div>=</div>
  1485. <!-- <el-input v-if="
  1486. indexList + 1 == itemVO.scoreRules.length &&
  1487. index >= 1
  1488. " disabled class="ml-2" style="width: 80px" /> -->
  1489. <jishuanqi
  1490. ref="jishuanqiRef"
  1491. :index="index"
  1492. :indexList="indexList"
  1493. :outerConditionValue="itemList.score"
  1494. class="ml-2"
  1495. style="width: 80px"
  1496. @handClick="countNoConditionFormula4"
  1497. />
  1498. <!-- <el-input
  1499. v-model="itemList.score"
  1500. class="ml-2"
  1501. style="width: 80px"
  1502. /> -->
  1503. </div>
  1504. <el-text
  1505. type="danger"
  1506. @click="dataleListItem(index, indexList)"
  1507. >
  1508. <el-icon>
  1509. <Delete />
  1510. </el-icon>
  1511. </el-text>
  1512. </div>
  1513. <div
  1514. v-if="indexList + 1 == itemVO.scoreRules.length"
  1515. class="ml-16 mt-2 text-xs cursor-pointer"
  1516. >
  1517. <el-text
  1518. type="primary"
  1519. @click="
  1520. addItemDataList(
  1521. index,
  1522. itemList,
  1523. indexList,
  1524. item
  1525. )
  1526. "
  1527. >
  1528. <el-icon>
  1529. <Plus />
  1530. </el-icon>
  1531. 添加子条件
  1532. </el-text>
  1533. </div>
  1534. </div>
  1535. </div>
  1536. </div>
  1537. <div
  1538. v-if="item?.scoreRuleMoreInnerVO?.length == 0"
  1539. class="ml-20 mt-2 text-xs cursor-pointer"
  1540. >
  1541. <el-text
  1542. type="primary"
  1543. @click="addItemFormulaList(item, index)"
  1544. >
  1545. <el-icon>
  1546. <Plus />
  1547. </el-icon>
  1548. 添加子条件
  1549. </el-text>
  1550. </div>
  1551. <div
  1552. v-if="
  1553. addmanyChange.innerConditionExpression.length >= 1 &&
  1554. index + 1 ==
  1555. addmanyChange.innerConditionExpression.length
  1556. "
  1557. class="mt-5 text-xs cursor-pointer"
  1558. >
  1559. <el-text
  1560. type="primary"
  1561. @click="addNewItemOldValue(item)"
  1562. >
  1563. <el-icon>
  1564. <Plus />
  1565. </el-icon>
  1566. 添加条件
  1567. </el-text>
  1568. </div>
  1569. </div>
  1570. <div
  1571. v-if="addmanyChange.innerConditionExpression.length < 1"
  1572. class="mt-5 text-xs cursor-pointer"
  1573. >
  1574. <el-text type="primary" @click="addNewItem">
  1575. <el-icon>
  1576. <Plus />
  1577. </el-icon>
  1578. 添加条件
  1579. </el-text>
  1580. </div>
  1581. <div class="float-right mr-8">
  1582. <el-button type="primary" @click="manyConditions"
  1583. >公式验证</el-button
  1584. >
  1585. </div>
  1586. </div>
  1587. </div>
  1588. </el-form-item>
  1589. </div>
  1590. </el-form>
  1591. </div>
  1592. </template>
  1593. <template #footer>
  1594. <div>
  1595. <el-button @click="cancelClick">取消</el-button>
  1596. <el-button type="primary" @click="confirmClick">确认</el-button>
  1597. </div>
  1598. </template>
  1599. </el-drawer>
  1600. <!-- 公式验证 -->
  1601. <el-dialog
  1602. v-model="dialogFormVisibleFormula"
  1603. title="完成值"
  1604. width="500"
  1605. :before-close="quxiaoCmputed"
  1606. >
  1607. <el-form :model="formulaForm">
  1608. <div v-for="(itemF, indexF) in formulaForm" :key="indexF">
  1609. <el-form-item :label="itemF.name">
  1610. <el-input v-model="itemF.value" autocomplete="off" />
  1611. </el-form-item>
  1612. </div>
  1613. <el-form-item label="得分">
  1614. <el-input v-model="grade" class="ml-3" autocomplete="off" disabled />
  1615. </el-form-item>
  1616. </el-form>
  1617. <template #footer>
  1618. <div class="dialog-footer">
  1619. <el-button @click="quxiaoCmputed">取消</el-button>
  1620. <el-button type="primary" @click="countComputed"> 计算 </el-button>
  1621. </div>
  1622. </template>
  1623. </el-dialog>
  1624. </div>
  1625. </template>
  1626. <style lang="scss" scoped>
  1627. .compute {
  1628. // border: 1px solid #f3f3f3;
  1629. background-color: #f3f3f3;
  1630. border-radius: 5px;
  1631. }
  1632. .text-color {
  1633. color: #f3f3f3;
  1634. }
  1635. .areYouOK {
  1636. background-color: #409eff;
  1637. }
  1638. .bgBack {
  1639. background-color: #f3f3f3;
  1640. }
  1641. .text_border {
  1642. display: flex;
  1643. align-items: center;
  1644. justify-content: center;
  1645. width: 14px;
  1646. height: 14px;
  1647. // margin-top: 5px;
  1648. margin-right: 5px;
  1649. font-size: 12px;
  1650. border: 1px solid gray;
  1651. border-radius: 50%;
  1652. }
  1653. </style>