vue3【实战】面包屑【组件封装】Breadcrumb (根据菜单自动生成,实时响应路由变化,添加顺滑的过渡动画)

效果预览

在这里插入图片描述

技术方案

vue3 ( vite | TS | vueUse | AutoImport ) + Element Plus + UnoCSS

技术要点

根据当前路由查询所有父级路由

/**
 * 从树状列表中获取指定节点的所有父节点
 *
 * @param treeList 树状列表,包含多个节点
 * @param value 目标节点的路径值
 * @param parents 存储父节点的数组
 * @returns 如果找到目标节点,返回包含所有父节点的数组;否则返回null
 */
function getAllParents(treeList: menu[], value: string, parents: menu[]) {
  // 遍历树中的每个节点
  for (const node of treeList) {
    // 如果找到目标节点
    if (node.path === value) {
      parents.push(node)
      // 返回所有父节点
      return parents
    }
    if (node.children && node.children.length > 0) {
      parents.push(node)
      const result: any = getAllParents(node.children, value, parents)
      if (result) {
        return result
      }
      // 如果递归未找到,则移除当前节点
      parents.pop()
    }
  }

  // 如果遍历完整棵树未找到,返回null
  return null
}

transition-group 实现过渡动画

注意:动画元素需添加 key

    <transition-group name="breadcrumb">
      <el-breadcrumb-item
        :data-index="index"
        v-for="(item, index) in parentsList"
        :key="item.path"
        :to="{ path: item.path }"
        >{{ item.name }}</el-breadcrumb-item
      >
    </transition-group>
<style scoped lang="scss">
.breadcrumb-move,
.breadcrumb-enter-active,
.breadcrumb-leave-active {
  transition: all 0.5s;
}

.breadcrumb-enter-from,
.breadcrumb-leave-to {
  opacity: 0;
  transform: translateX(20px);
}

.breadcrumb-leave-active {
  position: absolute;
}
</style>

代码实现

src/components/Breadcrumb.vue

<script setup lang="ts">
// 导入自定义的数据类型
import type { MenuProps, menu } from './Menu/types'

/** 父组件传参
 * @param menu_list 菜单列表
 */
const { menu_list } = defineProps<MenuProps>()

const route = useRoute()

let parentsList = ref()

parentsList.value = getData()

function getData() {
  let result: menu[] = []
  getAllParents(menu_list, route.path, result)

  return result
}

watch(
  () => route.path,
  () => {
    parentsList.value = getData()
  },
  { immediate: true }
)

/**
 * 从树状列表中获取指定节点的所有父节点
 *
 * @param treeList 树状列表,包含多个节点
 * @param value 目标节点的路径值
 * @param parents 存储父节点的数组
 * @returns 如果找到目标节点,返回包含所有父节点的数组;否则返回null
 */
function getAllParents(treeList: menu[], value: string, parents: menu[]) {
  // 遍历树中的每个节点
  for (const node of treeList) {
    // 如果找到目标节点
    if (node.path === value) {
      parents.push(node)
      // 返回所有父节点
      return parents
    }
    if (node.children && node.children.length > 0) {
      parents.push(node)
      const result: any = getAllParents(node.children, value, parents)
      if (result) {
        return result
      }
      // 如果递归未找到,则移除当前节点
      parents.pop()
    }
  }

  // 如果遍历完整棵树未找到,返回null
  return null
}
</script>

<template>
  <el-breadcrumb separator="/">
    <transition-group name="breadcrumb">
      <el-breadcrumb-item
        :data-index="index"
        v-for="(item, index) in parentsList"
        :key="item.path"
        :to="{ path: item.path }"
        >{{ item.name }}</el-breadcrumb-item
      >
    </transition-group>
  </el-breadcrumb>
</template>

<style scoped lang="scss">
.breadcrumb-move,
.breadcrumb-enter-active,
.breadcrumb-leave-active {
  transition: all 0.5s;
}

.breadcrumb-enter-from,
.breadcrumb-leave-to {
  opacity: 0;
  transform: translateX(20px);
}

.breadcrumb-leave-active {
  position: absolute;
}
</style>

src/components/Menu/types.ts

export interface menu {
  id: number
  name: string
  path: string
  nickName?: string
  icon?: string
  index?: string
  children?: menu[]
}

export interface MenuProps {
  menu_list: menu[]
  default_openeds?: string[]
  collapse?: boolean
}

页面使用

