projectAdd.vue 29 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927
  1. <template>
  2. <PageMain>
  3. <!-- 项目添加/编辑页面主容器 -->
  4. <div class="projectAdd">
  5. <!-- 项目表单,包含基本信息和方案配置 -->
  6. <el-form :model="projectAddFrom" :rules="projectAddRules" ref="ProjectAddRef">
  7. <!-- 基本信息描述 -->
  8. <el-descriptions title="基本信息">
  9. <el-descriptions-item>
  10. <!-- 保险公司选择 -->
  11. <el-form-item label="保险公司" prop="companyId">
  12. <el-select :disabled="isEdit" filterable v-model="projectAddFrom.companyId" placeholder="请选择"
  13. style="width: 40%" @change="initProduct">
  14. <el-option v-for="item in companyOption" :key="item.id" :value="item.id"
  15. :label="item.nameSimple"></el-option>
  16. </el-select>
  17. </el-form-item>
  18. <!-- 方案类型选择 -->
  19. <el-form-item label="方案类型" prop="schemeType">
  20. <el-radio-group :disabled="isEdit" v-model="projectAddFrom.schemeType" @change="schemeTypeChange">
  21. <el-radio :value="1">基础方案</el-radio>
  22. <el-radio :value="2">自选方案</el-radio>
  23. </el-radio-group>
  24. </el-form-item>
  25. <!-- 险种类型选择 -->
  26. <el-form-item label="险种类型" prop="productId">
  27. <el-radio-group :disabled="isEdit" v-model="projectAddFrom.productId" @change="initProduct">
  28. <el-radio-button v-for="item in insuranceType" :key="item.value" :value="item.value">{{ item.label
  29. }}</el-radio-button>
  30. </el-radio-group>
  31. </el-form-item>
  32. <!-- 规则条件配置 -->
  33. <div style="display: flex;">
  34. <span style="width: 10%"><a style="color: red">*</a>规则条件</span>
  35. <div style="width: 60%">
  36. <!-- 规则条件容器组件 -->
  37. <rule-condition-container :rulesAttrList="rulesAttrList" @Del="handleDel"></rule-condition-container>
  38. </div>
  39. </div>
  40. <!-- 添加规则条件按钮 -->
  41. <el-button style="margin: 10px 10%" plain type="primary" icon="plus" @click="addRules">添加条件</el-button>
  42. <!-- 方案配置描述 -->
  43. <el-descriptions>
  44. <template #title>
  45. <div style="display: flex; align-items: center">
  46. <span>方案配置</span>
  47. <!-- 添加新方案按钮(非编辑模式) -->
  48. <el-button v-show="!isEdit" type="primary" icon="plus" style="margin-left: 20px;"
  49. @click="addProject">添加新方案</el-button>
  50. </div>
  51. </template>
  52. <el-descriptions-item>
  53. <!-- 方案列表 -->
  54. <div class="configuration flex j-s a-start" v-for="(item, index) in projectAddFrom.schemeList">
  55. <el-button link type="primary"v-if="index > 0" @click="delScheme(index)">删除</el-button>
  56. <div class="flex-1 p-[20px]">
  57. <!-- 方案名称 -->
  58. <el-form-item label="方案名称" prop="schemeName">
  59. <el-input v-model="item.schemeName"></el-input>
  60. </el-form-item>
  61. <!-- 方案描述 -->
  62. <el-form-item label="方案描述" prop="description">
  63. <el-input type="textarea" v-model="item.description" maxlength="500"></el-input>
  64. </el-form-item>
  65. <!-- 驾意险配置 -->
  66. <div>
  67. <div style="display: flex; align-items: center; margin-bottom: 10px">
  68. <span style="margin-right: 20px">驾意险</span>
  69. <el-button link icon="plus" type="primary" @click="handleDriving(item, index)">选择驾意险</el-button>
  70. </div>
  71. <!-- 驾意险列表 -->
  72. <el-table :data="item.drivingList">
  73. <el-table-column label="名称" prop="productName">
  74. <template #default="scope">
  75. <el-button link type="primary" @click="getJYXDetail(scope.row)">{{ scope.row.productName
  76. }}</el-button>
  77. </template>
  78. </el-table-column>
  79. <!-- 客户端状态(仅自选方案显示) -->
  80. <el-table-column label="客户端状态" prop="selectedStatus" v-if="projectAddFrom.schemeType != 1">
  81. <template #default="scope">
  82. <el-select v-model="scope.row.selectedStatus">
  83. <el-option label="默认不选中" key="1" value="1"></el-option>
  84. <el-option label="默认选中" key="2" value="2"></el-option>
  85. <el-option label="强制选中" key="3" value="3"></el-option>
  86. </el-select>
  87. </template>
  88. </el-table-column>
  89. <!-- 驾意险份数 -->
  90. <el-table-column label="份数" prop="quantity">
  91. <template #default="scope">
  92. <el-input-number v-model="scope.row.quantity" style="width: 150px;" :min="1" :max="99"
  93. @change="numberChange($event, scope.row)"></el-input-number>份
  94. </template>
  95. </el-table-column>
  96. <!-- 驾意险操作 -->
  97. <el-table-column label="操作">
  98. <template #default="scope">
  99. <el-button link type="primary" @click="drivingTypeDel(item, scope.row)">删除</el-button>
  100. </template>
  101. </el-table-column>
  102. </el-table>
  103. </div>
  104. <!-- 险种配置 -->
  105. <div>
  106. <div style="display: flex; align-items: center; margin: 10px 0">
  107. <span style="margin-right: 20px">险种</span>
  108. <el-button link icon="plus" type="primary" @click="handlePopover(item, index)">选择险种</el-button>
  109. </div>
  110. <!-- 险种列表 -->
  111. <el-table :data="item.tableData">
  112. <el-table-column label="险种" prop="kindName" width="300">
  113. <template #default="scope">
  114. <a>{{ scope.row.kindName }}</a>
  115. </template>
  116. </el-table-column>
  117. <!-- 保额选择 -->
  118. <el-table-column label="保额" prop="optionId" align="center">
  119. <template #default="scope">
  120. <!-- 自选方案支持多选保额 -->
  121. <el-select :disabled="scope.row.insuranceId == '19'" v-if="projectAddFrom.schemeType === 2"
  122. v-model="scope.row.moneyId" style="width: 300px" multiple
  123. @change="() => { scope.row.optionId = scope.row.moneyId }">
  124. <el-option v-for="m in scope.row.options" :label="m.label" :key="m.id"
  125. :value="m.id"></el-option>
  126. </el-select>
  127. <!-- 基础方案只能选择一个保额 -->
  128. <el-select :disabled="scope.row.insuranceId == '19'" v-else v-model="scope.row.moneyId"
  129. style="width: 150px" @change="() => { scope.row.optionId = scope.row.moneyId }">
  130. <el-option v-for="m in scope.row.options" :label="m.label" :key="m.id"
  131. :value="m.id"></el-option>
  132. </el-select>
  133. </template>
  134. </el-table-column>
  135. <!-- 险种操作 -->
  136. <el-table-column label="操作">
  137. <template #default="scope">
  138. <!-- 交强险不可删除 -->
  139. <el-button
  140. :disabled="projectAddFrom.productId == '0330' && scope.row.id == '19' || projectAddFrom.productId == '0330034002' && scope.row.id == '19' || projectAddFrom.productId == '0330034001' && scope.row.id == '19'"
  141. link type="primary" @click="insuranceTypeDel(item, scope.row)">删除</el-button>
  142. </template>
  143. </el-table-column>
  144. </el-table>
  145. </div>
  146. </div>
  147. </div>
  148. </el-descriptions-item>
  149. </el-descriptions>
  150. </el-descriptions-item>
  151. </el-descriptions>
  152. </el-form>
  153. <!-- 底部操作按钮 -->
  154. <div class="btns">
  155. <el-button plain @click="quit">取消</el-button>
  156. <el-button type="primary" @click="save(ProjectAddRef)">保存</el-button>
  157. </div>
  158. <!-- 驾意险选择弹窗 -->
  159. <el-dialog :close-on-click-modal="false" v-model="drivingShow" title="选择驾意险" width="900">
  160. <driving ref="DrivingTypeRef" @close="handleDrivingClose"></driving>
  161. </el-dialog>
  162. <!-- 险种选择弹窗 -->
  163. <el-dialog :close-on-click-modal="false" v-model="insuranceShow" title="选择险种" width="500">
  164. <insurance ref="InsuranceTypeRef" @close="handleClose"></insurance>
  165. </el-dialog>
  166. <!-- 驾意险详情弹窗 -->
  167. <el-dialog :close-on-click-modal="false" v-model="JYXDetailShow" title="驾意险详情" width="600">
  168. <detail ref="JYXDetail"></detail>
  169. </el-dialog>
  170. <!-- 规则条件选择弹窗 -->
  171. <el-dialog :close-on-click-modal="false" v-model="ruleSelectShow" title="规则条件" width="600">
  172. <ruleSelect ref="RuleSelect" @close="handleRuleSelectClose"></ruleSelect>
  173. </el-dialog>
  174. </div>
  175. </PageMain>
  176. </template>
  177. <script setup lang="ts">
  178. // 导入API模块
  179. import api from "@/api";
  180. // 导入Element Plus组件和类型
  181. import { ElMessage, FormInstance, FormRules } from "element-plus";
  182. // 导入Vue Router
  183. import { useRouter, useRoute } from 'vue-router'
  184. // 导入自定义组件
  185. import insurance from '../../../../layouts/components/InsuranceType/index.vue'
  186. import driving from '../../../../layouts/components/DrivingType/index.vue'
  187. import rule from '../../../../components/ruleConditionContainer/index.vue'
  188. import detail from '../../../../layouts/components/JYXDetail/index.vue'
  189. import ruleSelect from '../../../../layouts/components/ruleSelect/index.vue'
  190. import Detail from "@/views/representative/detail.vue";
  191. // 导入Vue 3组合式API
  192. import { ref, onMounted, onBeforeMount, nextTick } from 'vue'
  193. // 路由实例
  194. const myRouter = useRouter()
  195. const myRoute = useRoute()
  196. // 表单引用
  197. const ProjectAddRef = ref<FormInstance>()
  198. // 组件引用
  199. const InsuranceTypeRef = ref(null)
  200. const DrivingTypeRef = ref(null)
  201. const JYXDetail = ref(null)
  202. const RuleSelect = ref()
  203. // 车牌地区数据
  204. const licensePlateRegion = ref();
  205. // 车牌号数据
  206. const licensePlateNumber = ref();
  207. /**
  208. * 获取车牌地区数据
  209. * @param value 地区代码
  210. */
  211. const regionLicenseRegion = (value: string) => {
  212. api.agreementApi.getAreaLicense(value).then((res: any) => {
  213. if (res.code == '200') {
  214. let data: any = [];
  215. res.data.map((val: any) => {
  216. data.push({
  217. code: val.areaNumber,
  218. name: val.license,
  219. })
  220. return val;
  221. })
  222. licensePlateRegion.value = data;
  223. }
  224. });
  225. }
  226. /**
  227. * 获取车牌号数据
  228. * @param value 地区代码
  229. */
  230. const regionLicenseNumber = (value: string) => {
  231. api.agreementApi.getAreaLicense(value).then((res: any) => {
  232. if (res.code == '200') {
  233. let data: any = [];
  234. res.data.map((val: any) => {
  235. data.push({
  236. code: val.areaNumber,
  237. name: val.license,
  238. })
  239. return val;
  240. })
  241. licensePlateNumber.value = data;
  242. }
  243. });
  244. }
  245. // 规则条件选择弹窗状态
  246. let ruleSelectShow = ref(false)
  247. /**
  248. * 处理规则条件选择关闭
  249. * @param data 选中的规则条件数据
  250. */
  251. const handleRuleSelectClose = (data) => {
  252. if (data && data.length > 0) {
  253. rulesAttrList.value = data.map(a => {
  254. // 处理车牌相关数据
  255. if (a.attrCode == 'LicenseNo') {
  256. a.dictLabal = licensePlateNumber.value;
  257. }
  258. if (a.attrCode == 'LicenseArea') {
  259. a.dictLabal = licensePlateRegion.value;
  260. }
  261. return {
  262. ...a,
  263. min: a.attrName == '能源类型' ? '0' : a.min ? a.min : '',
  264. minArray: a.minArray && a.minArray.length > 0 ? a.minArray : a.attrName == '使用性质' || a.attrName == '车辆种类' || a.attrName == '能源类型' ? [a.dictLabal[0].code] : [],
  265. max: a.max ? a.max : ''
  266. }
  267. })
  268. }
  269. ruleSelectShow.value = false
  270. }
  271. // 是否编辑模式
  272. let isEdit = ref(false)
  273. // 项目表单数据
  274. let projectAddFrom = ref({
  275. ruleAttrs: [], // 规则属性
  276. schemeType: 1, // 方案类型:1-基础方案,2-自选方案
  277. productId: '0330', // 险种类型
  278. schemeList: [{
  279. schemeName: '', // 方案名称
  280. description: '', // 方案描述
  281. tableData: [], // 险种列表
  282. drivingList: [], // 驾意险列表
  283. schemeInsuranceList: [], // 方案险种列表
  284. drivingIntentionList: [] // 驾意险意向列表
  285. }]
  286. })
  287. // 表单验证规则
  288. let projectAddRules = ref<FormRules>({
  289. companyId: [
  290. { required: true, trigger: "change", message: "请选择保险公司" }
  291. ],
  292. schemeType: [
  293. { required: true, trigger: "change", message: "请选择方案类型" }
  294. ],
  295. productId: [
  296. { required: true, trigger: "change", message: "请选择险种类型" }
  297. ]
  298. })
  299. // 驾意险详情弹窗状态
  300. let JYXDetailShow = ref(false)
  301. /**
  302. * 查看驾意险详情
  303. * @param row 驾意险数据行
  304. */
  305. const getJYXDetail = (row) => {
  306. JYXDetailShow.value = true
  307. nextTick(() => {
  308. JYXDetail.value.initData(row.drivingIntentionId)
  309. })
  310. }
  311. /**
  312. * 处理驾意险份数变化
  313. * @param e 新的份数值
  314. * @param row 驾意险数据行
  315. */
  316. const numberChange = (e, row) => {
  317. if (typeof e != 'number') {
  318. row.quantity = 1
  319. }
  320. }
  321. /**
  322. * 初始化产品方案
  323. * @param e 产品ID
  324. */
  325. const initProduct = async (e) => {
  326. // 获取规则条件中的能源类型、车辆种类、使用性质
  327. let energyType = null, vehicleType = null, carnature = null
  328. if (rulesAttrList.value && rulesAttrList.value.length > 0) {
  329. energyType = rulesAttrList.value.find(a => a.attrName === '能源类型')
  330. vehicleType = rulesAttrList.value.find(a => a.attrName === '车辆种类')
  331. carnature = rulesAttrList.value.find(a => a.attrName === '使用性质')
  332. }
  333. // 根据产品类型初始化默认险种
  334. if (e == '0330' || e == '0330034001') {
  335. // 交强险
  336. let obj = insuranceTypeList.value.filter(item => item.id == '19')
  337. if (obj) {
  338. obj.forEach(item => {
  339. item.insuranceId = item.id
  340. if (item.id == '19') {
  341. item.moneyId = item.options[0].id
  342. }
  343. })
  344. projectAddFrom.value.schemeList.forEach(item => {
  345. item.schemeName = ''
  346. item.description = ''
  347. item.drivingList = []
  348. item.tableData = [...obj]
  349. })
  350. }
  351. } else if (e == '034002') {
  352. // 商业险
  353. let obj = insuranceTypeList.value.find(item => item.id == '2')
  354. obj.insuranceId = obj.id
  355. projectAddFrom.value.schemeList.forEach(item => {
  356. item.schemeName = ''
  357. item.description = ''
  358. item.drivingList = []
  359. item.tableData = [obj]
  360. })
  361. } else if (e == '0330034002') {
  362. // 交强险+商业险
  363. let obj = insuranceTypeList.value.filter(item => item.id == '2' || item.id == '19')
  364. if (obj) {
  365. obj.forEach(item => {
  366. item.insuranceId = item.id
  367. if (item.id == '19') {
  368. item.moneyId = item.options[0].id
  369. }
  370. })
  371. projectAddFrom.value.schemeList.forEach(item => {
  372. item.schemeName = ''
  373. item.description = ''
  374. item.drivingList = []
  375. item.tableData = [...obj]
  376. })
  377. }
  378. } else {
  379. // 其他产品类型
  380. projectAddFrom.value.schemeList.forEach(item => {
  381. item.schemeName = ''
  382. item.description = ''
  383. item.drivingList = []
  384. item.tableData = []
  385. })
  386. }
  387. // 获取保险公司的方案配置
  388. if (projectAddFrom.value.companyId && projectAddFrom.value.productId && projectAddFrom.value.schemeType) {
  389. await initInsurance()
  390. await api.projectApi.getSchemeByCompany({
  391. companyId: projectAddFrom.value.companyId,
  392. productId: projectAddFrom.value.productId,
  393. schemeType: projectAddFrom.value.schemeType,
  394. energyType: energyType?.min,
  395. vehicleType: vehicleType?.minArray?.join(','),
  396. carnature: carnature?.minArray?.join(','),
  397. }).then(res => {
  398. if (res.code == 200) {
  399. if (res.data && res.data.schemeList.length > 0) {
  400. res.data.schemeList.forEach(item => {
  401. // 处理驾意险数据
  402. item.drivingList = item.drivingIntentionList
  403. // 处理险种数据
  404. item.tableData = item.schemeInsuranceList.map(sub => {
  405. let obj = insuranceTypeList.value.find(a => a.id === sub.insuranceId)
  406. return {
  407. ...sub,
  408. optionId: res.data.schemeType === 1 ? `${sub.optionId[0]}` : sub.optionId,
  409. moneyId: res.data.schemeType === 1 ? `${sub.optionId[0]}` : sub.optionId,
  410. options: obj?.options
  411. }
  412. })
  413. })
  414. projectAddFrom.value = res.data
  415. // 处理规则条件数据
  416. rulesAttrList.value = res.data.ruleAttrs.map(val => {
  417. if (val.attrCode == 'LicenseNo') {
  418. val.dictLabal = licensePlateNumber.value;
  419. }
  420. if (val.attrCode == 'LicenseArea') {
  421. val.dictLabal = licensePlateRegion.value;
  422. }
  423. return val
  424. })
  425. }
  426. }
  427. })
  428. }
  429. }
  430. // 险种列表
  431. let insuranceTypeList = ref([])
  432. /**
  433. * 初始化险种数据
  434. */
  435. const initInsurance = () => {
  436. api.projectApi.getBusinessInsurance(projectAddFrom.value.productId || '0330').then(res => {
  437. if (res.code == 200) {
  438. insuranceTypeList.value = res.data
  439. // 根据产品类型初始化默认险种
  440. if (projectAddFrom.value.productId == '0330' || projectAddFrom.value.productId == '0330034001') {
  441. let obj = insuranceTypeList.value.filter(item => item.id == '19')
  442. if (obj) {
  443. obj.forEach(item => {
  444. item.insuranceId = item.id
  445. if (item.id == '19') {
  446. item.moneyId = item.options[0].id
  447. }
  448. })
  449. projectAddFrom.value.schemeList.forEach(item => {
  450. item.drivingList = []
  451. item.tableData = [...obj]
  452. })
  453. }
  454. } else if (projectAddFrom.value.productId == '034002') {
  455. let obj = insuranceTypeList.value.find(item => item.id == '2')
  456. obj.insuranceId = obj.id
  457. projectAddFrom.value.schemeList.forEach(item => {
  458. item.drivingList = []
  459. item.tableData = [obj]
  460. })
  461. } else if (projectAddFrom.value.productId == '0330034002') {
  462. let obj = insuranceTypeList.value.filter(item => item.id == '2' || item.id == '19')
  463. if (obj) {
  464. obj.forEach(item => {
  465. item.insuranceId = item.id
  466. if (item.id == '19') {
  467. item.moneyId = item.options[0].id
  468. }
  469. })
  470. projectAddFrom.value.schemeList.forEach(item => {
  471. item.drivingList = []
  472. item.tableData = [...obj]
  473. })
  474. }
  475. } else {
  476. projectAddFrom.value.schemeList.forEach(item => {
  477. item.drivingList = []
  478. item.tableData = []
  479. })
  480. }
  481. } else {
  482. ElMessage({
  483. message: res.msg,
  484. type: 'warning'
  485. })
  486. }
  487. })
  488. }
  489. /**
  490. * 方案类型切换处理
  491. * @param e 方案类型
  492. */
  493. const schemeTypeChange = (e) => {
  494. projectAddFrom.value.schemeType = e
  495. initProduct(projectAddFrom.value.productId)
  496. }
  497. // 保险公司列表
  498. let companyOption = ref([])
  499. /**
  500. * 初始化保险公司列表
  501. */
  502. const initCompany = () => {
  503. api.projectApi.getCompanyList().then(res => {
  504. if (res.code == 200) {
  505. companyOption.value = res.data
  506. } else {
  507. ElMessage({
  508. message: res.msg,
  509. type: 'warning'
  510. })
  511. }
  512. })
  513. }
  514. /**
  515. * 添加新方案
  516. */
  517. const addProject = () => {
  518. projectAddFrom.value.schemeList.push({
  519. schemeName: '',
  520. description: '',
  521. tableData: [],
  522. drivingList: [],
  523. schemeInsuranceList: [],
  524. drivingIntentionList: []
  525. })
  526. }
  527. // 删除方案
  528. const delScheme = (index) => {
  529. projectAddFrom.value.schemeList.splice(index, 1)
  530. }
  531. // 规则条件显示状态
  532. let rulesShow = ref(false)
  533. /**
  534. * 打开规则条件选择弹窗
  535. */
  536. const addRules = () => {
  537. ruleSelectShow.value = true
  538. nextTick(() => {
  539. RuleSelect.value.initEditData(rulesAttrList.value)
  540. })
  541. }
  542. // 规则条件列表
  543. let rulesAttrList = ref([])
  544. // 默认规则条件列表
  545. let defaultAttrList = ref([])
  546. /**
  547. * 取消规则条件编辑
  548. * @param data 数据
  549. */
  550. const cancelRule = (data) => {
  551. rulesShow.value = false
  552. }
  553. /**
  554. * 删除规则条件
  555. * @param index 索引
  556. */
  557. const handleDel = (index) => {
  558. // 能源类型、使用性质、车辆种类不可删除
  559. if (rulesAttrList.value[index].attrName === '能源类型' || rulesAttrList.value[index].attrName === '使用性质' || rulesAttrList.value[index].attrName === '车辆种类') {
  560. return
  561. } else {
  562. rulesAttrList.value.splice(index, 1)
  563. }
  564. }
  565. // 险种类型列表
  566. let insuranceType = ref([])
  567. /**
  568. * 初始化险种类型
  569. */
  570. const initType = () => {
  571. api.commonApi.personInfo('insurance_type').then(res => {
  572. if (res.code == 200) {
  573. insuranceType.value = res.data
  574. projectAddFrom.value.productId = insuranceType.value[0].value
  575. } else {
  576. ElMessage({
  577. message: res.msg,
  578. type: 'warning'
  579. })
  580. }
  581. })
  582. }
  583. // 险种选择弹窗状态
  584. let insuranceShow = ref(false)
  585. /**
  586. * 处理险种选择关闭
  587. * @param obj 险种数据
  588. */
  589. const handleClose = (obj) => {
  590. if (obj.list && obj.list.length > 0) {
  591. if (projectAddFrom.value.schemeType === 2) {
  592. // 自选方案处理多选
  593. obj.list.forEach(a => {
  594. a.optionId = []
  595. a.options.forEach(b => {
  596. if (b.checked) {
  597. a.optionId.push(b.id)
  598. }
  599. })
  600. a.moneyId = a.optionId
  601. })
  602. } else {
  603. // 基础方案处理单选
  604. obj.list.forEach(a => {
  605. a.optionId = a.options.find(b => b.checked)?.id
  606. a.moneyId = a.optionId
  607. })
  608. }
  609. projectAddFrom.value.schemeList[obj.index].tableData = obj.list
  610. }
  611. insuranceShow.value = false
  612. }
  613. /**
  614. * 删除险种
  615. * @param item 方案项
  616. * @param row 险种行数据
  617. */
  618. const insuranceTypeDel = (item, row) => {
  619. let data = item.tableData.filter(a => a.insuranceId != row.insuranceId)
  620. item.tableData = [...data]
  621. }
  622. // 驾意险选择弹窗状态
  623. let drivingShow = ref(false)
  624. /**
  625. * 打开驾意险选择弹窗
  626. * @param item 方案项
  627. * @param index 索引
  628. */
  629. const handleDriving = (item, index) => {
  630. drivingShow.value = true
  631. nextTick(() => {
  632. DrivingTypeRef.value.initEditData(item.drivingList, index, myRoute.query.companyId)
  633. })
  634. }
  635. /**
  636. * 处理驾意险选择关闭
  637. * @param obj 驾意险数据
  638. */
  639. const handleDrivingClose = (obj) => {
  640. if (obj.list && obj.list.length > 0) {
  641. obj.list.forEach(sub => {
  642. sub.drivingIntentionId = sub.drivingIntentionId
  643. sub.selectedStatus = sub.selectedStatus ? sub.selectedStatus : '1'
  644. sub.quantity = sub.quantity ? sub.quantity : '1'
  645. })
  646. projectAddFrom.value.schemeList[obj.index].drivingList = obj.list
  647. }
  648. drivingShow.value = false
  649. }
  650. /**
  651. * 删除驾意险
  652. * @param item 方案项
  653. * @param row 驾意险行数据
  654. */
  655. const drivingTypeDel = (item, row) => {
  656. let data = item.drivingList.filter(a => a.id != row.id)
  657. item.drivingList = [...data]
  658. }
  659. /**
  660. * 打开险种选择弹窗
  661. * @param item 方案项
  662. * @param index 索引
  663. */
  664. const handlePopover = (item, index) => {
  665. insuranceShow.value = true
  666. nextTick(() => {
  667. InsuranceTypeRef.value.initEditData(item.tableData, index, projectAddFrom.value.schemeType, projectAddFrom.value.productId)
  668. })
  669. }
  670. /**
  671. * 初始化规则属性
  672. */
  673. const initAttr = () => {
  674. api.agreementApi.ruleAttrGroup({ attrName: '' }).then(res => {
  675. if (res.code == 200) {
  676. // 获取车辆信息相关的规则属性
  677. let list = res.data?.VehicleInformation?.filter(e => e.attrName === '能源类型' || e.attrName === '使用性质' || e.attrName === '车辆种类')
  678. rulesAttrList.value = list?.map(a => {
  679. if (a.attrCode == 'LicenseNo') {
  680. a.dictLabal = licensePlateNumber.value;
  681. }
  682. if (a.attrCode == 'LicenseArea') {
  683. a.dictLabal = licensePlateRegion.value;
  684. }
  685. return {
  686. ...a,
  687. operator: '1',
  688. min: a.attrName == '能源类型' ? '0' : '',
  689. minArray: a.minArray ? a.minArray : a.attrName == '使用性质' || a.attrName == '车辆种类' ? [a.dictLabal[0].code] : []
  690. }
  691. })
  692. defaultAttrList.value = [...list]
  693. } else {
  694. ElMessage({
  695. message: res.msg,
  696. type: 'warning'
  697. })
  698. }
  699. })
  700. }
  701. /**
  702. * 初始化编辑数据
  703. */
  704. const initEdit = async () => {
  705. initInsurance()
  706. await api.projectApi.getScheme(myRoute.query.id).then(res => {
  707. if (res.code == 200) {
  708. if (res.data && res.data.schemeList.length > 0) {
  709. res.data.schemeList.forEach(item => {
  710. item.drivingList = item.drivingIntentionList
  711. item.tableData = item.schemeInsuranceList.map(sub => {
  712. let obj = insuranceTypeList.value.find(a => a.id == sub.insuranceId)
  713. console.log("🚀 ~ initEdit ~ obj:", obj)
  714. return {
  715. ...sub,
  716. optionId: res.data.schemeType === 1 ? `${sub.optionId[0]}` : sub.optionId,
  717. moneyId: res.data.schemeType === 1 ? `${sub.optionId[0]}` : sub.optionId,
  718. options: obj?.options
  719. }
  720. })
  721. })
  722. projectAddFrom.value = res.data
  723. rulesAttrList.value = res.data.ruleAttrs.map(val => {
  724. if (val.attrCode == 'LicenseNo') {
  725. val.dictLabal = licensePlateNumber.value;
  726. }
  727. if (val.attrCode == 'LicenseArea') {
  728. val.dictLabal = licensePlateRegion.value;
  729. }
  730. return val
  731. })
  732. }
  733. } else {
  734. ElMessage({
  735. message: res.msg,
  736. type: 'warning'
  737. })
  738. }
  739. })
  740. }
  741. /**
  742. * 取消操作
  743. */
  744. const quit = () => {
  745. myRouter.push({
  746. path: '/quoteConfig/agreement/project',
  747. query: {
  748. id: myRoute.query.companyId
  749. }
  750. })
  751. }
  752. /**
  753. * 保存项目
  754. * @param ProjectAddRef 表单引用
  755. */
  756. const save = async (ProjectAddRef: FormInstance | undefined) => {
  757. if (!ProjectAddRef) {
  758. return
  759. }
  760. await ProjectAddRef.validate((valid) => {
  761. if (valid) {
  762. let formData = { ...projectAddFrom.value }
  763. formData.ruleAttrs = [...rulesAttrList.value]
  764. // 处理方案数据
  765. formData.schemeList.forEach(item => {
  766. item.drivingIntentionList = []
  767. item.schemeInsuranceList = []
  768. // 处理驾意险数据
  769. item.drivingList.forEach(sub => {
  770. let obj = {
  771. id: sub.id,
  772. drivingIntentionId: sub.drivingIntentionId,
  773. selectedStatus: sub.selectedStatus,
  774. quantity: sub.quantity
  775. }
  776. item.drivingIntentionList.push(obj)
  777. })
  778. // 处理险种数据
  779. item.tableData.forEach(ins => {
  780. let obj = {
  781. id: ins.id,
  782. insuranceId: ins.insuranceId,
  783. optionId: projectAddFrom.value.schemeType === 1 ? [ins.moneyId] : projectAddFrom.value.schemeType === 2 ? ins.moneyId : []
  784. }
  785. item.schemeInsuranceList.push(obj)
  786. })
  787. })
  788. // 调用保存API
  789. api.projectApi.saveScheme({ ...formData }).then(res => {
  790. if (res.code == 200) {
  791. ElMessage({
  792. message: res.msg,
  793. type: 'success'
  794. })
  795. myRouter.push({
  796. path: '/quoteConfig/agreement/project',
  797. query: {
  798. id: myRoute.query.companyId
  799. }
  800. })
  801. } else if (res.code != 400) {
  802. ElMessage({
  803. message: res.msg,
  804. type: 'warning'
  805. })
  806. }
  807. })
  808. } else {
  809. ElMessage({
  810. message: '请正确填写相关信息!',
  811. type: 'warning'
  812. })
  813. }
  814. })
  815. }
  816. /**
  817. * 组件挂载时执行
  818. */
  819. onBeforeMount(() => {
  820. // 初始化险种类型
  821. initType()
  822. // 初始化保险公司列表
  823. initCompany()
  824. // 初始化车牌地区数据
  825. regionLicenseRegion('0')
  826. // 初始化车牌号数据
  827. regionLicenseNumber('14')
  828. // 设置保险公司ID
  829. projectAddFrom.value.companyId = myRoute.query.companyId
  830. // 判断是否为编辑模式
  831. if (myRoute.query.id) {
  832. isEdit.value = true
  833. projectAddFrom.value.id = myRoute.query.id
  834. projectAddFrom.value.productId = myRoute.query.productId
  835. initEdit()
  836. } else {
  837. isEdit.value = false
  838. initAttr()
  839. initInsurance()
  840. }
  841. })
  842. </script>
  843. <style scoped lang="scss">
  844. .projectAdd {
  845. overflow-y: auto;
  846. height: 100%;
  847. }
  848. .configuration {
  849. background: #f0f0f0;
  850. padding: 20px;
  851. margin-bottom: 10px;
  852. border-radius: 5px;
  853. box-sizing: border-box;
  854. }
  855. .btns {
  856. display: flex;
  857. align-items: center;
  858. justify-content: center;
  859. }
  860. </style>