memberSet.vue 15 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513
  1. <template>
  2. <div>
  3. <save-form
  4. :inline="true"
  5. class="searchForm"
  6. save-key="memberSet"
  7. @submit="search"
  8. @reset="onReSet"
  9. :model.sync="searchForm"
  10. >
  11. <!-- 状态 指导老师 活动方案-->
  12. <el-form-item>
  13. <el-input
  14. v-model.trim="searchForm.search"
  15. clearable
  16. placeholder="会员名称"
  17. ></el-input>
  18. </el-form-item>
  19. <el-form-item>
  20. <el-button native-type="submit" type="danger">搜索</el-button>
  21. <!-- <el-button native-type="reset" type="primary">重置</el-button> -->
  22. </el-form-item>
  23. </save-form>
  24. <el-button
  25. type="primary"
  26. style="margin-bottom: 20px"
  27. v-permission="'memberRankSetting/add'"
  28. @click="addLeave"
  29. >新增会员等级</el-button
  30. >
  31. <el-table
  32. :data="tableList"
  33. :header-cell-style="{ background: '#EDEEF0', color: '#444' }"
  34. >
  35. <el-table-column
  36. align="center"
  37. prop="name"
  38. label="会员名称"
  39. ></el-table-column>
  40. <el-table-column align="center" prop="type" label="会员标识">
  41. <template slot-scope="scope">
  42. <el-image
  43. style="width: 100px; height: 100px"
  44. :src="scope.row.icon"
  45. :preview-src-list="[scope.row.icon]"
  46. >
  47. </el-image>
  48. </template>
  49. </el-table-column>
  50. <!-- <el-table-column
  51. align="center"
  52. prop="type"
  53. label="是否新用户试用"
  54. ></el-table-column> -->
  55. <el-table-column
  56. align="center"
  57. prop="updateTime"
  58. width="100px"
  59. label="修改时间"
  60. ></el-table-column>
  61. <el-table-column
  62. align="center"
  63. prop="type"
  64. label="修改人"
  65. ></el-table-column>
  66. <el-table-column align="center" label="操作">
  67. <template slot-scope="scope">
  68. <div>
  69. <!-- memberRankSetting/add -->
  70. <auth auths="memberRankSetting/get">
  71. <el-button type="text" @click="resetMember(scope.row)"
  72. >详情</el-button
  73. >
  74. </auth>
  75. <auth
  76. :auths="['memberRankSetting/get', 'memberRankSetting/update']"
  77. mulit
  78. >
  79. <el-button type="text" @click="resetMember(scope.row, 'update')"
  80. >修改</el-button
  81. >
  82. </auth>
  83. </div>
  84. </template>
  85. </el-table-column>
  86. </el-table>
  87. <el-dialog
  88. :title="title"
  89. :close-on-click-modal="false"
  90. :visible.sync="branchStatus"
  91. v-if="branchStatus"
  92. default-expand-all
  93. @close="onFormClose('ruleForm')"
  94. width="800px"
  95. >
  96. <el-form :model="form" :inline="true" ref="ruleForm">
  97. <el-alert
  98. title="会员信息"
  99. type="info"
  100. :closable="false"
  101. style="margin-bottom: 20px"
  102. >
  103. </el-alert>
  104. <el-form-item
  105. label="会员名称"
  106. prop="name"
  107. :label-width="formLabelWidth"
  108. :rules="[{ required: true, message: '请输入会员名称' }]"
  109. >
  110. <el-input
  111. :disabled="addDisabled"
  112. v-model.trim="form.name"
  113. autocomplete="off"
  114. style="width: 620px"
  115. maxlength="10"
  116. show-word-limit
  117. ></el-input>
  118. </el-form-item>
  119. <el-form-item
  120. label="会员介绍"
  121. prop="intro"
  122. :label-width="formLabelWidth"
  123. :rules="[{ required: true, message: '请输入会员介绍' }]"
  124. >
  125. <el-input
  126. maxlength="50"
  127. show-word-limit
  128. :disabled="addDisabled"
  129. v-model.trim="form.intro"
  130. autocomplete="off"
  131. type="textarea"
  132. :rows="3"
  133. style="width: 620px"
  134. ></el-input>
  135. </el-form-item>
  136. <el-form-item
  137. label="会员标识"
  138. prop="icon"
  139. :label-width="formLabelWidth"
  140. :rules="[{ required: true, message: '请上传会员标识' }]"
  141. >
  142. <upload
  143. v-if="!addDisabled"
  144. v-model="form.icon"
  145. :imageWidthM="200"
  146. :disabled="addDisabled"
  147. :imageHeightM="200"
  148. ></upload>
  149. <img v-else :src="form.icon" alt="" width="120px" height="120px" />
  150. <p style="color: red" v-if="!addDisabled">
  151. 请上传200*200像素,大小2M以内,格式为jpg、png、gif图片
  152. </p>
  153. </el-form-item>
  154. <!-- <br />
  155. <el-form-item
  156. label="是否新用户试用"
  157. prop="name"
  158. :label-width="formLabelWidth"
  159. >
  160. <el-select
  161. v-model.trim="form.isProbationPeriod"
  162. clearable
  163. filterable
  164. placeholder="请选择是否试用"
  165. >
  166. <el-option label="是" :value="true"></el-option>
  167. <el-option label="否" :value="false"></el-option>
  168. </el-select>
  169. </el-form-item>
  170. <el-form-item
  171. label="试用期限"
  172. prop="name"
  173. :label-width="formLabelWidth"
  174. >
  175. <el-input
  176. style="width: 200px"
  177. v-model.trim="form.name"
  178. autocomplete="off"
  179. >
  180. <template slot="append">天</template>
  181. </el-input>
  182. </el-form-item> -->
  183. <el-alert
  184. title="会员权益"
  185. type="info"
  186. :closable="false"
  187. style="margin-bottom: 20px"
  188. >
  189. </el-alert>
  190. <el-form-item :label="searchName" :label-width="formLabelWidth">
  191. <el-input
  192. style="width: 210px"
  193. v-model.trim="seachRoleValue"
  194. ></el-input>
  195. <el-button style="margin-left: 10px" type="danger" @click="seachRoles"
  196. >搜索</el-button
  197. >
  198. <el-button type="primary" @click="onReSetRole">重置</el-button>
  199. </el-form-item>
  200. <br />
  201. <el-form-item label="会员功能" :label-width="formLabelWidth">
  202. <el-checkbox
  203. :disabled="addDisabled"
  204. :indeterminate="isIndeterminate"
  205. @change="onCheckAll"
  206. v-model.trim="checkAll"
  207. >全选</el-checkbox
  208. >
  209. <div>
  210. <el-tree
  211. class="tree"
  212. :data="treeData"
  213. show-checkbox
  214. node-key="id"
  215. @check="onTreeCheck"
  216. :filter-node-method="filterNode"
  217. ref="trees"
  218. highlight-current
  219. :default-checked-keys="checkList"
  220. :props="defaultProps"
  221. >
  222. <div slot-scope="{ node, data }">
  223. {{ node.label }}
  224. </div>
  225. </el-tree>
  226. </div>
  227. </el-form-item>
  228. </el-form>
  229. <span slot="footer" class="dialog-footer">
  230. <el-button v-if="!addDisabled" @click="branchStatus = false"
  231. >取 消</el-button
  232. >
  233. <el-button @click="onSubmit" type="primary">确 定</el-button>
  234. </span>
  235. </el-dialog>
  236. <pagination
  237. save-key="memberSet"
  238. :total.sync="rules.total"
  239. sync
  240. :page.sync="rules.page"
  241. :limit.sync="rules.limit"
  242. :page-sizes="rules.page_size"
  243. @pagination="getList"
  244. />
  245. </div>
  246. </template>
  247. <script>
  248. import pagination from "@/components/Pagination/index";
  249. import Upload from "@/components/Upload/index";
  250. import {
  251. addMemberRank,
  252. getmemberRankList,
  253. getmemberRankDetail,
  254. resetMemberRank,
  255. } from "./api";
  256. import { getMemberPrivilegesItem } from "@/views/dictionaryManager/api";
  257. export default {
  258. components: { pagination, Upload },
  259. name: "memberSet",
  260. data() {
  261. return {
  262. formLabelWidth: "120px",
  263. searchForm: {
  264. search: null,
  265. },
  266. rules: {
  267. // 分页规则
  268. limit: 10, // 限制显示条数
  269. page: 1, // 当前页
  270. total: 0, // 总条数
  271. page_size: [10, 20, 40, 50], // 选择限制显示条数
  272. },
  273. tableList: [],
  274. title: "新增会员等级",
  275. branchStatus: false,
  276. form: {
  277. name: "",
  278. icon: "",
  279. into: "",
  280. },
  281. addDisabled: false,
  282. checkAll: false,
  283. isIndeterminate: false,
  284. treeData: [],
  285. defaultProps: {
  286. children: "children",
  287. label: "label",
  288. disabled: this.addDisabled,
  289. },
  290. result: {
  291. roleName: null,
  292. roleDesc: null,
  293. },
  294. seachRoleValue: "",
  295. silderList: [],
  296. slideCount: 0,
  297. pageType: "",
  298. allChildIds: [],
  299. checkList: [],
  300. searchName: "搜索\xa0\xa0\xa0\xa0\xa0\xa0\xa0",
  301. };
  302. },
  303. async mounted() {
  304. this.getList();
  305. },
  306. methods: {
  307. onFormClose(ruleForm) {
  308. (this.form = {
  309. name: "",
  310. icon: "",
  311. into: "",
  312. }),
  313. this.$refs.trees.setCheckedNodes([]);
  314. this.onTreeCheck();
  315. this.$refs[ruleForm].resetFields();
  316. },
  317. search() {
  318. this.rules.page = 1;
  319. this.getList();
  320. },
  321. onReSet() {},
  322. async getList() {
  323. try {
  324. const res = await getmemberRankList({
  325. search: this.searchForm.search,
  326. rows: this.rules.limit,
  327. page: this.rules.page,
  328. });
  329. this.tableList = res.data.rows;
  330. this.rules.total = res.data.total;
  331. } catch {}
  332. },
  333. async addLeave() {
  334. this.checkList = [];
  335. this.title = "新增会员等级";
  336. this.addDisabled = false;
  337. this.pageType = "create";
  338. await this.getNewTree();
  339. this.slideCount = 0;
  340. this.treeData = await this.setTableData(this.silderList, this.addDisabled);
  341. this.branchStatus = true;
  342. },
  343. onSubmit() {
  344. this.$refs.ruleForm.validate(async (flag) => {
  345. if (flag) {
  346. let tempIds = this.$refs.trees.getCheckedKeys();
  347. let halfIds = this.$refs.trees.getHalfCheckedKeys();
  348. let allIds = [...tempIds, ...halfIds];
  349. if (this.pageType == "update") {
  350. try {
  351. const res = await resetMemberRank({
  352. ...this.form,
  353. memberPrivilegesItemIdList: allIds,
  354. });
  355. this.$message.success("修改成功");
  356. this.branchStatus = false;
  357. this.getList();
  358. } catch {}
  359. } else if (this.pageType == "create") {
  360. try {
  361. const res = await addMemberRank({
  362. ...this.form,
  363. memberPrivilegesItemIdList: allIds,
  364. });
  365. this.$message.success("新建会员成功");
  366. this.branchStatus = false;
  367. this.getList();
  368. } catch {}
  369. } else {
  370. this.branchStatus = false;
  371. }
  372. }
  373. });
  374. },
  375. onCheckAll(val) {
  376. if (val) {
  377. // 先去掉半选
  378. this.isIndeterminate = false;
  379. this.$refs.trees.setCheckedNodes(this.treeData);
  380. } else {
  381. this.$refs.trees.setCheckedNodes([]);
  382. }
  383. },
  384. onTreeCheck() {
  385. let checkTree = this.$refs.trees.getCheckedKeys();
  386. this.checkAll = checkTree.length >= this.slideCount;
  387. this.isIndeterminate =
  388. checkTree.length > 0 && checkTree.length < this.slideCount;
  389. },
  390. filterNode(value, data) {
  391. if (!value) return true;
  392. return data.label.indexOf(value) !== -1;
  393. },
  394. seachRoles() {
  395. this.$refs.trees.filter(this.seachRoleValue);
  396. },
  397. onReSetRole() {
  398. this.seachRoleValue = "";
  399. // this.data = this.setTableData(this.silderList);
  400. this.$refs.trees.filter(this.seachRoleValue);
  401. // console.log(this.data);
  402. },
  403. setTableData(result, disabled) {
  404. let list = [];
  405. list = result.map((res) => {
  406. let tempList = {};
  407. tempList = {
  408. id: res.id,
  409. name: res.name,
  410. label: res.name,
  411. disabled: disabled ? disabled : false,
  412. };
  413. this.slideCount++;
  414. if (res.memberPrivilegesItems && res.memberPrivilegesItems.length > 0) {
  415. tempList.children = this.setTableData(
  416. res.memberPrivilegesItems,
  417. disabled
  418. );
  419. }
  420. return tempList;
  421. });
  422. return list;
  423. },
  424. async resetMember(row, type) {
  425. this.branchStatus = true;
  426. await this.resetTree(row);
  427. if (type) {
  428. this.title = "修改会员等级";
  429. this.pageType = "update";
  430. this.addDisabled = false;
  431. this.slideCount = 0;
  432. this.treeData = await this.setTableData(this.silderList, this.addDisabled);
  433. } else {
  434. this.addDisabled = true;
  435. this.title = "查看会员等级";
  436. this.pageType = "";
  437. this.slideCount = 0;
  438. this.treeData = await this.setTableData(this.silderList, this.addDisabled);
  439. }
  440. },
  441. //递归获取到所有的为子级的ID
  442. getParent(checkIds, data) {
  443. let removeIds = JSON.parse(JSON.stringify(checkIds));
  444. this.getAllChildIds(data);
  445. let tempAllChildIds = this.allChildIds;
  446. for (let i = checkIds.length; i > 0; i--) {
  447. if (!tempAllChildIds.includes(checkIds[i - 1])) {
  448. removeIds.splice(i - 1, 1);
  449. }
  450. }
  451. return removeIds;
  452. },
  453. getAllChildIds(data) {
  454. // 获取所有最子集编号
  455. let child = this.allChildIds;
  456. let tempList = [];
  457. data.forEach((item, index) => {
  458. let temp = [];
  459. if (item.children && item.children.length > 0) {
  460. temp = this.getAllChildIds(item.children);
  461. } else {
  462. child.push(item.id);
  463. }
  464. });
  465. },
  466. async resetTree(row) {
  467. try {
  468. this.treeData = await this.getNewTree()
  469. const res = await getmemberRankDetail({ memberRankSettingId: row.id });
  470. this.form = { ...res.data };
  471. this.checkAll =
  472. res.data.memberPrivilegesItemIdList?.length >= this.slideCount || false;
  473. // 反写树的值
  474. this.isIndeterminate =
  475. res.data.memberPrivilegesItemIdList?.length > 0 &&
  476. res.data.memberPrivilegesItemIdList?.length < this.slideCount;
  477. this.checkList = res.data.memberPrivilegesItemIdList;
  478. let tSplice = this.getParent(
  479. res.data.memberPrivilegesItemIdList||[],
  480. this.treeData
  481. );
  482. this.checkList = tSplice;
  483. this.$nextTick(() => {
  484. this.$refs.trees.setCheckedKeys(this.checkList);
  485. });
  486. } catch (e) {
  487. console.log(e);
  488. }
  489. },
  490. async getNewTree() {
  491. try {
  492. const resTree = await getMemberPrivilegesItem();
  493. this.silderList = resTree.data;
  494. this.slideCount = 0;
  495. return this.setTableData(resTree.data)
  496. } catch {}
  497. },
  498. },
  499. };
  500. </script>
  501. <style lang="scss" scoped>
  502. .tree {
  503. min-width: 630px;
  504. }
  505. </style>