• 从一个页面跳转到目标页面之后,对应的顶部路由高亮


    需求:页面跳转到目标页面之后,对应的顶部路由高亮 

    上面的更多 跳转到 学情分析下面的学生分析

    1. <template>
    2. <div class="topBar" ref="topBar" v-loading.fullscreen.lock="fullscreenLoading">
    3. <div class="topBar-navi">
    4. <div class="top-menu container">
    5. <div class="myMenu">
    6. <img :src="logo" alt="" />
    7. <!-- S2路由改造 -->
    8. <div class="parentRoute">
    9. <span
    10. :class="{ activeParent: currentIndex == index }"
    11. v-for="(item, index) in routeMenus"
    12. :key="index"
    13. @click="selectParentRoute(item, index)"
    14. >
    15. {{ filterTitle(item.meta.title) }}
    16. <!-- <i v-if="item.children" class="el-icon-arrow-down" /> -->
    17. </span>
    18. </div>
    19. </div>
    20. <!-- ***************** -->
    21. <div class="right-menu">
    22. <span class="right-menu-currentRole">{{ currentRoleObj.roleName }}</span>
    23. <el-button
    24. class="Topbar-identity"
    25. type="text"
    26. @click="handelShowDialog"
    27. :disabled="disabledRole"
    28. >
    29. 切换角色
    30. </el-button>
    31. <el-dropdown class="Topbar-dropdown">
    32. <span class="Topbar-el-dropdown-link">
    33. {{ name }}<i class="el-icon-arrow-down el-icon--right"></i>
    34. </span>
    35. <el-dropdown-menu slot="dropdown" class="Topbar-el-dropdown-menu">
    36. <div>
    37. 姓名 <span>{{ name }}</span>
    38. </div>
    39. <div class="Topbar-Group">
    40. 身份
    41. <span>{{ currentRoleObj.roleName }}</span>
    42. </div>
    43. <div>
    44. 学校 <span>{{ school }}</span>
    45. </div>
    46. <div class="user-center">
    47. <!-- <span @click.stop="toUserCenter">个人中心</span> -->
    48. <a class="Topbar-logout" @click="logout">退出登录</a>
    49. </div>
    50. </el-dropdown-menu>
    51. </el-dropdown>
    52. </div>
    53. </div>
    54. </div>
    55. <!-- S2二级菜单改造 -->
    56. <!-- ************ -->
    57. <div class="childRoute" v-if="subMenus">
    58. <div class="childRoute-menus container">
    59. <div
    60. :class="{ activeChild: currentChildIndex == index }"
    61. v-for="(item, index) in subMenus"
    62. :key="index"
    63. @click="selectChildRoute(item, index)"
    64. >
    65. {{ filterTitle(item.meta.title) }}
    66. </div>
    67. </div>
    68. </div>
    69. <!-- ************ -->
    70. <el-dialog
    71. title="是否退出登录"
    72. :visible.sync="DialogLogout"
    73. width="325px"
    74. height="134px"
    75. append-to-body
    76. center
    77. class="Topbar-el-dialog"
    78. >
    79. <span slot="footer" class="dialog-footer">
    80. <el-button @click="DialogLogout = false">取 消</el-button>
    81. <el-button type="primary" @click="LogoutConfirm">确 定</el-button>
    82. </span>
    83. </el-dialog>
    84. <el-dialog
    85. title="请选择你要切换的身份"
    86. :visible.sync="DialogVisible"
    87. width="474px"
    88. height="218px"
    89. append-to-body
    90. center
    91. class="Topbar-el-dialog"
    92. >
    93. <div
    94. v-for="(item, index) in teacherInfo.roleMap"
    95. :key="index"
    96. class="Topbar-role"
    97. :class="{ roleActive: currentRoleObj.roleType == item.roleType }"
    98. @click="selectRole(item)"
    99. >
    100. {{ item.roleName }}
    101. </div>
    102. <span slot="footer" class="dialog-footer">
    103. <el-button type="primary" @click="DialogVisible = false">关闭</el-button>
    104. </span>
    105. </el-dialog>
    106. <!-- 筛选项组件 -->
    107. <filterItems />
    108. </div>
    109. </template>
    110. <script>
    111. import variables from "@/assets/styles/variables.scss";
    112. import { mapState, mapActions, mapGetters, mapMutations } from "vuex";
    113. import $C from "@/assets/js/config.js";
    114. import filterItems from "./Sidebar/filterItems.vue";
    115. export default {
    116. components: { filterItems },
    117. name: "Topbar",
    118. data() {
    119. return {
    120. delaySearch: false, //搜索延迟
    121. DialogLogout: false,
    122. DialogVisible: false, //弹框默认影藏
    123. // 当前激活一级菜单的 index
    124. currentIndex: localStorage.getItem("parentPathIndex") || 0,
    125. // 二级菜单index
    126. currentChildIndex: localStorage.getItem("childPathIndex") || 0,
    127. // 角色
    128. currentRole: "", //当前角色名
    129. classesByRole: [], //角色下班级
    130. subjectByClass: [], //班级下学科
    131. currentGrade: "",
    132. currentGradeName: "",
    133. fullscreenLoading: false,
    134. disabledRole: false,
    135. // 当前班级
    136. current_class: "",
    137. currentSubject: "", //默认显示学科
    138. activeSubject: ""
    139. };
    140. },
    141. mounted() {
    142. this.GetUserStoreClasses();
    143. },
    144. watch: {
    145. currentRoleObj: {
    146. handler(val, old) {
    147. // 切换角色高亮默认第一个路由
    148. this.currentIndex = 0;
    149. this.currentChildIndex = 0;
    150. },
    151. deep: true
    152. }
    153. },
    154. computed: {
    155. ...mapGetters(["avatar", "storeClasses", "name", "school", "gradeList", "routeMenus"]),
    156. variables() {
    157. return variables;
    158. },
    159. // 二级菜单
    160. subMenus() {
    161. let menu = this.routeMenus[this.currentIndex]?.children || "";
    162. return menu;
    163. },
    164. // 一级路由
    165. parentMenu() {
    166. let parent = this.routeMenus[this.currentIndex].path;
    167. return parent;
    168. },
    169. // 页面logo图片
    170. logo() {
    171. return this.$store.state.user.teacherInfo.schoolVo.logo;
    172. },
    173. // 教师信息
    174. teacherInfo() {
    175. return this.$store.state.user.teacherInfo;
    176. },
    177. //角色信息
    178. currentRoleObj() {
    179. return this.$store.state.user.current_role;
    180. }
    181. },
    182. methods: {
    183. ...mapActions({ GetUserStoreClasses: "GetUserStoreClasses" }),
    184. ...mapMutations([
    185. "SET_CURRENT_CLASS",
    186. "SET_CURRENT_ROLE",
    187. "SET_CURRENT_SUBJECT",
    188. "SET_GRADE",
    189. "SET_CURRENT_GRADE",
    190. "SET_SUBJECT_LIST"
    191. ]),
    192. toUserCenter() {
    193. this.$router.push({ name: "UserCenterHome" });
    194. },
    195. // 点击一级路由菜单
    196. selectParentRoute(item, index) {
    197. this.currentIndex = index;
    198. localStorage.setItem("parentPathIndex", index);
    199. localStorage.setItem("childPathIndex", 0);
    200. let parentRoute = item.path;
    201. if (item.children) {
    202. // 有二级路由
    203. let defaultChild = item.children[0]?.path; //点击跳转默认第一个二级路由
    204. this.$router.push(`${parentRoute}/${defaultChild}`);
    205. } else {
    206. // 没有二级路由
    207. this.$router.push(parentRoute);
    208. }
    209. },
    210. // 子菜单选择事件
    211. selectChildRoute(item, index) {
    212. localStorage.setItem("childPathIndex", index);
    213. this.$router.push(`${this.parentMenu}/${item.path}`);
    214. },
    215. // 点击确认退出登录
    216. async LogoutConfirm() {
    217. this.$store.dispatch("LogOut").then(() => {
    218. location.href = "/";
    219. });
    220. this.DialogLogout = false;
    221. },
    222. // 点击退出登录
    223. logout() {
    224. this.DialogLogout = true;
    225. },
    226. handelShowDialog() {
    227. this.DialogVisible = true;
    228. this.disabledRole = true;
    229. let timer = setTimeout(() => {
    230. clearTimeout(timer);
    231. this.disabledRole = false;
    232. }, 6000);
    233. },
    234. // 切换角色
    235. selectRole(item) {
    236. this.fullscreenLoading = true;
    237. this.DialogVisible = false;
    238. localStorage.setItem("childPathIndex", 0);
    239. localStorage.setItem("parentPathIndex", 0);
    240. this.SET_CURRENT_ROLE(item);
    241. //当前角色下年级列表和默认年级
    242. if (item.grades[0]) {
    243. this.SET_GRADE(item.grades);
    244. this.SET_CURRENT_GRADE(item.grades[0]);
    245. this.currentGrade = item.grades[0].grade;
    246. }
    247. //角色下是否存在班级
    248. if (item.classes[0]) {
    249. //角色下班级
    250. this.classesByRole = item.classes;
    251. this.SET_CURRENT_CLASS(item.classes[0]);
    252. //改变默认班级
    253. this.current_class = item.classes[0].classNo;
    254. }
    255. //任课教师、考察科目教师角色下班级
    256. if (item.roleType == 106 || item.roleType == 113) {
    257. let currentRoleSub = this.teacherInfo.roleMap[item.roleType].classes.find(
    258. v => v.classNo == this.current_class
    259. );
    260. this.subjectByClass = currentRoleSub.subjects;
    261. this.currentSubject = currentRoleSub.subjects[0].subject;
    262. this.SET_CURRENT_SUBJECT(currentRoleSub.subjects[0]);
    263. this.SET_SUBJECT_LIST(currentRoleSub.subjects);
    264. }
    265. this.$store.dispatch("GetRoutes").then(v => {
    266. let parentRoute = v[0].path;
    267. if (v[0].children) {
    268. let toIndex = v[0].children[0].path;
    269. this.$router.push({
    270. path: `${parentRoute}/${toIndex}`,
    271. replace: true
    272. });
    273. } else {
    274. this.$router.push(parentRoute);
    275. }
    276. });
    277. //计算top高度并传参
    278. this.$nextTick(() => {
    279. const childHeight = this.$refs.topBar.offsetHeight;
    280. this.$emit("getHeight", childHeight);
    281. });
    282. let timer = setTimeout(() => {
    283. clearTimeout(timer);
    284. this.fullscreenLoading = false;
    285. }, 800);
    286. // });
    287. },
    288. //去掉子菜单角色名字段
    289. filterTitle(title) {
    290. let roleName = this.currentRole;
    291. if (title.includes("-")) {
    292. return title.substr(title.lastIndexOf("-") + 1);
    293. } else {
    294. return title.replace(roleName, "");
    295. }
    296. }
    297. }
    298. };
    299. </script>
    300. <style lang="scss" scoped>
    301. .topBar {
    302. &-navi {
    303. width: 100%;
    304. background: #fff;
    305. box-shadow: 0px -1px 0px 0px rgba(0, 0, 0, 0.04) inset;
    306. height: 55px;
    307. display: flex;
    308. .top-menu {
    309. // width: 100%;
    310. display: flex;
    311. justify-content: space-between;
    312. align-items: center;
    313. .myMenu {
    314. display: flex;
    315. align-items: center;
    316. width: 100%;
    317. img {
    318. width: 135px;
    319. }
    320. .parentRoute {
    321. width: 100%;
    322. > span {
    323. cursor: pointer;
    324. margin-left: 30px;
    325. }
    326. .activeParent {
    327. color: #34beea;
    328. }
    329. }
    330. .menuList {
    331. display: flex;
    332. }
    333. }
    334. .right-menu {
    335. text-align: right;
    336. width: 240px;
    337. display: flex;
    338. align-items: center;
    339. height: 100%;
    340. &-currentRole {
    341. margin-right: 10px;
    342. // width: 80px;
    343. height: 22px;
    344. line-height: 22px;
    345. border-radius: 4px;
    346. text-align: center;
    347. color: #34beea;
    348. background: rgba(52, 190, 234, 0.16);
    349. }
    350. &:focus {
    351. outline: none;
    352. }
    353. .Topbar-dropdown {
    354. .Topbar-el-dropdown-link {
    355. cursor: pointer;
    356. }
    357. }
    358. .Topbar-identity {
    359. display: inline-block;
    360. color: #777777;
    361. line-height: 21px;
    362. margin-right: 10px;
    363. &:hover {
    364. // background-color: red;
    365. color: #34beea;
    366. }
    367. }
    368. }
    369. }
    370. }
    371. .childRoute {
    372. height: 54px;
    373. background-color: #fff;
    374. box-shadow: 0px 4px 4px 0px rgba(209, 209, 209, 0.25);
    375. margin-bottom: 20px;
    376. cursor: pointer;
    377. &-menus {
    378. display: flex;
    379. align-items: center;
    380. > div {
    381. // line-height: 54px;
    382. height: 54px;
    383. padding: 16px 36px;
    384. }
    385. .activeChild {
    386. background: #34beea;
    387. color: #fff;
    388. }
    389. }
    390. }
    391. }
    392. .Topbar-el-dropdown-menu {
    393. width: 270px;
    394. height: 220px;
    395. padding: 32px 0 0 24px;
    396. overflow: hidden;
    397. div {
    398. width: 100%;
    399. height: 32px;
    400. display: flex;
    401. align-items: center;
    402. span {
    403. margin-left: 32px;
    404. }
    405. }
    406. .Topbar-Group {
    407. span:nth-child(1) {
    408. margin: 0 20px 0 32px;
    409. }
    410. img {
    411. // margin-right: 2px;
    412. }
    413. }
    414. .Topbar-install {
    415. display: inline-block;
    416. width: 56px;
    417. height: 21px;
    418. color: #303133;
    419. line-height: 21px;
    420. margin: 18px 0 12px 75px;
    421. white-space: nowrap;
    422. &:hover {
    423. color: #e54747;
    424. }
    425. }
    426. .user-center {
    427. display: flex;
    428. flex-direction: column;
    429. align-items: center;
    430. justify-content: center;
    431. margin-top: 30px;
    432. height: 42px;
    433. user-select: none;
    434. > span,
    435. > a {
    436. margin: 0;
    437. padding: 0;
    438. }
    439. > span {
    440. margin-bottom: 10px;
    441. color: #333;
    442. cursor: pointer;
    443. &:active {
    444. opacity: 0.5;
    445. }
    446. }
    447. > a {
    448. color: #e54747;
    449. }
    450. }
    451. }
    452. .Topbar-el-dialog {
    453. margin-top: 200px;
    454. .el-dialog__header {
    455. .el-dialog__title {
    456. margin-top: 30px;
    457. font-size: 16px;
    458. color: #606266;
    459. }
    460. }
    461. .el-dialog__body {
    462. .roleActive {
    463. color: #34beea;
    464. }
    465. .Topbar-role {
    466. height: 21px;
    467. text-align: center;
    468. font-size: 12px;
    469. margin-bottom: 21px;
    470. cursor: pointer;
    471. &:hover {
    472. color: #34beea;
    473. }
    474. }
    475. }
    476. }
    477. </style>

    一级路由循环渲染  currentIndex高亮   添加点击事件


                              :class="{ activeParent: currentIndex == index }"
                  v-for="(item, index) in routeMenus"
                  :key="index"
                  @click="selectParentRoute(item, index)"
                >
                  {{ filterTitle(item.meta.title) }}
                 
               
             
     

    二级路由  currentChildIndex高亮  添加点击事件

           

              :class="{ activeChild: currentChildIndex == index }"

              v-for="(item, index) in subMenus"

              :key="index"

              @click="selectChildRoute(item, index)"

            >

              {{ filterTitle(item.meta.title) }}

           

         

    在data中定义变量:

             // 当前激活一级菜单的 index

          currentIndex: localStorage.getItem("parentPathIndex") || 0,

          // 二级菜单index

          currentChildIndex: localStorage.getItem("childPathIndex") || 0,

     

     在跳转页面(也就是学情概览页面)的methods里面新增一个方法

     findMore(name, path) {

          let parentIndex = this.routeMenus.findIndex(v => v.meta.title == name);

          let childIndex = this.routeMenus[parentIndex].children.findIndex(v => v.path == path);

          localStorage.setItem("parentPathIndex", parentIndex);

          localStorage.setItem("childPathIndex", childIndex);

          this.$router.push(path);

        },

    在学情概览页面结构里面 点击更多的地方使用这个方法并传参: 

    routeMenus

     

    目标页面: 

     

  • 相关阅读:
    Python、Rust中的协程
    第五章 Linux常用应用软件
    数仓之全量表、增量表、快照表、切片表、拉链表
    html5 图像标签
    MySQL:删除重复记录、插入不重复记录
    QT Day2
    visual studio 2022调试技巧介绍
    CSS中如何实现一个自适应正方形(宽高相等)的元素?
    ARM 汇编基础知识
    y112.第六章 微服务、服务网格及Envoy实战 -- Envoy网格安全(二三)
  • 原文地址:https://blog.csdn.net/ll123456789_/article/details/134017171