路由概念
路由设置步骤
路由嵌套和路由传参
编程式路由
路由概念
Vue属于单页应用(SPA),整个应用程序里只有一个html页面。
SPA没有浏览历史记录的功能,应用路由可以实现该功能。
设置步骤
1.导入路由的库文件
<script src="https://unpkg.com/vue-router@4.0.6"></script>
2.定义路由组件
const Home = {
template: '<div>首页</div>'
}
const News = {
template: '<div>新闻</div>'
}
3.定义路由规则
const routes = [
{
path: '/home',
component: Home
},{
path: '/news',
component: News
}
]
4.创建路由实例router(基本万年不变)
const router = VueRouter.createRouter({
//配置路由模式
history: VueRouter.createWebHashHistory(),
//配置路由规则(当路由规则对象也为routes时,可简写为:routes)
routes: routes
})//路由模式如下
- createWebHistory 路由模式:路径中不带#号。(生产环境下不能直接访问,需要进行转发)
- createWebHashHistory 路由模式:路径中带#号。
5.将路由对象挂载到vue实例上
// 通过use(router)注入路由,从而让整个应用都有路由功能
Vue.createApp({
data() {
return {}
}
}).use(router).mount('#app');
补充:设置根路由
// 2. 定义路由规则对象(每个路由应该映射一个组件)
const routes = [
{
path: '/', //根路由
redirect: '/home' //把根路由重定向到home
},{
path: '/home',
component: Home
},{
path: '/news',
component: News
}
]
嵌套路由
路由套路由(有父子关系)
const routes = [
{
path: '/', //根路由
redirect: '/home' //把根路由重定向到home
}, {
path: '/home',
component: Home,
children: [ //配置子路由
{
path: '/home',
redirect: '/home/login'
}, {
path: '/home/login',
component: Login
}, {
path: '/home/reg',
component: Reg
}
]
}, {
path: '/news',
component: News
},
]
路由传参
params
<body>
<div id="app">
<p>
<router-link to="/home">home</router-link>
<router-link :to="{name:'News',params:{id:id,name:name}}">news</router-link>
</p>
<router-view></router-view>
</div><script src="https://unpkg.com/vue@3.0.11"></script>
<script src="https://unpkg.com/vue-router@4.0.6"></script><script type="text/javascript">
const Home = {
template: '<div>首页</div>'
}
const News = {
template: `<div>新闻;
参数1:{{$route.params.id}};
参数2:{{$route.params.name}}
</div>`
}const routes = [
{
path: '/',
redirect: '/home'
}, {
path: '/home',
name: 'Home', //每个路由规则中必须要有一个name属性
component: Home
}, {
path: '/news',
name: 'News',
component: News
}
]const router = VueRouter.createRouter({
history: VueRouter.createWebHashHistory(),
routes: routes
})Vue.createApp({
data() {
return {
id:1,
name:'zhangsan'
}
}
}).use(router).mount('#app');
</script>
</body>
query
<body>
<div id="app">
<p>
<router-link to="/home">home</router-link>
<router-link :to="{path:'/news',query:{id:id,name:name}}">news</router-link>
</p>
<router-view></router-view>
</div><script src="https://unpkg.com/vue@3.0.11"></script>
<script src="https://unpkg.com/vue-router@4.0.6"></script><script type="text/javascript">
const Home = {
template: '<div>首页</div>'
}
const News = {+
template: `<div>新闻;
参数1:{{$route.query.id}};
参数2:{{$route.query.name}}
</div>`
}const routes = [
{
path: '/',
redirect: '/home'
}, {
path: '/home',
component: Home
}, {
path: '/news',
component: News
}
]const router = VueRouter.createRouter({
history: VueRouter.createWebHashHistory(),
routes: routes
})Vue.createApp({
data() {
return {
id:1,
name:'zhangsan'
}
}
}).use(router).mount('#app');
</script>
</body>
params和query的区别
- query方式:类似于get方式,参数会在路由中显示,可以用做刷新后仍然存在的参数。利用路由规则中的path跳转。
- params方式:类似于post方式,参数不会在路由中显示,页面刷新后参数将不存在。利用路由规则中的name跳转
使用params传参,且刷新不丢失参数
<body>
<div id="app">
<p>
<router-link to="/home">home</router-link>
<!--<router-link :to="{name:'News',params:{id:id,name:name}}">news</router-link>-->
<router-link to="/news/100/lisi">news</router-link>
</p>
<router-view></router-view>
</div><script src="https://unpkg.com/vue@3.0.11"></script>
<script src="https://unpkg.com/vue-router@4.0.6"></script><script type="text/javascript">
const Home = {
template: '<div>首页</div>'
}
const News = {
template: `<div>新闻;
参数1:{{$route.params.id}};
参数2:{{$route.params.name}}
</div>`
}const routes = [
{
path: '/',
redirect: '/home'
}, {
path: '/home',
name: 'Home', //每个路由规则中必须要有一个name属性
component: Home
}, {
path: '/news/:id/:name',
name: 'News',
component: News
}
]const router = VueRouter.createRouter({
history: VueRouter.createWebHashHistory(),
routes: routes
})Vue.createApp({
data() {
return {
id:1,
name:'zhangsan'
}
}
}).use(router).mount('#app');
</script>
</body>
编程式路由(主要是路由跳转)
this.$router.push()
this.$router.go(n) 路由的前进后退,n代表跳转个数,正数前进,负数后退
this.$router.forward()/back() 前进一页/后退一页
<body>
<div id="app">
<p>
<button @click="toHome">首页</button>
<button @click="toNews">新闻</button>
<button @click="toLogin">登陆</button>
<button @click="doForward1">前进</button>
<button @click="doForward2">前进</button>
<button @click="doBack1">后退</button>
<button @click="doBack2">后退</button>
</p>
<router-view></router-view>
</div><script src="https://unpkg.com/vue@3.0.11"></script>
<script src="https://unpkg.com/vue-router@4.0.6"></script><script type="text/javascript">
const Home = {
template: '<div>首页</div>'
}
const News = {
template: '<div>新闻:{{$route.query.id}},{{$route.query.name}}</div>'
}
const Login = {
template: '<div>登陆</div>'
}const routes = [
{
path: '/',
redirect: '/home'
}, {
path: '/home',
component: Home
}, {
path: '/news',
component: News
}, {
path: '/login',
component: Login
}
]const router = VueRouter.createRouter({
history: VueRouter.createWebHashHistory(),
routes: routes
})Vue.createApp({
data() {
return {
id: 1,
name: 'zhangsan'
}
},
methods: {
toHome() {
//无参数时,push方法中直接写路由地址
this.$router.push('/home');
},
toNews() {
//有参数时,push方法中写一个json对象
this.$router.push({ path: '/news', query: { id:this.id, name:this.name } });
},
toLogin() {
this.$router.push('/login');
},
doForward1() {
this.$router.forward();
},
doForward2() {
this.$router.go(1);
},
doBack1() {
this.$router.back();
},
doBack2() {
this.$router.go(-1);
}
}
}).use(router).mount('#app');
</script>
</body>
watch监听路由
watch: {
// 监听路由跳转。
$route(newRoute, oldRoute) {
console.log('watch', newRoute, oldRoute)
}
}
导航守卫
- to:即将要进入的目标路由对象(去哪里),可以使用 to.path 获取即将要进入路由地址。
- from:当前导航正要离开的路由对象(从哪来),可以使用 from.path 获取正要离开的路由地址。
- next:一个函数,表示继续执行下一个路由。(如果没有next,将不会进入到下一个路由)
<body>
<div id="app">
<p>
<router-link to="/home">home</router-link>
<router-link to="/news">news</router-link>
<router-link to="/login">login</router-link>
</p>
<router-view></router-view>
</div><script src="https://unpkg.com/vue@3.0.11"></script>
<script src="https://unpkg.com/vue-router@4.0.6"></script><script type="text/javascript">
const Home = {
template: '<div>首页</div>'
}
const News = {
template: '<div>新闻</div>'
}
const Login = {
template: '<div>登录</div>'
}const routes = [
{
path: '/',
redirect: '/login'
}, {
path: '/home',
component: Home
}, {
path: '/news',
component: News
}, {
path: '/login',
component: Login
}
]const router = VueRouter.createRouter({
history: VueRouter.createWebHashHistory(),
routes: routes
})Vue.createApp({
data() {
return { }
}
}).use(router).mount('#app');// 添加全局路由守卫
router.beforeEach((to, from, next) => {
//创建守卫规则集合(这里表示'/home'与'/news'路径是需要权限验证的)
const nextRoute = ['/home', '/news'];
// 使用isLogin来模拟是否登录
let isLogin = false;
// 判断to.path(要跳转的路径)是否是需要权限验证的
if (nextRoute.indexOf(to.path) >= 0) {
if (!isLogin) {
router.push({
path: '/login'
})
//location.reload();
}
}
next(); //必须要有
});
</script>
</body>