<Breadcrumb class="ml-4" :menu_list="menu_list" />
const menu_list = [
  {
    name: '前端基础',
    icon: 'logos:codecov-icon',
    children: [
      {
        name: 'HTML',
        path: '/notes/HTML',
        icon: 'devicon:html5'
      },
      {
        name: 'CSS',
        path: '/notes/CSS',
        icon: 'devicon:css3'
      },
      {
        name: 'SCSS',
        path: '/notes/SCSS',
        icon: 'vscode-icons:file-type-scss'
      },
      {
        name: 'Javascript',
        path: '/notes/Javascript',
        icon: 'skill-icons:javascript',
        nickName: 'JS'
      },
      {
        name: 'Typescript',
        path: '/notes/Typescript',
        icon: 'logos:typescript-icon',
        nickName: 'TS',
        url: 'https://blog.csdn.net/weixin_41192489/article/details/139948123'
      }
    ]
  },
  {
    name: '前端框架',
    icon: 'logos:codeigniter-icon',
    children: [
      {
        name: 'Vue',
        path: '/notes/Vue',
        icon: 'logos:vue',
        children: [
          {
            name: 'Vue2',
            path: '/notes/Vue2'
          },
          {
            name: 'Vue3',
            path: '/notes/Vue3'
          }
        ]
      },
      {
        name: 'React',
        path: '/notes/React',
        icon: 'skill-icons:react-dark',
        children: [
          {
            name: 'react18',
            path: '/notes/React'
          }
        ]
      }
    ]
  },
  {
    name: 'moxb',
    path: '/notes/moxb'
  }
]

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/926945.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

pdf也算是矢量图——pdf大小调整--福昕pdf

有时候需要把pdf作为矢量图放到latex论文中&#xff0c;有时候需要裁剪掉空白的部分&#xff0c;就需要用福昕pdf进行编辑&#xff0c; 参考文章&#xff1a;福昕高级PDF编辑器裁切工具怎么用&#xff1f;裁切工具使用方法介绍_福昕PDF软件工具集 (foxitsoftware.cn)

【k8s】kubelet 的相关证书

在 Kubernetes 集群中&#xff0c;kubelet 使用的证书通常存放在节点上的特定目录。这些证书用于 kubelet 与 API 服务器之间的安全通信。具体的位置可能会根据你的 Kubernetes 安装方式和配置有所不同&#xff0c;下图是我自己环境【通过 kubeadm 安装的集群】中的kubelet的证…

Java项目Docker部署

docker将应用程序与该程序的依赖打包在一个文件里。运行这个文件就会生成一个虚拟容器&#xff0c;就不用担心环境问题&#xff0c;还可以进行版本管理、复制修改等。 docker安装 由于在CentOS下安装docker最常用&#xff0c;所以以Linux环境安装为主 1.安装工具包 缺少依赖…

【数据结构与算法】排序算法(上)——插入排序与选择排序

文章目录 一、常见的排序算法二、插入排序2.1、直接插入排序2.2、希尔排序( 缩小增量排序 ) 三、选择排序3.1、直接选择排序3.2、堆排序3.2.1、堆排序的代码实现 一、常见的排序算法 常见排序算法中有四大排序算法&#xff0c;第一是插入排序&#xff0c;二是选择排序&#xff…

Flink四大基石之Time (时间语义) 的使用详解

目录 一、引言 二、Time 的分类及 EventTime 的重要性 Time 分类详述 EventTime 重要性凸显 三、Watermark 机制详解 核心原理 Watermark能解决什么问题,如何解决的? Watermark图解原理 举例 总结 多并行度的水印触发 Watermark代码演示 需求 代码演示&#xff…

虚拟机docker记录

最近看了一个up的这个视频&#xff0c;感觉docker真的挺不错的&#xff0c;遂也想来搞一下&#xff1a; https://www.bilibili.com/video/BV1QC4y1A7Xi/?spm_id_from333.337.search-card.all.click&vd_sourcef5fd730321bc0e9ca497d98869046942 这里我用的是vmware安装ubu…

[ACTF2020 新生赛]BackupFile--详细解析

信息搜集 让我们寻找源文件&#xff0c;目录扫描&#xff1a; 找到了/index.php.bak文件&#xff0c;也就是index.php的备份文件。 后缀名是.bak的文件是备份文件&#xff0c;是文件格式的扩展名。 我们访问这个路径&#xff0c;就会直接下载该备份文件。 我们把.bak后缀删掉…

AD单通道AD多通道

AD单通道接线图 滑动变阻器的内部结构 左边和右边的两个引脚接的是电阻的两个固定端&#xff0c;中间这个引脚接的是滑动抽头&#xff0c;电位器外边这里有个十字形状的槽可以拧&#xff0c;往左拧&#xff0c;抽头就往左靠&#xff0c;往右拧&#xff0c;抽头就往右靠。所以外…

解决Ubuntu DNS覆盖写入127.0.0.53

ubuntu22.04解析网址时报错如图所示&#xff1a; 因为/etc/resolve.conf中存在 nameserver 127.0.0.53回环地址造成循环引用 原因&#xff1a; ubuntu17.0之后特有&#xff0c;systemd-resolvd服务会一直覆盖 解决方法&#xff1a; 1、修改resolv.config文件中的nameserver…

