@nstc-business/imes 1.1.4 → 1.1.6
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +1 -1
- package/src/components/measureCalc/MeasureEvalFlatTable.vue +31 -10
- package/src/components/measureCalc/MeasureStatFlatTable.vue +49 -10
- package/src/components/measureCalc/MeasureTreeTable.vue +66 -18
- package/src/components/measureCalc/helpers.js +56 -0
- package/src/components/measureCalc/index.vue +17 -4
package/package.json
CHANGED
|
@@ -157,20 +157,28 @@
|
|
|
157
157
|
<vxe-column title="模型指标得分" width="140" align="center">
|
|
158
158
|
<template #default="{ row }">
|
|
159
159
|
<div>{{ resultFn(row) }}</div>
|
|
160
|
-
<
|
|
161
|
-
|
|
160
|
+
<div
|
|
161
|
+
v-if="
|
|
162
162
|
!isQualFn(row) &&
|
|
163
163
|
row.result !== '' &&
|
|
164
164
|
row.result !== null &&
|
|
165
165
|
row.modifyRank === 1
|
|
166
166
|
"
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
167
|
+
class="modified-result-cell"
|
|
168
|
+
:class="{ 'is-over-limit': isModifiedResultOverFn(row) }"
|
|
169
|
+
>
|
|
170
|
+
<InputNumber
|
|
171
|
+
class="full-w"
|
|
172
|
+
:d-num="SCORE_DIGITS"
|
|
173
|
+
:disabled="ctx.readonly"
|
|
174
|
+
v-model="row.modifiedResult"
|
|
175
|
+
placeholder="修改模型指标得分"
|
|
176
|
+
@change="onModifiedResultChange(row)"
|
|
177
|
+
/>
|
|
178
|
+
<div v-if="isModifiedResultOverFn(row)" class="modified-result-tip">
|
|
179
|
+
调整得分不能超过{{ modifiedResultLimitTextFn(row) }}
|
|
180
|
+
</div>
|
|
181
|
+
</div>
|
|
174
182
|
</template>
|
|
175
183
|
</vxe-column>
|
|
176
184
|
<vxe-column
|
|
@@ -245,7 +253,9 @@ import {
|
|
|
245
253
|
indicatorResultText,
|
|
246
254
|
fullScoreText,
|
|
247
255
|
showLevelSerial,
|
|
248
|
-
isShowFullScore
|
|
256
|
+
isShowFullScore,
|
|
257
|
+
modifiedResultLimitText,
|
|
258
|
+
isModifiedResultOverLimit
|
|
249
259
|
} from './helpers'
|
|
250
260
|
import { fillQualReasonFromOption } from './qualReason'
|
|
251
261
|
|
|
@@ -456,4 +466,15 @@ export default {
|
|
|
456
466
|
/deep/ .el-select .el-input__inner {
|
|
457
467
|
text-align: center;
|
|
458
468
|
}
|
|
469
|
+
.modified-result-cell.is-over-limit ::v-deep .el-input__inner {
|
|
470
|
+
border-color: #ff3b30;
|
|
471
|
+
}
|
|
472
|
+
.modified-result-tip {
|
|
473
|
+
margin-top: 2px;
|
|
474
|
+
line-height: 16px;
|
|
475
|
+
font-size: 12px;
|
|
476
|
+
color: #ff3b30;
|
|
477
|
+
text-align: left;
|
|
478
|
+
white-space: normal;
|
|
479
|
+
}
|
|
459
480
|
</style>
|
|
@@ -111,19 +111,27 @@
|
|
|
111
111
|
<vxe-column title="指标得分" width="140" align="center">
|
|
112
112
|
<template #default="{ row }">
|
|
113
113
|
<div>{{ resultFn(row) }}</div>
|
|
114
|
-
<
|
|
115
|
-
|
|
114
|
+
<div
|
|
115
|
+
v-if="
|
|
116
116
|
row.result !== '' &&
|
|
117
117
|
row.result !== null &&
|
|
118
118
|
row.modifyRank === 1
|
|
119
119
|
"
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
120
|
+
class="modified-result-cell"
|
|
121
|
+
:class="{ 'is-over-limit': isModifiedResultOverFn(row) }"
|
|
122
|
+
>
|
|
123
|
+
<InputNumber
|
|
124
|
+
class="full-w"
|
|
125
|
+
:d-num="SCORE_DIGITS"
|
|
126
|
+
:disabled="ctx.readonly"
|
|
127
|
+
v-model="row.modifiedResult"
|
|
128
|
+
placeholder="修改指标得分"
|
|
129
|
+
@change="onModifiedResultChange(row)"
|
|
130
|
+
/>
|
|
131
|
+
<div v-if="isModifiedResultOverFn(row)" class="modified-result-tip">
|
|
132
|
+
调整得分不能超过{{ modifiedResultLimitTextFn(row) }}
|
|
133
|
+
</div>
|
|
134
|
+
</div>
|
|
127
135
|
</template>
|
|
128
136
|
</vxe-column>
|
|
129
137
|
|
|
@@ -144,7 +152,9 @@ import {
|
|
|
144
152
|
digitsCalc,
|
|
145
153
|
SCORE_DIGITS,
|
|
146
154
|
resultByShowStyle,
|
|
147
|
-
indicatorResultText
|
|
155
|
+
indicatorResultText,
|
|
156
|
+
modifiedResultLimitText,
|
|
157
|
+
isModifiedResultOverLimit
|
|
148
158
|
} from './helpers'
|
|
149
159
|
|
|
150
160
|
/** 与表格列顺序一致,供 setMergeCells 计算列索引 */
|
|
@@ -207,6 +217,24 @@ export default {
|
|
|
207
217
|
this.$set(row, 'scoreMapID', option.scoreMapID)
|
|
208
218
|
this.$set(row, 'scoreText', option.scoreText)
|
|
209
219
|
this.$set(row, 'scoreValue', option.scoreValue)
|
|
220
|
+
},
|
|
221
|
+
/** 调整得分上限展示文案(标红提示用) */
|
|
222
|
+
modifiedResultLimitTextFn(row) {
|
|
223
|
+
return modifiedResultLimitText(row)
|
|
224
|
+
},
|
|
225
|
+
/** 调整得分是否超限(标红判定) */
|
|
226
|
+
isModifiedResultOverFn(row) {
|
|
227
|
+
return isModifiedResultOverLimit(row)
|
|
228
|
+
},
|
|
229
|
+
/** 调整得分失焦提交:超限时弹出明显提示(不拦截输入、不改写原值) */
|
|
230
|
+
onModifiedResultChange(row) {
|
|
231
|
+
if (!isModifiedResultOverLimit(row)) return
|
|
232
|
+
const weightText =
|
|
233
|
+
row.weight === '' || row.weight == null ? 100 : row.weight
|
|
234
|
+
this.$message.warning(
|
|
235
|
+
`${row.name || '该指标'}的调整得分不能超过${modifiedResultLimitText(row)}` +
|
|
236
|
+
`(指标满分值${row.fullScore}×占模型权重${weightText}%)`
|
|
237
|
+
)
|
|
210
238
|
}
|
|
211
239
|
}
|
|
212
240
|
}
|
|
@@ -258,4 +286,15 @@ export default {
|
|
|
258
286
|
/deep/ .el-select .el-input__inner {
|
|
259
287
|
text-align: center;
|
|
260
288
|
}
|
|
289
|
+
.modified-result-cell.is-over-limit ::v-deep .el-input__inner {
|
|
290
|
+
border-color: #ff3b30;
|
|
291
|
+
}
|
|
292
|
+
.modified-result-tip {
|
|
293
|
+
margin-top: 2px;
|
|
294
|
+
line-height: 16px;
|
|
295
|
+
font-size: 12px;
|
|
296
|
+
color: #ff3b30;
|
|
297
|
+
text-align: left;
|
|
298
|
+
white-space: normal;
|
|
299
|
+
}
|
|
261
300
|
</style>
|
|
@@ -182,19 +182,28 @@
|
|
|
182
182
|
<vxe-column title="模型指标系数数值" min-width="200" align="center">
|
|
183
183
|
<template #default="{ row }">
|
|
184
184
|
<template v-if="isQuantIndicatorFn(row) || isSubModelFn(row)">
|
|
185
|
-
<
|
|
186
|
-
|
|
185
|
+
<div
|
|
186
|
+
v-if="
|
|
187
187
|
isQuantIndicatorFn(row) &&
|
|
188
188
|
row.modifyRank === 1 &&
|
|
189
189
|
row.result !== '' &&
|
|
190
190
|
row.result !== null
|
|
191
191
|
"
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
192
|
+
class="modified-result-cell"
|
|
193
|
+
:class="{ 'is-over-limit': isModifiedResultOverFn(row) }"
|
|
194
|
+
>
|
|
195
|
+
<InputNumber
|
|
196
|
+
class="full-w"
|
|
197
|
+
:d-num="SCORE_DIGITS"
|
|
198
|
+
:disabled="ctx.readonly"
|
|
199
|
+
v-model="row.modifiedResult"
|
|
200
|
+
placeholder="请输入"
|
|
201
|
+
@change="onModifiedResultChange(row)"
|
|
202
|
+
/>
|
|
203
|
+
<div v-if="isModifiedResultOverFn(row)" class="modified-result-tip">
|
|
204
|
+
调整得分不能超过{{ modifiedResultLimitTextFn(row) }}
|
|
205
|
+
</div>
|
|
206
|
+
</div>
|
|
198
207
|
<span v-else>{{ resultFn(row) }}</span>
|
|
199
208
|
</template>
|
|
200
209
|
<span v-else class="color-placeholder">—</span>
|
|
@@ -359,17 +368,25 @@
|
|
|
359
368
|
<template #default="{ row }">
|
|
360
369
|
<template v-if="isQuantIndicatorFn(row)">
|
|
361
370
|
<div>{{ resultFn(row) }}</div>
|
|
362
|
-
<
|
|
363
|
-
|
|
371
|
+
<div
|
|
372
|
+
v-if="
|
|
364
373
|
row.result !== '' && row.result !== null && row.modifyRank === 1
|
|
365
374
|
"
|
|
366
|
-
|
|
367
|
-
|
|
368
|
-
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
|
|
372
|
-
|
|
375
|
+
class="modified-result-cell"
|
|
376
|
+
:class="{ 'is-over-limit': isModifiedResultOverFn(row) }"
|
|
377
|
+
>
|
|
378
|
+
<InputNumber
|
|
379
|
+
class="full-w"
|
|
380
|
+
:d-num="SCORE_DIGITS"
|
|
381
|
+
:disabled="ctx.readonly"
|
|
382
|
+
v-model="row.modifiedResult"
|
|
383
|
+
placeholder="修改模型指标得分"
|
|
384
|
+
@change="onModifiedResultChange(row)"
|
|
385
|
+
/>
|
|
386
|
+
<div v-if="isModifiedResultOverFn(row)" class="modified-result-tip">
|
|
387
|
+
调整得分不能超过{{ modifiedResultLimitTextFn(row) }}
|
|
388
|
+
</div>
|
|
389
|
+
</div>
|
|
373
390
|
</template>
|
|
374
391
|
<template v-else-if="isSubModelFn(row) && ctx.parentCalced">
|
|
375
392
|
<div>{{ resultFn(row) }}</div>
|
|
@@ -453,7 +470,9 @@ import {
|
|
|
453
470
|
fullScoreText,
|
|
454
471
|
hierarchySerial,
|
|
455
472
|
hierarchySerialPrefix,
|
|
456
|
-
isShowFullScore
|
|
473
|
+
isShowFullScore,
|
|
474
|
+
modifiedResultLimitText,
|
|
475
|
+
isModifiedResultOverLimit
|
|
457
476
|
} from './helpers'
|
|
458
477
|
|
|
459
478
|
export default {
|
|
@@ -684,6 +703,24 @@ export default {
|
|
|
684
703
|
},
|
|
685
704
|
childNumberPrefix(row) {
|
|
686
705
|
return hierarchySerialPrefix(this.rowSerial(row))
|
|
706
|
+
},
|
|
707
|
+
/** 调整得分上限展示文案(标红提示用) */
|
|
708
|
+
modifiedResultLimitTextFn(row) {
|
|
709
|
+
return modifiedResultLimitText(row)
|
|
710
|
+
},
|
|
711
|
+
/** 调整得分是否超限(标红判定) */
|
|
712
|
+
isModifiedResultOverFn(row) {
|
|
713
|
+
return isModifiedResultOverLimit(row)
|
|
714
|
+
},
|
|
715
|
+
/** 调整得分失焦提交:超限时弹出明显提示(不拦截输入、不改写原值) */
|
|
716
|
+
onModifiedResultChange(row) {
|
|
717
|
+
if (!isModifiedResultOverLimit(row)) return
|
|
718
|
+
const weightText =
|
|
719
|
+
row.weight === '' || row.weight == null ? 100 : row.weight
|
|
720
|
+
this.$message.warning(
|
|
721
|
+
`${row.name || '该指标'}的调整得分不能超过${modifiedResultLimitText(row)}` +
|
|
722
|
+
`(指标满分值${row.fullScore}×占模型权重${weightText}%)`
|
|
723
|
+
)
|
|
687
724
|
}
|
|
688
725
|
}
|
|
689
726
|
}
|
|
@@ -833,4 +870,15 @@ export default {
|
|
|
833
870
|
color: #ff3b30 !important;
|
|
834
871
|
}
|
|
835
872
|
}
|
|
873
|
+
.modified-result-cell.is-over-limit ::v-deep .el-input__inner {
|
|
874
|
+
border-color: #ff3b30;
|
|
875
|
+
}
|
|
876
|
+
.modified-result-tip {
|
|
877
|
+
margin-top: 2px;
|
|
878
|
+
line-height: 16px;
|
|
879
|
+
font-size: 12px;
|
|
880
|
+
color: #ff3b30;
|
|
881
|
+
text-align: left;
|
|
882
|
+
white-space: normal;
|
|
883
|
+
}
|
|
836
884
|
</style>
|
|
@@ -551,6 +551,62 @@ export function isSameScore(a, b) {
|
|
|
551
551
|
if (Number.isNaN(na) || Number.isNaN(nb)) return false
|
|
552
552
|
return na.toFixed(SCORE_DIGITS) === nb.toFixed(SCORE_DIGITS)
|
|
553
553
|
}
|
|
554
|
+
|
|
555
|
+
/**
|
|
556
|
+
* 调整得分上限:指标满分值 × 占模型权重%
|
|
557
|
+
* 时间:2026-10-22 人员:Qoder && 辛善露
|
|
558
|
+
* 入参:node 指标行、digits 页面得分小数位
|
|
559
|
+
* 出参:Number 上限(已向下截断到 digits 位);null 表示不限制
|
|
560
|
+
* 方法内容:非「调整指标得分」不限制;满分值为空不限制(后端 compareFullScore 不生效);
|
|
561
|
+
* 权重为空按 100 处理(后端 multiplyWeight 权重为空时直接返回 result);
|
|
562
|
+
* 结果向下截断到页面得分小数位,保证提示上限即可输入的最大值
|
|
563
|
+
*/
|
|
564
|
+
export function modifiedResultLimit(node, digits = SCORE_DIGITS) {
|
|
565
|
+
if (!node || node.modifyRank !== 1) return null
|
|
566
|
+
if (node.fullScore === '' || node.fullScore == null) return null
|
|
567
|
+
const full = Number(node.fullScore)
|
|
568
|
+
if (Number.isNaN(full)) return null
|
|
569
|
+
let weight = 100
|
|
570
|
+
if (node.weight !== '' && node.weight != null) {
|
|
571
|
+
weight = Number(node.weight)
|
|
572
|
+
if (Number.isNaN(weight)) return null
|
|
573
|
+
}
|
|
574
|
+
// 高精度乘除后按字符串截断,避免 0.29*100 之类的浮点误差
|
|
575
|
+
const raw = String(N.div(N.mul(full, weight, digits + 4), 100, digits + 4))
|
|
576
|
+
const [intPart, decPart = ''] = raw.split('.')
|
|
577
|
+
const cut = decPart.slice(0, digits).padEnd(digits, '0')
|
|
578
|
+
return Number(`${intPart}.${cut}`)
|
|
579
|
+
}
|
|
580
|
+
|
|
581
|
+
/**
|
|
582
|
+
* 调整得分上限展示文案
|
|
583
|
+
* 时间:2026-10-22 人员:Qoder && 辛善露
|
|
584
|
+
* 入参:node 指标行、digits 页面得分小数位
|
|
585
|
+
* 出参:String 上限文案(固定 digits 位);不限制返回空串
|
|
586
|
+
* 方法内容:用于标红文案与 warning 提示,保证与判定阈值同源
|
|
587
|
+
*/
|
|
588
|
+
export function modifiedResultLimitText(node, digits = SCORE_DIGITS) {
|
|
589
|
+
const limit = modifiedResultLimit(node, digits)
|
|
590
|
+
return limit === null ? '' : limit.toFixed(digits)
|
|
591
|
+
}
|
|
592
|
+
|
|
593
|
+
/**
|
|
594
|
+
* 调整得分是否超过上限
|
|
595
|
+
* 时间:2026-10-22 人员:Qoder && 辛善露
|
|
596
|
+
* 入参:node 指标行、digits 页面得分小数位
|
|
597
|
+
* 出参:Boolean
|
|
598
|
+
* 方法内容:未调整(空值)或上限为 null 时返回 false;否则按数字比较
|
|
599
|
+
*/
|
|
600
|
+
export function isModifiedResultOverLimit(node, digits = SCORE_DIGITS) {
|
|
601
|
+
if (!node || node.modifiedResult === '' || node.modifiedResult == null) {
|
|
602
|
+
return false
|
|
603
|
+
}
|
|
604
|
+
const limit = modifiedResultLimit(node, digits)
|
|
605
|
+
if (limit === null) return false
|
|
606
|
+
const val = Number(node.modifiedResult)
|
|
607
|
+
return !Number.isNaN(val) && val > limit
|
|
608
|
+
}
|
|
609
|
+
|
|
554
610
|
let _uid = 0
|
|
555
611
|
/**
|
|
556
612
|
* 归一化整棵树:
|
|
@@ -256,7 +256,9 @@ import {
|
|
|
256
256
|
resolveCalcEchoValue,
|
|
257
257
|
shouldApplyModifiedVal,
|
|
258
258
|
fillDefaultModifiedResult,
|
|
259
|
-
isSameScore
|
|
259
|
+
isSameScore,
|
|
260
|
+
isModifiedResultOverLimit,
|
|
261
|
+
modifiedResultLimitText
|
|
260
262
|
} from './helpers'
|
|
261
263
|
import { preprocessStatIndicatorDeepList, mergeStatModelNode, statItemChildren } from './statModelHelper'
|
|
262
264
|
import { withRequestTimestamp ,getCommonEnum } from './api'
|
|
@@ -542,6 +544,7 @@ export default {
|
|
|
542
544
|
})
|
|
543
545
|
},
|
|
544
546
|
isSubModel,
|
|
547
|
+
isSameScore,
|
|
545
548
|
subModelResultText(node) {
|
|
546
549
|
return formatSubModelResult(node, this.model)
|
|
547
550
|
},
|
|
@@ -984,10 +987,20 @@ export default {
|
|
|
984
987
|
item.result !== null &&
|
|
985
988
|
item.modifyRank === 1 &&
|
|
986
989
|
(item.modifiedResult || item.modifiedResult === 0) &&
|
|
987
|
-
!isSameScore(item.modifiedResult, item.result)
|
|
990
|
+
!this.isSameScore(item.modifiedResult, item.result)
|
|
988
991
|
) {
|
|
989
|
-
|
|
990
|
-
|
|
992
|
+
if (isModifiedResultOverLimit(item)) {
|
|
993
|
+
// 超限:阻断测算,不写入 indicatorCalcList
|
|
994
|
+
obj.state = false
|
|
995
|
+
const weightText =
|
|
996
|
+
item.weight === '' || item.weight == null ? 100 : item.weight
|
|
997
|
+
this.messageStr +=
|
|
998
|
+
`${item.name}的调整得分不能超过${modifiedResultLimitText(item)}` +
|
|
999
|
+
`(指标满分值${item.fullScore}×占模型权重${weightText}%);`
|
|
1000
|
+
} else {
|
|
1001
|
+
calcItem.modifiedResult = item.modifiedResult
|
|
1002
|
+
hasCalc = true
|
|
1003
|
+
}
|
|
991
1004
|
}
|
|
992
1005
|
if (hasCalc) obj.indicatorCalcList.push(calcItem)
|
|
993
1006
|
return obj
|