如何改变url页面还不刷新?
URL 的 hash 也就是锚点(#) 本质上就是改变了 window.location 的 href 属性 我们可以通过直接赋值 locaion.hash 来改变 href 但是页面不刷新 可以通过原生 class 选择器 获取到元素 然后通过原生监听获取到点击事件监听 location.hash 的改变
html5 的 history 他有六种方式改变 url
- replaceState 替换原来的路径
- pushState 使用新的路径
- popState 路径的回退
- go 向前活向后改变路径
- forward 向前改变路径
- back 向后改变路径
vue-router
它是基于路由和组件的 路由用于设定访问路径 将路径和组件映射在一起 在vue-router单页面应用中,页面的路径的改变就是组件的切换
路由的使用步骤
- 创建路由需要映射的组件
- 通过createRouter创建路由对象 并且传入routes 和history对象
- 配置路由映射:组件和路径映射关系的routes数组
- 创建基于hash或者history的模式
-
使用app注册路由对象(use方法)
-
路由使用:通过router-link>router-view>
import {
createRouter,
createWebHashHistory,
createWebHistory,
} from 'vue-router';
import home from './main';
创建一个新路由 映射关系
const router = createRouter({
// 指定采用的路由模式模式 hash
history: createWebHashHistory(),
// 指定采用的路由模式模式 history
history: createWebHistory(),
// 映射关系
routes: [
{
name: 'home',
pash: '/',
redirect: '/home',
component: /* webpackChunkName:'home' */ import('./main.js'),
},
{ path: '/home/:id', component: home },
{
path: './:pathMatch(.*)',
component: home,
children: [
{
path: '',
redirect: 'homeChildren',
},
],
},
],
})
1.router-view></router-view:占位符 路由切换的组件放的位置
2.router-link> 路由的按钮 它相当于在页面渲染了一个a元素 为什么不直接使用a元素呢 因为他a元素自身有点击事件
2.1 router-link 的属性
- to:想要跳转的path路径 可以是一个字符串/对象
- repalce 替换的模式跳转 不会把跳转记录到历史里面 也就是浏览器的返回和前进
- router-link-active router会自动给当前点击的路由加上这个名称的class 我们可以修改这个class来给点击的按钮添加css
- active-class 这个属性是可以修改.router-link-active 默认选中的class名
- .router-link-exact-active 是一个精准匹配 他是可以精准到具体子路由的 3.路由懒加载
- 能把不同路由对应的组件分割成不同的代码块,然后当路由被访问的时候才加载对应组件,这样就会更加高效;也能提高首屏渲染速度
- 因为component可以传入一个组件 也可以传入一个函数 该函数需要返回一个Promise 所以我们可以用import()
- component:import('./main.js') 在路由映射组件的时候可以使用import函数来进行分包优化路由的懒加载
- /* webpackChunkName:'name'*/ 这是webpack魔法注释 它可以让webpack打包的时候 只来定包的名字 4.其他额外
- name 路由记录独一无二的名称 在动态路由的时候可以用到
- meta 自定义的属性 5.动态路由
- 我们可能有一个 User 组件,它应该对所有用户进行渲染,但是用户的ID是不同的;
- 在Vue Router中,我们可以在路径中使用一个动态字段来实现,我们称之为 路径参数;
- 当我们匹配到了没有配置的路由的时候 我们需要配置一个notfind配置
path:'./:pathMatch(.*)*'可以用$route.parms.pathMatch 来回去nodefind的路径 最后那个*就是 是否解析当前路径 如果加上了 就会解析成一个数组 方便后续操作 - 在template中 可以直接通过$route.params
- 在created 通过this.$route.params
- 在setup中 我们需要使用vue-router库提供的一个hook useRoute 该hook 返回一个route对象 对象保存着路由相关的值
- 组件的嵌套 children:[] 嵌套的子路由 在path直接写路径 因为vue已经做了处理前面添加了父路由的路径
- 代码的页面跳转 在options里面是this.$router.push('./home')
也可以是一个对象this.$router.push({path:'./home', query:{name:'xsh'}})
在setup函数中 通过useRouter来获取router 然后router.push({path:'./home', query:{name:'xsh'})
- route.forward()向前一步
- route.go(-1) 向前还是向后
- route.back() 向后一步
- 可以用$route.query获取到参数
动态路由的使用方式
可能在项目中会根据用户不同的权限注册不同的路由 这个时候就可以用addRoute方法了
如果给添加一个子路由 router.addRoute('home',homeMomentRoute)
删除路由的三种方式
- 添加一个name相同的路由这会将删除之前已经添加的路由 因为他们具有相同的name 并且name必须是唯一的 新的覆盖老的路由
- 通过removeRoute方法 传入路由的名称route.removeRoute('about')
- 调用addRoute的方法返回值回调 router.hasRoute() 检查是否路由存在 router.getRoutes() 检查一个包含所有路由记录的数组
路由导航守卫
vue-router 提供的导航首位主要用于跳转/取消的方式守卫导航 全局的前置beforeEach是在导航触发时候回调(也就是进行任何路由跳转前) 他有两个参数
- to 即将进入的route对象
- form 即将离开的route对象 返回值
- false 取消当前导航不跳转
- 不返回/undefined 进行默认导航
- 返回一个路由地址 可以是string 也可以是一个object 对象包含着path和query 和params等信息 next(vue3不推荐使用了) 在vue2中我们是通过next()函数来决定如何进行跳转 在vue3 我们是通过返回值来控制的 不再推荐使用next()因为开发中很容易调用多次next()
其他导航守卫
vue-router官网:router.vuejs.org/zh/guide/ad…
- 导航被激活
- 在失活的组件(离开的组件)里调用beforeRouteLeava守卫
- 全局的beforEach 判断是否真的会跳转过去
- 在重用得组件里面调用beforeRouteUpdate 一个组件内部跳转 它跟随的参数不一样 /user/123 -> /user/321
- 在路由配置里面调用beforeEnter 相当于在路由配置下面加上 beforeEnter() 这个就是在route配置文件内部加上的守卫函数
- 解析异步路由组件 ()=>import('./home')
- 在被激活的组件里面调用beforeRouteEnter(next) 里面获取不到this 获取不到组件实例 如果想要拿到this的话 得需要调用next next((instance)=>{ log() })
- 调用全局的beforeResolve 异步组件被解析之后 在跳转之前 准备跳转了
- 导航已经被确定
- 调用全局的afterEach
- 触发DOM更新 已经导航过去了 准备开始渲染了
- 调用在被激活的组件里面调用beforeRouteEnter里面传入的next函数