hint: Updates were rejected because the tip of your current branch is behind!

问题 本地仓库往远段仓库推代码时候提示&#xff1a; error: failed to push some refs to 192.168.2.1:java-base/java-cloud.git hint: Updates were rejected because the tip of your current branch is behind! refs/heads/master:refs/heads/master [rejected] (…

[golang][MAC]Go环境搭建+VsCode配置

一、go环境搭建 1.1 安装SDK 1、下载go官方SDK 官方&#xff1a;go 官方地址 中文&#xff1a;go 中文社区 根据你的设备下载对应的安装包&#xff1a; 2、打开压缩包&#xff0c;根据引导一路下一步安装。 3、检测安装是否完成打开终端&#xff0c;输入&#xff1a; go ve…

关于VNC连接时自动断联的问题

在服务器端打开VNC Server的选项设置对话框&#xff0c;点左边的“Expert”&#xff08;专家&#xff09;&#xff0c;然后找到“IdleTimeout”&#xff0c;将数值设置为0&#xff0c;点OK关闭对话框。搞定。 注意,服务端有两个vnc服务,这俩都要设置ide timeout为0才行 附件是v…

AIGC时代 | 如何从零开始学网页设计及3D编程

文章目录 一、网页设计入门1. 基础知识2. 学习平台与资源3. 示例代码&#xff1a;简单的HTMLCSSJavaScript网页 二、3D编程入门1. 基础知识2. 学习平台与资源3. 示例代码&#xff1a;简单的Unity 3D游戏 《编程真好玩&#xff1a;从零开始学网页设计及3D编程》内容简介作者简介…

virtualbox给Ubuntu22创建共享文件夹

1.在windows上的操作&#xff0c;创建共享文件夹Share 2.Ubuntu22上的操作&#xff0c;创建共享文件夹LinuxShare 3.在virtualbox虚拟机设置里&#xff0c;设置共享文件夹 共享文件夹路径&#xff1a;选择Windows系统中你需要共享的文件夹 共享文件夹名称&#xff1a;挂载至wi…

C#窗体简单登录

创建一个Windows登录程序&#xff0c;创建两个窗体&#xff0c;一个用来登录&#xff0c;一个为欢迎窗体&#xff0c;要求输入用户名和密码&#xff08;以个人的姓名和学号分别作为用户名和密码&#xff09;&#xff0c;点击【登录】按钮登录&#xff0c;登录成功后显示欢迎窗体…

es 3期 第12节-选择合适的数据查询方式

#### 1.Elasticsearch是数据库&#xff0c;不是普通的Java应用程序&#xff0c;传统数据库需要的硬件资源同样需要&#xff0c;提升性能最有效的就是升级硬件。 #### 2.Elasticsearch是文档型数据库&#xff0c;不是关系型数据库&#xff0c;不具备严格的ACID事务特性&#xff…

Educator头歌:离散数学 - 图论

第1关&#xff1a;图的概念 任务描述 本关任务&#xff1a;学习图的基本概念&#xff0c;完成相关练习。 相关知识 为了完成本关任务&#xff0c;你需要掌握&#xff1a;图的概念。 图的概念 1.一个图G是一个有序三元组G<V,R,ϕ>&#xff0c;其中V是非空顶点集合&am…

day30|leetcode 452. 用最少数量的箭引爆气球, 435. 无重叠区间 , 763.划分字母区间

重叠区间专题 11.用最少的数量引爆气球 有一些球形气球贴在一堵用 XY 平面表示的墙面上。墙面上的气球记录在整数数组 points &#xff0c;其中points[i] [xstart, xend] 表示水平直径在 xstart 和 xend之间的气球。你不知道气球的确切 y 坐标。 一支弓箭可以沿着 x 轴从不同…

电脑提示报错“Directx error”怎么解决?是什么原因导致的?游戏软件提示“Directx error”错误的解决方案

DirectX Error&#xff08;DX错误&#xff09;通常指的是在使用基于DirectX技术的应用程序&#xff08;尤其是游戏&#xff09;时遇到的问题。这个问题可能由多种因素导致&#xff0c;以下是一些可能的原因及相应的解决方案&#xff1a; 可能的原因 DirectX版本不匹配&#x…

K8S网络系列--Flannel网络下UDP、VXLAN模式的通信流程机制分析

文章目录 前言一、了解overlay、underlay容器网络二、网络通信1.分类2.网络虚拟设备对2.1、什么是网络虚拟设备对veth pair?2.2、如何查看容器的网卡与主机的哪个veth设备对是成对的关系? 3、vxlan和vtep3.1、vtep3.2、vxlan相关概念 三、Flannel网络模式剖析0、flannel的作用…